« Le titre affiché reste en français sur la page anglaise, alors que le gabarit est censé être traduit. » Ce symptôme est apparu sur un site utilisant les block bindings, l’API stabilisée avec WordPress 6.5 en avril 2024 qui permet de lier dynamiquement un attribut de bloc (le contenu d’un paragraphe, la source d’une image) à une donnée externe — un champ personnalisé, une métadonnée, ou une source enregistrée via register_block_bindings_source() — plutôt que de saisir une valeur statique dans l’éditeur.
Ce cas est distinct de l’Interactivity API, également livrée avec la même version de WordPress mais qui répond à un besoin différent (interactivité front-end sans rechargement complet), et distinct des patterns synchronisés déjà traités précédemment, un mécanisme de duplication de structure de bloc plutôt que de liaison de données.
Symptôme : un contenu lié qui ignore la langue courante
Sur ce site, un gabarit de page produit utilisait un bloc paragraphe lié, via block bindings, à un champ personnalisé stockant un slogan marketing. Ce champ personnalisé, comme la majorité des champs ACF ou natifs sur un site traduit avec Polylang, existe en plusieurs exemplaires, un par langue, chacun rattaché à sa propre traduction du contenu parent. Après traduction du gabarit, le texte statique du paragraphe changeait bien de langue, mais le slogan lié par block bindings continuait d’afficher systématiquement la valeur du champ de la version française, quelle que soit la langue réellement consultée.
Diagnostic : la source liée n’est pas consciente du contexte de langue

Le fonctionnement des block bindings repose sur une source enregistrée qui expose une fonction de récupération de valeur (get_value_callback), appelée avec l’identifiant du bloc en contexte. Si cette fonction va chercher la valeur directement via get_post_meta() sur l’identifiant de l’article courant, sans tenir compte du fait que Polylang gère chaque traduction comme un article WordPress distinct avec son propre identifiant, le comportement dépend entièrement de quel identifiant est réellement transmis au moment du rendu. Sur ce site, le callback avait été codé en récupérant l’identifiant du post depuis une variable globale renseignée une seule fois au chargement initial de la page, sans être recalculée lors du rendu du gabarit sur la traduction, ce qui produisait systématiquement l’ID de l’article source français.
Correctif : rendre le callback conscient du contexte réel
Le correctif consiste à faire en sorte que la fonction de récupération de valeur utilise systématiquement l’identifiant de l’article réellement affiché au moment du rendu (get_the_ID() dans le bon contexte, ou l’argument fourni nativement par l’API de block bindings), plutôt qu’une référence figée en amont :
register_block_bindings_source( 'monsite/slogan', array(
'label' => __( 'Slogan marketing', 'monsite' ),
'get_value_callback' => function( $source_args, $block_instance ) {
$post_id = $block_instance->context['postId'] ?? get_the_ID();
return get_post_meta( $post_id, 'slogan_marketing', true );
},
) );
En s’appuyant sur le contexte du bloc plutôt que sur une variable globale capturée trop tôt, le callback retourne toujours la valeur associée à l’article réellement rendu, qu’il s’agisse de la version française ou d’une traduction, sans nécessiter de logique spécifique à Polylang dans le callback lui-même : la traduction est déjà gérée en amont par le fait que chaque langue possède son propre article WordPress avec son propre champ personnalisé.
Le cas des champs volontairement partagés entre langues
Un cas différent, à ne pas confondre avec le bug corrigé ci-dessus, concerne les champs pour lesquels une équipe éditoriale souhaite explicitement une valeur partagée entre toutes les langues (un numéro de téléphone d’assistance commun, par exemple). Dans ce cas précis, il ne s’agit pas d’un bug mais d’un choix, et le callback peut légitimement ignorer la langue courante pour retourner une valeur commune, à condition que ce choix soit documenté clairement dans le code pour qu’un futur développeur ne le confonde pas avec le bug traité ici.
Vérifier après toute nouvelle source enregistrée
Toute nouvelle source de block bindings ajoutée sur un site multilingue mérite un test systématique consistant à vérifier son affichage sur chaque langue configurée avant mise en production, exactement comme on testerait n’importe quel champ personnalisé classique. L’API étant encore récente au moment des faits, les bonnes pratiques de développement autour du multilingue n’étaient pas encore largement diffusées dans la communauté, ce qui explique la fréquence de ce type d’oubli sur les premiers projets à l’adopter.
- Ne jamais capturer l’identifiant d’article dans une variable globale en dehors du contexte de rendu du bloc
- Utiliser le contexte fourni par l’API de block bindings plutôt qu’une référence figée
- Documenter explicitement les cas où une valeur doit rester volontairement partagée entre langues
- Tester chaque nouvelle source de liaison sur toutes les langues configurées avant mise en production
En résumé
Les block bindings ne connaissent pas nativement la notion de langue : c’est au développeur de la source enregistrée de s’assurer que le contexte de rendu réel, et non une référence capturée trop tôt, détermine la valeur retournée. Ce piège, propre à toute API récente encore peu documentée sur ses interactions avec le multilingue, se corrige simplement une fois identifié, mais mérite un test systématique sur chaque nouvelle liaison ajoutée à un site traduit.