La documentation officielle de Gutenberg décrit InnerBlocks comme le composant qui « permet à un bloc d’accepter du contenu de bloc imbriqué ». Rien dans cette définition n’indique une quelconque fragilité. Pourtant, dans bien des équipes, la composition par InnerBlocks traîne une réputation de complexité excessive, au point que certains développeurs préfèrent tout écrire dans un unique bloc monolithique plutôt que d’accepter des blocs enfants.
Cette prudence part souvent d’une mauvaise expérience réelle : un bloc composite devenu impossible à faire évoluer. Mais en y regardant de plus près, la cause n’est presque jamais InnerBlocks lui-même : c’est l’absence de contraintes posées autour de lui.
Ce que fait réellement InnerBlocks
Le composant se limite à définir une zone où d’autres blocs peuvent être insérés, à l’intérieur du bloc parent. Rien de plus :
import { InnerBlocks } from '@wordpress/block-editor';
function Edit() {
return (
<div className="bloc-temoignages">
<InnerBlocks
allowedBlocks={ [ 'mon-extension/temoignage' ] }
template={ [
[ 'mon-extension/temoignage' ],
[ 'mon-extension/temoignage' ],
] }
/>
</div>
);
}
Cette configuration limite déjà considérablement les dérives : seul le bloc mon-extension/temoignage peut être inséré, et deux instances apparaissent par défaut à la création du bloc parent. Un bloc composite n’est donc pas condamné à accueillir n’importe quoi, dans n’importe quel ordre.
D’où vient réellement la complexité perçue

Les projets qui souffrent avec InnerBlocks présentent presque toujours l’un de ces symptômes, indépendants du composant lui-même : un allowedBlocks absent qui autorise tous les blocs du site, un save.js du parent qui tente de lire le contenu des enfants au lieu de laisser InnerBlocks.Content faire son travail, ou une logique métier dupliquée entre le bloc parent et ses enfants faute d’avoir utilisé le block context pour partager des données.
Retirer InnerBlocks dans ces cas-là ne résout rien : la complexité migre simplement ailleurs, souvent vers un unique attribut de type tableau stockant toute la structure, bien plus difficile à éditer visuellement qu’une composition de blocs distincts.
Un découpage qui limite vraiment les dérives
- Toujours poser
allowedBlocks, même avec un seul bloc autorisé : cela évite qu’un contributeur insère un bloc du cœur incompatible avec le style du composant. templateLockpermet de figer la structure sans empêcher l’édition du contenu texte, un compromis souvent suffisant pour un client peu technique.- Le
block context, déclaré dansblock.json, transmet des données du parent vers les enfants sans dupliquer d’attributs. - Un bloc parent ne doit jamais recalculer ce que ses enfants savent déjà : il doit se contenter d’orchestrer leur affichage.
Un contre-exemple révélateur
Comparons deux façons d’implémenter un bloc « grille de tarifs » à trois colonnes. La première stocke toute la grille dans un unique attribut JSON, édité via un formulaire personnalisé dans InspectorControls. La seconde utilise InnerBlocks avec un bloc colonne-tarif répété trois fois.
Dans le premier cas, ajouter un champ (par exemple une mention « populaire ») impose de modifier le schéma de l’attribut, la fonction de migration associée, et le formulaire d’édition entier. Dans le second cas, il suffit d’ajouter un attribut au bloc colonne-tarif, sans toucher au bloc parent. La composition réduit ici la surface de code à modifier, exactement l’inverse de sa réputation.
Quand la prudence reste justifiée
Cela ne signifie pas que InnerBlocks convient à tous les cas. Un bloc qui doit garantir un ordre d’affichage strict et non modifiable par l’utilisateur, ou qui exige une cohérence de données impossible à exprimer bloc par bloc (un total calculé à partir de plusieurs lignes, par exemple), gagnera parfois à rester un bloc unique avec des attributs structurés. La décision doit porter sur la nature du contenu, pas sur une méfiance générale envers la composition.
Sur nos revues de code, on rejette rarement un bloc composite pour son usage d’
InnerBlocks. On rejette en revanche systématiquement l’absence d’allowedBlocks, bien plus révélatrice d’un manque de réflexion sur le bloc.
En résumé
La réputation de complexité d’InnerBlocks vient presque toujours d’un découpage insuffisamment pensé, pas du composant en lui-même. Bien contraint par allowedBlocks, template et templateLock, il réduit souvent la dette technique plutôt que de l’augmenter, en particulier sur des blocs composites amenés à évoluer.