<?php

namespace Opencart\Admin\Model\Extension\Alsendo\Module;

require_once(DIR_EXTENSION . 'alsendo/src/DTO/Entity/AlsendoShipmentStatusEntity.php');
require_once(DIR_EXTENSION . 'alsendo/src/DTO/Entity/AlsendoRegionEntity.php');

use Opencart\Extension\Alsendo\DTO\Entity\AlsendoRegionEntity;
use Opencart\Extension\Alsendo\DTO\Entity\AlsendoShipmentStatusEntity;
use Opencart\System\Engine\Model;
use Opencart\System\Engine\Registry;

class AlsendoShipmentStatus extends Model {

    public function __construct(Registry $registry) {
        parent::__construct($registry);
    }

    public function getShipmentTriggerStatusId(): ?int {
        $query = $this->db->query("SELECT `value` FROM `" . DB_PREFIX . "setting`
        WHERE `code` = 'alsendo' AND `key` = 'shipment_trigger_status_id' LIMIT 1");
        if (!$query->num_rows || $query->row['value'] === null) {
            return null;
        }
        return (int)$query->row['value'];
    }

    public function setShipmentTriggerStatusId(?int $statusId): void {
        $val = !empty($statusId) ? $statusId : 'NULL';
        $query = $this->db->query("SELECT `value` FROM `" . DB_PREFIX . "setting` 
        WHERE `code` = 'alsendo' AND `key` = 'shipment_trigger_status_id' LIMIT 1");
        if ($query->num_rows) {
            $this->db->query("UPDATE `" . DB_PREFIX . "setting` 
            SET `value` = $val 
            WHERE `code` = 'alsendo' AND `key` = 'shipment_trigger_status_id'");
        } else {
            $this->db->query("INSERT INTO `" . DB_PREFIX . "setting` 
            SET `store_id` = 0, 
                `code` = 'alsendo', 
                `key` = 'shipment_trigger_status_id', 
                `value` = $val, 
                `serialized` = 0");
        }
    }

    public function populate(): void {
        $this->load->model('extension/alsendo/module/alsendo_region');
        /** @var AlsendoRegionEntity $currentRegion */
        $currentRegion = $this->model_extension_alsendo_module_alsendo_region->getCurrentRegion();

        $statuses = [
            ['name' => 'new', 'order' => 100],
            ['name' => 'cancelled', 'order' => 200]
        ];

        foreach ($statuses as $status) {
            $exists = $this->db->query("SELECT `id` FROM `" . DB_PREFIX . "alsendo_shipment_status` WHERE `name` = '" . $this->db->escape($status['name']) . "' AND `region_id` = '".$currentRegion->id."' LIMIT 1");
            if (!$exists->num_rows) {
                $this->db->query("INSERT INTO `" . DB_PREFIX . "alsendo_shipment_status` SET
                `name` = '" . $this->db->escape($status['name']) . "',
                `order` = '" . $this->db->escape($status['order']) . "',
                `region_id` = '".$currentRegion->id."'");
            }
        }
    }

    /**
     * @return AlsendoShipmentStatusEntity[]
     */
    public function getCurrentRegionShipmentStatuses(): array {
        $this->load->model('extension/alsendo/module/alsendo_region');
        /** @var AlsendoRegionEntity $currentRegion */
        $currentRegion = $this->model_extension_alsendo_module_alsendo_region->getCurrentRegion();

        $query = $this->db->query("SELECT * FROM `" . DB_PREFIX . "alsendo_shipment_status` WHERE `region_id` = '".$currentRegion->id."' ORDER BY `order` ASC");


        $this->load->model('localisation/order_status');
        $openCartOrderStatuses = $this->model_localisation_order_status->getOrderStatuses();
        $openCartOrderStatuses = array_column($openCartOrderStatuses, null, 'order_status_id');

        $alsendoStatuses = [];

        if ($query->num_rows === 0){
            $this->populate();
            $query = $this->db->query("SELECT * FROM `" . DB_PREFIX . "alsendo_shipment_status` WHERE `region_id` = '".$currentRegion->id."' ORDER BY `order` ASC");
        }

        if ($query->num_rows) {
            foreach ($query->rows as $row) {
                $alsendoShipmentStatus = AlsendoShipmentStatusEntity::fromArray([
                    'id' => (int)$row['id'],
                    'name' => $row['name'],
                    'order' => (int)$row['order'],
                    'region_id' => $row['region_id'] ? (int)$row['region_id'] : null,
                    'data' => $row['data'],
                    'order_status_id' => $row['order_status_id'] ? (int)$row['order_status_id'] : null,
                ]);

                if (!empty($alsendoShipmentStatus->orderStatusId) && array_key_exists($alsendoShipmentStatus->orderStatusId, $openCartOrderStatuses)) {
                    $alsendoShipmentStatus->setMappedOrderStatus($openCartOrderStatuses[$alsendoShipmentStatus->orderStatusId]);
                }

                $alsendoStatuses[] = $alsendoShipmentStatus;
            }
        }

        return $alsendoStatuses;
    }

    public function updateMappings(array $mapping): void {
        foreach ($mapping as $shipmentStatusId => $orderStatusId) {
            $val = !empty($orderStatusId) ? (int)$orderStatusId : 'NULL';
            $this->db->query("UPDATE `" . DB_PREFIX . "alsendo_shipment_status`
            SET `order_status_id` = $val
            WHERE `id` = " . (int)$shipmentStatusId);
        }
    }
}