<?php

namespace App\Services;

use App\Repositories\Interfaces\DisbursementAttachmentRepositoryInterface;
use App\Repositories\Interfaces\DisbursementRepositoryInterface;
use App\Repositories\Interfaces\PaymentRepositoryInterface;
use App\Repositories\Interfaces\ProfessionalRepositoryInterface;
use App\Repositories\Interfaces\TransactionRepositoryInterface;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\File;

class TransactionService
{

    protected $transactionRepository;
    protected $disbursementRepository;
    protected $paymentRepository;
    protected $professionalRepository;
    protected $disbursementAttachmentRepository;
    protected $emailService;

    public function __construct(TransactionRepositoryInterface $transactionRepository,
        DisbursementRepositoryInterface $disbursementRepository, PaymentRepositoryInterface $paymentRepository,
        ProfessionalRepositoryInterface $professionalRepository, DisbursementAttachmentRepositoryInterface $disbursementAttachmentRepository,
        EmailService $emailService
    ) {
        $this->transactionRepository = $transactionRepository;
        $this->disbursementRepository = $disbursementRepository;
        $this->paymentRepository = $paymentRepository;
        $this->professionalRepository = $professionalRepository;
        $this->disbursementAttachmentRepository = $disbursementAttachmentRepository;
        $this->emailService = $emailService;

    }

    public function getTransactionsForDisbursement($request)
    {
        $professionalId = $request->get('professional_id');
        if (!$professionalId) {
            return [];
        }
        $dateFilters = explode('-', $request->get('date'));
        $dateFrom = trim($dateFilters[0]);
        $dateTo = trim($dateFilters[1]);
        $filters = [
            'professional_id' => $professionalId,
            'start_date' => Date('Y-m-d', strtotime($dateFrom)),
            'end_date' => Date('Y-m-d', strtotime($dateTo)),
        ];
        return $this->transactionRepository->getTransactionsForDisbursement($filters);
    }

    public function disbursePayment($request)
    {
        $strRandom = '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz';
        $paymentRefNo = 'PO-'.date('mY').'-'.substr(str_shuffle($strRandom),0, 5);
        // Create record of disbursement
        $disbursementPayload = [
            'payment_reference_no' => $request->get('reference_no'),
            'amount' => $request->get('total_payout'),
            'professional_id' => $request->get('professional_id'),
            'payout_reference' => $paymentRefNo,
            'mop' => $request->get('mop'),
            'account_no' => $request->get('account_no'),
            'created_by' => Auth::id()
        ];
        $disbursement = $this->disbursementRepository->create($disbursementPayload);
        // Store Attachments
        $file = $request->file('attachment');

        $destinationPath = public_path().'/uploads/disbursements/'.$paymentRefNo.'/';

        if (!File::exists($destinationPath)){
            mkdir($destinationPath, 0755, true);
        }

        $filename = $file->getClientOriginalName();
        $newFilename = Date('YmdHis').'_'.$filename;
        $file->move($destinationPath, $newFilename);

        $attachmentPayload = [
            'filename' => $newFilename,
            'disbursement_id' => $disbursement->id
        ];

        $this->disbursementAttachmentRepository->create($attachmentPayload);

        // Payload for updating payments that has been disbursed
        $payload = [
            'payment_ids' => $request->get('transactions'),
            'attributes' => [
                'is_disbursed' => 1,
                'disbursement_id' => $disbursement->id
            ]
        ];
        $this->paymentRepository->disbursePayment($payload);

        $disbursementData = [
            'transactions' => $this->transactionRepository->getDisbursedTransactions($disbursement->id),
            'total_amount' => $disbursement->amount,
            'payout_ref' => $paymentRefNo,
            'professional' => $this->professionalRepository->find($disbursement->professional_id),
            'email' => 'jfradejas.webdev@gmail.com',
            'name' => 'Joshua Fradejas',
            'total_amount' => $disbursement->amount
        ];

        $this->emailService->sendPayoutEmail($disbursementData);

        return $paymentRefNo;
    }

    public function getDisbursementDetails($payoutRef)
    {
        $disbursement = $this->disbursementRepository->getByPayoutRef($payoutRef);

        $disbursementData = [
            'transactions' => $this->transactionRepository->getDisbursedTransactions($disbursement->id),
            'total_amount' => $disbursement->amount,
            'payout_ref' => $payoutRef,
            'professional' => $this->professionalRepository->find($disbursement->professional_id),
        ];

        return $disbursementData;
    }

    public function getAllDisbursements()
    {
        return $this->disbursementRepository->all();
    }
}
