vendredi 25 septembre 2026

À propos

Contact

Extensions

Mettre à jour une extension privée hors WordPress.org : serveur de mises à jour

Une extension vendue sous licence à des cabinets d'architecture ne peut pas transiter par WordPress.org. Comment lui offrir malgré tout le confort d'une mise à jour en un clic ?

Par Clément Hadrot • 16 septembre 2021 • 4 min de lecture • Aucun commentaire
Mettre à jour une extension privée hors WordPress.org : serveur de mises à jour

Un cabinet d’architecture a fait développer une extension de gestion de projets qu’il a ensuite proposée, sous licence, à d’autres cabinets partenaires. Cette extension ne pouvait évidemment pas être publiée sur WordPress.org : elle était payante, réservée à un public restreint, et intégrait des éléments propriétaires. Restait un problème concret : comment offrir à ses clients le même confort qu’une extension du répertoire officiel, avec une notification et un bouton « Mettre à jour » dans l’admin ?

Le mécanisme interne que WordPress interroge

Chaque fois que l’admin WordPress vérifie les mises à jour disponibles, il construit un objet stocké dans le transient update_plugins, en interrogeant WordPress.org pour chaque extension installée. Le filtre pre_set_site_transient_update_plugins permet d’intercepter cette construction et d’y injecter ses propres informations de version.

add_filter( 'pre_set_site_transient_update_plugins', 'kaolin_verifier_mise_a_jour' );

function kaolin_verifier_mise_a_jour( $transient ) {
    if ( empty( $transient->checked ) ) {
        return $transient;
    }

    $info_distante = kaolin_recuperer_infos_version();

    if ( $info_distante && version_compare( KAOLIN_PROJETS_VERSION, $info_distante->version, '<' ) ) {
        $transient->response[ plugin_basename( __FILE__ ) ] = $info_distante;
    }

    return $transient;
}

Écrire ce mécanisme entièrement à la main est possible, mais fastidieux : il faut aussi gérer l’écran de détail de la mise à jour (plugins_api), le téléchargement sécurisé du paquet, et l’invalidation correcte du cache. C’est du code qui se ressemble d’un projet à l’autre, ce qui en fait un candidat naturel pour une bibliothèque partagée.

plugin-update-checker : éviter de tout réécrire

L'essentiel à retenir : WordPress interroge un transient précis pour savoir si une mise à jour existe ; plugin-update-checker évite de réimplémenter tout le protocole à la main ; Une vérification de licence doit conditionner l'accès au paquet, pas seulement l'affichage

La bibliothèque open source plugin-update-checker, largement utilisée dans l’écosystème des extensions commerciales, implémente ce protocole de bout en bout. Elle s’intègre en quelques lignes, à condition d’exposer soi-même un point de terminaison qui renvoie un fichier de métadonnées au format attendu.

require plugin_dir_path( __FILE__ ) . 'vendor/plugin-update-checker/plugin-update-checker.php';

use YahnisElsts\PluginUpdateChecker\v5\PucFactory;

$kaolin_maj = PucFactory::buildUpdateChecker(
    'https://updates.kaolin-projets.test/metadata.json',
    __FILE__,
    'kaolin-gestion-projets'
);

Le fichier metadata.json exposé par le serveur de mise à jour contient les informations attendues par le protocole : numéro de version, URL du paquet ZIP, notes de version, exigences de compatibilité.

{
  "name": "Kaolin Gestion de Projets",
  "version": "2.3.0",
  "download_url": "https://updates.kaolin-projets.test/paquets/kaolin-gestion-projets-2.3.0.zip",
  "requires": "5.6",
  "tested": "5.8",
  "sections": {
    "changelog": "<h4>2.3.0</h4><ul><li>Correction d'un bug d'export PDF</li></ul>"
  }
}

Sécuriser l’accès au paquet par une licence

Exposer un fichier ZIP à une URL fixe et prévisible serait une erreur : n’importe qui découvrant l’URL pourrait télécharger l’extension sans jamais avoir payé de licence. La bonne pratique consiste à générer une URL de téléchargement temporaire, ou à exiger une clé de licence en paramètre, vérifiée côté serveur avant de livrer le paquet.

$kaolin_maj->addQueryArgFilter( function ( $query_args ) {
    $query_args['licence_key'] = get_option( 'kaolin_licence_key' );
    $query_args['site_url']    = home_url();
    return $query_args;
} );

Côté serveur, chaque requête de vérification ou de téléchargement doit valider la clé de licence transmise, son état d’activation, et idéalement le nombre de sites déjà associés à cette licence, avant de répondre avec les informations de version ou le fichier lui-même.

Ce que le client final ne voit jamais, mais qui compte

Pour les cabinets partenaires utilisateurs de cette extension, tout se passe exactement comme avec une extension classique du répertoire officiel : une notification apparaît dans l’admin, le changelog s’affiche dans la fenêtre de détail habituelle, et un clic suffit à mettre à jour. Cette transparence, obtenue grâce à pre_set_site_transient_update_plugins et à plugin-update-checker, a considérablement réduit le nombre de demandes de support liées à des versions obsolètes de l’extension en circulation chez les clients.

Un mécanisme de mise à jour invisible pour l’utilisateur final est un mécanisme réussi : le client ne doit jamais avoir à se demander comment installer la nouvelle version manuellement.

Pour aller plus loin

Distribuer une extension en dehors de WordPress.org ne prive pas ses utilisateurs du confort natif de mise à jour, à condition d’implémenter soi-même, ou via une bibliothèque éprouvée comme plugin-update-checker, le même protocole que celui utilisé en interne par WordPress. C’est un investissement initial non négligeable, largement rentabilisé dès que le nombre de sites clients dépasse la dizaine.

Partager :

À propos de l'auteur

Clément Hadrot

Développeur WordPress, passionné par Elementor, le FSE et l’automatisation par IA.

Voir tous ses articles

Dans la même veine

À lire aussi