Problem
The stated code-style convention is: final on local variables, but NOT on method/constructor parameters in new/edited code (legacy code keeps final params and migrates incrementally as it's touched). But the guideline docs still say the opposite, so the docs and the convention contradict each other:
- .claude/guidelines.md (AI-agent rulebook): "Immutability: Use
final for all method parameters and local variables where possible" — the all method parameters clause is now wrong.
- CODE_REVIEW_GUIDELINES.md (human-facing): the "Use
final for Variables Not Reassigned" section and several examples show final on parameters (e.g. public void process(final String input)).
Both files carry a "keep these two in sync" preamble, so they must be updated together.
This surfaced during the two-axis review of #166 / PR #199: AppPrefs.vibrateEnabled(final Context context) was flagged as a hard violation of the convention, while the docs technically endorsed it. That final has since been dropped in #199, which leaves AppPrefs mixed (the new method has no final param; the ~7 legacy methods still do).
Scope (one PR)
- Docs — update both guideline files so they state the actual convention:
final on locals, not on parameters; note that legacy code keeps final params and migrates incrementally when a method is otherwise edited. Fix the inline examples so they don't teach final params.
- AppPrefs — drop
final from the parameters of the remaining legacy methods (criticalLevel, warningLevel, batteryLevels, setBatteryLevels, drainLimitPph, clampDrainLimit, private prefs) so the file is internally consistent — a concrete reference application of the corrected convention. (final on locals stays.)
Not in scope: a codebase-wide final-param sweep. Legacy files migrate incrementally as they're touched, per the convention.
Acceptance criteria
Problem
The stated code-style convention is:
finalon local variables, but NOT on method/constructor parameters in new/edited code (legacy code keepsfinalparams and migrates incrementally as it's touched). But the guideline docs still say the opposite, so the docs and the convention contradict each other:finalfor all method parameters and local variables where possible" — theall method parametersclause is now wrong.finalfor Variables Not Reassigned" section and several examples showfinalon parameters (e.g.public void process(final String input)).Both files carry a "keep these two in sync" preamble, so they must be updated together.
This surfaced during the two-axis review of #166 / PR #199:
AppPrefs.vibrateEnabled(final Context context)was flagged as a hard violation of the convention, while the docs technically endorsed it. Thatfinalhas since been dropped in #199, which leavesAppPrefsmixed (the new method has nofinalparam; the ~7 legacy methods still do).Scope (one PR)
finalon locals, not on parameters; note that legacy code keepsfinalparams and migrates incrementally when a method is otherwise edited. Fix the inline examples so they don't teachfinalparams.finalfrom the parameters of the remaining legacy methods (criticalLevel,warningLevel,batteryLevels,setBatteryLevels,drainLimitPph,clampDrainLimit, privateprefs) so the file is internally consistent — a concrete reference application of the corrected convention. (finalon locals stays.)Not in scope: a codebase-wide
final-param sweep. Legacy files migrate incrementally as they're touched, per the convention.Acceptance criteria
finalparameter.AppPrefshas nofinalon parameters;finalon locals unchanged.finalon a parameter is a no-op modifier).