public const string STATUT_PAR_DEFAUT = 'brouillon'; — cette déclaration ne compilait pas avant PHP 8.3, qui introduit la possibilité de typer explicitement une constante de classe, exactement comme cela était déjà possible pour une propriété depuis PHP 7.4.
Ce changement reste discret dans la majorité du code applicatif, mais il a une conséquence directe sur les doublures de test qui redéfinissent une constante dans une sous-classe : PHP applique désormais une règle de compatibilité de type entre la constante d’origine et sa redéfinition.
Ce que PHP 8.3 vérifie concrètement
Avant PHP 8.3, une constante de classe n’avait pas de type déclaré : sa redéfinition dans une classe fille pouvait changer librement de nature, d’une chaîne de caractères vers un entier par exemple, sans qu’aucune vérification ne s’y oppose. Avec une constante typée, PHP applique désormais une règle de variance similaire à celle des méthodes : le type de la constante redéfinie dans la classe fille doit être compatible avec le type déclaré dans la classe parente.
class Commande
{
public const string STATUT_PAR_DEFAUT = 'brouillon';
}
class CommandeUrgente extends Commande
{
// Valide : même type déclaré
public const string STATUT_PAR_DEFAUT = 'urgent';
}
L’effet sur une classe de test qui redéfinit une constante
Une pratique répandue pour rendre une classe testable consiste à extraire une sous-classe de test qui redéfinit une constante afin de modifier un comportement par défaut, par exemple pour raccourcir un délai d’expiration pendant les tests :
class GestionnaireSession
{
public const int DUREE_EXPIRATION_SECONDES = 3600;
}
class GestionnaireSessionPourTest extends GestionnaireSession
{
// Valide à partir de PHP 8.3 : même type déclaré (int)
public const int DUREE_EXPIRATION_SECONDES = 2;
}
Tant que la sous-classe de test redéfinit la constante avec un type identique ou compatible, aucune erreur ne survient. Le point de vigilance apparaît quand une constante non typée dans du code existant est typée après coup, à l’occasion d’une modernisation du code, sans que la sous-classe de test correspondante ne soit mise à jour en parallèle.

Le piège lors d’une migration progressive
Ajouter un type à une constante de classe existante, sans vérifier ses redéfinitions dans les sous-classes (y compris celles réservées aux tests), peut faire échouer silencieusement une passe d’analyse statique, ou provoquer une erreur fatale à l’exécution si une sous-classe de test redéfinissait la constante avec un type incompatible qui n’avait jamais posé problème auparavant :
class ServiceExport
{
public const int LIMITE_LIGNES = 10000;
}
class ServiceExportPourTest extends ServiceExport
{
// Erreur en PHP 8.3 si la constante parente devient typée int :
// le type ici (string) n'est pas compatible.
public const string LIMITE_LIGNES = 'illimite';
}
La correction ne consiste pas à retirer le typage de la constante parente, ce qui reviendrait à renoncer au bénéfice du changement, mais à revoir la sous-classe de test pour qu’elle respecte un type compatible, quitte à repenser la valeur utilisée pour simuler le cas limite recherché.
Ce qui n’est pas concerné
- Les propriétés typées, stables depuis PHP 7.4, ne sont pas affectées par ce changement : la nouveauté de PHP 8.3 porte spécifiquement sur les constantes de classe.
- Une constante non typée reste parfaitement valide en PHP 8.3 : le typage des constantes est une possibilité, jamais une obligation, ce qui permet d’adopter cette fonctionnalité progressivement, classe par classe.
- Les constantes d’interface suivent la même règle de compatibilité de type quand elles sont typées, ce qui mérite d’être vérifié si une doublure de test implémente une interface dont une constante devient typée.
En résumé
Le typage des constantes de classe introduit par PHP 8.3 impose une règle de compatibilité de type entre une constante et ses redéfinitions, y compris dans les sous-classes créées spécifiquement pour les besoins d’un test. Avant de typer une constante existante lors d’une modernisation de code, il vaut la peine de vérifier l’ensemble de ses redéfinitions, tests compris, pour éviter une erreur qui n’apparaîtrait qu’à l’exécution de la suite.