<?php

namespace App\Http\Livewire;

use App\Models\Product;
use App\Services\Log;
use Illuminate\Http\RedirectResponse;
use Illuminate\Support\Facades\Auth;
use Illuminate\Validation\Rule;
use LaravelIdea\Helper\App\Models\_IH_Product_C;
use Livewire\Component;
use Livewire\WithPagination;
use Schema;

class Products extends Component {
    use WithPagination;

    protected string $paginationTheme = 'bootstrap';

    public $passphrase, $algorithm, $privateKey, $filterSearch, $deleteId, $productId, $externalReference, $source, $name, $description, $requireNonExpired, $status, $bulkAction, $bulkItems, $bulkActionStatus, $bulkActionConfirm;

    protected $listeners = [ 'createItem', 'updateItem', 'bulkAction', 'bulkActionConfirmed', 'filterItems' ];

    protected function getCreateRules(): array {
        return [
            'externalReference' => 'required_if:source,envato',
            'source'            => 'required',
            'name'              => 'required',
            'description'       => 'required',
            'status'            => 'required',
            'requireNonExpired' => 'boolean',
            'passphrase'        => [ 'string' ],
            'algorithm'         => [ 'integer', Rule::in( array( 1, 2, 3, 6, 7, 8, 9, 10 ) ) ],
            'privateKey'        => [ 'string' ],
        ];
    }

    protected function getUpdateRules(): array {
        return [
            'externalReference' => 'required_if:source,envato',
            'source'            => 'required',
            'name'              => 'required',
            'description'       => 'required',
            'status'            => 'required',
            'passphrase'        => [ 'string' ],
            'algorithm'         => [ 'integer', Rule::in( array( 1, 2, 3, 6, 7, 8, 9, 10 ) ) ],
            'privateKey'        => [ 'string' ],
        ];
    }

    protected function getDeleteRules(): array {
        return [
            'deleteId' => 'required',
        ];
    }

    public function createItemUpdated( $propertyName ): void {
        $this->validateOnly( $propertyName, $this->getCreateRules() );
    }

    public function updateItemUpdated( $propertyName ): void {
        $this->validateOnly( $propertyName, $this->getUpdateRules() );
    }

    public function createItem(): RedirectResponse {
        $this->validate( $this->getCreateRules() );
        $this->dispatchBrowserEvent( 'close-create-modal' );

        $product = new Product();

        $this->assignItemFields( $product );

        $this->resetInputs();

        return redirect()->back();
    }

    public function updateItem(): RedirectResponse {
        $this->validate( $this->getUpdateRules() );
        $this->dispatchBrowserEvent( 'close-update-modal' );

        $product = Product::find( $this->productId );

        if ( $product ) {
            $this->assignItemFields( $product );
        }

        $this->resetInputs();

        return redirect()->back();
    }

    public function deleteItem(): RedirectResponse {
        $this->validate( $this->getDeleteRules() );
        $this->dispatchBrowserEvent( 'close-delete-modal' );

        Product::find( $this->deleteId )->delete();

        return redirect()->back();
    }

    public function openCreateModal(): void {
        $this->resetInputs();
        $this->dispatchBrowserEvent( 'open-create-modal' );
    }

    public function openUpdateModal( $id ): void {
        $this->resetInputs();
        $product = Product::find( $id );

        $this->productId         = $product->id;
        $this->externalReference = $product->external_reference;
        $this->source            = $product->source;
        $this->name              = $product->name;
        $this->description       = $product->description;
        $this->requireNonExpired = $product->require_non_expired;
        $this->status            = $product->status;
        $this->passphrase        = $product->passphrase;
        $this->algorithm         = $product->algorithm;
        $this->privateKey        = $product->private_key;

        $this->dispatchBrowserEvent( 'open-update-modal' );
    }

    public function resetInputs(): void {
        $this->externalReference = '';
        $this->source            = 'internal';
        $this->name              = '';
        $this->description       = '';
        $this->requireNonExpired = false;
        $this->status            = '';
        $this->passphrase        = '';
        $this->algorithm         = '';
        $this->privateKey        = '';

        $this->resetValidation();
    }

    public function bulkAction(): void {
        $this->dispatchBrowserEvent( 'open-confirm-bulk-action' );
    }

    public function bulkActionConfirmed(): void {
        if ( $this->bulkAction == 'delete' ) {
            Product::whereIn( 'id', $this->bulkItems )->delete();

            Log::add( '124', Auth::id(), request()->ip(), [ 'license-key-ids' => $this->bulkItems ] );

            $this->bulkAction = '';
            $this->bulkItems  = [];
        }

        if ( $this->bulkAction == 'change-status' && in_array( $this->bulkActionStatus, [ 'active', 'inactive' ] ) ) {
            Product::whereIn( 'id', $this->bulkItems )->update( [ 'status' => $this->bulkActionStatus ] );

            Log::add( '123', Auth::id(), request()->ip(), [ 'license-key-ids' => $this->bulkItems ] );

            $this->bulkAction       = '';
            $this->bulkActionStatus = '';
            $this->bulkItems        = [];
        }

        $this->dispatchBrowserEvent( 'close-confirm-bulk-action' );
        $this->dispatchBrowserEvent( 'reset-bulk-input' );
    }

    public function filterItems(): void {
        $this->dispatchBrowserEvent( 'filter-done' );
    }

    public function render() {
        return view( 'livewire.products.manage', [
                'products' => Product::where( function ( $q ) {
                    if ( $this->filterSearch != '' ) {
                        foreach ( Schema::getColumnListing( 'products' ) as $column ) {
                            $q->orWhere( $column, 'like', '%' . $this->filterSearch . '%' );
                        }
                    }
                } )->orderBy( 'id', 'DESC' )->paginate( getOption( 'ui', 'itemsPerTable', 10 ) )
            ]
        );
    }

    /**
     * @param Product $product
     *
     * @return void
     */
    public function assignItemFields( Product $product ): void {
        $product->external_reference  = $this->externalReference;
        $product->source              = $this->source;
        $product->name                = $this->name;
        $product->description         = $this->description;
        $product->require_non_expired = (bool) $this->requireNonExpired;
        $product->status              = $this->status;
        $product->passphrase          = $this->passphrase;
        $product->algorithm           = (int) $this->algorithm;
        $product->private_key         = $this->privateKey;

        $product->save();
    }
}
