getApplication()->getEventManager(); /** @var \Zend\ServiceManager\ServiceManager $sm */ $sm = $e->getApplication()->getServiceManager(); // S'assurer que notre Request personnalisée est utilisée $request = $sm->get('Request'); $sm->setAllowOverride(true); $sm->setService('Request', $request); $sm->setAllowOverride(false); // Process to save device Infos for all view see https://stackoverflow.com/questions/24524899/zf2-add-global-variable-to-view // can be call in view with $this.layout()->viewDeviceInfos $eventManager->attach(MvcEvent::EVENT_RENDER, function ($e) { $sm = $e->getApplication()->getServiceManager(); // getServiceLocator(); // activation ou non de la partie mobile CWR $table = $sm->get('Reservation\Model\ConfigurationTable'); $config = $table->getConfig(1); $CWRActive = $config->CWRMobile ? $config->CWRMobile : false; $layoutViewModel = $e->getViewModel(); if ($CWRActive) { // A voir pour un paramétrage de la versions mobile ou non $viewDeviceInfos = [ // Check if the "mobile" word exists in User-Agent 'isMob' => is_numeric(strpos(strtolower($_SERVER["HTTP_USER_AGENT"]), "mobile")), // Check if the "tablet" word exists in User-Agent 'isTab' => is_numeric(strpos(strtolower($_SERVER["HTTP_USER_AGENT"]), "tablet")), // Platform check 'isWin' => is_numeric(strpos(strtolower($_SERVER["HTTP_USER_AGENT"]), "windows")), 'isAndroid' => is_numeric(strpos(strtolower($_SERVER["HTTP_USER_AGENT"]), "android")), 'isIPhone' => is_numeric(strpos(strtolower($_SERVER["HTTP_USER_AGENT"]), "iphone")), 'isIPad' => is_numeric(strpos(strtolower($_SERVER["HTTP_USER_AGENT"]), "ipad")) ]; } else { $viewDeviceInfos = [ // Check if the "mobile" word exists in User-Agent 'isMob' => false, // Check if the "tablet" word exists in User-Agent 'isTab' => false, // Platform check 'isWin' => false, 'isAndroid' => false, 'isIPhone' => false, 'isIPad' => false ]; } $viewDeviceInfos['isIOS'] = $viewDeviceInfos['isIphone'] || $viewDeviceInfos['isIPad']; $layoutViewModel->viewDeviceInfos = $viewDeviceInfos; $table = $sm->get('Application\Model\ConfigApiPushTable'); $config = $table->fetch(); // Ne jamais exposer rest_key côté client (layout visible dans le JSON des fetch) // $config peut être [] si aucune entrée en base $configObj = is_object($config) ? $config : (object)array(); $layoutViewModel->configApiPush = (object)array( 'app_id' => isset($configObj->app_id) ? $configObj->app_id : null, 'url_api' => isset($configObj->url_api) ? $configObj->url_api : null, 'isValid' => isset($configObj->isValid) ? $configObj->isValid : 0, ); }); $request = $e->getRequest(); // Détection des iframes Edusign $isEdusignIframe = false; if ($request instanceof \Zend\Http\Request) { $uri = $request->getUri()->getPath(); // Méthode 1 : Détecter toutes les routes /edusign/* if (strpos($uri, '/edusign') === 0) { $isEdusignIframe = true; } // Méthode 2 : Vérifier le cookie edusign_iframe (pour navigation après login) if ($request->getCookie() && isset($request->getCookie()->edusign_iframe)) { $isEdusignIframe = true; } } // Configuration de session adaptée if ($isEdusignIframe) { try { // Configuration session normale (sans modifier cookie_path) $this->initSession(array( 'use_cookies' => true, 'cookie_httponly' => true, 'cookie_secure' => true, )); // Réécrire le cookie de session avec SameSite=None après le démarrage $eventManager = $e->getApplication()->getEventManager(); $eventManager->attach(MvcEvent::EVENT_DISPATCH, function($e) { // Réécrire le cookie PHPSESSID avec SameSite=None if (session_id()) { header('Set-Cookie: ' . session_name() . '=' . session_id() . '; Path=/; Secure; HttpOnly; SameSite=None', false); } }, 1000); } catch (\Exception $ex) { $blockDebug = array( array( "id" => "debug1", "block" => "text", "text" => "# Debug\n ".$ex->getMessage(). "\n" ) ); // $e->getResponse()->getHeaders()->addHeaderLine('Content-Type', 'application/json'); echo json_encode($blockDebug); exit(); } } else { // Configuration normale (votre config existante) $this->initSession(array( // 'remember_me_seconds' => 180, 'use_cookies' => true, 'cookie_httponly' => true, )); } // getUser $auth_service = $sm->get('zfcuser_auth_service'); $gestName = ''; // Attacher le contrôle d'authentification à l'événement DISPATCH $eventManager->attach(MvcEvent::EVENT_DISPATCH, array($this, 'checkAuthSecu'), 100); date_default_timezone_set('Europe/Paris'); $langfile = "fr_FR"; $allLangues = array(); $routeCallback = function ($e) { // $table = new Tables('lang',$e->getApplication()->getServiceManager()->get('Zend\Db\Adapter\Adapter')); // $langTable = $table->getTable(); // $result = $langTable->select(array('active'=>'1')); $langTable = $e->getApplication()->getServiceManager()->get('Reservation\Model\LangueTable'); $result = $langTable->getAll(); $availableLanguages = array(); $defaultLanguage = 'fr_FR'; foreach ($result as $row) { $availableLanguages[] = $row->codeLang; if ($row->default == '1') { $defaultLanguage = $row->codeLang; } } //$availableLanguages = array ('fr_FR', 'en_US'); $language = ""; $fromRoute = false; //see if language could be find in url $lang_session = new Container('lang'); $lang = $lang_session->lang; //echo $lang; $langfile = $lang; $sess = new Container("loc"); $loc = $sess->loc; // var_dump("locCallBack",$loc); if ($loc) { if ($loc->langue == "UK") { $defaultLanguage = 'en_US'; } else { $defaultLanguage = 'fr_FR'; } } if ($lang) { $language = $lang; $fromRoute = true; //or use language from http accept } else { $headers = $e->getApplication()->getRequest()->getHeaders(); if ($headers->has('Accept-Language')) { $headerLocale = $headers->get('Accept-Language')->getPrioritized(); $language = substr($headerLocale[0]->getLanguage(), 0, 5); } } if (!in_array($language, $availableLanguages)) { $language = $defaultLanguage; } $e->getApplication()->getServiceManager()->get('translator')->setLocale($language); }; $eventManager->attach(MvcEvent::EVENT_ROUTE, $routeCallback); $sm = $e->getApplication()->getServiceManager(); $table = new Tables('lang', $sm->get('Zend\Db\Adapter\Adapter')); $result = $table->getTable()->select(array('active' => '1')); $langueBO = array(); foreach ($result as $row) { $allLangues[] = $row; if ($row->codeLang == "fr_FR") { $langueBO[] = $row; } } $router = $sm->get('router'); $request = $sm->get('request'); $matchedRoute = $router->match($request); $idCampagne = ""; $logoCampagne = ""; $params = $controller = $action = $route = null; if ($matchedRoute) { $params = $matchedRoute->getParams(); $controller = $params['controller']; $action = $params['action']; $route = $matchedRoute->getMatchedRouteName(); ## RECUP CAMPAGNE $urlAcces = !empty($params['acces']) ? $params['acces'] : ''; if ($urlAcces) { $tableCampagne = $e->getApplication()->getServiceManager()->get('Reservation\Model\CampagneTable'); $camps = $tableCampagne->getCampagnesByUrlAcces($urlAcces); $now = time(); foreach ($camps as $camp) { $dateDebutTS = strtotime($camp->dateDebut); $dateFinTS = strtotime($camp->dateFin); //vérification ouverture de la campagne if ($now >= $dateDebutTS && $now <= $dateFinTS) { $idCampagne = $camp->id; $logoCampagne = $camp->logo; } } } } $module_array = explode('\\', $controller); $module = array_pop($module_array); //roles $authorize = $sm->get('BjyAuthorize\Provider\Identity\ProviderInterface'); $roles = $authorize->getIdentityRoles(); $isAdmin = false; if (in_array('admin', $roles)) { $isAdmin = true; } // getUser $auth_service = $sm->get('zfcuser_auth_service'); $gestName = ''; if ($auth_service && $auth_service->hasIdentity()) { $gestName = $auth_service->getIdentity()->getUsername(); } $sess = new Container("locSess"); $loc = $sess->loc; // var_dump($_SESSION["loc"],$isAdmin, $gestName, $module, $controller, $action, $route, $params); //$allLangues = array(); if ($route) { $routesArr = explode('/', $route); if (in_array('zfcuser', $routesArr)) { $allLangues = $langueBO; } syslog(LOG_INFO, __FILE__ . "." . __FUNCTION__ . "." . __LINE__ . "_$_SERVER[REMOTE_ADDR] : route=" . json_encode($routesArr)); } syslog(LOG_INFO, __FILE__ . "." . __FUNCTION__ . "." . __LINE__ . "_$_SERVER[REMOTE_ADDR] : controller=$controller action=$action route=$route module=$module isAdmin=$isAdmin($gestName) idCampagne=$idCampagne"); $e->getViewModel()->setVariables( array( 'CURRENT_MODULE_NAME' => $module, 'CURRENT_CONTROLLER_NAME' => $controller, 'CURRENT_ACTION_NAME' => $action, 'CURRENT_ROUTE_NAME' => $route, 'ALL_LANGUES' => $allLangues, 'IS_ADMIN' => $isAdmin, 'CURRENT_PARAMS' => $params, 'idCampagne' => $idCampagne, 'logoCampagne' => $logoCampagne, ) ); $moduleRouteListener = new ModuleRouteListener(); $moduleRouteListener->attach($eventManager); } public function initSession($config) { $sessionConfig = new SessionConfig(); $sessionConfig->setOptions($config); $sessionManager = new SessionManager($sessionConfig); $sessionManager->start(); Container::setDefaultManager($sessionManager); } public function getConfig() { return include __DIR__ . '/config/module.config.php'; } public function getServiceConfig() { return array( 'factories' => array( 'Application\Model\CodeTable' => function ($sm) { $tableGateway = $sm->get('CodeTableGateway'); $table = new CodeTable($tableGateway); return $table; }, 'CodeTableGateway' => function ($sm) { $dbAdapter = $sm->get('Zend\Db\Adapter\Adapter'); $resultSetPrototype = new ResultSet(); $resultSetPrototype->setArrayObjectPrototype(new Code()); return new TableGateway('codes', $dbAdapter, null, $resultSetPrototype); }, 'Application\Model\PaysTable' => function ($sm) { $tableGateway = $sm->get('PaysTableGateway'); $table = new PaysTable($tableGateway); return $table; }, 'PaysTableGateway' => function ($sm) { $dbAdapter = $sm->get('Zend\Db\Adapter\Adapter'); $resultSetPrototype = new ResultSet(); $resultSetPrototype->setArrayObjectPrototype(new Pays()); return new TableGateway('pays', $dbAdapter, null, $resultSetPrototype); }, 'Application\Model\LocataireTable' => function ($sm) { $tableGateway = $sm->get('LocataireTableGateway'); $table = new LocataireTable($tableGateway); return $table; }, 'LocataireTableGateway' => function ($sm) { $dbAdapter = $sm->get('Zend\Db\Adapter\Adapter'); $resultSetPrototype = new ResultSet(); $resultSetPrototype->setArrayObjectPrototype(new Locataire()); return new TableGateway('locataires', $dbAdapter, null, $resultSetPrototype); }, 'Application\Model\TypelogementTable' => function ($sm) { $tableGateway = $sm->get('TypelogementTableGateway'); $table = new TypelogementTable($tableGateway); return $table; }, 'TypelogementTableGateway' => function ($sm) { $dbAdapter = $sm->get('Zend\Db\Adapter\Adapter'); $resultSetPrototype = new ResultSet(); $resultSetPrototype->setArrayObjectPrototype(new Typelogement()); return new TableGateway('type_logement', $dbAdapter, null, $resultSetPrototype); }, /*attribution de la table*/ 'Application\Model\EchangeXmlSql' => function ($sm) { $tableGateway = $sm->get('EchangeXmlSqlTableGateway'); $table = new EchangeXmlSql($tableGateway); return $table; }, 'EchangeXmlSqlTableGateway' => function ($sm) { $dbAdapter = $sm->get('Zend\Db\Adapter\Adapter'); $resultSetPrototype = new ResultSet(); $resultSetPrototype->setArrayObjectPrototype(new EchangeXmlObject()); return new TableGateway('reservations', $dbAdapter, null, $resultSetPrototype); }, /*fin attribution*/ 'Application\Model\ComptesTable' => function ($sm) { $tableGateway = $sm->get('ComptesTableGateway'); $table = new ComptesTable($tableGateway); return $table; }, 'ComptesTableGateway' => function ($sm) { $dbAdapter = $sm->get('Zend\Db\Adapter\Adapter'); $resultSetPrototype = new ResultSet(); $resultSetPrototype->setArrayObjectPrototype(new Comptes()); return new TableGateway('comptes', $dbAdapter, null, $resultSetPrototype); }, // Ajout du service ComptesDTable 'Application\Model\ComptesDTable' => function ($sm) { $tableGateway = $sm->get('ComptesDTableGateway'); $table = new \Application\Model\ComptesDTable($tableGateway); return $table; }, 'ComptesDTableGateway' => function ($sm) { $dbAdapter = $sm->get('Zend\Db\Adapter\Adapter'); $resultSetPrototype = new ResultSet(); $resultSetPrototype->setArrayObjectPrototype(new \ArrayObject()); return new TableGateway('comptes_d', $dbAdapter, null, $resultSetPrototype); }, 'Application\Model\PileTable' => function ($sm) { $tableGateway = $sm->get('PileTableGateway'); $table = new PileTable($tableGateway); return $table; }, 'PileTableGateway' => function ($sm) { $dbAdapter = $sm->get('Zend\Db\Adapter\Adapter'); $resultSetPrototype = new ResultSet(); $resultSetPrototype->setArrayObjectPrototype(new Pile()); return new TableGateway('pile', $dbAdapter, null, $resultSetPrototype); }, 'Application\Model\DocumentsTable' => function ($sm) { $tableGateway = $sm->get('DocumentsTableGateway'); $table = new DocumentsTable($tableGateway); return $table; }, 'DocumentsTableGateway' => function ($sm) { $dbAdapter = $sm->get('Zend\Db\Adapter\Adapter'); $resultSetPrototype = new ResultSet(); $resultSetPrototype->setArrayObjectPrototype(new Documents()); return new TableGateway('documents', $dbAdapter, null, $resultSetPrototype); }, 'Application\Model\LocaTable' => function ($sm) { $tableGateway = $sm->get('LocaTableGateway'); $table = new LocaTable($tableGateway); return $table; }, 'LocaTableGateway' => function ($sm) { $dbAdapter = $sm->get('Zend\Db\Adapter\Adapter'); $resultSetPrototype = new ResultSet(); $resultSetPrototype->setArrayObjectPrototype(new Loca()); return new TableGateway('locataires', $dbAdapter, null, $resultSetPrototype); }, 'Application\Model\SessionWLTable' => function ($sm) { $tableGateway = $sm->get('SessionWLTableGateway'); $table = new SessionWLTable($tableGateway); return $table; }, 'SessionWLTableGateway' => function ($sm) { $dbAdapter = $sm->get('Zend\Db\Adapter\Adapter'); $resultSetPrototype = new ResultSet(); $resultSetPrototype->setArrayObjectPrototype(new SessionWL()); return new TableGateway('session', $dbAdapter, null, $resultSetPrototype); }, 'Application\Model\UrlTokenTable' => function ($sm) { $tableGateway = $sm->get('UrlTokenTableGateway'); $table = new UrlTokenTable($tableGateway); return $table; }, 'UrlTokenTableGateway' => function ($sm) { $dbAdapter = $sm->get('Zend\Db\Adapter\Adapter'); $resultSetPrototype = new ResultSet(); $resultSetPrototype->setArrayObjectPrototype(new UrlToken()); return new TableGateway('urlToken', $dbAdapter, null, $resultSetPrototype); }, 'Application\Model\ConfigApiPushTable' => function ($sm) { //LOLODEV $tableGateway = $sm->get('ConfigApiPushTableGateway'); $table = new ConfigApiPushTable($tableGateway); return $table; }, 'ConfigApiPushTableGateway' => function ($sm) { $dbAdapter = $sm->get('Zend\Db\Adapter\Adapter'); $resultSetPrototype = new ResultSet(); $resultSetPrototype->setArrayObjectPrototype(new ConfigApiPush()); return new TableGateway('configApiPush', $dbAdapter, null, $resultSetPrototype); }, 'Request' => 'Application\Factory\SecureRequestFactory', ), ); } public function getAutoloaderConfig() { return array( 'Zend\Loader\StandardAutoloader' => array( 'namespaces' => array( __NAMESPACE__ => __DIR__ . '/src/' . __NAMESPACE__, ), ), ); } private function checkPostRequestFromCurrentConnectedUser(MvcEvent $e) { $request = $e->getApplication()->getServiceManager()->get('Request'); if ($request->isPost()) { if ($request->getPost('locId', null) == null) { return true; } $locIdPost = $request->getPost('locId'); $locIdSession = $_SESSION['loc']['loc']->id; // $resa = $_SESSION['locSess']; // var_dump( $_SESSION['loc'], $locIdSession, array_keys($_SESSION) ); if ($locIdPost == $locIdSession) { return true; } die(); } } public function checkAuthSecu(MvcEvent $e, $checkId = null) { // Récupérer les informations de la route courante $request = $e->getRequest(); $router = $e->getApplication()->getServiceManager()->get('router'); $matchedRoute = $router->match($request); // Routes exclues de la vérification d'authentification $excludedRoutes = array('zfcuser/login', 'login', 'user/login', 'connexion', 'signature/pms2', 'apirest/login', 'apirest/logout', 'apirest/retourDG', 'edusign', 'zfcuser/forgetpwd', 'identification', 'home', 'reservation/formulaireCampagne', 'reservation/formulaireCampagneUpload', 'proxyDocs', 'autoresponse', 'paiementResponse'); $isAdminRoute = false; // Exclusion par préfixe d'URI (fallback si la route apiBO ne matche pas) $uri = $request->getUri()->getPath(); if (strpos($uri, '/api/bo/') === 0 || $uri === '/api/bo') { return; } else if ($uri === '/etudiant/' || $uri === '/etudiant') { // Ici je souhaite laisser passer pour la connection spécifique Hec avec idSharepad // les deux uri sont nécéssaire car redirection dans le process return; } else if (strpos($uri, '/reservation/paiement') === 0) { // Laisser passer les requêtes prise d'empreinte et paiement qui ne passent pas par la route reservation/paiementResponse return; } else if (strpos($uri, '/reservation/apipaiementdispatch') === 0) { // Laisser passer les requêtes dispatch de paiement qui ne passent pas par la route reservation/paiementResponse return; } // Actions exclues par route : array('nom_route' => array('action1', 'action2')) // $excludedRouteActions = array( // 'reservations' => array( 'loadaiguillages', 'loadactions'), // ); // var_dump($matchedRoute);exit(); if ($matchedRoute) { $currentRoute = $matchedRoute->getMatchedRouteName(); $isAdminRoute = ($currentRoute === 'zfcadmin' || strpos($currentRoute, 'zfcadmin/') === 0); // Si la route courante est dans la liste des routes exclues, autoriser l'accès if (in_array($currentRoute, $excludedRoutes)) { return; } // // Si la route+action est dans la liste des exclusions par action, autoriser l'accès // if (isset($excludedRouteActions[$currentRoute])) { // $currentAction = $matchedRoute->getParam('action'); // if (in_array($currentAction, $excludedRouteActions[$currentRoute])) { // return; // } // } } $auth = $e->getApplication()->getServiceManager()->get('zfcuser_auth_service'); $hasAuth = $auth->hasIdentity(); // Variable pour stocker le type de connexion détecté $connectionType = 'aucune'; // 1. Vérifier si l'utilisateur est admin via $auth->hasIdentity if ($hasAuth) { // Utilisateur admin authentifié $connectionType = 'admin'; return; } // 2. Si pas admin, vérifier si c'est un résident via la session 'loc' $sess = new Container('loc'); // var_dump("checkAuthSecu", $hasAuth, $checkId, $sess->loc, $_SESSION['loc']); if ($sess->loc && $sess->loc->id && $sess->loc->id > 0) { // Utilisateur résident $connectionType = 'resident'; if ($checkId && $hasAuth) { $hasAuth = ($_SESSION['loc']['id'] == $checkId); } } // 3. NOUVEAU : Vérifier si un downloadToken est présent if ($connectionType === 'aucune') { $downloadToken = $request->getQuery('downloadToken'); syslog(LOG_INFO, __FILE__ . "." . __FUNCTION__ . "." . __LINE__ . "_$_SERVER[REMOTE_ADDR] : downloadToken=" . $downloadToken); if ($downloadToken) { try { $db = $e->getApplication()->getServiceManager()->get('Zend\Db\Adapter\Adapter'); $sql = "SELECT user_id FROM auth_tokens WHERE token = ? AND expires_at > NOW() LIMIT 1"; $statement = $db->query($sql); $result = $statement->execute(array($downloadToken)); $tokenData = $result->current(); if ($tokenData) { // Token valide - authentifier temporairement l'utilisateur $sess = new Container('loc'); // Charger l'utilisateur si pas déjà en session if (!$sess->loc || $sess->loc->id != $tokenData['user_id']) { // Vous devez avoir une méthode pour charger l'utilisateur // Adaptez selon votre code $userTable = $e->getApplication()->getServiceManager()->get('Reservation\Model\LocatairesTable'); $loc = $userTable->getLocataire($tokenData['user_id']); if ($loc) { $sess->loc = $loc; $connectionType = 'token_download'; syslog(LOG_INFO, __FILE__ . "." . __FUNCTION__ . "." . __LINE__ . "Authentification via downloadToken pour user " . $tokenData['user_id']); } } else { // Utilisateur déjà en session $connectionType = 'token_download'; } } else { syslog(LOG_INFO, __FILE__ . "." . __FUNCTION__ . "." . __LINE__ . "Token de téléchargement invalide: " . $downloadToken); } } catch (\Exception $ex) { syslog(LOG_ERR, __FILE__ . "." . __FUNCTION__ . "." . __LINE__ . "Erreur vérification downloadToken: " . $ex->getMessage()); } } } // 4. Vérifier si l'appel est fait en local sur le serveur if ($connectionType === 'aucune' && $this->isLocalRequest()) { $connectionType = 'local'; } // Les routes admin ne sont accessibles qu'aux connexions admin. if ($isAdminRoute && $connectionType != 'admin') { $this->logUnauthorizedAccess($e, $connectionType); return $this->buildUnauthorizedResponse($e); } if ($connectionType != 'aucune') { return; } // 5. Aucune condition n'est vérifiée - renvoyer 401 et logger $this->logUnauthorizedAccess($e, $connectionType); return $this->buildUnauthorizedResponse($e); } private function buildUnauthorizedResponse(MvcEvent $e) { $response = new Response(); $response->setStatusCode(401); $response->setContent(json_encode(array( 'status' => 401, 'message' => 'Vous devez être authentifié pour accéder à cette ressource.', // 'remote_addr' => $_SERVER['REMOTE_ADDR'], // 'server_addr' => $_SERVER['SERVER_ADDR'] ))); $response->getHeaders()->addHeaderLine('Content-Type', 'application/json'); // Définir la réponse dans l'événement et arrêter la propagation $e->setResponse($response); $e->stopPropagation(true); // Arrêter complètement l'exécution du framework return $response; } /** * Vérifie si la requête provient du serveur local */ private function isLocalRequest() { $remoteAddr = $_SERVER['REMOTE_ADDR']; $serverAddr = $_SERVER['SERVER_ADDR']; // Vérifier si l'adresse IP est identique if ($remoteAddr === $serverAddr) { return true; } // Vérifier si c'est une adresse locale (127.0.0.1, localhost) $localAddresses = array('127.0.0.1', '::1', 'localhost'); if (in_array($remoteAddr, $localAddresses)) { return true; } return false; } /** * Enregistre les tentatives d'accès non autorisées dans un fichier CSV */ private function logUnauthorizedAccess(MvcEvent $e, $connectionType = 'aucune') { try { //code... $logFile = __DIR__ . '/../../public/log_route_auth.csv'; // var_dump("logUnauthorizedAccess", $logFile); // Créer le fichier et l'en-tête s'il n'existe pas if (!file_exists($logFile)) { $handle = fopen($logFile, 'w'); if ($handle) { fputcsv($handle, array('Date', 'Route', 'Type Requête', 'Query Params', 'Controller', 'Action', 'Module', 'Paramètres Route', 'IP', 'User Agent', 'Type Connexion'), ';'); // Utiliser ';' comme séparateur fflush($handle); // Vider le buffer fclose($handle); } } // Récupérer les informations de la requête /** * Retrieve the HTTP request object from the event. * @var \Zend\Http\Request $request The HTTP request instance */ $request = $e->getRequest(); $router = $e->getApplication()->getServiceManager()->get('router'); $matchedRoute = $router->match($request); // var_dump("logUnauthorizedAccess", $matchedRoute); $route = ''; $controller = ''; $action = ''; $module = ''; $routeParams = ''; if ($matchedRoute) { $route = $matchedRoute->getMatchedRouteName(); $params = $matchedRoute->getParams(); $controller = isset($params['controller']) ? $params['controller'] : ''; $action = isset($params['action']) ? $params['action'] : ''; $routeParams = json_encode($params); // Extraire le module du nom du contrôleur if ($controller) { $module_array = explode('\\', $controller); $module = isset($module_array[0]) ? $module_array[0] : ''; } } // var_dump("logUnauthorizedAccess", $route, $controller, $action, $module, $routeParams); $method = $request->getMethod(); $queryParams = ''; $userAgent = isset($_SERVER['HTTP_USER_AGENT']) ? $_SERVER['HTTP_USER_AGENT'] : ''; // Préparer la nouvelle ligne $newLine = array( date('Y-m-d H:i:s'), $route, $method, $queryParams, $controller, $action, $module, $routeParams, $_SERVER['REMOTE_ADDR'], $userAgent, $connectionType ); // var_dump("logUnauthorizedAccess", $newLine); // Créer une clé unique pour détecter les doublons (sans la date) $uniqueKey = $route . '|' . $method . '|' . $queryParams . '|' . $controller . '|' . $action . '|' . $module . '|' . $routeParams . '|' . $_SERVER['REMOTE_ADDR'] . '|' . $connectionType; // Vérifier si cette ligne existe déjà if (!$this->isDuplicateLogEntry($logFile, $uniqueKey)) { // Écrire dans le fichier CSV seulement si ce n'est pas un doublon $handle = fopen($logFile, 'a'); if ($handle) { fputcsv($handle, $newLine, ';'); // Utiliser ';' comme séparateur fflush($handle); // Vider le buffer pour s'assurer que les données sont écrites fclose($handle); } } } catch (\Throwable $th) { var_dump("logUnauthorizedAccess ERROR", $th->getMessage()); exit(); } } /** * Vérifie si une entrée de log est un doublon */ private function isDuplicateLogEntry($logFile, $uniqueKey) { if (!file_exists($logFile)) { return false; } $handle = fopen($logFile, 'r'); if (!$handle) { return false; } // Ignorer l'en-tête $header = fgetcsv($handle, 0, ';'); // Utiliser ';' comme séparateur pour la lecture while (($data = fgetcsv($handle, 0, ';')) !== FALSE) { // Utiliser ';' comme séparateur pour la lecture if (count($data) >= 10) { // Créer la clé unique pour cette ligne (sans la date) $existingKey = $data[1] . '|' . $data[2] . '|' . $data[3] . '|' . $data[4] . '|' . $data[5] . '|' . $data[6] . '|' . $data[7] . '|' . $data[8] . '|' . (isset($data[10]) ? $data[10] : ''); if ($existingKey === $uniqueKey) { fclose($handle); return true; // Doublon trouvé } } } fclose($handle); return false; // Pas de doublon } }