[FR] Hook, introduction et informations utiles

RemRem edited this page Apr 22, 2017 · 2 revisions

! Ce document est en cours de rédaction.


  1. Qu'est-ce qu'un hook ?
  2. Comment ça fonctionne ?
    2. 1. Au niveau du core
    2. 2. Au niveau d'un addon
  3. Notes & recommandations
  4. Liste des hook disponible ?
  5. Demander la création d'un hook

1. Qu'est ce qu'un hook ?

Un hook (de l'anglais, signifie crochet ou hameçon) est un système qui permet de faire appel a du script (A) au sein d'un script (B) sans avoir recours à la moindre modification du script B. Le système de hook de BlogoText permet, par exemple, l'interaction des différents addons avec le core (comportement du core, traitement sur le contenu...) sans modifier le core, les développeurs d'addons peuvent donc avoir plus de libertés et plus de possibilités.

Un hook se décompose en plusieurs parties :

  • le hook-trigger qui permet d’exécuter une fonction (A) depuis le script (B).
  • le hook-check (optionnel) qui contrôle les données reçus après les traitement effectué par la fonction (A).
  • le hook-push qui permet de déclarer la fonction (A) à exécuter pour un hook-trigger.

2. Comment ça fonctionne ?

Voici, schématiquement comment l'on peut se représenter le fonctionnement d'un hook à travers un exemple d'utilisation depuis un addon :

  • le core de BlogoText est initialisé
  • le core charge l'addon
  • l'addon déclare sa configuration
  • l'addon déclare son hook action : lorsque le core a fini de préparer un article et avant de l'afficher, la fonction addon_format_article() doit traiter l'article
  • l'addon déclare la fonction addon_format_article()
  • le core récupère la demande d'un article (via l'URL)
  • le core prépare l'article
  • le core actionne le hook-trigger
  • le hook-trigger vérifie la présence du hook-push
  • le hook-trigger envoie une copie de l'article à la fonction addon_format_article() (définie par le hook-push de l'addon)
  • la fonction retourne l'article après traitement
  • le hook-check vérifie l'article
  • le hook-check remplace l'article par la copie de l'article modifiée par addon_format_article()
  • le core envoie l'article modifié au template
  • le template affiche l'article modifié au visiteur

Ainsi, sans modifier le core de BlogoText, ni l'article original, l'on peux étendre les fonctionnalités du core grâce aux addons.

2. 1. Au niveau du core

Selon les besoins, il faut identifier les emplacements propices pour placer un hook-trigger, il faut ensuite choisir les données que l'on souhaite envoyer aux différents hook-push (éviter tout ce qui est relatif à la sécurité, avoir un impact négatif sur le comportement du core ou bien encore qui pourrais modifier l'intégrité des données ou la structure de la base de données ou des fichiers ...) et enfin, selon les besoins, vérifier que les données reçues après le hook-trigger permettent d'être exploitées.

Un exemple concret :

// le core est initialisé
// les addons sont chargés

// la donnée que l'on souhaite rendre accessible
$data_1 = 'Hello';

/**
 * on exécute le hook-trigger
 * le 1er paramètre est un uid pour identifier le hook
 * les paramètres suivant sont les données auxquelles les hook-push auront accès
 * hook_trigger() retournera un tableau : 
 *     array(
 *         0 => l'uid du hook
 *         1 => les données du 2éme paramètre
 *         2 => les données du 3éme paramètre
 *         ...
 */
$tmp_hook = hook_trigger( 'uid_du_hook' , $data_1 );

/**
 * on vérifie les données en sortie
 * le 1er paramètre est l'uid pour identifier le hook
 * le 2éme paramètre correspond au nombre de paramètres du hook_trigger()
 * le 3éme paramètre sont le tableau de sortie du hook_trigger()
if (hook_check('uid_du_hook', 2, $tmp_hook)) {
    // les données sont valides, on peut "mettre à jour" notre variable de départ
    $data_1 = $tmp_hook['1'];
}

2. 2. Au niveau d'un addon

Si votre addon à besoin d'un accès au core ou aux données traitées par le core, vous utiliserez un hook-push via la fonction hook_push().

Vous devez placer vos hook-push dans votre fichier principal (PHP) après avoir déclaré votre addon ($GLOBALS['addons'][])

Pour déclarer un hook-push la syntaxe est la suivante : hook_push( $uid_hook , $fonction , $priorité );

  • $uid_hook, string, voir la liste des hooks disponible (4. Liste des hook disponible)
  • $fonction, string, le nom de la fonction que vous souhaitez accrocher au hook-trigger
  • $priorité, int, optionnel, entre 0 et 200 (de préférence), [todo] expliquer le système de priorité

La fonction qui sera exécutée recevra un tableau en arguments, ce tableau est organisé tel que :

array(
    0 => l'uid du hook
    1 => les données du 2éme paramètre
    2 => les données du 3éme paramètre
     ...

N'oubliez pas de définir votre fonction, avec les arguments et le comportement qui conviennent !

La fonction définie par le hook-trigger, doit, quoiqu'il arrive, retourner le tableau qu'elle a reçue en argument.

Cas concret, l'addon qui est pris en exemple dans la partie "2. 1. Au niveau du core".

// nous sommes dans votre addon
// $GLOBALS['addons'][] est défini

// on pousse l’exécution de la fonction addon_complement()
// lorsque le hook 'uid_du_hook' sera déclenché via le
// hook-trigger correspondant.
hook_push( 'uid_du_hook' , 'addon_complement' , 100 );

// on défini la fonction qui sera exécutée
function addon_complement( $arguments ){
    // la donnée est contenue dans $arguments['1']
    // nous allons la modifier
    $arguments['1'] = $arguments .' world';

    // nous renvoyons l'ensemble des arguments
    return $arguments;
}

Dans l'exemple de la partie "2. 1. Au niveau du core", la variable envoyée en 2éme argument était un string 'Hello', durant le traitement du hook 'uid_du_hook', notre fonction addon_complement() a été exécutée pour modifier le premier argument tel que maintenant $arguments['1'] = 'Hello world' et à renvoyer l'ensemble de $arguments au système de hook. Si le système de hook ne trouve pas d'erreur, il écrasera la variable d'origine par $arguments['1'] tel que notre fonction lui a renvoyé via $arguments. Après les traitements du hook, le core va continuer ses processus avec la variable contenant 'Hello world'.

3. Notes & recommandations

  • bien que cela soit possible, éviter d'utiliser des hook-trigger au sein de vos addons
  • utiliser le système de hook si vous n'avez pas d'autres moyens de parvenir à vos objectifs
  • optimiser votre code, évitez les regex dans vos fonctions, certains hook peuvent envoyer beaucoup de données et du coup, vos fonctions peuvent ralentir le fonctionnement du core.
  • la fonction définie par le hook-trigger, doit, quoiqu'il arrive, retourner le tableau qu'elle a reçue en argument.
  • Le décalage dans les numéros de variables et la position de cette même variable au sein du tableau passé en arguments est le fruit du système de "comptage" de PHP dans un tableau, nous (humain) comptons à partir de 1, php compte à partir de 0, du coup : example( 1er_argument , 2nd_argument ) est considéré comme example( argument_0, argument_1 ) par php;
  • éviter de passer en argument d'un hook-trigger tout ce qui est relatif à la sécurité, avoir un impact négatif sur le comportement du core ou bien encore qui pourrais modifier l'intégrité ou la structure de la base de données et des fichiers ...

4. Liste des hook disponible

Attention !

Cette liste de hook ne sera peut-être plus valable pour la version 4.0 de BlogoText.

  • system-start
    • Paramètres
      • ['0'] (string) l'UID du hook
    • Utilité : Premier hook à être lancé
  • show_index
    • Paramètres
      • ['0'] (string) l'UID du hook
      • ['1'] (string) HTML (complet)
    • Utilité : à la fin de afficher_index() (// only used by the main page of the blog (not on admin) : shows main blog page.)
  • list_items
    • Paramètres
      • ['0'] (string) l'UID du hook
      • ['1'] (array) liste des articles/liens/commentaires...
      • ['2'] (string) le type de contenu (articles/commentaires/links/rss)
    • Utilité : Permet de travailler sur les éléments après l'extraction de la base de donnée et avant les différents processus de traitement de contenus du core
  • conversion_theme_addons_end
    • Paramètres
      • ['0'] (string) l'UID du hook
      • ['1'] (string) HTML (complet)
    • Utilité : Permet de travailler sur l'ensemble du code HTML final avant l'envoie (?)
  • before_redirection
    • Paramètres
      • ['0'] (string) l'UID du hook
      • ['1'] (string) URL de redirection
    • Utilité : Permet quelques actions (modifications d'URL...) avant une redirection (par ex. après qu'un visiteur ai posté un commentaire)
  • before_show_rss_no_cache
    before_show_atom_no_cache
    • Paramètres
      • ['0'] (string) l'UID du hook
      • ['0'] (array) le contenu qui sera diffusé sur le flux RSS/ATOM
    • Utilité : Permet de travailler sur le contenu des flux RSS/ATOM avant diffusion.

5. Demander la création d'un hook

Si vous avez besoin d'un hook, ou qu'un hook ait accès à certaines données, il suffit de le demander via une issue. Soyez précis dans votre demande quant à l'endroit où il devrait être placé (ou au moment de son exécution), les données que le hook doit pouvoir traiter. N'hésitez pas aussi à expliquer la finalité du hook afin que la communauté puisse juger de sa pertinence ou vous indiquer une autre solution.

You can’t perform that action at this time.
You signed in with another tab or window. Reload to refresh your session. You signed out in another tab or window. Reload to refresh your session.
Press h to open a hovercard with more details.