<?php

namespace Modules\Stock\Service;

use Entity\Model\Paravrac;
use Entity\Model\ParTxco;
use Entity\Model\Sparnum;
use Exception;
use Helpers\Outil\Roles;
use Modules\GlobalApplication\Repository\LicenceOxalys;
use Modules\Stock\Enum\CodeParametreVracEnum;
use Modules\Stock\Enum\TypeEnteteEnum;
use Modules\Stock\Enum\TypeParametreVracEnum;
use Modules\Stock\Repository\ParavracRepo;
use PDO;
use Helpers\Outil\Sql;

readonly class ParametrageService
{
    private Paravrac $paravrac;

    public function __construct(private PDO $pdo)
    {
        $this->paravrac = new Paravrac($this->pdo);
    }

    /**
     * @param TypeEnteteEnum $typeEntete
     * @param ?string $codeSociete
     * @return null|array<string,string>
     * @throws Exception
     */
    public function getParametreNumerotation(TypeEnteteEnum $typeEntete, ?string $codeSociete = null): ?array
    {
        $sparnum = new Sparnum($this->pdo);
        if (!$parametreNumerotation = $sparnum->find(['TYPE_ENT' => $typeEntete->name, 'CODE_STE' => ''])) {
            $parametreNumerotation = $sparnum->find(['TYPE_ENT' => $typeEntete->name, 'CODE_STE' => $codeSociete]);
        }

        return $parametreNumerotation;
    }

    /**
     * @param string $typeParametre
     * @param array<string,string> $codesParametres
     * @return array<string,array<string,string>>
     */
    public function getParametres(string $typeParametre, array $codesParametres): array
    {
        $parametres = [];
        foreach ($codesParametres as $codeparv => $defaultValue) {
            if (!$parametre = $this->paravrac->find(['TYPEPARV' => $typeParametre, 'CODEPARV' => $codeparv])) {
                $this->paravrac->insert($parametre = [
                    'TYPEPARV' => $typeParametre,
                    'CODEPARV' => $codeparv,
                    'LIB01PARV' => $defaultValue
                ]);
            }

            $parametres[$codeparv] = $parametre;
        }

        return $parametres;
    }

    /**
     * @return bool
     */
    public function isBonTransfertMultisociete(): bool
    {
        return Sql::toBool($this->paravrac->find([
            'TYPEPARV' => TypeParametreVracEnum::PARAMSTO->name,
            'CODEPARV' => CodeParametreVracEnum::BT_MULTISOCIETE->name
        ])['LIB01PARV']);
    }

    /**
     * @return bool
     */
    public function isBlancInterditTiers(): bool
    {
        return Sql::toBool($this->paravrac->find([
            'TYPEPARV' => TypeParametreVracEnum::PARASTOGEN->name,
            'CODEPARV' => CodeParametreVracEnum::BLANCINTERDIT_TIERS->name
        ])['LIB01PARV']);
    }

    /**
     * @throws Exception
     */
    public function isBonEntreeReintegrationDefault(): bool
    {
        return Sql::toBool((new ParTxco($this->pdo))->find(1)['BE_CONSO']);
    }

    /**
     * @return bool
     * @throws Exception
     */
    public function isQteDispoComputableWithQteReservee(): bool
    {
        return !Sql::toBool((new ParavracRepo($this->pdo))->findComputeQteDispoWithQteReserveeParametre()['LIB01PARV']);
    }

    /**
     * @param CodeParametreVracEnum $codeParametreVracEnum
     * @return bool
     */
    public function isImputationFacultative(CodeParametreVracEnum $codeParametreVracEnum): bool
    {
        return Sql::toBool($this->paravrac->find([
            'TYPEPARV' => TypeParametreVracEnum::PARASTOGEN->name,
            'CODEPARV' => $codeParametreVracEnum->name
        ])['LIB01PARV']);
    }

    /**
     * @return bool
     */
    public function isQteTheoriqueAMasquer(): bool
    {
        return Sql::toBool($this->paravrac->find([
            'TYPEPARV' => TypeParametreVracEnum::PARAMSTO->name,
            'CODEPARV' => CodeParametreVracEnum::INV_MASQUER_QTE_THEO->name
        ])['LIB01PARV']);
    }

    /**
     * @return bool
     */
    public function isVisibilitePrixActif(): bool
    {
        return Sql::toBool($this->paravrac->find([
            'TYPEPARV' => TypeParametreVracEnum::PARAMSTO->name,
            'CODEPARV' => CodeParametreVracEnum::ST_VISIPRIXACTIF->name
        ])['LIB01PARV']);
    }

    /**
     * @return bool
     */
    public function hasDroitModificationPrix(): bool
    {
        return Sql::toBool(Roles::droitsUtilisateur($this->pdo, 'HA_CA_VIPX'));
    }

    public function isCodeGestionActive(): bool
    {
        return (new LicenceOxalys($this->pdo))->codeGestionActive();
    }
}
