<?php

namespace Ignite\Core\Repositories;

use Illuminate\Support\Carbon;
use Ignite\Core\Entities\User;
use Ignite\Core\Entities\Transaction;
use Ignite\Core\Contracts\Repositories\TransactionRepository as TransactionRepositoryInterface;

class TransactionRepository implements TransactionRepositoryInterface
{
    /**
     * The allowed transaction types with matching keys and values.
     *
     * @return array
     */
    public function getAllowedTypes()
    {
        $types = array_merge(
            Transaction::query()->newModelInstance()->getTypes(),
            config('transaction.types', [])
        );

        return array_combine(array_values($types), array_values($types));
    }

    /**
     * The current user's balance.
     *
     * @param  User|null $user
     * @return mixed
     */
    public function getBalance($user = null)
    {
        if ($user) {
            return Transaction::byUser($user)->sum('value');
        }

        return Transaction::byCurrentUser()->sum('value');
    }

    /**
     * Find transactions by user.
     *
     * @param  int|User $user
     *
     * @return \Illuminate\Database\Eloquent\Collection|Transaction[]
     */
    public function findByUser($user)
    {
        if ($user instanceof User) {
            $user = $user->getKey();
        }

        return Transaction::with('claimParticipant')->where('user_id', $user)->get();
    }

    /**
     * Find transactions for the authenticated user.
     *
     * @return Transaction[]|\Illuminate\Database\Eloquent\Collection
     */
    public function findAuthenticated()
    {
        return $this->findByUser(auth()->user());
    }

    /**
     * Create a transaction.
     *
     * @param  array $data
     * @return Transaction
     */
    public function create(array $data)
    {
        $transaction = new Transaction($data);

        try {
            $date = Carbon::createFromFormat('m/d/Y', $data['transaction_date']);
            $transaction->setAttribute('tax_date', $date);
            $transaction->setAttribute('transaction_date', $date);
        } catch (\Exception $e) {
            $transaction->setAttribute('tax_date', $now = now());
            $transaction->setAttribute('transaction_date', $now);
        }

        $transaction->save();

        return $transaction;
    }
}
