Six months of typed class constants, and the useful case turned out not to be the one the feature was announced for.
abstract class Report
{
abstract public const string SLUG = ''; // not legal
// constants cannot be abstract. the type is the only
// thing the parent can enforce:
public const string SLUG = 'unnamed';
}
final class VatReport extends Report
{
public const string SLUG = 'vat';
}
What I wanted was an abstract constant a child must declare, which does not exist — a typed constant with a placeholder default is as close as it gets, and a child that forgets silently inherits unnamed. The type stops the wrong kind of value and not the missing one, so the real enforcement is still a test that reflects over the subclasses.