Aller au contenu
Rechercher
Discutons
Menu

Dossier module PrestaShop · chapitre 5 sur 6

Une page de réglages et une administration en français pour ton module PrestaShop

La page de réglages d'un module tient dans une méthode, getContent(), et un formulaire décrit en tableau PHP que PrestaShop dessine pour toi. C'est l'ancienne façon de faire, et c'est justement pour ça qu'elle s'affiche à l'identique en 1.7.8.11 et en 9.2.0. Voici celle de Markdown Twin, sa traduction française, et une valeur par défaut qui n'a jamais atteint le labo.

Par Sébastien GrillotTesté au labo : 19 octobre 2026Publié : 19 octobre 2026
Testé sur
PrestaShop 9.2.0 · PHP 8.3.32
Et sur
PrestaShop 1.7.8.11 · PHP 7.4.33
Traduction
38 chaînes, système de traduction classique

L'essentiel en 5 points

  1. Le bouton « Configurer » n'apparaît que si la classe du module a une méthode getContent().
  2. HelperForm, l'outil historique du cœur, dessine le même formulaire en 1.7.8.11 et en 9.2.0, sans une ligne propre à chaque version.
  3. Chaque valeur reçue se vérifie avant d'être enregistrée : interrupteurs forcés à 0 ou 1, nombres bornés, texte débarrassé de ses balises.
  4. Changer une valeur par défaut dans le code ne change rien chez une boutique où le module est déjà installé.
  5. Le système de traduction classique tient dans un fichier PHP par langue. PrestaShop conseille le nouveau système aux modules qui ne visent pas plus vieux que la 1.7.6.

5.1Le bouton « Configurer » et getContent()

Dans le gestionnaire de modules, certains modules ont un bouton « Configurer », d'autres non. Tu t'es déjà demandé pourquoi ? La documentation de PrestaShop répond en une ligne : « PrestaShop will check if this method exists and will only display the “Configure” button if this method is declared. »

La méthode en question, c'est getContent(), et je la trouve bien nommée. Elle est appelée quand on ouvre la page de réglages, et elle fait deux choses. Si le formulaire vient d'être envoyé, elle enregistre. Dans tous les cas, elle affiche le formulaire.

public function getContent()
{
    $out = '';
    if (Tools::isSubmit('submitMarkdownTwin')) {
        $in = [];
        foreach (array_keys(Renderer::TYPES) as $t) {
            $in['type_' . $t] = Tools::getValue('MDTWIN_TYPE_' . strtoupper($t));
        }
        foreach (['accept', 'discovery', 'noindex', 'schema', 'product_facts', 'llms', 'content_selector', 'skip_selector', 'llms_intro', 'llms_limit', 'cache_ttl'] as $k) {
            $in[$k] = Tools::getValue('MDTWIN_' . strtoupper($k));
        }
        Settings::save($in);
        $out .= $this->displayConfirmation($this->l('Settings saved.'));
    }
    $base = $this->context->link->getBaseLink();

    return $out . $this->renderForm($base);
}
markdowntwin.php : getContent() de Markdown Twin 1.0.0

Tools::isSubmit() regarde si le bouton d'envoi a été cliqué, Tools::getValue() lit un champ du formulaire, displayConfirmation() affiche le bandeau vert « Réglages enregistrés ». Trois outils du cœur, présents depuis toujours, et c'est tout !

Je te montre ce que ça donne dans l'administration de la 9.2.0, en français.

La page de réglages de Markdown Twin dans l'administration de PrestaShop 9.2.0
Les réglages de Markdown Twin en 9.2.0 : les pages qui ont un jumeau, les interrupteurs, puis la zone de contenu et les parties à écarter

5.2Le formulaire, dessiné par HelperForm

Tu n'écris pas une ligne de HTML pour ce formulaire, et crois-moi, c'est reposant. Tu le décris dans un tableau PHP, champ par champ, et HelperForm le dessine avec le style de l'administration. La documentation la présente elle-même comme « the legacy way of creating configuration pages for modules using HelperForm ».

L'ancienne façon, donc : celle de toujours.

Pourquoi pas la nouvelle, avec Symfony et ses formulaires ?

Parce que la boutique visée tourne en 1.7.8, et que je voulais le même module en 9.2.0 aussi. La 1.7.8.11 embarque Symfony 3.4.49, la 9.2.0 Symfony 6.4.46. Je ne parierais pas un euro sur un formulaire Symfony qui tourne tel quel sur les deux. HelperForm, lui, est là dans les deux versions. Au labo, la même page de réglages s'est affichée dans les deux administrations, à partir du même code.

Voici le début de la description du formulaire. Un interrupteur Oui / Non revenant six fois, on l'a rangé dans une petite fonction.

$switch = function ($name, $label, $desc) {
    return [
        'type' => 'switch', 'label' => $label, 'name' => $name, 'desc' => $desc, 'is_bool' => true,
        'values' => [['id' => $name . '_on', 'value' => 1, 'label' => $this->l('Yes')], ['id' => $name . '_off', 'value' => 0, 'label' => $this->l('No')]],
    ];
};
$fields = [
    'form' => [
        'legend' => ['title' => $this->l('Markdown Twin'), 'icon' => 'icon-file-text'],
        // [...]
        'input' => [
            // [...]
            $switch('MDTWIN_ACCEPT', $this->l('Content negotiation'), $this->l('The normal URL answers in Markdown to "Accept: text/markdown". Browsers never ask for Markdown: visitors always get the HTML page.')),
            // [...]
            ['type' => 'text', 'label' => $this->l('llms.txt entries'), 'name' => 'MDTWIN_LLMS_LIMIT', 'class' => 'fixed-width-sm', 'desc' => $this->l('Maximum number of products listed (10 to 2000).')],
        ],
        'submit' => ['title' => $this->l('Save'), 'name' => 'submitMarkdownTwin'],
    ],
];
$h = new HelperForm();
$h->module = $this;
$h->name_controller = $this->name;
$h->token = Tools::getAdminTokenLite('AdminModules');
$h->currentIndex = AdminController::$currentIndex . '&configure=' . $this->name;
$h->default_form_language = (int) $this->context->language->id;
$h->submit_action = 'submitMarkdownTwin';
// [...] les valeurs actuelles, lues dans la configuration
$h->fields_value = $values;

return $h->generateForm([$fields]);
markdowntwin.php : renderForm() de Markdown Twin 1.0.0 (extrait, les coupes sont marquées [...])

Regarde la ligne du jeton, Tools::getAdminTokenLite('AdminModules'). Le formulaire part avec le jeton de l'administration, celui que PrestaShop contrôle sur la page des modules. C'est gratuit, et c'est HelperForm qui le glisse dans le formulaire.

5.3Ne rien enregistrer sans le vérifier

Garde ça en tête, un formulaire d'administration, c'est une porte d'entrée comme une autre. Dans son exemple de page de réglages, la documentation de PrestaShop vérifie d'ailleurs la valeur reçue avec la classe Validate avant de l'enregistrer.

Markdown Twin fait le tri dans Settings::save(), et j'aime bien sa façon de faire : les interrupteurs deviennent 0 ou 1, quoi qu'on envoie. Les types de pages sont pris dans une liste fermée. Les nombres sont bornés, de 10 à 2 000 produits pour /llms.txt, de 0 à 86 400 secondes pour le cache. Et les textes perdent leurs balises.

\Configuration::updateValue(self::PREFIX . 'LLMS_LIMIT', max(10, min(2000, (int) (isset($in['llms_limit']) ? $in['llms_limit'] : $d['llms_limit']))));
\Configuration::updateValue(self::PREFIX . 'CACHE_TTL', max(0, min(86400, (int) (isset($in['cache_ttl']) ? $in['cache_ttl'] : $d['cache_ttl']))));
classes/Settings.php : l'enregistrement de deux réglages, Markdown Twin 1.0.0 (extrait)

Un employé qui tape « 999999 » dans le champ du sommaire en aura 2 000. Pas de message d'erreur, mais pas de sommaire d'un million de lignes non plus ;)

5.4Le piège des valeurs par défaut

Regarde bien le champ « Zone de contenu » sur la capture. Tu ne remarques rien ? Il contient #main, main, [role="main"], #content-wrapper, #content, body.

Or, dans le code de la version 1.0.0, la valeur par défaut est différente. #content-wrapper est passé en deuxième position, parce que certaines pages de blog n'ont pas de #main, et que main y attrapait l'en-tête et le menu avec le contenu.

Alors, pourquoi le labo affiche-t-il l'ancienne ? J'avoue que la première fois, ça surprend :)

Parce que le module y a été installé avant ce changement. À l'installation, les valeurs par défaut sont écrites dans la configuration de la boutique, une fois. Ensuite, c'est la valeur en base qui compte, et changer le défaut dans le code ne la touche pas.

public static function install()
{
    foreach (self::defaults() as $k => $v) {
        if (false === \Configuration::get(self::PREFIX . strtoupper($k))) {
            \Configuration::updateValue(self::PREFIX . strtoupper($k), $v);
        }
    }

    return true;
}
classes/Settings.php : l'installation des réglages, Markdown Twin 1.0.0

C'est voulu, et je trouve que c'est très bien comme ça. Un marchand qui a réglé son module ne veut pas voir ses réglages écrasés à chaque mise à jour. Mais ça veut dire une chose, pour toi qui écris le module, et je te la souligne. Si une nouvelle version doit vraiment changer une valeur chez les boutiques qui ont déjà le module, c'est un script de mise à jour qui doit le faire. On en parle dans le chapitre sur la livraison.

5.5Traduire le module en français

Tout le module est écrit en anglais, je te l'ai dit. C'est ce que conseille la documentation, « we suggest writing all your wordings in English, and then translating them to other languages. » Et une chaîne qui n'a pas de traduction s'affiche en anglais, sans erreur.

PrestaShop a deux systèmes de traduction pour les modules. Le système classique est le plus ancien, et la documentation le présente comme « a heritage from previous versions of PrestaShop ». Le nouveau système, par domaines de traduction, est disponible pour les modules depuis la 1.7.6. Leur page de comparaison est nette : si ton module ne vise pas plus vieux que la 1.7.8, c'est le nouveau qui est recommandé.

Markdown Twin utilise le classique. Pas le plus moderne, mais le plus simple à fabriquer. Chaque phrase passe par $this->l(), et les traductions françaises vivent dans un seul fichier, translations/fr.php.

<?php

global $_MODULE;
$_MODULE = [];
$_MODULE['<{markdowntwin}prestashop>markdowntwin_bd55e0753e089474f86518e6c39a4566'] = 'Markdown Twin';
$_MODULE['<{markdowntwin}prestashop>markdowntwin_ecd7cbe91f0211a5568325e9a22b1646'] = 'Un jumeau Markdown de chaque page pour les assistants et agents d\'IA : le même contenu sans l\'interface, avec les faits et les données structurées de la page. C\'est toujours la page HTML que les moteurs de recherche indexent.';
translations/fr.php de Markdown Twin 1.0.0 (les deux premières des 38 chaînes)

La clé a l'air barbare, je te l'accorde, mais elle se lit. Le nom du module entre chevrons, puis un nom de fichier (par défaut, le nom technique du module), puis l'empreinte MD5 de la phrase anglaise. Change un seul mot de la phrase anglaise, et l'empreinte change, la traduction ne colle plus.

D'habitude, ce fichier sort de l'administration, dans International › Traductions, qui lit le code du module et propose un formulaire. Chez Kōeki, on le génère avec un petit script, qui relit toutes les phrases $this->l('…') du module, calcule leurs empreintes, et refuse de finir s'il en manque une traduction. Comme ça, une phrase ajoutée sans traduction ne peut pas partir en livraison.

Le module est écrit, réglable, traduit. Il reste le plus important, et ma partie préférée : le tester pour de vrai, le relire avec un œil méchant, et le livrer. Tout est dans le dernier chapitre.

Sources

Historique de ce chapitre

  • 19 octobre 2026 : première version, page de réglages de Markdown Twin 1.0.0 en 9.2.0 et 1.7.8.11.
Sébastien Grillot

Co-fondateur de Kōeki · Consultant SEO et IA

Sébastien Grillot

Consultant SEO depuis 2009 : c'est ici, sur Inside da WeB, qu'il a monté sa première agence, spécialisée dans l'e-commerce. Il construit aujourd'hui ses propres outils avec l'IA, modules PrestaShop compris.

FermerLa page de réglages de Markdown Twin dans l'administration de PrestaShop 9.2.0