<?php

namespace App\Repositories\Backend\Superadmin;


use App\Models\Superadmin\Plans\Plans;
use App\Models\Superadmin\Payments\Payments;
use App\Models\Access\User\User;
use App\Repositories\BaseRepository;
use Illuminate\Support\Facades\DB;
use App\Exceptions\GeneralException;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Support\Facades\Hash;
use App\Helpers\Stripe\StripeActions;
use DateTime;

class PlansRepository extends BaseRepository
{

    const MODEL = Plans::class;


    public function __construct()
    {


    }


    public function getForDataTable($status = 1, $trashed = false)
    {

        $dataTableQuery = $this->query()
            ->select([
                config('tables.agency_table') . '.id',
                config('tables.agency_table') . '.agency_name',
                config('tables.agency_table') . '.phone',
                config('tables.agency_table') . '.email',
                config('tables.agency_table') . '.website',
                config('tables.agency_table') . '.balance',
                config('tables.agency_table') . '.status',
                config('tables.agency_table') . '.created_at',
                config('tables.agency_table') . '.updated_at',
            ]);

        if ($trashed == "true") {
            return $dataTableQuery->onlyTrashed();
        }
        // active() is a scope on the UserScope trait
        return $dataTableQuery;
    }


    public function create($input)
    {

        $data = $input['data'];
        $cuisine = $this->createUserStub($data);
        return DB::transaction(function () use ($cuisine, $data) {
            if ($cuisine->save()) {
                $id = DB::getPdo()->lastInsertId();
                $stripe = new StripeActions();
                $name = $data->first_name . ' ' . $data->last_name;
                $city = DB::table('dx_cities')->where('id',$data->city)->pluck('name');
                $country = DB::table('dx_countries')->where('id',$data->country)->pluck('name');
                $state = DB::table('dx_states')->where('id',$data->state)->pluck('name');
                $address = [
                    "line1" => $data->address,
                    "city" => $city[0],
                    "country" => $country[0],
                    "state" => $state[0]
                ];
                $customer = $stripe->createCustomer($name, $data->email, $address, $data->stripeToken);
                $data = array(
                    'first_name' => $data->first_name,
                    'last_name' => $data->last_name,
                    'email' => $data->email,
                    'password' => Hash::make($data->password),
                    'status' => 1,
                    'confirmed' => 1,
                    'agency_id' => $id,
                    'stripe_customer_id' => $customer->id,
                    'confirmation_code' => md5(uniqid(mt_rand(), true)),
                    'created_at' => new DateTime(),
                    'updated_at' => new DateTime(),
                );
                $user = DB::table('users')->insert($data);
                $userid = DB::getPdo()->lastInsertId();
                
                //event(new UserCreated($cuisine));
                $role = array(
                    'user_id' => $userid,
                    'role_id' => 4,
                );
                DB::table('role_user')->insert($role);
                return $userid;
            }

            throw new GeneralException(trans('exceptions.backend.takeaway.cuisine.create_error'));
        });
    }

    public function chargeAgency($userid, $message) {
        $stripe = new StripeActions();
        $user = User::where('id', $userid)->first();
        $payment = $stripe->createCharge($user->stripe_customer_id, env("DEFAULT_CHARGE_AMOUNT") * 100, $message);
        $agency = Plans::find($user->agency_id);
        $this->updateBalance($agency, env("DEFAULT_CHARGE_AMOUNT"));
        $this->recordPayment($userid, $agency, $payment);
    }

    private function updateBalance($agency, $price) {
        $agency->update([
            'balance' => $agency->balance + $price,
        ]);
    }

    private function recordPayment($user_id, $agency, $payment) {
        $agency->update([
            'balance' => $agency->balance - $agency->transection_price,
        ]);
        $payment = array(
            'receipt_url' => $payment->receipt_url,
            'amount' => $agency->transection_price,
            'payment_id' => $payment->id,
            'user_id' => $user_id
        );
        Payments::create($payment);
        return true;
    }


    public function update(Model $plans, array $input)
    {

        $data = $input['data']->all();
        DB::transaction(function () use ($plans, $data) {
            if ($plans->update($data)) {
                //For whatever reason this just wont work in the above call, so a second is needed for now

                return true;
            }

            throw new GeneralException(trans('exceptions.backend.takeaway.cuisine.update_error'));
        });
    }


    public function delete(Model $plans)
    {
        if (parent::delete($plans)) {

            return true;
        }

        throw new GeneralException(trans('exceptions.backend.plan.delete_error'));
    }


    public function forceDelete(Model $plans)
    {
        if (is_null($plans->deleted_at)) {
            throw new GeneralException(trans('exceptions.backend.takeaway.cuisine.delete_first'));
        }

        DB::transaction(function () use ($plans) {
            if (parent::forceDelete($plans)) {
                //event(new UserPermanentlyDeleted($cuisine));
                return true;
            }

            throw new GeneralException(trans('exceptions.backend.takeaway.cuisine.delete_error'));
        });
    }


    public function restore(Model $plans)
    {
        if (is_null($plans->deleted_at)) {
            throw new GeneralException(trans('exceptions.backend.takeaway.cuisine.cant_restore'));
        }

        if (parent::restore(($plans))) {
            //event(new UserRestored($cuisine));
            return true;
        }

        throw new GeneralException(trans('exceptions.backend.takeaway.cuisine.restore_error'));
    }


    protected function createUserStub($input)
    {
        $plan = self::MODEL;
        $plan = new $plan;
        $plan->agency_name = $input['agency_name'];
        $plan->phone = $input['phone'];
        $plan->email = $input['email'];
        $plan->website = $input['website'];
        $plan->transection_price = $input['transection_price'];
        $plan->country = $input['country'];
        $plan->city = $input['city'];
        $plan->balance = 0;
        $plan->address = $input['address'];
        $plan->state = $input['state'];
        $plan->zip_code = $input['zip_code'];

        return $plan;
    }
}
