Système de Hooks

= Introduction = Les Hooks sont une fonctionnalité pour les développeurs, disponible à partir de Dolibarr 3.2, leur permettant d'ajouter du code personnalisé aux pages standards de Dolibarr sans avoir à modifier les fichiers du coeur de Dolibarr. Contrairement aux triggers (autre manière d'interagir avec le code de Dolibarr) qui sont liés aux événements de Dolibarr, les Hooks peuvent s'exécuter n'importe ou et à n'importe quel moment dès lors qu'ils ont été prévu dans le core de Dolibarr. Ce sont des points d'insertion dans le programme.
 * Les Hooks sont actifs ou pas selon un contexte (souvent un contexte par module : par exemple "productcard" pour les produits, "invoicecard" pour les factures...). Pour trouver les Hooks existants faites une recherche pour "initHooks("
 * Les Hooks sont des fonctions qui s'insèrent dans ou remplacent le code standard. Pour rechercher le code qu'il est possible de surcharger faites une recherche pour "executeHooks(".

= Ajouter un hook pour permettre l'insertion de code = Pour implémenter un hook dans votre propre module (afin que votre module puisse être "hooké" par d'autres), vous devrez procéder à 2 étapes.

Ces étapes doivent êtres reproduites pour chaque script php de votre module où vous voulez implémenter des hooks.

1- Initialiser l'object HookManager (placez ce bout de code au début de votre script php, juste après ou avant les includes):

$hookmanager->initHooks accepte 1 paramètre (un array de contextes) et active la prise en charge des hooks pour ce script:

- 'context' est la chaine qui contient le contexte d'exécution. C'est un simple indicateur qui peut être utilisé par les fonctions de hook pour détecter dans quel cas elles sont appelées (plusieurs pages/modules peuvent appeler le même hook à différent endroit, et une fonction de hook peut ne vouloir s'exécuter que pour un contexte donné et pas les autres).

Note: Vous pouvez positionner plusieurs contextes en même temps (par exemple si vous avez besoin d'avoir un context commun à plusieurs pages mais que vous voulez aussi un context propre à une page donnée).

2- Placer ensuite l'appel des hooks la où permettre l'ajout de code:

$hookmanager->executeHooks accepte 4 paramètres et ajoute un hook (qui est un point d'entrée dans votre script pour des fonctions externes à votre script et module):

- 'hookname' est le nom de la méthode qui sera appelée. Par exemple: 'formObjectOptions'

- $parameters is a custom array to send more custom data to the hook (the hooking function can then process it). Place here anything you want, it can be a file, an array of strings, anything.. For example:

- $object is the object you want to pass onto the hooking function, mainly the current module's data (eg: invoice object if it is invoice module, etc..). This can be anything you want, but remember this will be the main component hooking functions will be using.

- $action is a string indicating the current action (can be set to null or to something sensible like 'create' or 'edit').

Note: Vous devrez refaire cette étape plusieurs fois si vous voulez ajouter plusieurs hooks à différent endroits de votre script.

Maintenant votre module devrait pouvoir être hooké, vous pouvez suivre la procédure ci-dessous dans Implémenter un hook pour implémenter une fonction hook qui en prendra avantage (permet aussi de tester que cela fonctionne).

= Implémenter un Hook = Pour utiliser un Hook (donc ajouter ou surcharger une partie de code), vous devez d'abord avoir défini un descripteur de module (voir Développement_module pour cela). Ensuite vous devez suivre les étapes suivantes :

1. Ajouter votre module au contexte où le hook doit d'exécuter. Ce qui veut dire que lorsqu'on se trouve dans le contexte donné, votre code sera appelé. Pour cela, éditer le descripteur de votre module (/htdocs/yourmodulename/core/modules/modYourModuleName.class.php) et renseignez la variable $this->module_parts comme sur l'exemple :

Note: il est possible de trouver le contexte d'un module en rajoutant (rajoutez ce bout de code dans le fichier php où réside l'appel des hooks, et supprimer le, une fois la valeur du context relevé).

Attention: N'oubliez pas de désactiver puis de réactiver votre module dans l'interface d'administration des modules afin que la modification soit prise en compte car la sauvegarde des couples "modules-hooks" qui doit être gérée est faite en base, laquelle n'est mise à jour qu'au moment de l'activation du module.

2. Pour remplacer une fonction existante par la votre (surcharge)

Créez /htdocs/yourmodulename/class/actions_yourmodulename.class.php dans votre module avec un code qui contient la méthode appelée par le hook (le nom de cette méthode se voit au moment de l'appel executeHooks). Voici un exemple:

La méthode sera alors automatiquement appelée au moment de l'appel du code qui contient le executeHooks fournissant à votre code les éléments $parameters, $object et $action.

Avec:
 * $parameters est un tableau (array) de meta-data regroupant les données du hook (son contexte accessible par $parameters['context'] mais d'autres information peuvent etre disponible selon le cas)
 * $object est l'objet sur lequel vous désirez travailler (par exemple : product pour le contexte productcard)
 * $action désigne l'action à exécuter (par exemple "create", "edit" or "view").
 * $hookmanager n'est propagé que pour permettre à votre hook d'appeler d'autres hooks.

Retours: En général, il sera 0. Il peut être 1, ce qui dans certains cas signifie que ce que fait votre hook remplace complètement ce que devait faire Dolibarr juste après l'appel du hook.
 * Le code retour d'un hook doit 0 ou 1 en cas de succès, négatif en cas d'erreur.
 * Si la méthode positionne la propriété $this->results avec un tableau, alors le tableau $hookmanager->resArray sera automatiquement enrichi avec le contenu de ce tableau, lequel pourra être réutilisé plus tard.
 * Si la méthode positionne la propriété $this->resprints avec une chaîne, alors cette chaîne sera affiché par le gestionnaire de hook (executeHook), tout de suite à la sortie de votre méthode.
 * Votre hook peut de plus modifier les valeurs de $object et $action.

= Liste des Hooks disponibles dans Dolibarr = Trouver les hooks disponibles dans Dolibarr ? Faites une recherche sur "executeHooks(" dans le code source et vous trouverez facilement toutes les fonctions déjà implémentées.

En voici une liste (non complète):

...

Note: veuillez noter que cette liste peut changer à tout moment dans le futur au fur et à mesure que les hooks et contextes soient implémentés dans Dolibarr, donc si vous voulez vraiment savoir si un hook ou contexte spécifique existe, veuillez chercher directement dans le code source avec la méthode indiquée ci-dessus.

= Liste des Contexts disponibles dans Dolibarr = Pour trouver les contextes disponibles dans Dolibarr, la procédure est similaire aux hooks. Faites une recherche sur "initHooks(" dans le code source et vous trouverez facilement tous les contextes déjà implémentées.

En voici une liste (non complète):

...

Note: veuillez noter que cette liste peut changer à tout moment dans le futur au fur et à mesure que les hooks et contextes soient implémentés dans Dolibarr, donc si vous voulez vraiment savoir si un hook ou contexte spécifique existe, veuillez chercher directement dans le code source avec la méthode indiquée ci-dessus.

= Voir aussi =
 * Triggers
 * Interfaces Dolibarr toward foreign systems
 * Interfaces from foreign systems toward Dolibarr