Pour commencer cette série sur la Création d'un module avec Drupal 8, analysons les besoins de notre module. Cette première phase va nous permettre de définir le travail d'implémentation à effectuer et de commencer à chercher comment effectuer le portage.
Sur D7, mon module internal link devait correspondre aux contraintes suivantes :
- Pouvoir créer des « liens » sous forme d’entités, avec différentes options telle que la sensibilité à la casse, le poids du lien, la visibilité selon des critères spécifiques (domaine/sous-domaine, restriction par pages). Les liens devaient être "multilingues" et on devait pouvoir appliquer des attributes tels que "class" ou "rel" ;
- Avoir le choix d’appliquer les liens de manière automatisée ou manuelle. Pour un type de contenu donné, on devait pouvoir autoriser un choix « manuel » par l’auteur du contenu. Si un choix manuel était effectué, alors seuls les liens choisis étaient appliqués. Dans le cas contraire, c’est le mode automatique qui prenait la main, si il était activé pour le type de contenu bien entendu;
- Pouvoir appliquer des liens sur des champs particuliers, dans des affichages particuliers. Ça ne pouvait donc pas être un filtre d’affichage appliqué à un format de texte, les filtres d’affichages ne faisant pas la différence entre les champs. Je ne voulais pas non plus que ça soit un formateur de champ, car ça impliquerait d’être cantonné à ce formateur et ainsi de ne plus pouvoir en utiliser un autre, ou alors de devoir ajouter des fonctionnalités au formateur au fil du temps ;
- Appliquer le parsing des liens lors d’un processus s’effectuant AVANT la mise en cache de l’affichage, afin d’éviter que le parsing s’effectue à chaque affichage du contenu, et génère une certaine lourdeur d’affichage. Cette contrainte impliquant elle même une bonne gestion de l’invalidation des caches ;
Bref, un module ayant tout pour donner quelques bons maux de tête lors de son développement. Sur D7, le module était fonctionnel. Nous allons maintenant récapituler les différents éléments qui vont être nécessaire pour un portage vers D8, en incluant quelques mots-clés pour donner quelques pistes.
- Une gestion par entité, incluant une partie administrative permettant de créer, modifier et supprimer les entités: ContentEntityBase, ContentEntityForm, EntityListBuilder, EntityViewBuilder;
- Une partie configuration globale, pour choisir les entités/champs sur lesquels nous appliquerons les liens: ConfigEntityBase, FormBase, FormElement, FieldType, FieldWidget;
- Des fonctions de récupération de données: Service, DependencyInjection;
- Des fonctions de tests et de parsing de données: Service, DependencyInjection;
Vous allez rapidement vous rendre compte que ces quelques contraintes et mots-clés vont nous amener assez loin dans l'implémentation. Je ne peux certifier que les directions prises sont les meilleures, j'ai simplement tenté de faire au mieux en m'inspirant des modules existants et de mes (maigres) connaissances du noyau D8.
Maintenant que nous avons défriché un peu la logique d'implémentation, nous allons pouvoir avancer sur la mise en place.