Skip to content

Conversation

@AlexSkrypnyk
Copy link
Member

@AlexSkrypnyk AlexSkrypnyk commented Nov 24, 2025

Summary by CodeRabbit

  • New Features

    • Naming conventions now support configurable formats (snake_case or camelCase) for variables and parameters instead of fixed snake_case enforcement
    • New error codes introduced for camelCase naming violations
  • Documentation

    • Updated configuration examples demonstrating both snake_case and camelCase format options
    • Enhanced package metadata describing expanded naming convention support

✏️ Tip: You can customize this high-level summary in your review settings.

@coderabbitai
Copy link

coderabbitai bot commented Nov 24, 2025

📝 Walkthrough

Walkthrough

This PR refactors the naming convention sniffs from enforcing exclusively snake_case to supporting configurable naming formats (snakeCase or camelCase). The abstract base class is renamed and extended with format-aware validation and conversion methods. Concrete sniff classes are renamed and updated to use the new configurable approach. Tests and documentation are updated accordingly.

Changes

Cohort / File(s) Summary
Core Sniff Classes
src/DrevOps/Sniffs/NamingConventions/AbstractVariableNamingSniff.php, src/DrevOps/Sniffs/NamingConventions/LocalVariableNamingSniff.php, src/DrevOps/Sniffs/NamingConventions/ParameterNamingSniff.php
Renamed classes from AbstractSnakeCaseSniff/LocalVariableSnakeCaseSniff/ParameterSnakeCaseSniff to their -Naming equivalents. Added public $format property (default 'snakeCase'), new methods for camelCase validation (isCamelCase, isValidFormat), format conversion (toCamelCase, toFormat), and dual error codes for both formats. Refactored validation logic to be format-driven with runtime error code selection.
Unit Tests
tests/Unit/AbstractVariableNamingSniffTest.php, tests/Unit/LocalVariableNamingSniffTest.php, tests/Unit/ParameterNamingSniffTest.php
Renamed test classes and updated imports to reflect sniff renamings. Added comprehensive test coverage for camelCase behavior, format validation, and dynamic error code selection. Introduced new test methods and data providers for the new format-configurable functionality. Removed LocalVariableSnakeCaseSniffTest.php (replaced by LocalVariableNamingSniffTest.php).
Functional Tests
tests/Functional/LocalVariableNamingSniffFunctionalTest.php, tests/Functional/ParameterNamingSniffFunctionalTest.php
Renamed test classes and updated sniff source references from snake_case names to -Naming equivalents. Updated expected error codes and messages to reflect new naming scheme.
Configuration & Documentation
src/DrevOps/ruleset.xml, README.md, CLAUDE.md, composer.json
Updated ruleset to reference renamed sniffs with inline comments showing format configuration option. Updated documentation to describe configurable naming (snakeCase or camelCase) with examples. Added keywords field and updated description in composer.json.

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20–30 minutes

  • Format property behavior: Verify the default 'snakeCase' value is correctly applied and that the format-driven logic branches appropriately in validation and error code selection
  • New methods (isCamelCase, isValidFormat, toCamelCase, toFormat): Confirm each method handles both snakeCase and camelCase correctly, and that invalid format values trigger the expected runtime errors
  • Error code ternary logic: Check that error codes are selected dynamically based on the configured format in both LocalVariableNamingSniff and ParameterNamingSniff
  • Test coverage completeness: Ensure unit and functional tests adequately cover both snakeCase (default) and camelCase scenarios, including edge cases in format conversion

Possibly related PRs

  • PR #10: Performs the identical refactor renaming snake-case sniffs to configurable -Naming sniffs, adding a $format property and camelCase/snakeCase methods
  • PR #11: Directly reverts this PR's changes, restoring the original snake_case-only class names and removing format-configurable logic
  • PR #1: Builds on this refactoring by further generalizing variable/parameter naming sniff functionality and introducing the configurable AbstractVariableNamingSniff base class

Pre-merge checks and finishing touches

✅ Passed checks (3 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly and accurately summarizes the main change: refactoring naming convention sniffs to support configurable case formats (snake_case or camelCase) instead of enforcing only snake_case.
Docstring Coverage ✅ Passed Docstring coverage is 90.24% which is sufficient. The required threshold is 80.00%.
✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch feature/allow-chose-case2

Comment @coderabbitai help to get the list of available commands and usage tips.

@codecov-commenter
Copy link

codecov-commenter commented Nov 24, 2025

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 100.00%. Comparing base (0e318f4) to head (936991a).
⚠️ Report is 1 commits behind head on main.
✅ All tests successful. No failed tests found.

Additional details and impacted files
@@            Coverage Diff            @@
##              main       #12   +/-   ##
=========================================
  Coverage   100.00%   100.00%           
=========================================
  Files            6         6           
  Lines          387       409   +22     
=========================================
+ Hits           387       409   +22     

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 4

♻️ Duplicate comments (1)
tests/Unit/AbstractVariableNamingSniffTest.php (1)

592-626: Same conversion issue as toCamelCase test.

Line 624 exhibits the same problem identified in the toCamelCase test: 'camelCase_from_camel' => ['camelCase', 'testVariable', 'testvariable'] expects an already-camelCase input to be lowercased entirely, which is incorrect.

This expectation should be corrected in alignment with fixing the toCamelCase implementation/expectations.

📜 Review details

Configuration used: CodeRabbit UI

Review profile: ASSERTIVE

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 0e318f4 and 936991a.

📒 Files selected for processing (13)
  • CLAUDE.md (9 hunks)
  • README.md (3 hunks)
  • composer.json (1 hunks)
  • src/DrevOps/Sniffs/NamingConventions/AbstractVariableNamingSniff.php (3 hunks)
  • src/DrevOps/Sniffs/NamingConventions/LocalVariableNamingSniff.php (2 hunks)
  • src/DrevOps/Sniffs/NamingConventions/ParameterNamingSniff.php (3 hunks)
  • src/DrevOps/ruleset.xml (1 hunks)
  • tests/Functional/LocalVariableNamingSniffFunctionalTest.php (4 hunks)
  • tests/Functional/ParameterNamingSniffFunctionalTest.php (5 hunks)
  • tests/Unit/AbstractVariableNamingSniffTest.php (11 hunks)
  • tests/Unit/LocalVariableNamingSniffTest.php (1 hunks)
  • tests/Unit/LocalVariableSnakeCaseSniffTest.php (0 hunks)
  • tests/Unit/ParameterNamingSniffTest.php (3 hunks)
💤 Files with no reviewable changes (1)
  • tests/Unit/LocalVariableSnakeCaseSniffTest.php
🧰 Additional context used
🧬 Code graph analysis (5)
src/DrevOps/Sniffs/NamingConventions/LocalVariableNamingSniff.php (1)
src/DrevOps/Sniffs/NamingConventions/AbstractVariableNamingSniff.php (4)
  • AbstractVariableNamingSniff (16-573)
  • isParameter (438-472)
  • isValidFormat (102-108)
  • toFormat (168-174)
tests/Functional/ParameterNamingSniffFunctionalTest.php (1)
tests/Functional/FunctionalTestCase.php (1)
  • FunctionalTestCase (17-142)
tests/Unit/ParameterNamingSniffTest.php (3)
src/DrevOps/Sniffs/NamingConventions/ParameterNamingSniff.php (1)
  • ParameterNamingSniff (17-194)
tests/Unit/UnitTestCase.php (2)
  • UnitTestCase (18-152)
  • processCode (46-53)
src/DrevOps/Sniffs/NamingConventions/AbstractVariableNamingSniff.php (1)
  • register (50-52)
src/DrevOps/Sniffs/NamingConventions/ParameterNamingSniff.php (1)
src/DrevOps/Sniffs/NamingConventions/AbstractVariableNamingSniff.php (3)
  • AbstractVariableNamingSniff (16-573)
  • isValidFormat (102-108)
  • toFormat (168-174)
tests/Unit/AbstractVariableNamingSniffTest.php (6)
src/DrevOps/Sniffs/NamingConventions/AbstractVariableNamingSniff.php (1)
  • AbstractVariableNamingSniff (16-573)
src/DrevOps/Sniffs/NamingConventions/LocalVariableNamingSniff.php (1)
  • LocalVariableNamingSniff (16-84)
src/DrevOps/Sniffs/NamingConventions/ParameterNamingSniff.php (1)
  • ParameterNamingSniff (17-194)
tests/Unit/LocalVariableNamingSniffTest.php (1)
  • CoversClass (18-193)
tests/Unit/ParameterNamingSniffTest.php (1)
  • CoversClass (18-265)
tests/Unit/UnitTestCase.php (1)
  • UnitTestCase (18-152)
🪛 markdownlint-cli2 (0.18.1)
README.md

98-98: Fenced code blocks should be surrounded by blank lines

(MD031, blanks-around-fences)


106-106: Fenced code blocks should be surrounded by blank lines

(MD031, blanks-around-fences)


135-135: Fenced code blocks should be surrounded by blank lines

(MD031, blanks-around-fences)


141-141: Fenced code blocks should be surrounded by blank lines

(MD031, blanks-around-fences)

🪛 PHPMD (2.15.0)
src/DrevOps/Sniffs/NamingConventions/AbstractVariableNamingSniff.php

106-106: Missing class import via use statement (line '106', column '28'). (undefined)

(MissingImport)


172-172: Missing class import via use statement (line '172', column '28'). (undefined)

(MissingImport)

tests/Unit/LocalVariableNamingSniffTest.php

49-59: The parameter $should_have_errors is not named in camelCase. (undefined)

(CamelCaseParameterName)


53-53: The variable $should_have_errors is not named in camelCase. (undefined)

(CamelCaseVariableName)


56-58: The method testProcess uses an else expression. Else clauses are basically not necessary and you can simplify the code by not using them. (undefined)

(ElseExpression)


136-136: The variable $error_code_snake is not named in camelCase. (undefined)

(CamelCaseVariableName)


144-144: The variable $error_code_camel is not named in camelCase. (undefined)

(CamelCaseVariableName)


158-158: The variable $class_name is not named in camelCase. (undefined)

(CamelCaseVariableName)


159-159: The variable $original_format is not named in camelCase. (undefined)

(CamelCaseVariableName)


181-181: The variable $first_error is not named in camelCase. (undefined)

(CamelCaseVariableName)

src/DrevOps/Sniffs/NamingConventions/LocalVariableNamingSniff.php

63-63: The variable $error_code is not named in camelCase. (undefined)

(CamelCaseVariableName)

tests/Unit/ParameterNamingSniffTest.php

208-208: The variable $error_code_snake is not named in camelCase. (undefined)

(CamelCaseVariableName)


216-216: The variable $error_code_camel is not named in camelCase. (undefined)

(CamelCaseVariableName)


230-230: The variable $class_name is not named in camelCase. (undefined)

(CamelCaseVariableName)


231-231: The variable $original_format is not named in camelCase. (undefined)

(CamelCaseVariableName)


253-253: The variable $first_error is not named in camelCase. (undefined)

(CamelCaseVariableName)

src/DrevOps/Sniffs/NamingConventions/ParameterNamingSniff.php

60-60: The variable $error_code is not named in camelCase. (undefined)

(CamelCaseVariableName)

tests/Unit/AbstractVariableNamingSniffTest.php

489-489: Missing class import via use statement (line '489', column '23'). (undefined)

(MissingImport)


529-529: Missing class import via use statement (line '529', column '23'). (undefined)

(MissingImport)


568-568: Missing class import via use statement (line '568', column '23'). (undefined)

(MissingImport)


606-606: Missing class import via use statement (line '606', column '23'). (undefined)

(MissingImport)


634-634: Missing class import via use statement (line '634', column '23'). (undefined)

(MissingImport)


648-648: Missing class import via use statement (line '648', column '23'). (undefined)

(MissingImport)

🔇 Additional comments (14)
composer.json (1)

3-16: Composer metadata reflects configurable naming feature correctly

The updated description and added keywords accurately describe the new snakeCase/camelCase configurability and data-provider focus; no behavioral impact and looks good.

src/DrevOps/ruleset.xml (1)

5-15: Ruleset entries for LocalVariableNaming/ParameterNaming are wired correctly

The new rules reference the renamed sniffs and clearly document the default snakeCase and optional camelCase configuration; nothing else in the ruleset is impacted.

tests/Functional/LocalVariableNamingSniffFunctionalTest.php (1)

11-11: LocalVariableNaming functional tests correctly target the renamed sniff

The class name, $sniffSource value, and all expected messages/sources now consistently reference LocalVariableNaming and the NotSnakeCase code with the new “snakeCase format; try …” wording. This aligns with the refactored sniff and README examples.

Also applies to: 17-17, 22-22, 34-66, 80-82, 96-103

tests/Functional/ParameterNamingSniffFunctionalTest.php (1)

11-11: ParameterNaming functional tests are correctly updated for the new sniff and fixer behavior

The class name, $sniffSource, expected messages/sources, and phpcbf invocation now consistently target DrevOps.NamingConventions.ParameterNaming and its NotSnakeCase code, while explicitly leaving local-variable renames to LocalVariableNamingSniff. Test coverage for inherited params, properties, and docblock fixing remains coherent.

Also applies to: 17-17, 22-22, 34-46, 60-66, 100-100, 118-118

src/DrevOps/Sniffs/NamingConventions/ParameterNamingSniff.php (1)

10-16: Format-driven parameter naming enforcement looks internally consistent

The refactor to ParameterNamingSniff cleanly delegates format handling to AbstractVariableNamingSniff: process() filters reserved and inherited parameters, defers local variables to LocalVariableNamingSniff, then uses isValidFormat()/toFormat() and selects NotSnakeCase vs NotCamelCase based on $this->format. The error message and data ($var_name, $this->format, $suggestion) align with the updated tests and README, and the existing docblock-fix logic remains scoped to fixing only matching @param entries. No functional issues spotted here.

Also applies to: 17-18, 24-28, 42-43, 53-82

src/DrevOps/Sniffs/NamingConventions/LocalVariableNamingSniff.php (1)

10-82: Configurable format + dynamic error-code logic looks coherent

The refactor in process() cleanly wires local-variable enforcement into the new format abstraction:

  • Filters (reserved, static property, class property, parameter) are unchanged semantically, so scope boundaries stay the same.
  • isValidFormat() / toFormat() usage delegates all format-specific behavior to AbstractVariableNamingSniff, which centralizes the rules nicely.
  • Mapping $this->format === 'snakeCase'CODE_VARIABLE_NOT_SNAKE_CASE and otherwise → CODE_VARIABLE_NOT_CAMEL_CASE keeps the PHPCS source codes stable and predictable.

No correctness issues stand out here; the behavior for both snakeCase and camelCase formats should be consistent with the base class helpers.

tests/Unit/LocalVariableNamingSniffTest.php (1)

21-191: Unit coverage for both formats is good; Ruleset mutation is slightly brittle

The tests exercise the key behaviors well:

  • dataProviderProcess() accurately distinguishes what LocalVariableNamingSniff is responsible for (locals only, parameters/properties/static accesses excluded).
  • testCamelCaseFormatIntegration() is a useful integration-style check that actually runs through the camelCase path and asserts the NotCamelCase code via the PHPCS source.
  • Restoring the original format in finally avoids cross-test contamination.

One thing to be aware of: directly poking at $this->ruleset->sniffs[$class_name] relies on PHPCS’s internal storage details for sniffs. That’s acceptable here, but it’s a potential future fragility if PHPCS changes its internals. If that ever becomes an issue, an alternative would be to construct a dedicated Ruleset/Config per test with format preconfigured, rather than mutating the instantiated sniff.

tests/Unit/ParameterNamingSniffTest.php (1)

7-29: Parameter sniff tests correctly reflect the new configurable behavior

These updates look consistent with the refactored sniff:

  • testRegister() and testErrorCodeConstant() now correctly target ParameterNamingSniff and validate both NotSnakeCase and NotCamelCase constants.
  • dataProviderProcess() expectations map cleanly to the sniff’s responsibilities:
    • Only parameters are checked; locals, properties, reserved vars are ignored.
    • Interface and extends scenarios are treated as inherited parameters and skipped, matching isInheritedParameter() semantics.
  • The camelCase tests (testErrorCodeSelection() and testCamelCaseFormatIntegration()) ensure both the conditional error-code selection and the real PHPCS execution path for the camelCase configuration are covered.

As with the local-variable tests, mutating $this->ruleset->sniffs[$class_name]->format couples the test to PHPCS’s internal Ruleset structure. It’s fine for now, but if PHPCS changes how it stores sniffs, these tests might need to be updated to configure the sniff via configuration instead.

Also applies to: 36-48, 196-263

tests/Unit/AbstractVariableNamingSniffTest.php (6)

7-20: LGTM! Clean refactoring of class names and imports.

The updates correctly reflect the architectural change from AbstractSnakeCaseSniff to AbstractVariableNamingSniff, and the test class coverage is properly aligned.


32-425: LGTM! Consistent instantiation updates throughout existing tests.

All test methods correctly instantiate LocalVariableNamingSniff (or ParameterNamingSniff where appropriate for parameter-specific testing). The updates are consistent and align with the class renames.


478-516: LGTM! Comprehensive camelCase detection test.

The test thoroughly covers valid camelCase patterns and invalid cases including snake_case, PascalCase, and edge cases with underscores. The test structure mirrors the existing snake_case detection test.


554-590: LGTM! Well-structured format validation test.

The test correctly validates that isValidFormat dispatches to the appropriate validation method based on the configured format. The data provider covers both snakeCase and camelCase formats with valid and invalid cases for each.


628-654: LGTM! Proper exception handling tests.

Both tests correctly verify that invalid format values throw RuntimeException with clear error messages. These defensive checks ensure configuration errors are caught early.


518-552: Test expectations are correct; implementation works as designed.

The toCamelCase method is specifically designed to convert snake_case to camelCase using underscores as delimiters. When input has no underscores (PascalCase, camelCase), the method correctly lowercases the entire string because there are no delimiters to work with.

Test cases verification:

  • 'TestVariable' → no underscores → lowercased to 'testvariable'
  • 'testVariable' → no underscores → lowercased to 'testvariable'
  • 'test_variable' → splits on _'testVariable'
  • '_test_variable' → removes leading _ → splits → 'testVariable'

The test expectations on lines 545-546 are accurate and validate correct behavior.

Comment on lines 50 to 55
Run a single test file:
```bash
./vendor/bin/phpunit tests/Unit/AbstractVariableSnakeCaseSniffTest.php
./vendor/bin/phpunit tests/Unit/LocalVariableSnakeCaseSniffTest.php
./vendor/bin/phpunit tests/Unit/ParameterSnakeCaseSniffTest.php
./vendor/bin/phpunit tests/Unit/LocalVariableNamingSniffTest.php
./vendor/bin/phpunit tests/Unit/ParameterNamingSniffTest.php
```
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor

Align documentation with configurable naming and updated test names

The overall description now reflects configurable naming (snakeCase or camelCase), but a few spots are still out of sync:

  • “Run a single test file” still references AbstractVariableSnakeCaseSniffTest.php; the base test file appears to have been renamed to AbstractVariableNamingSniffTest.php, so this example should be updated.
  • In the directory structure, LocalVariableNamingSniff.php and ParameterNamingSniff.php are described as enforcing snake_case only; elsewhere in the doc you describe them as configurable. Consider rewording those bullets to “enforces configurable naming (snakeCase or camelCase)” for consistency.
  • The unit test overview still calls out AbstractVariableSnakeCaseSniffTest.php and describes only snake_case-focused tests, while the new tests also cover camelCase and error-code selection/integration for both sniffs.
  • The “Code Style Conventions” section still says “Use snake_case for local variables and method parameters”. Given the standard is now configurable, you might want to clarify that snake_case is the default, but camelCase can be enforced by setting $format = 'camelCase' in the sniffs’ configuration.

Updating these references will keep the guidance consistent with the new behavior and reduce confusion for contributors and tooling that relies on this file.

Also applies to: 90-93, 96-99, 181-195, 292-293

🤖 Prompt for AI Agents
In CLAUDE.md around lines 50-55 (also apply changes at 90-93, 96-99, 181-195,
292-293): update references and wording to reflect that naming is configurable
(snake_case or camelCase) and that test filenames changed; replace occurrences
of AbstractVariableSnakeCaseSniffTest.php with
AbstractVariableNamingSniffTest.php in examples and the unit test overview,
change descriptions for LocalVariableNamingSniff.php and
ParameterNamingSniff.php from “enforces snake_case only” to “enforces
configurable naming (snake_case or camelCase)” or similar, adjust the unit test
overview text to mention tests cover both snake_case and camelCase and
error-code selection/integration, and modify the Code Style Conventions line to
state that snake_case is the default but camelCase can be enforced via $format =
'camelCase' in sniff configuration.

---
PHP_CodeSniffer standard enforcing:
- `snake_case` naming for local variables and function/method parameters
- Consistent naming conventions for local variables and function/method parameters (configurable: `snakeCase` or `camelCase`)
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor

Configurable naming docs are clear; fix markdown fenced-block spacing for lint

The new sections for LocalVariableNaming and ParameterNaming, including examples and error-code names, match the configurable snakeCase/camelCase behavior and look good. The only issue is the markdownlint MD031 warnings around fenced code blocks immediately following the “With …” lines; add a blank line before each ```php fence to satisfy the rule.

You can fix all four places like this:

-**With `snakeCase` (default):**
-```php
+**With `snakeCase` (default):**
+
+```php
@@
-**With `camelCase`:**
-```php
+**With `camelCase`:**
+
+```php
@@
-**With `snakeCase` (default):**
-```php
+**With `snakeCase` (default):**
+
+```php
@@
-**With `camelCase`:**
-```php
+**With `camelCase`:**
+
+```php

This should clear the MD031 “Fenced code blocks should be surrounded by blank lines” findings while keeping the rendered output the same.

Also applies to: 63-65, 73-91, 93-122, 130-155, 159-159

🤖 Prompt for AI Agents
In README.md around lines 22, 63-65, 73-91, 93-122, 130-155 and 159, the fenced
PHP code blocks that immediately follow the "With `snakeCase`/`camelCase`" lines
are not preceded by a blank line and trigger markdownlint MD031; insert a single
blank line between each "With ..." line and the following ```php fence so each
fenced code block is surrounded by blank lines, and apply this same change to
all the listed ranges to resolve the MD031 warnings while keeping content
unchanged.

Comment on lines +18 to 26
/**
* The naming convention to enforce.
*
* Valid values: 'snakeCase', 'camelCase'
*
* @var string
*/
public $format = 'snakeCase';

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick | 🔵 Trivial

Format abstraction is well-structured; consider whether misconfig should hard-fail

The new $format property together with isCamelCase(), isValidFormat(), toCamelCase(), and toFormat() cleanly encapsulates naming behavior:

  • isCamelCase() and toCamelCase() behave as expected for lowerCamelCase and align with the existing snake_case helpers.
  • isValidFormat() / toFormat() provide a single switch point for children, which keeps the concrete sniffs simple and consistent.

One design choice to confirm: an unsupported $format value currently throws a RuntimeException from both isValidFormat() and toFormat(). That’s reasonable as a fail-fast guard for misconfigured standards, but if you’d prefer PHPCS to continue without fatal errors, you might instead log a warning and treat the variable as valid by default. Otherwise, this abstraction looks solid.

Also applies to: 80-108, 138-174

Comment on lines +60 to +62
$error_code = ($this->format === 'snakeCase') ?
self::CODE_PARAMETER_NOT_SNAKE_CASE :
self::CODE_PARAMETER_NOT_CAMEL_CASE;
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick | 🔵 Trivial

Consider renaming $error_code to satisfy PHPMD CamelCaseVariableName (optional)

PHPMD flagged $error_code as not camelCase. If you want to keep PHPMD clean here, you can either adjust its ruleset for sniffs or rename the variable to camelCase:

-      $error_code = ($this->format === 'snakeCase') ?
-        self::CODE_PARAMETER_NOT_SNAKE_CASE :
-        self::CODE_PARAMETER_NOT_CAMEL_CASE;
+      $errorCode = ($this->format === 'snakeCase') ?
+        self::CODE_PARAMETER_NOT_SNAKE_CASE :
+        self::CODE_PARAMETER_NOT_CAMEL_CASE;
@@
-        $error_code,
+        $errorCode,

This is cosmetic only; behavior is unchanged.

Also applies to: 67-67

🧰 Tools
🪛 PHPMD (2.15.0)

60-60: The variable $error_code is not named in camelCase. (undefined)

(CamelCaseVariableName)

🤖 Prompt for AI Agents
In src/DrevOps/Sniffs/NamingConventions/ParameterNamingSniff.php around lines
60-62 and 67, a variable named $error_code violates PHPMD CamelCaseVariableName;
rename it to $errorCode (and update all its usages within the method/file) so
the variable follows camelCase, and run tests or PHPMD to verify no references
remain to the old name.

@AlexSkrypnyk AlexSkrypnyk merged commit 08ceac6 into main Nov 24, 2025
12 checks passed
@AlexSkrypnyk AlexSkrypnyk deleted the feature/allow-chose-case2 branch November 24, 2025 12:16
@AlexSkrypnyk
Copy link
Member Author

@coderabbitai
create a description with examples for these new rules

@coderabbitai
Copy link

coderabbitai bot commented Nov 24, 2025

Tip

For best results, initiate chat on the files or code changes.

@AlexSkrypnyk, here's a comprehensive description with examples for the new configurable naming convention rules:


DrevOps Naming Convention Rules

This standard provides configurable naming convention enforcement for PHP variables and parameters, supporting both snake_case and camelCase formats.

Rules Overview

1. LocalVariableNaming

Enforces consistent naming for local variables within functions and methods.

Error Codes:

  • LocalVariableNaming.NotSnakeCase - Variable not in snake_case format
  • LocalVariableNaming.NotCamelCase - Variable not in camelCase format

2. ParameterNaming

Enforces consistent naming for function and method parameters.

Error Codes:

  • ParameterNaming.NotSnakeCase - Parameter not in snake_case format
  • ParameterNaming.NotCamelCase - Parameter not in camelCase format

Configuration

Default (snake_case)

<rule ref="DrevOps.NamingConventions.LocalVariableNaming"/>
<rule ref="DrevOps.NamingConventions.ParameterNaming"/>

Configure for camelCase

<rule ref="DrevOps.NamingConventions.LocalVariableNaming">
    <properties>
        <property name="format" value="camelCase"/>
    </properties>
</rule>

<rule ref="DrevOps.NamingConventions.ParameterNaming">
    <properties>
        <property name="format" value="camelCase"/>
    </properties>
</rule>

Examples

snake_case Format (Default)

Valid Code:

function processOrder($order_id, $user_name) {
    $total_amount = 100;
    $tax_rate = 0.15;
    $final_price = $total_amount * (1 + $tax_rate);
    
    return $final_price;
}

class OrderProcessor {
    public function calculate($item_count, $base_price) {
        $discount_rate = 0.1;
        $final_total = $base_price * $item_count * (1 - $discount_rate);
        
        return $final_total;
    }
}

Invalid Code (with violations):

// ❌ LocalVariableNaming.NotSnakeCase
function processOrder($orderId, $userName) {
    $totalAmount = 100;  // Variable "totalAmount" is not in snakeCase format; try "total_amount"
    $taxRate = 0.15;     // Variable "taxRate" is not in snakeCase format; try "tax_rate"
    
    return $totalAmount * (1 + $taxRate);
}

// ❌ ParameterNaming.NotSnakeCase
class OrderProcessor {
    public function calculate($itemCount, $basePrice) {
        // Parameter "itemCount" is not in snakeCase format; try "item_count"
        // Parameter "basePrice" is not in snakeCase format; try "base_price"
        return $itemCount * $basePrice;
    }
}

camelCase Format

Valid Code:

function processOrder($orderId, $userName) {
    $totalAmount = 100;
    $taxRate = 0.15;
    $finalPrice = $totalAmount * (1 + $taxRate);
    
    return $finalPrice;
}

class OrderProcessor {
    public function calculate($itemCount, $basePrice) {
        $discountRate = 0.1;
        $finalTotal = $basePrice * $itemCount * (1 - $discountRate);
        
        return $finalTotal;
    }
}

Invalid Code (with violations):

// ❌ LocalVariableNaming.NotCamelCase
function processOrder($order_id, $user_name) {
    $total_amount = 100;  // Variable "total_amount" is not in camelCase format; try "totalAmount"
    $tax_rate = 0.15;     // Variable "tax_rate" is not in camelCase format; try "taxRate"
    
    return $total_amount * (1 + $tax_rate);
}

// ❌ ParameterNaming.NotCamelCase
class OrderProcessor {
    public function calculate($item_count, $base_price) {
        // Parameter "item_count" is not in camelCase format; try "itemCount"
        // Parameter "base_price" is not in camelCase format; try "basePrice"
        return $item_count * $base_price;
    }
}

Automatic Fixes

Both sniffs provide automatic fixes via phpcbf:

# Fix snake_case violations
vendor/bin/phpcbf --standard=DrevOps path/to/file.php

# The fixer will automatically convert:
$totalAmount$total_amount
$userName$user_name

Exclusions and Ignored Variables

The following are automatically excluded from checks:

  • PHP superglobals ($_GET, $_POST, $_SERVER, etc.)
  • Class properties (checked by separate rules)
  • Promoted constructor properties
  • Variables in inherited method parameters

Would you like me to format this as a specific document (e.g., add it to README.md or create a separate RULES.md file)?

@AlexSkrypnyk
Copy link
Member Author

AlexSkrypnyk commented Nov 24, 2025

@coderabbitai
create a description of changes introduced in this PR

@coderabbitai
Copy link

coderabbitai bot commented Nov 24, 2025

Tip

For best results, initiate chat on the files or code changes.

@AlexSkrypnyk, here's a comprehensive description of changes introduced in this PR:


🎯 Overview

This PR refactors the naming convention sniffs to support configurable naming formats, allowing users to enforce either snake_case (default) or camelCase for variables and parameters. Previously, the standard only supported snake_case enforcement.


✨ Key Changes

1. Class Renames (Breaking Changes)

  • AbstractSnakeCaseSniffAbstractVariableNamingSniff
  • LocalVariableSnakeCaseSniffLocalVariableNamingSniff
  • ParameterSnakeCaseSniffParameterNamingSniff

2. New Configuration Property

Added a format property to both sniffs with two supported values:

  • snakeCase (default - maintains backward compatibility)
  • camelCase (new option)

3. New Error Codes

Each sniff now has two error codes:

  • LocalVariableNaming:
    • LocalVariableNaming.NotSnakeCase (existing, renamed from LocalVariableSnakeCase.NotSnakeCase)
    • LocalVariableNaming.NotCamelCase (new)
  • ParameterNaming:
    • ParameterNaming.NotSnakeCase (existing, renamed from ParameterSnakeCase.NotSnakeCase)
    • ParameterNaming.NotCamelCase (new)

4. New Methods in AbstractVariableNamingSniff

  • isCamelCase(string $name): bool - Validate camelCase format
  • isValidFormat(string $name): bool - Validate against configured format
  • toCamelCase(string $name): string - Convert to camelCase
  • toFormat(string $name): string - Convert to configured format

5. Updated Package Metadata

  • Description: Now mentions "consistent naming (snakeCase or camelCase)"
  • Keywords: Added array with relevant terms (phpcs, standards, naming-conventions, etc.)

📝 Configuration Examples

Default Behavior (snake_case)

<rule ref="DrevOps.NamingConventions.LocalVariableNaming"/>
<rule ref="DrevOps.NamingConventions.ParameterNaming"/>

Configure for camelCase

<rule ref="DrevOps.NamingConventions.LocalVariableNaming">
    <properties>
        <property name="format" value="camelCase"/>
    </properties>
</rule>

<rule ref="DrevOps.NamingConventions.ParameterNaming">
    <properties>
        <property name="format" value="camelCase"/>
    </properties>
</rule>

🔄 Before & After

Before (snake_case only)

// ✅ Valid
function process($user_name) {
    $total_amount = 100;
}

// ❌ Invalid - LocalVariableSnakeCase.NotSnakeCase
function process($userName) {
    $totalAmount = 100;
}

After (configurable)

// With format="snakeCase" (default)
function process($user_name) {
    $total_amount = 100;  // ✅ Valid
}

// With format="camelCase"
function process($userName) {
    $totalAmount = 100;  // ✅ Valid
}

🚨 Breaking Changes

  1. Class Names Changed:

    • Direct references to LocalVariableSnakeCaseSniff or ParameterSnakeCaseSniff will break
    • Update to LocalVariableNamingSniff and ParameterNamingSniff
  2. Rule References in XML:

    • Old: DrevOps.NamingConventions.LocalVariableSnakeCase
    • New: DrevOps.NamingConventions.LocalVariableNaming
    • Old: DrevOps.NamingConventions.ParameterSnakeCase
    • New: DrevOps.NamingConventions.ParameterNaming
  3. Error Code Names:

    • Old: LocalVariableSnakeCase.NotSnakeCase
    • New: LocalVariableNaming.NotSnakeCase
    • Old: ParameterSnakeCase.NotSnakeCase
    • New: ParameterNaming.NotSnakeCase

🔧 Migration Guide

Update XML Configuration

- <rule ref="DrevOps.NamingConventions.LocalVariableSnakeCase"/>
+ <rule ref="DrevOps.NamingConventions.LocalVariableNaming"/>

- <rule ref="DrevOps.NamingConventions.ParameterSnakeCase"/>
+ <rule ref="DrevOps.NamingConventions.ParameterNaming"/>

Update Inline Suppressions

- // phpcs:ignore DrevOps.NamingConventions.LocalVariableSnakeCase.NotSnakeCase
+ // phpcs:ignore DrevOps.NamingConventions.LocalVariableNaming.NotSnakeCase

- // phpcs:ignore DrevOps.NamingConventions.ParameterSnakeCase.NotSnakeCase
+ // phpcs:ignore DrevOps.NamingConventions.ParameterNaming.NotSnakeCase

✅ Backward Compatibility

  • Default behavior unchanged: snake_case remains the default format
  • Existing configurations work: Rules auto-upgrade if using DrevOps ruleset
  • No code changes required: Only if using custom configurations or direct class references

📊 Test Coverage

  • ✅ 100% code coverage maintained
  • ✅ All existing tests updated and passing
  • ✅ New tests added for camelCase functionality
  • ✅ Integration tests validate both formats
  • ✅ Functional tests cover format selection and error codes

📚 Documentation Updates

  • ✅ README.md updated with new configuration examples
  • ✅ CLAUDE.md updated with API changes
  • ✅ Code examples demonstrate both formats
  • ✅ Error code documentation updated

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants