Setting the scene
PHP 8.1 introduced enumerations.
Since version 2.0, the PER Coding Standard defines a rule for enum case capitalization.
Neither PHPCS itself nor PHPCSExtra contains a sniff to verify the capitalization of enum case names.
Proposed new sniff: Universal.NamingConventions.EnumCaseName
To address this rule from PER:
Enum case declarations MUST use PascalCase capitalization.
So case Hearts; and case DiamondsRed; are fine, while case HEARTS;, case hearts; and case diamonds_red; are violations.
Notes for the implementation
The case keyword inside an enum is tokenized as a dedicated T_ENUM_CASE token, so registering [T_ENUM_CASE] is a good entry point. The case name is the following T_STRING.
For the PascalCase check, the sniff can use Common::isCamelCaps($name, true, true, true). The final true enables strict mode, which forbids two consecutive uppercase letters (so JsonValue is valid but JSONValue is not). I'm assuming this matches PER's definition, but I'm not certain. This relies on the PascalCase definition in section 2.1:
The term "StudlyCaps" in PSR-1 MUST be interpreted as PascalCase where the first letter of each word is capitalized including the very first letter.
The sniff would enforce PascalCase only, which is what PER requires. If support for other conventions is wanted later, a $case property defaulting to PascalCase could be added.
This sniff should not be auto-fixable. Renaming a case is a breaking change, and the sniff cannot know if the offending name is used elsewhere in the codebase.
Suggested error code:
Describe the solution you'd like
A new sniff as outlined above.
The sniff should be able to flag the following:
enum Suit
{
// OK.
case Hearts;
case DiamondsRed;
case Type3D;
// Error: consecutive uppercase letters.
case JSONValue;
// Error: all uppercase.
case HEARTS;
// Error: lowercase first character (and camelCase in general).
case hearts;
case diamondsRed;
// Error: snake_case / contains underscores.
case diamonds_red;
case DIAMONDS_RED;
// Error: leading underscore.
case _Hidden;
}
// Backed enums are treated the same.
enum Rank: string
{
// OK.
case Hearts = 'H';
// Error: snake_case name.
case diamonds_red = 'D';
}
Also see the examples outlined in the PER documents (rules + migration guide).
Additional context (optional)
This ticket is the result of a detailed analysis of the rules as outlined in PER-CS 2.0, as well as a critical look at what's still missing rule-wise.
Setting the scene
PHP 8.1 introduced enumerations.
Since version 2.0, the PER Coding Standard defines a rule for enum case capitalization.
Neither PHPCS itself nor PHPCSExtra contains a sniff to verify the capitalization of enum case names.
Proposed new sniff:
Universal.NamingConventions.EnumCaseNameTo address this rule from PER:
So
case Hearts;andcase DiamondsRed;are fine, whilecase HEARTS;,case hearts;andcase diamonds_red;are violations.Notes for the implementation
The
casekeyword inside an enum is tokenized as a dedicatedT_ENUM_CASEtoken, so registering[T_ENUM_CASE]is a good entry point. The case name is the followingT_STRING.For the PascalCase check, the sniff can use
Common::isCamelCaps($name, true, true, true). The finaltrueenables strict mode, which forbids two consecutive uppercase letters (soJsonValueis valid butJSONValueis not). I'm assuming this matches PER's definition, but I'm not certain. This relies on the PascalCase definition in section 2.1:The sniff would enforce PascalCase only, which is what PER requires. If support for other conventions is wanted later, a
$caseproperty defaulting toPascalCasecould be added.This sniff should not be auto-fixable. Renaming a case is a breaking change, and the sniff cannot know if the offending name is used elsewhere in the codebase.
Suggested error code:
InvalidDescribe the solution you'd like
A new sniff as outlined above.
The sniff should be able to flag the following:
Also see the examples outlined in the PER documents (rules + migration guide).
Additional context (optional)
This ticket is the result of a detailed analysis of the rules as outlined in PER-CS 2.0, as well as a critical look at what's still missing rule-wise.