<?php

use API\Partenaire\Service\PartenaireService;
use API\Provigis\ProvigisService;
use Helpers\Cache\Cache;
use Helpers\Cache\OPCache;
use Helpers\ExportTo\EmailCsvService;
use Helpers\Outil\EnvHelper;
use Helpers\Outil\Outils;
use Helpers\Roles\ParseConfigFile;
use Helpers\Session\ParseBase1;
use Helpers\Session\UserSession;
use Helpers\Trad\ITrad;
use Helpers\Trad\Trad;
use Helpers\Fichier\AvatarFileService;
use Helpers\Trad\TradDev;
use Helpers\Trad\TradRecette;
use Psr\SimpleCache\CacheInterface;
use Skeleton\Renderer\RendererInterface;
use Psr\Container\ContainerInterface;
use Helpers\Fichier\Fichier;
use Helpers\User\User;
use Helpers\User\UserInterface;
use Symfony\Component\HtmlSanitizer\HtmlSanitizer;
use Symfony\Component\HtmlSanitizer\HtmlSanitizerConfig;
use Symfony\Component\HtmlSanitizer\HtmlSanitizerInterface;
use Symfony\Component\String\Slugger\AsciiSlugger;
use Symfony\Component\String\Slugger\SluggerInterface;

if ((isset($_SESSION['AUTH_SSO']) && $_SESSION['AUTH_SSO'] == 1) || (isset($_SESSION['lastAUTH_SSO']) && $_SESSION['lastAUTH_SSO'] == 1)) {
    $_SESSION['lastAUTH_SSO'] = 1;
    $broker                   = 'sso';
} else {
    $broker = '';
}

if ((new ParseBase1())->getBroker() == 1) {
    $broker  .= '';
} else {
    $broker  .= (new ParseBase1())->getBroker();
}

if (substr(str_replace('/oxaproc', '', $_SERVER['REQUEST_URI']), 0, 3) == 'sso' && (!isset($_SESSION['lastAUTH_SSO']) || !$_SESSION['lastAUTH_SSO'])) {
    header('Location: ../index.php');
    exit();
}



if (!isset($_SESSION['batch']) || (isset($_SESSION['batch']) && !$_SESSION['batch'])) {
    /**
     * Recuperation des extension Twig Globale
     */
    $extention = \Skeleton\Renderer\TwigRendererFactory::getAllTwigExtensions();
} else {
    $extention;
}

/**
 * NOTE : Never use ```function() use()``` here, it will break when cached.
 */
// $_SESSION['Session_Login'] = 'OXAUSER';
// $_SESSION['environnement'] = 'production';

// $c->get('driverPDO') = "odbc:Driver={ODBC Driver 18 for SQL Server};TrustServerCertificate=yes;";
return [
    'database.hostSQL' => (new ParseBase1())->getOxaSql()->Server,
    'database.usernameSQL' => (new ParseBase1())->getOxaSql()->Login,
    'database.passwordSQL' => (new ParseBase1())->getOxaSql()->Password,
    'database.nameSQL' => (new ParseBase1())->getOxaSql()->Name,

    'database.hostCAT' => (new ParseBase1())->getOxaCat()->Server,
    'database.usernameCAT' => (new ParseBase1())->getOxaCat()->Login,
    'database.passwordCAT' => (new ParseBase1())->getOxaCat()->Password,
    'database.nameCAT' => (new ParseBase1())->getOxaCat()->Name,


    'database.hostPROC' => (new ParseBase1())->getOxaProc()->Server,
    'database.usernamePROC' => (new ParseBase1())->getOxaProc()->Login,
    'database.passwordPROC' => (new ParseBase1())->getOxaProc()->Password,
    'database.namePROC' => (new ParseBase1())->getOxaProc()->Name,

    'database.hostDW' => (new ParseBase1())->getOxaDW()->Server ?? '',
    'database.usernameDW' => (new ParseBase1())->getOxaDW()->Login ?? '',
    'database.passwordDW' => (new ParseBase1())->getOxaDW()->Password ?? '',
    'database.nameDW' => (new ParseBase1())->getOxaDW()->Name ?? '',

    'database.hostFT' => (new ParseBase1())->getOxaFT()->Server ?? null,
    'database.usernameFT' => (new ParseBase1())->getOxaFT()->Login ?? null,
    'database.passwordFT' => (new ParseBase1())->getOxaFT()->Password ?? null,
    'database.nameFT' => (new ParseBase1())->getOxaFT()->Name ?? null,
    'driverPDO' => 'odbc:Driver={ODBC Driver 18 for SQL Server};TrustServerCertificate=yes;MARS_Connection=yes;',

    'BASE' => '../../ini/base1.ini',

    /**
     * Recuperation des extensions
     */
    'twig.extensions' => $extention,
    'PRODUCT_CODE' => 'OXAPROC',

    'base' => '/oxaproc' . $broker . '/',
    'baseUrl' => '/oxaproc' . $broker . '/',
    'baseForCookie' => '/oxaproc' . $broker,

    'host' => function () {
        return ParseConfigFile::getConfigFileIni()['SERVERWEBHTTP'] ?? $_SESSION['base1']['_serveurweb'];
    },
    'hostFront' => function () {
        return ParseConfigFile::getConfigFileIni()['SERVERWEBHTTP_FRONTAL'] ?? $_SESSION['base1']['_serveurweb_frontal'];
    },

    'urlOxaLink' => function (ContainerInterface $c) {
        return Outils::getPreferredProtocol()
            . $c->get('hostFront') . '/oxalink'
            . Outils::getBrokerPrefix()
            . '/index.php';
    },
    'urlOxaLinkIndex' => function (ContainerInterface $c) {
        return Outils::getPreferredProtocol()
            . $c->get('hostFront')
            . '/oxalink'
            . Outils::getBrokerPrefix();
    },
    'urlOxaproc' => function (ContainerInterface $c) {
        return Outils::getPreferredProtocol()
            . $c->get('hostFront')
            . '/oxaproc'
            . Outils::getBrokerPrefix();
    },
    'urlOxaprocSso' => function (ContainerInterface $c) {
        return Outils::getPreferredProtocol()
            . $c->get('hostFront')
            . '/oxaprocsso'
            . Outils::getBrokerPrefix();
    },
    'urlOxaprocWithVarServ' => function (ContainerInterface $c) {
        return Outils::getPreferredProtocol()
            . ($_SERVER['HTTP_HOST'] ?? $_SERVER['SERVER_NAME'])
            . '/oxaproc'
            . Outils::getBrokerPrefix();
    },

    \Psr\Http\Message\ServerRequestInterface::class => \GuzzleHttp\Psr7\ServerRequest::fromGlobals(),

        //ResponseInterface::class => DI\Factory(ResponseInterface::class),
    RendererInterface::class => DI\Factory(\Skeleton\Renderer\TwigRendererFactory::class),
    'RendererInterface::class' => DI\Factory(\Skeleton\Renderer\TwigRendererFactory::class),
    \PDO::class => function (ContainerInterface $c) {
        return new \Skeleton\Pdo\PdoSkeletonV2(
            $c->get('driverPDO')
            . ';Server=' . $c->get('database.hostSQL')
            . ';database=' . $c->get('database.nameSQL'),
            $c->get('database.usernameSQL'),
            $c->get('database.passwordSQL')
        );
    },
    'PDO.oxasql' => function (ContainerInterface $c) {
        return $c->get(\PDO::class);
    },
    'PDO.oxacat' => function (ContainerInterface $c) {
        return new \Skeleton\Pdo\PdoSkeletonV2(
            $c->get('driverPDO')
            . ';Server=' . $c->get('database.hostCAT')
            . ';database=' . $c->get('database.nameCAT'),
            $c->get('database.usernameCAT'),
            $c->get('database.passwordCAT')
        );
    },
    'PDO.oxaproc' => function (ContainerInterface $c) {
        return new \Skeleton\Pdo\PdoSkeletonV2(
            $c->get('driverPDO')
            . ';Server=' . $c->get('database.hostPROC')
            . ";database=" . $c->get('database.namePROC'),
            $c->get('database.usernamePROC'),
            $c->get('database.passwordPROC')
        );
    },
    'PDO.oxaft' => function (ContainerInterface $c) {
        if (empty((new ParseBase1())->getOxaFT()->Server)) {
            return $c->get(\PDO::class);
        }

        return new \Skeleton\Pdo\PdoSkeletonV2(
            $c->get('driverPDO')
            . ';Server=' . $c->get('database.hostFT')
            . ";database=" . $c->get('database.nameFT'),
            $c->get('database.usernameFT'),
            $c->get('database.passwordFT')
        );
    },
    'PDO.storage' => function (ContainerInterface $c) {

        $connexion = array(
            'DataBase' => $c->get('database.nameSQL'),
            'UID' => $c->get('database.usernameSQL'),
            'PWD' => $c->get('database.passwordSQL'),
            'CharacterSet' => 'UTF-8'
        );

        $conn = \sqlsrv_connect($c->get('database.hostSQL'), $connexion);
        return $conn;

        // return new \PDO("sqlsrv:server=" . $c->get('database.hostSQL') . ";database=" . $c->get('database.nameSQL'), $c->get('database.usernameSQL') , $c->get('database.passwordSQL'));
    },
    'PDO.oxadw' => function (ContainerInterface $c) {
        if (trim($c->get('database.hostDW')) == '') {
            return false;
        }
        try {
            return new \Skeleton\Pdo\PdoSkeletonV2(
                $c->get('driverPDO')
                . ';Server=' . $c->get('database.hostDW')
                . ";database=" . $c->get('database.nameDW'),
                $c->get('database.usernameDW'),
                $c->get('database.passwordDW')
            );
        } catch (Exception $e) {
            return false;
        }
    },
    'settings' => [
        'displayErrorDetails' => true,
    ],
    'application.name' => 'oxaproc',
    'AvatarFileRepo' => function () {
        // TODO : get directory from ParseConfigFile directly instead of using SESSION
        return new AvatarFileService(Fichier::buildPath(
            realpath((new ParseBase1())->getRep()->images),
            'avatar'
        ));
    },
    CacheInterface::class => function () {
        return new Cache();
    },
    OPCache::class => function () {
        return new OPCache((new ParseBase1())->getRep()->tmp . '/oxaproc_opcache');
    },
    EnvHelper::class => function () {
        return new EnvHelper();
    },
    ITrad::class => function (ContainerInterface $c) {
        if ($_SERVER['HTTP_HOST'] == 'localhost' || $_SERVER['HTTP_HOST'] == '127.0.0.1') {
            return new TradDev();
        }
        switch ($_SESSION['environnement'] ?? '') {
            case 'developpement':
            case 'nonregression':
                return new TradRecette(
                    $c->get(\PDO::class),
                    $c->get(CacheInterface::class),
                    Trad::getPreferedLang(),
                    (new ParseBase1())->getBroker()
                );
        }

        return new Trad(
            $c->get(\PDO::class),
            $c->get(CacheInterface::class),
            Trad::getPreferedLang(),
            (new ParseBase1())->getBroker()
        );
    },
    'ProvigisService' => function (ContainerInterface $c) {
        return new ProvigisService($c);
    },
    PartenaireService::class => function (ContainerInterface $c) {
        return new PartenaireService($c);
    },
    EmailCsvService::class => function (ContainerInterface $c) {
        return new EmailCsvService($c);
    },
    SluggerInterface::class => function () {
        return new AsciiSlugger();
    },
    UserInterface::class => function () {
        return (new User())->initObjectSource($_SESSION);
    }
];
