Deprecated: Creation of dynamic property WC_Product_Variation::$prix_promo is deprecated in ... on line ... — ce message envahit les logs juste après une montée de version PHP vers 8.3 sur une boutique qui gère des produits variables depuis plusieurs années. Le réflexe est de chercher le bug dans le cœur de WooCommerce ; la cause est presque toujours ailleurs, dans du code maison ou une extension tierce.
PHP 8.2 a introduit la dépréciation des propriétés dynamiques (celles qu’on assigne directement à un objet sans qu’elles soient déclarées dans sa classe), et PHP 8.3 rend ces avertissements plus visibles dans les journaux de production, notamment quand WP_DEBUG_LOG est actif. WC_Product_Variation hérite de WC_Product, une classe qui n’autorise pas l’attribut #[AllowDynamicProperties] par défaut sur toutes ses branches, ce qui expose immédiatement tout code y ajoutant une propriété à la volée.
Repérer précisément la source du message
Le message de dépréciation contient le nom exact de la propriété fautive et le fichier concerné. Dans la grande majorité des cas rencontrés sur des boutiques en production, la source appartient à l’une de ces trois catégories :
- Un hook comme
woocommerce_product_variation_get_priceouwoocommerce_ajax_variation_thresholddans lequel du code assigne$variation->mon_champ = ...;au lieu d’utiliser le système de métadonnées. - Une extension de tarification dynamique qui stocke un état temporaire directement sur l’objet produit pendant le calcul du panier.
- Un script d’import CSV maison qui construit des objets
WC_Product_Variationet leur attache des champs personnalisés avant l’appel àsave().
Pourquoi la correction ne doit jamais passer par des propriétés directes
Assigner une propriété directement à un objet produit ne persiste jamais la donnée : WooCommerce sérialise ses produits via son système de métadonnées interne (WC_Data), pas via les attributs PHP bruts de l’objet. Une propriété dynamique fonctionne donc « par accident » tant qu’elle reste en mémoire dans la même requête, mais disparaît dès qu’un autre processus recharge le produit — et génère en prime l’avertissement de dépréciation.

// À éviter : propriété dynamique non déclarée
$variation->prix_promo = 19.90;
// Remplacement correct, avec persistance réelle
$variation->update_meta_data( '_prix_promo', 19.90 );
$variation->save();
// Lecture correspondante
$prix_promo = $variation->get_meta( '_prix_promo', true );
Cas particulier : état temporaire dans une même requête
Si le besoin est réellement de faire transiter une valeur temporaire dans la même requête PHP (par exemple pour un calcul intermédiaire de règle de tarification), la solution propre consiste à stocker cette valeur en dehors de l’objet produit — dans un tableau statique, une transient courte durée, ou une variable de contexte du plugin — plutôt que sur l’objet WC_Product_Variation lui-même.
// Alternative sans toucher à l'objet produit
static $cache_regles = [];
$cache_regles[ $variation->get_id() ] = 19.90;
Méthodes WooCommerce concernées à vérifier en priorité
Sur les extensions de tarification et les imports personnalisés, les points d’entrée les plus fréquemment en cause sont les surcharges de get_price(), get_variation_attributes() et les callbacks branchés sur woocommerce_get_children. Auditez chaque endroit où une variable $variation est manipulée avant un save() ou un wc_get_product() intermédiaire.
Sur nos projets, la revue de code avant une montée de version PHP majeure inclut systématiquement une recherche
grep -rn ">[a-z_]* = "restreinte aux fichiers manipulant des objetsWC_Product, pour repérer ces assignations directes avant qu’elles ne remontent en production.
Prévention pour les prochaines montées de version
Activez WP_DEBUG_LOG sur un environnement de recette avant chaque montée de PHP, et surveillez spécifiquement les lignes contenant Creation of dynamic property. Ce n’est pas un avertissement à ignorer par confort : PHP a annoncé son intention de renforcer ce comportement dans ses versions futures, et le code qui fonctionne « par accident » aujourd’hui finira par produire une erreur fatale plutôt qu’un simple avertissement.
En résumé
La dépréciation observée sur WC_Product_Variation après une montée en PHP 8.3 ne vient jamais du cœur de WooCommerce, mais d’un code qui traite l’objet produit comme un tableau libre plutôt que comme une entité gérée par métadonnées. Remplacer chaque assignation directe par update_meta_data() et get_meta() élimine le message et rend, en prime, la donnée réellement persistante.