<?php
namespace Modules\Evaluation\Controller;

use Entity\Model\EvalModel;
use Entity\Model\GrilSte;
use GuzzleHttp\Psr7\Response;
use Helpers\Ariane\Ariane;
use Helpers\ExportTo\Outils;
use Helpers\Fichier\Fichier;
use Helpers\Filter\FiltreAvance\Generator;
use Helpers\Outil\Roles;
use Helpers\Outil\Sql;
use Helpers\Pagination\PaginatorGestion;
use Helpers\Trad\Trad;
use Helpers\Validator\Validator;
use Modules\Evaluation\MenuContextuel\ModelMenuContextuel;
use Modules\Evaluation\Repository\Category;
use Modules\Evaluation\Repository\Model;
use Skeleton\Controller\Controller;
use Helpers\Session\Enums\MenuTopEnum;
use Helpers\Session\Session;

class ModelController extends Controller
{
    /**
     * @var array<mixed>
     */
    protected array $droits = [];

    /**
     * init
     * gestion des droits
     *
     * @return void
     */
    public function init()
    {
        $droits = [
            'HA_MQUESCM' => Roles::droitsUtilisateur($this->pdo, 'HA_MQUESCM', $_SESSION["Session_Login"]), // Droit de création et modification des modèles et les catégories de modèles
            'HA_CEVAVIS' => Roles::droitsUtilisateur($this->pdo, 'HA_CEVAVIS', $_SESSION["Session_Login"]), // Droit de visu des campagnes
            'HA_CEVALCM' => Roles::droitsUtilisateur($this->pdo, 'HA_CEVALCM', $_SESSION["Session_Login"]), // Droit de création et modification des campagnes
            'HA_CEVASUP' => Roles::droitsUtilisateur($this->pdo, 'HA_CEVASUP', $_SESSION["Session_Login"]), // Droit de suppression des campagnes d'évaluation
            'HA_BIBQTCM' => Roles::droitsUtilisateur($this->pdo, 'HA_BIBQTCM', $_SESSION["Session_Login"]), // Droit de création et modification de questionnaire
        ];

        $this->droits = $droits;
    }

    public function indexAction() : string
    {
        $trad = $this->getTranslationService();

        $post = $this->request->getParsedBody();

        $categoryRepo = new Category($this->pdo, $this->pdoStorage);
        $categoryListTemp = $categoryRepo->categoryList();

        $paginator = new PaginatorGestion();
        $paginator->generate('', 'DTE_CREAT', 'DESC');
        $modelRepository = new Model($this->pdo);
        $modelList = $modelRepository->modelList($post);
        $infoPagination = PaginatorGestion::getInfoPagination();
        $menuContextuel   = new ModelMenuContextuel($this->pdo, $this->router, $this->getTranslationService());

        foreach ($modelList as &$model) {
            $model['menuContextuel'] = $menuContextuel->generate($model['ID_MODEL'], $model['LIB_MODEL']);
        }
        unset($model);

        $categoryList = [
            ''  => $trad->t('Aucune')
        ];
        foreach ($categoryListTemp as $category) {
            $categoryList[$category['ID_GRILLE']] = $category['LIB_GRILLE'];
        }

        $companiesList = [
            '' => $trad->t('Toutes')
        ];
        $temporaryCompaniesList = $modelRepository->companiesList();
        foreach ($temporaryCompaniesList as $value) {
            $companiesList[$value['CODE_STE']] = $value['RAIS_SOC'];
        }

        $menuActive = 'Evaluations';
        
        Ariane::generate(0, $trad->t('Gestion'), $post, $infoPagination['nbrArticle']);

        $advancedFilter = new Generator($post);
        $advancedFilter->setFiltre('ID_MODEL', 'text', $trad->t('Code'));
        $advancedFilter->setFiltre('LIB_MODEL', 'text', $trad->t('Libellé'));
        $advancedFilter->setFiltre('ID_GRILLE', 'text', $trad->t('Catégorie'));

        return $this->renderer->render('@Evaluation/Modele/index', [
            'menuActive'          => Session::verifySessionTypeMenuTop(MenuTopEnum::S2C) ? 'Consultations' : $menuActive,
            'menuLeft'            => 'models',
            'modelList'           => $modelList,
            'categoryList'        => $categoryList,
            'companiesList'       => $companiesList,
            'filtreAvance'        => $advancedFilter->getFiltres(),
            'initFiltreAvance'    => $advancedFilter->getInit(),
            'post'                => $post,
            'infoPagination'      => $infoPagination,
            'titre'               => $trad->t('Modèles de questionnaire'),
            'droits'              => $this->droits, //['HA_MQUESCM' => true],//$droits,
        ]);
    }
    
    /**
     * createEditAction
     *
     * @return string|Response
     */
    public function createEditAction()
    {
        $post = $this->request->getParsedBody();
        $id = $this->request->getAttribute('id');
        $menuActive = 'Evaluations';
        
        $trad = $this->getTranslationService();

        $categoryRepo = new Category($this->pdo, $this->pdoStorage);
        $categoryListTemp = $categoryRepo->categoryList();
        $categoryList = [
            ''  => $trad->t('Aucune')
        ];
        foreach ($categoryListTemp as $category) {
            $categoryList[$category['ID_GRILLE']] = $category['LIB_GRILLE'];
        }

        $modelRepo = new Model($this->pdo);
        $modelList = $modelRepo->modelList();

        if (\is_array($post) && !empty($post)) {
            if (!isset($post['TTE_SOC']) && $post['societe'] == '') {
                return new Response(200, [], (string) \json_encode([
                    'statut' => 'E',
                    'erreur' => $trad->t('Vous devez sélectionner au moins une société.')
                ]));
            }
            $validator = $this->createValidator();

            $validator->isStringSansEspace("Code", $post['CODE'], 1, 10);
            $validator->isStringAvecEspace("Libellé", $post['LIBELLE'], 0, 30);
            $validator->isStringAvecEspace("Description", $post['DESCRIPTION'], 0, 3000);

            foreach ($modelList as $model) {
                if (\strtoupper($post['CODE']) == \strtoupper($model['ID_MODEL'])) {
                    return new Response(200, [], (string) \json_encode([
                    'statut' => 'E',
                    'erreur' => $trad->t('Le code saisi est déjà utilisé.')
                    ]));
                }
            }
            
            if (!$validator->isValid()) {
                return new Response(200, [], (string) \json_encode([
                    'statut' => 'E',
                    'erreur' => $validator->getError()
                    ]));
            } else {
                if ($id) {
                    $update = [
                        ':ID_MODEL'     => $post['CODE'],
                        ':LIB_MODEL'    => $post['LIBELLE'],
                        ':DESCRIPTION'  => $post['COMMENTAIRE'] ?? '',
                        ':ID_GRILLE'    => $post['CATEGORIE'],
                        ':DTE_MODIF'    => \date('Ymd'),
                        ':MODIF_PAR'    => \strtoupper($_SESSION['Session_Login']),
                        ':NON_MODIF_AO' => Sql::setBoolSql($post['MODIF_CONSULT'] ?? ''),
                        ':TTE_SOC'      => Sql::setBoolSql($post['TTE_SOC'] ?? ''),
                    ];
                    $modelRepo->modelUpdate($update);
                    if ($update[':TTE_SOC'] == '0x46') {
                        $societes = \explode('/', $post['societe']);
                    }
                    return new Response(200, [], (string) \json_encode([
                        'statut'    => 'O',
                        'path'      => $this->router->generateUri('Evaluation.Model.index')
                        ]));
                } else {
                    foreach ($modelList as $model) {
                        if (\strtoupper($post['CODE']) == \strtoupper($model['ID_MODEL'])) {
                            return new Response(200, [], (string) \json_encode([
                            'statut' => 'E',
                            'erreur' => $trad->t('Le code saisi est déjà utilisé.')
                            ]));
                        }
                    }
                    $insert = [
                        ':ID_MODEL'     => $post['CODE'],
                        ':LIB_MODEL'    => $post['LIBELLE'],
                        ':DESCRIPTION'  => $post['COMMENTAIRE'] ?? '',
                        ':ID_GRILLE'    => $post['CATEGORIE'],
                        ':DTE_CREAT'    => \date('Ymd'),
                        ':CREE_PAR'     => \strtoupper($_SESSION['Session_Login']),
                        ':DTE_MODIF'    => \date('Ymd'),
                        ':MODIF_PAR'    => \strtoupper($_SESSION['Session_Login']),
                        ':NON_MODIF_AO' => Sql::setBoolSql($post['MODIF_CONSULT'] ?? ''),
                        ':TTE_SOC'      => Sql::setBoolSql($post['TTE_SOC'] ?? ''),
                    ];
    
                    if ($insert[':TTE_SOC'] == '0x46') {
                        $societes = \explode('/', $post['societe']);
                    }
    
                    $modelRepo->modelNew($insert, $societes ?? []);
                    return new Response(200, [], (string) \json_encode([
                        'statut'    => 'O',
                        'path'      => $this->router->generateUri('Evaluation.Model.index')
                        ]));
                }
            }
        } else {
            Ariane::generate(0, $trad->t('Gestion'), $post, PaginatorGestion::getNbrArticle(), $this->router->generateUri('Evaluation.Model.index'));
            if ($id) {
                Ariane::generate(1, $trad->t('Modification modèle'));
                $action = 'modification';
                $model = $modelRepo->modelDetail($id);
                $companiesList = $modelRepo->modelCompaniesList($id);
                foreach ($companiesList as $company) {
                    $model['societe'] .= $model['societe'] != ''
                        ? '/' . $company['CODE_STE']
                        : $company['CODE_STE'];
                }
            } else {
                Ariane::generate(1, $trad->t('Nouveau modèle'));
                $action = 'creation';
            }

            return $this->renderer->render('@Evaluation/Modele/editModele', [
                'menuActive'    => Session::verifySessionTypeMenuTop(MenuTopEnum::S2C) ? 'Consultations' : $menuActive,
                'menuLeft'      => 'models',
                'post'          => $post,
                'title'         => $trad->t('Gestion modèles'),
                'model'         => $model ?? [],
                'categoryList'  => $categoryList,
                'modelList'     => $modelList,
                'action'        => $action,
                'path'          => 'Evaluation.Model.createEdit',
                'droits'        => $this->droits, //['HA_MQUESCM' => true]//$droits
            ]);
        }
    }
        
    /**
     * validateAction
     *
     * @return string|Response
     */
    public function validateAction()
    {
        $post = $this->request->getParsedBody();
        $id = $this->request->getAttribute('id');
        $modelRepo = new Model($this->pdo);

        $trad = $this->getTranslationService();

        $modelList = [];
        $model = [];

        if (\is_array($post) && \count($post) > 0) {
            $validator = $this->createValidator();

            $validator->isStringAvecEspace("Libellé", $post['LIBELLE'], 1, 30);
            $validator->isStringAvecEspace("Code", $post['CODE'], 1, 10);

            if (!isset($post['TTE_SOC']) && $post['societe'] == '') {
                return $this->renderer->render('@popup-erreur/ErreurCreation', [
                    'ErreurValid' => $trad->t('Vous devez sélectionner au moins une société.'),
                ]);
            }

            if (isset($post['societe']) && $post['societe'] != '') {
                $societes = \explode('/', $post['societe']);
                foreach ($societes as $company) {
                    $validator->zoom('Societe', $company, $trad->t('sociétés'), $this->pdo);
                }
            }

            if (!$validator->isValid()) {
                return $this->renderer->render('@popup-erreur/ErreurCreation', [
                    'ErreurValid' => $validator->getError(),
                ]);
            } else {
                if ($id != '') {
                    $update = [
                        ':ID_MODEL'     => $post['CODE'],
                        ':LIB_MODEL'    => $post['LIBELLE'],
                        ':DESCRIPTION'  => $post['DESCRIPTION'] ?? '',
                        ':ID_GRILLE'    => $post['CATEGORIE'],
                        ':DTE_MODIF'    => \date('Ymd'),
                        ':MODIF_PAR'    => \strtoupper($_SESSION['Session_Login']),
                        ':NON_MODIF_AO' => Sql::toBool($post['MODIF_CONSULT'] ?? ''),
                        ':TTE_SOC'      => Sql::toBool($post['TTE_SOC'] ?? ''),
                    ];
                    if ($update[':TTE_SOC'] == '0x46') {
                        $societes = \explode('/', $post['societe']);
                    }

                    (new GrilSte($this->pdo))->delete(['ID_MODEL' => $post['CODE']]);
                    $modelRepo->modelUpdate($update, $societes ?? []);
                    
                    return new Response(443, [], (string) \json_encode([
                        'path'      => $this->router->generateUri('Evaluation.Model.index')
                    ]));
                } else {
                    $modelList = $modelRepo->modelList();
                    
                    foreach ($modelList as $model) {
                        if (\strtoupper($post['CODE']) == \strtoupper($model['ID_MODEL'])) {
                            return $this->renderer->render('@popup-erreur/ErreurCreation', [
                                'ErreurValid' => $trad->t('Le code saisi est déjà utilisé.'),
                            ]);
                        }
                    }

                    $insert = [
                        ':ID_MODEL'     => $post['CODE'],
                        ':LIB_MODEL'    => $post['LIBELLE'],
                        ':DESCRIPTION'  => $post['DESCRIPTION'] ?? '',
                        ':ID_GRILLE'    => $post['CATEGORIE'],
                        ':DTE_CREAT'    => \date('Ymd'),
                        ':CREE_PAR'     => \strtoupper($_SESSION['Session_Login']),
                        ':DTE_MODIF'    => \date('Ymd'),
                        ':MODIF_PAR'    => \strtoupper($_SESSION['Session_Login']),
                        ':NON_MODIF_AO' => Sql::toBool($post['MODIF_CONSULT'] ?? ''),
                        ':TTE_SOC'      => Sql::toBool($post['TTE_SOC'] ?? ''),
                    ];
    
                    if ($insert[':TTE_SOC'] == '0x46') {
                        $societes = \explode('/', $post['societe']);
                    }
    
                    $modelRepo->modelNew($insert, $societes ?? []);
                    return new Response(443, [], (string) \json_encode([
                        'path'      => $this->router->generateUri('Evaluation.Model.index')
                    ]));
                }
            }
        } else {
            return $this->redirect('Evaluation.Model.index');
        }
    }
    
    /**
     * creationAction
     *
     * @return string|Response
     */
    public function creationAction()
    {
        $post = $this->request->getParsedBody();

        $trad = $this->getTranslationService();

        $categoryRepo = new Category($this->pdo, $this->pdoStorage);
        $categoryListTemp = $categoryRepo->categoryList();
        $categoryList = [
            ''  => $trad->t('Aucune')
        ];
        foreach ($categoryListTemp as $category) {
            $categoryList[$category['ID_GRILLE']] = $category['LIB_GRILLE'];
        }

        $modelRepo = new Model($this->pdo);
        $modelList = $modelRepo->modelList();

        if (\is_array($post) && !empty($post)) {
            foreach ($modelList as $model) {
                if (\strtoupper($post['CODE']) == \strtoupper($model['ID_MODEL'])) {
                    return new Response(200, [], (string) \json_encode([
                    'statut' => 'E',
                    'erreur' => $trad->t('Le code saisi est déjà utilisé.')
                    ]));
                }
            }

            if (!isset($post['TTE_SOC']) && $post['societe'] == '') {
                return new Response(200, [], (string) \json_encode([
                    'statut' => 'E',
                    'erreur' => $trad->t('Vous devez sélectionner au moins une société.')
                ]));
            }

            $validator = $this->createValidator();

            $validator->isStringSansEspace("Code", $post['CODE'], 1, 10);
            $validator->isStringAvecEspace("Libellé", $post['LIBELLE'], 0, 30);
            $validator->isStringAvecEspace("Description", $post['DESCRIPTION'], 0, 3000);

            if (!$validator->isValid()) {
                return new Response(200, [], (string) \json_encode([
                    'statut' => 'E',
                    'erreur' => $validator->getError()
                    ]));
            } else {
                $insert = [
                    ':ID_MODEL'     => $post['CODE'],
                    ':LIB_MODEL'    => $post['LIBELLE'],
                    ':DESCRIPTION'  => $post['COMMENTAIRE'] ?? '',
                    ':ID_GRILLE'    => $post['CATEGORIE'],
                    ':DTE_CREAT'    => \date('Ymd'),
                    ':CREE_PAR'     => \strtoupper($_SESSION['Session_Login']),
                    ':DTE_MODIF'    => \date('Ymd'),
                    ':MODIF_PAR'    => \strtoupper($_SESSION['Session_Login']),
                    ':NON_MODIF_AO' => Sql::setBoolSql($post['MODIF_CONSULT'] ?? ''),
                    ':TTE_SOC'      => Sql::setBoolSql($post['TTE_SOC'] ?? ''),
                ];

                if ($insert[':TTE_SOC'] == '0x46') {
                    $societes = \explode('/', $post['societe']);
                }

                $modelRepo->modelNew($insert, $societes ?? []);
                return new Response(200, [], (string) \json_encode([
                    'statut'    => 'O',
                    'path'      => $this->router->generateUri('Evaluation.Model.index')
                    ]));
            }
        } else {
            $menuActive = 'Evaluations';

            Ariane::generate(0, $trad->t('Gestion'), $post, PaginatorGestion::getNbrArticle(), $this->router->generateUri('Evaluation.Model.index'));
            Ariane::generate(1, $trad->t('Nouveau modèle'));

            return $this->renderer->render('@Evaluation/Modele/editModele', [
                'menuActive'    => Session::verifySessionTypeMenuTop(MenuTopEnum::S2C) ? 'Consultations' : $menuActive,
                'menuLeft'      => 'models',
                'post'          => $post,
                'title'         => $trad->t('Gestion modèles'),
                'categoryList'  => $categoryList,
                'modelList'     => $modelList,
                'action'        => 'creation',
                'path'          => 'Evaluation.Model.creation',
                'droits'        => $this->droits, //['HA_MQUESCM' => true]//$droits
            ]);
        }
    }
    
    /**
     * modificationAction
     *
     * @return  string|Response
     */
    public function modificationAction()
    {
        $post = $this->request->getParsedBody();
        $id = $this->request->getAttribute('id');

        $trad = $this->getTranslationService();

        $modelRepo = new Model($this->pdo);
        $model = $modelRepo->modelDetail($id);
        $modelList = $modelRepo->modelList();

        $categoryRepo = new Category($this->pdo, $this->pdoStorage);
        $categoryListTemp = $categoryRepo->categoryList();
        $categoryList = [
            ''  => $trad->t('Aucune')
        ];
        foreach ($categoryListTemp as $category) {
            $categoryList[$category['ID_GRILLE']] = $category['LIB_GRILLE'];
        }


        if (\is_array($post) && \count($post) > 0) {
            $validator = $this->createValidator();

            $validator->isStringAvecEspace("Libellé", $post['LIBELLE'], 0, 30);

            if (!isset($post['TTE_SOC']) && $post['societe'] == '') {
                return new Response(200, [], (string) \json_encode([
                    'statut' => 'E',
                    'erreur' => $trad->t('Vous devez sélectionner au moins une société.')
                    ]));
            }

            if (!$validator->isValid()) {
                return new Response(200, [], (string) \json_encode([
                    'statut' => 'E',
                    'erreur' => $validator->getError()
                    ]));
            } else {
                $update = [
                    ':ID_MODEL'     => $post['CODE'],
                    ':LIB_MODEL'    => $post['LIBELLE'],
                    ':DESCRIPTION'  => $post['COMMENTAIRE'] ?? '',
                    ':ID_GRILLE'    => $post['CATEGORIE'],
                    ':DTE_MODIF'    => \date('Ymd'),
                    ':MODIF_PAR'    => \strtoupper($_SESSION['Session_Login']),
                    ':NON_MODIF_AO' => Sql::setBoolSql($post['MODIF_CONSULT'] ?? ''),
                    ':TTE_SOC'      => Sql::setBoolSql($post['TTE_SOC'] ?? ''),
                ];

                $modelRepo->modelUpdate($update);
            }

            return $this->redirect('Evaluation.Model.index');
        } else {
            // $menuLeft = $trad->t('Catégories Modèles');
            $menuActive = 'Evaluations';
    
            Ariane::generate(1, $trad->t('Modification modèle'));

            return $this->renderer->render('@Evaluation/Modele/editModele', [
                'menuLeft'        => 'models',
                'menuActive'      => Session::verifySessionTypeMenuTop(MenuTopEnum::S2C) ? 'Consultations' : $menuActive,
                'categoryList'    => $categoryList,
                'modelList'       => $modelList,
                'model'           => $model,
                'post'            => $post,
                'action'          => 'modification',
                'path'            => "path('Evaluation.Model.modification')",
                'title'           => $trad->t('Modification modèle'),
                'droits'          => $this->droits,
            ]);
        }
    }
    
    /**
     * suppressionAction
     *
     * @return Response
     */
    public function suppressionAction()
    {
        $id = $this->request->getAttribute('id');
        $modelRepo = new Model($this->pdo);

        $delete = [
            ':ID_MODEL' => $id,
        ];

        $modelRepo->modelDelete($delete);

        return $this->redirect('Evaluation.Model.index');
    }
    
    public function exportAction() : string
    {
        $modelRepository  = new Model($this->pdo);
        $modelList = $modelRepository->modelList();
        $modelModel = new EvalModel($this->pdo);

        // Récupération des formats des champs
        $fieldList = $modelModel->getArchitecture($this->getTranslationService());
        
        // On génère l'entête du fichier d'export
        $tab = [];
        foreach ($fieldList as $key => $field) {
            $tab[\substr($modelModel->table, 0, 9) . '.' . $key] = $field['nomChamp'];
        }
        
        Outils::gestionEmailAsync2(
            "export_liste_modeles",
            $modelList,
            $this->JWTKEY,
            $this->router,
            $this->getTranslationService(),
            $tab
        );
        return 'ok';
    }

    public function favoriAction() : string
    {
        $id = $this->request->getAttribute('id');
        $post = $this->request->getParsedBody();

        $fav = new Model($this->pdo);

        if ($post['favEta']!='-1') {
            $fav->modelRemoveFav($id, $_SESSION['Session_Login']);
        } else {
            $fav->modelAddFav($id, $_SESSION['Session_Login']);
        }
        return $id;
    }
}
