<?php

namespace App\Jobs;

use App\Models\Generator;
use App\Models\LicenseKey;
use App\Models\Product;
use App\Services\Api\V1\ResponseService;
use Illuminate\Bus\Queueable;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Foundation\Bus\Dispatchable;
use Illuminate\Queue\InteractsWithQueue;
use Illuminate\Queue\SerializesModels;
use Illuminate\Support\Facades\Http;

class ProcessRandomAssignLicenseKeysEndpointCalls implements ShouldQueue {
	use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;

	protected int $productId;
	protected string $ownerName;
	protected string $ownerEmail;
	protected int $quantity;
	protected bool $generate;
	protected string $webhookUrl;
	protected string $identifier;


	protected array $response;

	/**
	 * Create a new job instance.
	 */
	public function __construct( $productId, $ownerName, $ownerEmail, $quantity, $generate, $webhookUrl, $identifier ) {
		$this->productId  = $productId;
		$this->ownerName  = $ownerName;
		$this->ownerEmail = $ownerEmail;
		$this->quantity   = $quantity;
		$this->generate   = $generate;
		$this->webhookUrl = $webhookUrl;
		$this->identifier = $identifier;
	}

	/**
	 * Execute the job.
	 */
	public function handle(): void {
		$product = Product::find( $this->productId );

		if ( ! $product ) {
			$this->response = [
				'response' => [
					'code'       => 805,
					'message'    => 'Product not found',
					'identifier' => $this->identifier
				]
			];
		}

		$count = LicenseKey::where( [ 'product_id' => $this->productId, 'status' => 'available' ] )->whereNull( 'contract_id' )->count();

		if ( ! $this->generate && $count < $this->quantity ) {
			$this->response = [
				'response' => [
					'code'               => 802,
					'message'            => 'Insufficient license keys',
					'available_quantity' => $count,
					'identifier'         => $this->identifier
				]
			];
		}

		$licenseKeys = LicenseKey::where( 'status', 'available' )->whereNull( 'contract_id' )->take( $this->quantity )->get();
		if ( $licenseKeys ) {
			foreach ( $licenseKeys as $licenseKey ) {
				$licenseKey->status      = 'assigned';
				$licenseKey->owner_name  = $this->ownerName;
				$licenseKey->owner_email = $this->ownerEmail;
				$licenseKey->assigned_at = now();
				$licenseKey->updated_at  = now();

				$licenseKey->save();
			}
		}

		$generatedLicenseKeys = [];
		$generateQuantity     = abs( $this->quantity - $licenseKeys->count() );
		if ( $this->generate && $generateQuantity > 0 ) {
			$generator = Generator::where( [ 'product_id' => $this->productId, 'status' => '1' ] )->first();

			if ( ! $generator ) {
				$this->response = [
					'response' => [
						'code'       => 806,
						'message'    => 'Generator not found',
						'identifier' => $this->identifier
					]
				];
			}

			$generatedLicenseKeys = ResponseService::generateLicenseKeys( $generator, $generateQuantity, false, 'assigned', $this->ownerName, $this->ownerEmail );
		}

		$this->response = [
			'response' => [
				'code'         => 803,
				'message'      => 'License keys assigned',
				'license_keys' => array_merge( $licenseKeys->toArray(), $generatedLicenseKeys ),
				'identifier'   => $this->identifier
			]
		];

		Http::withoutVerifying()->post( $this->webhookUrl, ResponseService::respond( $this->response ) );
	}
}
