Ajoute et Supprime tous les handlers
541756
function addEventListeners() {
			ctrl.ngelt.on('wheel', wheelOnElt);
			ctrl.ngelt.on('computegrabbersizes', ctrl.updateSize);
//			ctrl.elt.addEventListener("wheel", function (event) {
//				boxesScrollServices.execAndApplyIfScrollable($scope, this, wheel, [event]);
//			}, {passive: true, capture: true});
			ctrl.ngsb.on("mouseout", mouseoutOnSb);
			ctrl.ngsb.on("mousedown", mousedownOnSb); // sur le mousedown, si dans le grabber, on init le mode drag, sinon on inc/dec les pages tant que l'on est appuyé
			ctrl.ngsb.on("mouseup", mouseup);  // on stop l'inc/dec des pages
			ctrl.ngsb.on("click", boxesScrollServices.stopEvent); // desactive la propagation entre autrepour eviter la fermeture des popup
			ctrl.ngelt.on("mousemove", mousemoveOnElt); // on définit la couleur du grabber
			if (!ctrl.ngelt.css('display') !== 'none') { // si c'est une popup, le resize de l'ecran ne joue pas
				ng.element($window).on("resize", updateSize);
			}
			$document.on("mousedown", mousedownOnDoc);
			$document.on("keydown", keydownOnOnDoc);
			$document.on("scroll", invalidSizes);
		}
1180121
public function onKernelRequest(GetResponseEvent $event)
    {
        /*
            if (HttpKernel::MASTER_REQUEST != $event->getRequestType()) {
                // ne rien faire si ce n'est pas la requête principale
                return;
            }
        */

        if (
            $this->container->get('claroline.manager.ip_white_list_manager')->isWhiteListed()
        ) {
            if (!$this->storage->getToken()) {
                $this->replaceToken();
            } elseif ($this->storage->getToken()->getUser() === 'anon.') {
                $this->replaceToken();
            }
        }
    }
268321
def signals(self, signals=('QUIT', 'USR1', 'USR2')):
        ''''''
        for sig in signals:
            signal.signal(getattr(signal, 'SIG' + sig), self.handler)
879056
public function process(ServerRequestInterface $request, RequestHandlerInterface $handler): ResponseInterface
    {
        /*
        // TODO : ajouter le header "Retry-After" avec une gestion des options, genre durée de la maintenance, et durée avant de faire un refresh !!!!
        // https://github.com/php-middleware/maintenance/blob/master/src/MaintenanceMiddleware.php
                $headers = [];
                if ($this->retryAfter !== '') {
                    $headers['Retry-After'] = $this->retryAfter;
                    if ($this->refresh > 0) { // seconds
                        $headers['Refresh'] = (string) $this->refresh;
                    }
                }


        // TODO : version alternative pour ajouter le header !!!!
        //https://github.com/middlewares/shutdown/blob/master/src/Shutdown.php#L46
                if (is_int($this->retryAfter)) {
                    return $response->withHeader(self::RETRY_AFTER, (string) $this->retryAfter);
                }
                if ($this->retryAfter instanceof DateTimeInterface) {
                    return $response->withHeader(self::RETRY_AFTER, $this->retryAfter->format('D, d M Y H:i:s \G\M\T')); //$datetime->format(DateTime::RFC2822);
                }

        */

        //if ($this->app->isDownForMaintenance() && !in_array($this->request->getClientIp(), ['86.10.190.248', '86.4.7.24']))
//        $config = $this->container->config;
        //if ($config['settings.isDownForMaintenance']) {
        if ($this->isDown === true) {
            //return (new Response(503))->withHeader('Refresh', 10)->write('Be right back !');

            //$retryAfter = $config['settings.maintenanceRetryAfter'];

            /*
                        if (is_int($retryAfter)) {
                            $retryAfter = (string) $retryAfter;
                        }
            */

            throw new ServiceUnavailableHttpException($this->retryAfter);
        }

        /*
        //https://github.com/juliangut/janitor/blob/master/src/Handler/Render.php#L65
                if ($watcher instanceof ScheduledWatcherInterface) {
                    $response = $response
                        ->withHeader('Expires', $watcher->getEnd()->format('D, d M Y H:i:s e'))
                        ->withHeader('Retry-After', $watcher->getEnd()->format('D, d M Y H:i:s e'));
                } else {
                    $response = $response->withHeader('Cache-Control', 'max-age=0')
                        ->withHeader('Cache-Control', 'no-cache, must-revalidate')
                        ->withHeader('Pragma', 'no-cache');
                }
                return $response->withStatus(503)
                    ->withHeader('Content-Type', $contentType)
                    ->withBody($body);
        */

        //https://www.shellhacks.com/redirect-site-maintenance-page-apache-htaccess/
        // Header Set Cache-Control "max-age=0, no-store"

        return $handler->handle($request);
    }
1122163
protected function getInput() {

        @set_time_limit(120);
        @ini_set('max_execution_time', 120);

        // Initialisation.
        $html = array();
        $text = $this->getText();

        // JS
        (new RequireJSUtility())
            ->addDomReadyJS("$('[data-toggle=\"tooltip\"], .hasTooltip').tooltip({container:'body',html:true});", false, "bootstrap");

        if (!empty($this->value)) {
            $value = new Registry($this->value);
        }

        $class = $this->element['class'] ? ' ' . (string)$this->element['class'] : '';

        // On récupère l'instance de gestion ACL.
        $acl    = Acl::getInstance($this->form->getDb());
	    $simple = $acl->getSimpleAcl();

        // On récupère les sections et les actions.
        $actions = $this->getActions();

        // On charge les groupes utilisateurs.
        $groups = $this->getUserGroups();

	    // On charge les rôles.
	    $roles = $acl->getRoles();

        // Building tab nav
        $html[] = '<div role="tabpanel" class="nav-tabs-left">';

        $html[] = '<ul class="nav nav-tabs" role="tablist">';

        foreach ($groups as $i => $group) {
            $tab_class = $i == 0 ? ' class="active"' : '';
            $html[] = '<li role="presentation"' . $tab_class . '><a href="#group-' . $group->id . '" aria-controls="group-' . $group->id . '" role="tab" data-toggle="tab">';
            $html[] = str_repeat('<span class="level">&ndash;</span> ', $curLevel = $group->level) . $group->title;
            $html[] = '</a></li>';
        }

        $html[] = '</ul>';
        $html[] = '<div class="tab-content">';

        foreach ($groups as $i => $group) {

            $tab_class = $i == 0 ? ' active' : '';

            $html[] = '<div role="tabpanel" class="tab-pane' . $tab_class .'" id="group-' . $group->id . '">';

            $html[] = '<table class="rights table table-condensed' . $class . '">';

            $html[] = '<thead>';
            $html[] = '<tr>';
            $html[] = '<th>' . $text->translate('APP_GLOBAL_RIGHTS_HEADING_SECTION') . '</th>';
            $html[] = '<th>' . $text->translate('APP_GLOBAL_RIGHTS_HEADING_ACTION') . '</th>';
            $html[] = '<th>' . $text->translate('APP_GLOBAL_RIGHTS_HEADING_RIGHT') . '</th>';

            if ($group->parent_id) {
                $html[] = '<th id="aclactionth' . $group->id . '">';
                $html[] = '<span class="acl-action">' . $text->translate('APP_GLOBAL_RIGHTS_HEADING_CALCULATED_SETTING') . '</span>';
                $html[] = '</th>';
            }

            $html[] = '</tr>';
            $html[] = '</thead>';

            $html[] = '<tbody>';

            // On parcourt les sections.
            foreach ($actions as $section) {

                $rowspan = count($section->actions);

                foreach ($section->actions as $i => $action) {

                    $html[] = '<tr>';

                    if ($i == 0) {
                        $html[] = '<td class="section" rowspan="' . $rowspan . '"><span class="hasTooltip" title="' . $text->translate($section->description) . '">' . $text->translate($section->title) . '</td>';
                    }

                    $html[] = '<td class="action"><span class="hasTooltip" title="' . $text->translate($action->description) . '">' . $text->translate($action->title) . '</td>';
                    $html[] = '<td class="right">';

                    $html[] = '<select class="form-control input-sm"'
                        . ' name="' . $this->name . '[' . $section->name . '][' . $action->name . '][' . $group->id . ']"'
                        . ' id="' . $this->id . '_' . $section->name . '_' . $action->name	. '_' . $group->id . '"'
                        . ' title="' . $text->sprintf('APP_GLOBAL_RIGHTS_SELECT_ALLOW_DENY_GROUP', $text->translate($action->title), trim($group->title)) . '">';

                    // On récupère les droits pour l'action hérités pour le groupe.
                    $inheritedRule = $acl->checkGroup($group->id, $section->name, $action->name);

                    // On récupère les droits pour l'action NON HÉRITÉS pour le groupe.
                    $assetRule = null;

	                $groups = new RoleAggregate();
	                $groups->addRole($roles[$group->id]);
                    $res = $simple->isAllowedReturnResult($groups, $section->name, $action->name)->collection;

                    if ($res->count() > 0) {
                        $res->top();
                        while($res->valid()) {
                            $priority = $res->current()->getPriority();

                            // La règle est appliqué à ce groupe en particulier si la priorité est à zero.
                            if ($priority == 0) {
                                $assetRule = $res->current()->getAction();
                            }

                            $res->next();
                        }
                    }

                    // Build the dropdowns for the permissions sliders

                    // The parent group has "Not Set", all children can rightly "Inherit" from that.
                    $html[] = '<option value=""' . ($assetRule === null ? ' selected="selected"' : '') . '>'
                        . $text->translate(empty($group->parent_id) ? 'APP_GLOBAL_RIGHTS_NOT_SET' : 'APP_GLOBAL_RIGHTS_INHERITED') . '</option>';
                    $html[] = '<option value="1"' . ($assetRule === true ? ' selected="selected"' : '') . '>' . $text->translate('APP_GLOBAL_RIGHTS_ALLOWED')
                        . '</option>';
                    $html[] = '<option value="0"' . ($assetRule === false ? ' selected="selected"' : '') . '>' . $text->translate('APP_GLOBAL_RIGHTS_DENIED')
                        . '</option>';

                    $html[] = '</select>&#160; ';

                    // If this asset's rule is allowed, but the inherited rule is deny, we have a conflict.
                    if (($assetRule === true) && ($inheritedRule === false)) {
                        $html[] = $text->translate('APP_GLOBAL_RIGHTS_CONFLICT');
                    }

                    $html[] = '</td>';

                    // Build the Calculated Settings column.
                    // The inherited settings column is not displayed for the root group in global configuration.
                    if ($group->parent_id) {

                        $html[] = '<td headers="aclactionth' . $group->id . '">';

                        // This is where we show the current effective settings considering currrent group, path and cascade.
                        // Check whether this is a component or global. Change the text slightly.

                        if ($acl->checkGroup($group->id, "app", "admin") !== true) {

                            if ($inheritedRule === true) {
                                $html[] = '<span class="label label-success">' . $text->translate('APP_GLOBAL_RIGHTS_ALLOWED') . '</span>';
                            } elseif ($inheritedRule === false) {
                                $html[] = '<span class="label label-danger">' . $text->translate('APP_GLOBAL_RIGHTS_NOT_ALLOWED') . '</span>';
                            }

                        } elseif ($section->name != 'app') {
                                $html[] = '<span class="label label-success"><i class="fa fa-lock"></i> ' . $text->translate('APP_GLOBAL_RIGHTS_ALLOWED_ADMIN')
                                    . '</span>';
                        } else {

                            // Special handling for  groups that have global admin because they can't  be denied.
                            // The admin rights can be changed.

                            if ($section->name === 'app' && $action->name === 'admin') {
                                $html[] = '<span class="label label-success">' . $text->translate('APP_GLOBAL_RIGHTS_ALLOWED') . '</span>';
                            } elseif ($inheritedRule === false) {
                                // Other actions cannot be changed.
                                $html[] = '<span class="label label-danger"><i class="fa fa-lock"></i> '
                                    . $text->translate('APP_GLOBAL_RIGHTS_NOT_ALLOWED_ADMIN_CONFLICT') . '</span>';
                            } else {
                                $html[] = '<span class="label label-success"><i class="fa fa-lock"></i> ' . $text->translate('APP_GLOBAL_RIGHTS_ALLOWED_ADMIN')
                                    . '</span>';
                            }
                        }

                        $html[] = '</td>';
                    }

                    $html[] = '</tr>';

                }

            }


            $html[] = '';
            $html[] = '';
            $html[] = '';
            $html[] = '</tbody>';

            $html[] = '</table>';

            $html[] = '</div>';

        }

        $html[] = '</div>';
        $html[] = '</div>';

        return implode($html);

    }
637360
protected function initialise() {

        // On définit le fuseau horaire.
        @date_default_timezone_set($this->get('timezone', 'Europe/Paris'));

        // On instancie le logger.
        $logger = new Logger($this->get('application_name'));
        $logger->pushHandler(new StreamHandler(JPATH_LOGS . "/" . $this->get('application_logfile'), $this->get('logger_level')));
        $this->setLogger($logger);

        // PID
        $this->set('application_pid_file', JPATH_TMP . "/" . $this->get('application_pid_file'));

    }
718789
private void executeHandlers(List<Event> filteredEvents) {
        for (EventHandler current : eventHandlers) {
            for (Event event : filteredEvents) {
                current.handleEvent(event);
            }
        }
    }
1364300
def u2handlers(self):
        
        handlers = []
        handlers.append(u2.ProxyHandler(self.proxy))
        return handlers
502308
def ajContractions(self):
        
        for lin in lignesFichier(self.path("contractions.la")):
            ass1, ass2 = tuple(lin.split(':'))
            self.lemmatiseur._contractions[ass1] = ass2
396462
def handlers(self):
        """"""
        if getattr(self, '_http'):
            yield from self.http.handlers()
        if getattr(self, '_cli'):
            yield from self.cli.handlers()
1356909
public function ajouter()
    {
        $newIdPersonne=0;
        $formulaire = new formGenerator();
        if (isset($this->variablesPost['submit'])) {
            $modeAffichage='';
            if (isset($this->variablesGet['modeAffichage']) && $this->variablesGet['modeAffichage']!='') {
                $modeAffichage = $this->variablesGet['modeAffichage'];
            }


            switch ($modeAffichage) {
                case 'nouveauDossier':
                case "modifEvenement":
                    $tabForm = array(
                    'prenom'    => array('default'=> '',  'value' => '',  'required'=>false, 'error'=>'', 'type'=>'text'),
                    'nom'        => array('default'=> '',  'value' => '',  'required'=>true, 'error'=>'', 'type'=>'text'),
                    'description'    => array('default'=> '',  'value' => '',  'required'=>false, 'error'=>'', 'type'=>'text'),
                    'dateNaissance'    => array('default'=> '',  'value' => '',  'required'=>false, 'error'=>'', 'type'=>'date'),
                    'dateDeces'    => array('default'=> '',  'value' => '',  'required'=>false, 'error'=>'', 'type'=>'date'),
                    'metier'    => array('default'=> 'aucune' ,  'value' => '',  'required'=>false , 'error'=>'', 'type'=>'numeric',  'checkExist'=>
                                    array('table'=> 'metier',  'primaryKey'=> 'idMetier')));

                    break;

                default:
                    $tabForm = array(
                    'prenom'    => array('default'=> '',  'value' => '',  'required'=>false, 'error'=>'', 'type'=>'text'),
                    'nom'        => array('default'=> '',  'value' => '',  'required'=>true, 'error'=>'', 'type'=>'text'),
                    'description'    => array('default'=> '',  'value' => '',  'required'=>false, 'error'=>'', 'type'=>'text'),
                    'nouveauMetier'    => array('default'=> '',  'value' => '',  'required'=>false, 'error'=>'', 'type'=>'text'),
                    'dateNaissance'    => array('default'=> '',  'value' => '',  'required'=>false, 'error'=>'', 'type'=>'date'),
                    'dateDeces'    => array('default'=> '',  'value' => '',  'required'=>false, 'error'=>'', 'type'=>'date'),
                    'metier'    => array('default'=> 'aucune' ,  'value' => '',  'required'=>false , 'error'=>'', 'type'=>'numeric',  'checkExist'=>
                                    array('table'=> 'metier',  'primaryKey'=> 'idMetier')));

                    break;
            }
            $erreur = $formulaire->getArrayFromPost($tabForm);

            if (count($erreur) === 0) {
                $prenom = mysql_escape_string($tabForm['prenom']['value']);
                $nom    = mysql_escape_string($tabForm['nom']['value']);
                $description   = isset($_POST['descriptionPerson'])?mysql_escape_string($_POST['descriptionPerson']):mysql_escape_string(htmlspecialchars($tabForm['description']['value']));
                $dateNaissance = $this->date->toBdd($this->date->convertYears($tabForm['dateNaissance']['value']));
                $dateDeces     = $this->date->toBdd($this->date->convertYears($tabForm['dateDeces']['value']));

                /*if (!empty($tabForm['nouveauMetier']['value']))
                {
                    // nouveau metier
                    $nomMetier = mysql_escape_string($tabForm['nouveauMetier']['value']);
                    $sql = "SELECT idMetier FROM metier WHERE nom='".$nomMetier."' LIMIT 1";
                    $rep = $this->connexionBdd->requete($sql);
                    if (mysql_num_rows($rep) === 1)
                    {
                        $res = mysql_fetch_object($rep);
                        $idMetier = $res->idMetier;
                        echo "métier existe";
                    }
                    else
                    {
                        $sql = "INSERT INTO metier (nom) VALUES ('".$nomMetier."')";
                        $this->connexionBdd->requete($sql);
                        $idMetier = mysql_insert_id();
                        echo 'métier existe pas';
                    }
                }
                else if (empty($tabForm['metier']['error']) AND !empty($tabForm['metier']['value']))
                {*/
                    // valeur du select
                    $idMetier      = $tabForm['metier']['value'];
                    //echo 'métier select';
                /*}
                else
                {
                    // choix par défaut
                    $idMetier = 1;
                    echo 'défaut';
                }*/
                $sql ="INSERT INTO personne (prenom,  nom,  dateNaissance,  dateDeces,  description,  idMetier ) VALUES
                    ('".$prenom."', '".$nom."', '".$dateNaissance."', '".$dateDeces."', '".$description."', ".$idMetier.")";


                $this->connexionBdd->requete($sql);

                $newIdPersonne = mysql_insert_id();
            } else {
                $this->erreurs->ajouter($tabForm);
            }
            $this->erreurs->ajouter($tabForm);
        }

        return $newIdPersonne;
    }
845685
protected function load() {

        // On initialise les variables
        $roles     = $this->getRoles();
        $resources = $this->getResources();
        $sections  = $this->getActions();
        $rules     = $this->getRules();

        // On parcourt les actions par section.
        foreach ($sections as $section) {

            // Si la section a des actions.
            if (!empty($section->actions)) {

                // On récupère la ressource.
                $resource = $resources[$section->name];

                // On crée une règle pour chaque action.
                foreach ($section->actions as $action) {

                    // On récupère les autorisations des rôles pour cette action.
                    if (isset($rules[$section->name]) && isset($rules[$section->name]->rules->{$action->name})) {
                        $ruleValues = $rules[$section->name]->rules->{$action->name};

                        // Et pour chaque rôle.
                        foreach ($roles as $role) {

                            // 3 valeurs possibles :
                            //   1    => le groupe est présent et autorisé
                            //   0    => le groupe est présent et non autorisé
                            //   null => le groupe n'est pas présent et donc hérite des droits du parent.
                            // Le groupe est présent, on crée une règle ACL pour le tri action-rôle-ressource.

                            if (is_object($ruleValues) && property_exists($ruleValues, $role->getName())) {

                                $rule = new Rule($action->name);
                                $rule->setRole($role);
                                $rule->setResource($resource);
                                $rule->setAction((bool) $ruleValues->{$role->getName()});

                                // On ajoute la règle au gestionnaire.
                                $this->acl->addRule($rule);

                            }

                        }
                    }

                }

            }

        }

    }
739496
function pparse($handle)
    {
        if (!$this->loadfile($handle)) {
            die("Template->pparse(): Impossible de charger le fichier template pour le modèle $handle");
        }

        // actually compile the template now.
        if (!isset($this->compiled_code[$handle]) || empty($this->compiled_code[$handle])) {
            // Actually compile the code now.
            $this->compiled_code[$handle] = $this->compile($this->uncompiled_code[$handle]);
        }
        // Run the compiled code.
        eval($this->compiled_code[$handle]);
        //return true;
    }
646064
protected function getActions() {

        if (empty($this->actions)) {

            // On charge les droits depuis le XML.
            $data = simplexml_load_file(JPATH_ROOT . "/rights.xml");

            // On contrôle que les données sont bien chargées.
            if ((!($data instanceof \SimpleXMLElement)) && (!is_string($data))) {
                throw new \RuntimeException($this->text->translate('APP_ERROR_RIGHTS_NOT_LOADED'));
            }

            // On initialise les actions.
            $result = array();

            // On récupère les sections.
            $sections = $data->xpath("/rights/section");

            if (!empty($sections)) {

                foreach ($sections as $section) {

                    $tmp          = new \stdClass();
                    $tmp->name    = (string)$section['name'];
                    $tmp->actions = array();

                    $actions = $section->xpath("action[@name]");

                    if (!empty($actions)) {

                        foreach ($actions as $action) {
                            $tmp2       = new \stdClass();
                            $tmp2->name = (string)$action['name'];
                            $tmp->actions[] = $tmp2;
                        }

                        $result[] = $tmp;
                    }

                }

            }

            $this->actions = $result;

        }

        return $this->actions;

    }
524049
def bind(self, handler, argspec):
        
        self.handlers[argspec.key].append((handler, argspec))
1222699
function BoxScrollCtrl($window, $document, $interval, $timeout, $scope, boxesScrollServices) {
		var ctrl = this;
		ctrl.reItems;
		ctrl.ngelt; // le composant lui meme
		ctrl.elt; // le composant lui meme
		ctrl.infos = null;

		ctrl.removeEventListeners = removeEventListeners; // gestion des events
		ctrl.addEventListeners = addEventListeners; // gestion des events
		ctrl.updateInfos = updateInfos; // met a jours les infos 
		ctrl.updateTotal = updateTotal;
		ctrl.updateLimit = updateLimit;
		ctrl.updateBegin = updateBegin;
		ctrl.updateSize = updateSize;
		ctrl.getInnerLimit = getInnerLimit;
		ctrl.getEltArea = getEltArea;
		ctrl.getScrollbarArea = getScrollbarArea;

		/**
		 * Retourne la limit pour les calcul interne, cad le nombre d'items vraiment visible
		 * @returns {Number|type.ngLimit|boxesscrollL#1.BoxScrollCtrl.$scope.ngLimit}
		 */
		function getInnerLimit() {
			var items = getItems();
			var notInDeck = 0;
			if (items.length) {
				do {
					notInDeck = notInDeck + 1;
					var cont = false;
					var item = items[items.length - notInDeck];
					if (item) {
						var area = getArea(item);
						if (ctrl.horizontal) {
							cont = area.right > getEltArea().right;
						} else {
							cont = area.bottom > getEltArea().bottom;
						}
						if (!cont) {
							notInDeck--;
						}
					}
				} while (cont);
			} else {
				notInDeck = 1;
			}
			var fix = ($scope.ngLimit - items.length) + notInDeck;
			return $scope.max ? $scope.ngLimit : $scope.ngLimit - fix;
		}
		var hasFocus = false;
		/**
		 * Ajoute et Supprime tous les handlers
		 */
		function addEventListeners() {
			ctrl.ngelt.on('wheel', wheelOnElt);
			ctrl.ngelt.on('computegrabbersizes', ctrl.updateSize);
//			ctrl.elt.addEventListener("wheel", function (event) {
//				boxesScrollServices.execAndApplyIfScrollable($scope, this, wheel, [event]);
//			}, {passive: true, capture: true});
			ctrl.ngsb.on("mouseout", mouseoutOnSb);
			ctrl.ngsb.on("mousedown", mousedownOnSb); // sur le mousedown, si dans le grabber, on init le mode drag, sinon on inc/dec les pages tant que l'on est appuyé
			ctrl.ngsb.on("mouseup", mouseup);  // on stop l'inc/dec des pages
			ctrl.ngsb.on("click", boxesScrollServices.stopEvent); // desactive la propagation entre autrepour eviter la fermeture des popup
			ctrl.ngelt.on("mousemove", mousemoveOnElt); // on définit la couleur du grabber
			if (!ctrl.ngelt.css('display') !== 'none') { // si c'est une popup, le resize de l'ecran ne joue pas
				ng.element($window).on("resize", updateSize);
			}
			$document.on("mousedown", mousedownOnDoc);
			$document.on("keydown", keydownOnOnDoc);
			$document.on("scroll", invalidSizes);
		}
		function removeEventListeners() {
			ctrl.ngelt.off('wheel', wheelOnElt);
			ctrl.ngelt.off('computegrabbersizes', ctrl.updateSize);
			ctrl.ngsb.off("mouseout", mouseoutOnSb);
			ctrl.ngsb.off("mousedown", mousedownOnSb);
			ctrl.ngsb.off("mouseup", mouseup);
			ctrl.ngsb.off("click", boxesScrollServices.stopEvent);
			ctrl.ngelt.off("mousemove", mousemoveOnElt);
			ng.element($window).off("resize", updateSize);
			$document.off("mousedown", mousedownOnDoc);
			$document.off("keydown", keydownOnOnDoc);
			$document.off("scroll", invalidSizes);
		}
		function invalidSizes(event) {
			ctrl.getScrollbarArea().invalid = true;
			ctrl.getEltArea().invalid = true;
		}
		function keydownOnOnDoc(event) {
			if (!$scope.allowKeynav || !hasFocus || event.which < 33 || event.which > 40)
				return;
			boxesScrollServices.execAndApplyIfScrollable($scope, this, keydown, [event]);
		};
		function mousedownOnDoc(event) {
			hasFocus = ctrl.elt.contains(event.target);
		}
		function mousemoveOnElt(event) {
			boxesScrollServices.execAndApplyIfScrollable($scope, this, mousemove, [event]);
		}
		function mousedownOnSb(event) {
			hasFocus = true;
			boxesScrollServices.execAndApplyIfScrollable($scope, this, mousedown, [event]);
		}
		function mouseoutOnSb(event) {
			if (!isDragMode()) {
				hideScrollbar(SHOWSB_TIMEOUT);
			}
		}
		function wheelOnElt(event) {
			boxesScrollServices.execAndApplyIfScrollable($scope, this, wheel, [event]);
		}
		/**
		 * begin, limit ou total on changés
		 */
		var infosTimer;
		function updateInfos() {
			if (infosTimer) {
				$timeout.cancel(infosTimer);
			}
			ctrl.infos = null;
			if (!isNaN($scope.ngBegin) && !isNaN($scope.ngLimit) && !isNaN($scope.total) && $scope.total > 1) {
				var from = $scope.total ? $scope.ngBegin + 1 : 0;
				var to = $scope.ngBegin + boxesScrollServices.minXmax(0, ctrl.getInnerLimit(), $scope.total);
				ctrl.infos = "[" + from + "-" + to + "]/" + $scope.total;
				infosTimer = $timeout(function (c) {
					c.infos = null;
				}, $scope.showInfoDelay || 1000, true, ctrl);
			}
		}
		/**
		 * Le nombre d'items a changé
		 * On repositionne le grabber en 0
		 * Si pas d'items, grabber = 100%
		 * Sinon on set limit a 1, ce qui va lancer le processus updateLimit->adjustLimit
		 */
		function updateTotal() {
			$scope.ngBegin = 0;
			moveGrabber(getGrabberOffsetPercentFromBegin($scope.ngBegin));
			adjustLimit();
			updateGrabberSizes();
			updateInfos();
		}
		/**
		 * La limit a ete mis a jour
		 */
		function updateLimit() {
			moveGrabber(getGrabberOffsetPercentFromBegin($scope.ngBegin));
			adjustLimit();
			updateGrabberSizes();
			updateInfos();
		}
		/**
		 * begin a ete mis a jour
		 */
		function updateBegin() {
			moveGrabber(getGrabberOffsetPercentFromBegin($scope.ngBegin));
			adjustLimit();
//			updateGrabberSizes();
			updateInfos();
		}
		/**
		 * La fenetre a ete redimentionn�
		 */
		var resizeTimer = null;
		function updateSize() {
			if (resizeTimer) {
				$timeout.cancel(resizeTimer);
			}
			if ($scope.ngLimit > 2) {
				resizeTimer = $timeout(function (s) {
					adjustLimit();
					updateGrabberSizes();
				}, 200, true, $scope);
			} else {
				adjustLimit();
				updateGrabberSizes();
			}
		}
		/**
		 * Gere les differents rendus de la scrollbar.
		 * Si on passe au dessus du trigger
		 * Mousemove(!drag) and mouseup
		 * @param {type} event
		 * @returns {undefined}
		 */
		function manageScrollbarRender(event) {
			if (modeTimer) {
				$timeout.cancel(modeTimer);
			}
			var m = boxesScrollServices.getMousePosition(event);
			if (isTriggerOver(m)) { // la souris est au dessus du declencheur
				showScrollbar();
			}
			if (isScrollbarVisible()) {
				if (isScrollbarOver(m)) { // la souris est au dessus de la scrollbar
					showScrollbar();
					if (compareGrabberAndMousePosition(m) === 0) { // la souris est au dessus du curseur
						showScrollbar('hover');
					}
				} else {
					hideScrollbar(SHOWSB_TIMEOUT);
				}
			}
		}
		/**
		 * Gere la navigation clavier
		 * @param {type} event
		 */
		function keydown(event) {
			var inc = 0;
			if (ctrl.horizontal) {
				if (event.which === 37) { // LEFT
					inc = -1;
				} else if (event.which === 39) { // RIGHT
					inc = 1;
				}
			} else {
				var innerLimit = ctrl.getInnerLimit();
				if (event.which === 38) { // UP
					inc = -1;
				} else if (event.which === 40) { // DOWN
					inc = 1;
				} else if (event.which === 33) { // PAGEUP
					inc = -innerLimit;
				} else if (event.which === 34) { // PAGEDOWN
					inc = innerLimit;
				} else if (event.which === 35) { // END
					inc = $scope.total - $scope.ngBegin - innerLimit;
				} else if (event.which === 36) { // HOME
					inc = -$scope.ngBegin;
				}
			}
			if (inc !== 0) {
				boxesScrollServices.stopEvent(event);
				$scope.ngBegin = $scope.ngBegin + inc;
			}
		}
		/**
		 * la souris bouge au dessus de la scrollbar
		 * @param {jqEvent} event
		 */
		function mousemove(event) {
			if (!isDragMode()) {
				manageScrollbarRender(event);
			}
		}
		var downData = {timer: null, scope: null, inc: 0, end: 0};
		var offsetMouse;
		function mousedown(event) {
			var m = boxesScrollServices.getMousePosition(event);
			boxesScrollServices.stopEvent(event);
			var pos = compareGrabberAndMousePosition(m);
			if (!isNaN(pos)) { // dans la scrollbar
				if (pos === 0) { // on a click sur le curseur passage en mode drag
					offsetMouse = getOffsetMouseFromGrabber(m);
					showScrollbar('drag');
					document.addEventListener('mousemove', dragHandler, false);
					document.addEventListener("mouseup", endDrag, false);
				} else {
					var innerLimit = ctrl.getInnerLimit();
					$scope.ngBegin = $scope.ngBegin + (innerLimit * pos); // next or previous page
					downData.scope = $scope;
					downData.inc = pos; // vaut 1 ou -1
					downData.end = getBeginFromPercent(getGrabberOffsetPercentFromMousePosition(m, 0));
					if (pos < 0) {
						downData.end -= innerLimit;
					}
					downData.timer = $interval(function (data) {
						var next = data.scope.ngBegin + (innerLimit * data.inc); // next or previous page;
						if (next * data.inc > data.end * data.inc) {
							$interval.cancel(data.timer);
							return;
						}
						data.scope.ngBegin = next;
					}, 300, 0, true, downData);
				}
			}
		}
		function mouseup(event) {
			if (downData.timer) {
				$interval.cancel(downData.timer);
			}
		}
		function endDrag(event) {
			offsetMouse = 0;
			document.removeEventListener('mousemove', dragHandler);
			document.removeEventListener('mouseup', endDrag);
			boxesScrollServices.execAndApplyIfScrollable($scope, this, manageScrollbarRender, [event]); // 
		}
		function dragHandler(event) {
			boxesScrollServices.stopEvent(event);
			var m = boxesScrollServices.getMousePosition(event);
			var percent = getGrabberOffsetPercentFromMousePosition(m, offsetMouse);
			var begin = getBeginFromPercent(percent);
			if (begin <= $scope.total - ctrl.getInnerLimit()) {
				$scope.ngBegin = begin;
			}
		}
		var wheelData = {timer: null, begin: null};
		function wheel(event) {
			boxesScrollServices.stopEvent(event);
			hideScrollbar();
			wheelData.begin = manageWheelHandler(event, wheelData.begin || $scope.ngBegin);
//			moveGrabber(getGrabberOffsetPercentFromBegin(wheelData.begin));
//			if (!wheelData.timer) {
//				$scope.ngBegin = wheelData.begin;
//				wheelData.timer = $timeout(function (scope, data) {
//					scope.ngBegin = data.begin;
//					data.timer = null;
//					data.begin = null;
//				}, 60, true, $scope, wheelData);
//			}
			$scope.ngBegin = wheelData.begin;
			wheelData.begin = null;
		}
		function manageWheelHandler(event, begin) {
			var evt = event.originalEvent || event;
			return boxesScrollServices.minXmax(0, begin + ((evt.deltaY < 0) ? -SCROLLBY : SCROLLBY), $scope.total - ctrl.getInnerLimit());
		}
		function getGrabberOffsetPercentFromBegin(begin) {
			return begin * 100 / $scope.total;
		}
		function getGrabberOffsetPercentFromMousePosition(m, offset) {
			var grabberOffsetPercent;
			var rect = getTriggerArea();
			var grabberOffsetPixel;
			var onePercent;
			if (ctrl.horizontal) {
				onePercent = rect.width / 100;
				grabberOffsetPixel = m.x - rect.left - offset;
			} else {
				onePercent = rect.height / 100;
				grabberOffsetPixel = m.y - rect.top - offset;
			}
			grabberOffsetPercent = grabberOffsetPixel / onePercent;
			return boxesScrollServices.minXmax(0, grabberOffsetPercent, 100 - getGrabberSizePercentFromScopeValues());
		}
		/**
		 * Est on en mode drag&drop
		 */
		function isDragMode() {
			return ctrl.ngsb.attr('mode') === 'drag';
		}
		function isScrollbarVisible() {
			return ctrl.ngsb.attr('mode') !== 'hidden';
		}
		function showScrollbar(mode) {
			ctrl.ngsb.attr('mode', mode || null);
		}
		var modeTimer;
		function hideScrollbar(defer) {
			if (isScrollbarVisible()) {
				if (modeTimer) {
					$timeout.cancel(modeTimer);
				}
				if (defer) {
					ctrl.ngsb.attr('mode', null);
					modeTimer = $timeout(function () {
						ctrl.ngsb.attr('mode', 'hidden');
					}, defer);
				} else {
					ctrl.ngsb.attr('mode', 'hidden');
				}
			}
		}
		/**
		 * La souris est elle au dessus de la scrollbar
		 * @param {MouseCoordonates} m
		 * @returns {Boolean}
		 */
		function isScrollbarOver(m) {
			return document.elementFromPoint(m.x, m.y) === ctrl.sb;
		}
		/**
		 * 
		 * @param {MouseCoordonates} m
		 * @returns {Boolean}
		 */
		function isTriggerOver(m) {
			var result = false;
			if (document.elementFromPoint(m.x, m.y) === ctrl.elt) {
				if (ctrl.horizontal) {
					result = m.y >= getTriggerArea().top; // on est au dessus de la scrollbar trigger
				} else {
					result = m.x >= getTriggerArea().left; // on est au dessus de la scrollbar trigger
				}
			}
			return result;
		}
		/**
		 * La souris est elle avant le grabber (-1), apres le grabber (1) sur le grabber (0), pas au dessus NaN
		 * @param {type} m
		 * @returns {Number}
		 */
		function compareGrabberAndMousePosition(m) {
			if (isScrollbarOver(m)) {
				if (ctrl.horizontal) {
					var start = getScrollbarArea().left + getGrabberOffsetPixelFromPercent(getGrabberOffsetPercentFromBegin($scope.ngBegin));
					if (m.x < start)
						return -1;
					var end = start + getGrabberSizePixelFromPercent(getGrabberSizePercentFromScopeValues());
					if (m.x > end)
						return 1;
					if (m.x >= start && m.x <= end)
						return 0;
				} else {
					var start = getScrollbarArea().top + getGrabberOffsetPixelFromPercent(getGrabberOffsetPercentFromBegin($scope.ngBegin));
					if (m.y < start)
						return -1;
					var end = start + getGrabberSizePixelFromPercent(getGrabberSizePercentFromScopeValues());
					if (m.y > end)
						return 1;
					if (m.y >= start && m.y <= end)
						return 0;
				}
			}
			return Number.NaN;
		}
		function getOffsetMouseFromGrabber(m) {
			var result = 0;
			if (ctrl.horizontal) {
				var start = getTriggerArea().left + getGrabberOffsetPixelFromPercent(getGrabberOffsetPercentFromBegin($scope.ngBegin));
				result = m.x - start;
			} else {
				var start = getTriggerArea().top + getGrabberOffsetPixelFromPercent(getGrabberOffsetPercentFromBegin($scope.ngBegin));
				result = m.y - start;
			}
			return result;
		}
		function adjustLimit() {
			var items = getItems(); // il y en a au moins un
			computeDirectionIfNeeded(items);
			if ($scope.max) {
				$scope.ngLimit = $scope.max;
			} else if ($scope.total) {
				var nbItems = items.length;
				if (nbItems) {
					var firstItem = items[0];
					var lastItem = items[nbItems - 1];
					var containerSize = ctrl.horizontal ?
							  getArea(lastItem).right - getArea(firstItem).left :
							  getArea(lastItem).bottom - getArea(firstItem).top;
					var offset = getOffsetPixelContainerBeforeItem(firstItem); // on ignore les éléments avant
					var empty = getHeightArea() - offset - containerSize; // zone non remplie
					var inc = 0;
					var average = containerSize / nbItems;
					if (average) { // protect div par 0
						var floatValue = empty / average;
						inc = floatValue < 0 ? Math.ceil(floatValue) : Math.ceil(floatValue); // on veut en voir une de plus
						if (inc === floatValue) { // on tombe pile poil, on rajoute un, pour tjs avoir un de plus
							inc++;
						}
					}
					var max = $scope.total - $scope.ngBegin;
					if (inc !== -1) { // si un depasse on laisse
						var newLimit = boxesScrollServices.minXmax(1, $scope.ngLimit + inc, max + 1);
						if (newLimit !== $scope.ngLimit) {
							$scope.ngLimit = newLimit;
						}
					}
				}
			}
		}
		function computeDirectionIfNeeded(items) {
			if (ctrl.ngelt.is('box-scroll') || ctrl.ngelt.attr('box-scroll') !== undefined) {
				if (!ctrl.ngelt.hasClass('vertical') && !ctrl.ngelt.hasClass('horizontal') && items.length) {
					var inlineDisplays = ['table-cell'];
					var display = ng.element(items[0]).css('display');
					ctrl.ngelt.removeClass('horizontal');
					ctrl.ngelt.removeClass('vertical');
					var inlineElt = display.indexOf('inline') !== -1;
					if (inlineElt || inlineDisplays.indexOf(display) !== -1) {
						if (inlineElt) {
							ctrl.ngelt.css('display', 'flex');
						}
						ctrl.ngelt.addClass('horizontal');
						ctrl.horizontal = true;
					} else {
						ctrl.ngelt.addClass('vertical');
						ctrl.horizontal = false;
					}
				}
			}
		}
		function getItems() {
			var items = ctrl.ngelt.find("[ng-repeat]");
			var result = [];
			items.each(function (idx, item) {
				var ngRepeat = ng.element(item).attr('ng-repeat');
				if (ngRepeat.match(ctrl.reItems)) {
					result.push(item);
				}
			});
			return result;
		}
		/**
		 * Calcul la taille des grabbers 
		 */
		function updateGrabberSizes() {
			if (ctrl.horizontal !== undefined) {
				var bgSizeElt = ctrl.ngelt.css('background-size');
				var bgSizeSb = ctrl.ngsb.css('background-size');

				var grabbersizePixel = '100%';
				if(getInnerLimit() !== $scope.total) {
					grabbersizePixel = getGrabberSizePixelFromPercent(getGrabberSizePercentFromScopeValues())+'px';
				}

				if (ctrl.horizontal) {
					bgSizeElt = bgSizeElt.replace(/.*\s+/, grabbersizePixel + ' ');
					bgSizeSb = bgSizeSb.replace(/.*\s+/, grabbersizePixel + ' ');
				} else {
					bgSizeElt = bgSizeElt.replace(/px\s+\d+(\.\d+)*.*/, 'px ' + grabbersizePixel);
					bgSizeSb = bgSizeSb.replace(/px\s+\d+(\.\d+)*.*/, 'px ' + grabbersizePixel);
				}
				ctrl.ngelt.css({'background-size': bgSizeElt});
				ctrl.ngsb.css({'background-size': bgSizeSb});
			}
		}
		/**
		 * Corrige et déplace le curseur
		 * @param {number} percent
		 */
		function moveGrabber(percent) {
			var offset = 0;
			if (percent && $scope.total) {
				var grabberSizePercent = getGrabberSizePercentFromScopeValues();
				var grabberOffsetPercent = boxesScrollServices.minXmax(0, percent, 100 - grabberSizePercent);
				offset = getGrabberOffsetPixelFromPercent(grabberOffsetPercent);
				var grabberSize = getGrabberSizePixelFromPercent(grabberSizePercent);
				if (offset >= getHeightArea() - grabberSize) {
					offset = getHeightArea() - grabberSize;
				}
			}
			if (ctrl.horizontal) {
				ctrl.ngelt.css({'background-position': offset + 'px bottom'});
				ctrl.ngsb.css({'background-position': offset + 'px bottom'});
			} else {
				ctrl.ngelt.css({'background-position': 'right ' + offset + 'px'});
				ctrl.ngsb.css({'background-position': 'right ' + offset + 'px'});
			}
		}
		/**
		 * Calcul ngBegin à partir de la position du curseur
		 * @param {number} percent : la position en % du curseur, son offset
		 */
		function getBeginFromPercent(percent) {
			return Math.round(percent * $scope.total / 100);
		}
		/**
		 * Calcul la position du curseur en px
		 * @param {type} percentOffset
		 * @returns {Number}
		 */
		function getGrabberOffsetPixelFromPercent(percentOffset) {
			var sbLenght = getHeightArea(); // Longueur de la scrollbar
			var grabberOffsetPixel = sbLenght * percentOffset / 100;
			return Math.max(grabberOffsetPixel, 0);
		}
		/**
		 * Retourne la taille en pourcent du grabber en fonction de ngLimit et total
		 * @returns {Number}
		 */
		function getGrabberSizePercentFromScopeValues() {
			if ($scope.total) {
				return Math.min((($scope.max || ctrl.getInnerLimit()) / $scope.total) * 100, 100);
			}
			return 100;
		}
		/**
		 * Calcul la hauteur du grabber
		 * @param {type} percentSize
		 * @returns {Number}
		 */
		function getGrabberSizePixelFromPercent(percentSize) {
			return Math.max(getHeightArea() * percentSize / 100, GRABBERMIN);
		}
		/**
		 * Retourne l'offset en pixel avant l'item
		 * Typiquement la taille du header dans un tableau 
		 * @param {HtmlElement} item
		 * @returns {number}
		 */
		function getOffsetPixelContainerBeforeItem(item) {
			if (ctrl.horizontal) {
				return getArea(item).left - getEltArea().left;
			} else {
				return getArea(item).top - getEltArea().top;
			}
		}
		/**
		 * Retourne la hauteur utile 
		 * @returns {number}
		 */
		function getHeightArea() {
			return ctrl.horizontal ? getEltArea().width : getEltArea().height;
		}
		/**
		 * Retourne la zone correspondante à l'indicateur de position de la scrollbar, permet aussi de faire apparaitre la scrollbar au survol
		 * @return {Rectangle}
		 */
		var triggerArea = getNullArea();
		function getTriggerArea() {
			if (triggerArea.invalid) {
				var clientRect = ctrl.elt.getClientRects();
				if (clientRect && clientRect.length) {
					var rect = clientRect[0];
					if (rect) {
						// zone de la scrollbar
						var bgSize = ctrl.ngelt.css('background-size');
						if (ctrl.horizontal) {
							var m = bgSize.match(/\D*\d+\D*(\d+)\D*/);
							var s = m.length > 0 ? parseInt(m[1]) : 4;
							triggerArea = {
								left: rect.left, right: rect.right,
								width: rect.width, height: s,
								top: rect.bottom - s, bottom: rect.bottom
							};
						} else {
							var m = bgSize.match(/\D*(\d+)\D*\d+\D*/);
							var s = m.length > 0 ? parseInt(m[1]) : 4;
							triggerArea = {
								left: rect.right - s, right: rect.right,
								width: s, height: rect.height,
								top: rect.top, bottom: rect.bottom
							};
						}
					}
				}
			}
			return triggerArea;
		}
		/**
		 * Retourne la zone correspondante à la scrollbar
		 * @return {Rectangle}
		 */
		var sbArea = getNullArea();
		function getScrollbarArea() {
			if (sbArea.invalid) {
				sbArea = getArea(ctrl.sb, true);
			}
			return sbArea;
		}
		/**
		 * Retourne la zone correspondante à la directive
		 * @return {Rectangle}
		 */
		var eltArea = getNullArea();
		function getEltArea() {
			if (eltArea.invalid) {
				eltArea = getArea(ctrl.elt, true);
			}
			return eltArea;
		}
		/**
		 * Retourne la zone correspondante à l'element html en argument
		 * @param {HTMLElement} elt
		 * @param {boolean} validation
		 * @return {Rectangle}
		 */
		function getArea(elt, validation) {
			var clientRect = elt.getClientRects();
			if (clientRect && clientRect.length) {
				var rect = clientRect[0];
				if (rect) {
					rect.invalid = validation && !isElementInViewport(rect);
					return rect;
				}
			}
			return getNullArea();
		}
		function isElementInViewport(rect) {
			if (ctrl.horizontal) {
				return rect.left >= 0 && rect.right <= (window.innerWidth || document.documentElement.clientWidth);
			} else {
				return rect.top >= 0 && rect.bottom <= (window.innerHeight || document.documentElement.clientHeight);
			}
		}
		/**
		 * Retourne un rectangle de valeurs 0
		 * @return {Rectangle}
		 */
		function getNullArea() {
			return {left: 0, right: 0, width: 0, height: 0, top: 0, bottom: 0, invalid: true};
		}
	}
604300
public function getModels()
    {
        $tables = $this->driver->getTablesNames();
        $pivotTables = $this->getConfig('pivot_tables', []);

        foreach ($tables as $table) {
            // Crée l'instance du modèle pour la table correspondante
            $this->models[$table] = $this->createModel($table);

            // Crée l'instance du pivot si la table est définie ou reconnue comme tel
            if (array_key_exists($table, $pivotTables)) {
                if ($pivotTables[$table] !== null) {
                    $this->pivots[$table] = new Pivot($table, $pivotTables[$table]);
                }
            }
            elseif (in_array($table, $pivotTables) || strpos($table, '_has_') !== false) {
                $this->pivots[$table] = new Pivot($table);
            }
        }

        // Ajoute les relations 1-n et 1-1 selon les contraintes définies dans la BDD
        foreach ($this->models as $model) {
            $this->addRelationsAccordingToConstraints($model);
        }

        // Ajoute les relations n-n via les instances des pivots
        foreach ($this->pivots as $pivot) {
            $pivot->addBelongsToManyRelationsToRelatedModels();
        }

        // Ajoute les relations polymorphiques selon les informations renseignées dans la config
        foreach ($this->getConfig('polymorphic_relations', []) as $relation => $relatedTables) {
            list($table, $morphName) = explode('.', $relation);

            $this->addPolymorphicRelations($this->models[$table], $morphName, $relatedTables);
        }

        return $this->models;
    }