Skip to content

t1323: Fix TTSR shell-local-params rule false-positives on currency/pricing text#2296

Merged
marcusquinn merged 1 commit intomainfrom
bugfix/ttsr-currency-false-positives
Feb 25, 2026
Merged

t1323: Fix TTSR shell-local-params rule false-positives on currency/pricing text#2296
marcusquinn merged 1 commit intomainfrom
bugfix/ttsr-currency-false-positives

Conversation

@marcusquinn
Copy link
Owner

@marcusquinn marcusquinn commented Feb 25, 2026

Summary

  • Expanded negative lookaheads in the shell-local-params TTSR rule regex to exclude currency/pricing patterns that were causing false-positives
  • Fixed across all three enforcement points: TTSR plugin (index.mjs), linters-local.sh, and pre-commit-hook.sh
  • Added exclusions for: pipe characters (markdown table cells), and 20+ common currency/pricing unit words (per, mo, month, year, flat, each, fee, plan, tier, user, seat, etc.)

Problem

The regex $[1-9] in the shell-local-params rule was matching dollar amounts like $5 per month, $9 mo, $3 monthly in markdown tables and pricing documentation. The existing negative lookahead (?![0-9.,/]) only excluded multi-digit amounts ($28) and amounts with decimals/commas/slashes ($1.99, $1,000, $5/mo), but not standalone single-digit amounts followed by currency unit words.

Testing

Verified with 28 test cases covering:

  • True positives: bare $1-$9 in shell commands (still correctly detected)
  • True negatives: currency amounts with digits/decimals/commas/slashes (still excluded)
  • New true negatives: $5 per month, $9 mo, $3 monthly, $7 annual, $5 flat, $1 trial, pipe-delimited table cells, etc.

All 28 tests pass with zero failures. ShellCheck and Node syntax checks pass clean.

Closes #2194

Summary by CodeRabbit

Release Notes

  • Bug Fixes
    • Reduced false positives in linting validation by properly handling Markdown table syntax and currency/pricing patterns.
    • Improved parameter validation to correctly recognize legitimate parameter usage in additional contexts.

…alse-positives

The shell-local-params TTSR rule regex $[1-9] was matching dollar amounts
like $5/mo, $9 per month in markdown tables and pricing text. Expanded
negative lookaheads across all three enforcement points (TTSR plugin,
linters-local.sh, pre-commit-hook.sh) to exclude:
- $[1-9] followed by pipe (markdown table cell boundary)
- $[1-9] followed by common currency unit words (per, mo, month, year,
  flat, each, off, fee, plan, tier, user, seat, unit, addon, setup,
  trial, credit, annual, quarterly, monthly)

Closes #2194
@gemini-code-assist
Copy link

Summary of Changes

Hello @marcusquinn, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed!

This pull request refines the shell-local-params linter rule to significantly reduce false positives when detecting direct usage of positional parameters in shell scripts. By enhancing the regular expressions to intelligently ignore common currency and pricing text, as well as markdown table formatting, the change ensures the linter accurately identifies problematic shell code without flagging legitimate documentation or pricing examples.

Highlights

  • Regex Expansion: Expanded negative lookaheads in the shell-local-params TTSR rule regex to prevent false positives on currency and pricing patterns.
  • Broad Application: Applied the fix across all three enforcement points: the TTSR plugin (index.mjs), linters-local.sh, and pre-commit-hook.sh.
  • New Exclusions: Introduced exclusions for pipe characters (markdown table cells) and over 20 common currency/pricing unit words (e.g., per, mo, month, year, flat, each, fee, plan, tier, user, seat).
Changelog
  • .agents/plugins/opencode-aidevops/index.mjs
    • Modified the pattern regex for the shell-local-params rule to include new negative lookaheads.
    • Added (?!\s*[|]) to exclude pipe characters.
    • Added (?!\s+(?:per|mo(?:nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)\b) to exclude common currency/pricing unit words.
  • .agents/scripts/linters-local.sh
    • Added new awk patterns to skip lines containing $N followed by a pipe character (/\$[1-9][[:space:]]*\|/).
    • Added new awk patterns to skip lines containing $N followed by common currency/pricing unit words, both with trailing punctuation/space and at the end of the line.
  • .agents/scripts/pre-commit-hook.sh
    • Updated the grep -vE command within the validate_positional_parameters function to include new exclusion patterns.
    • Added '\$[1-9]\s*\|' to exclude pipe characters.
    • Added '\$[1-9]\s+(per|mo(nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)\b' to exclude common currency/pricing unit words.
Activity
  • No human activity has occurred on this pull request yet.
Using Gemini Code Assist

The full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips.

Invoking Gemini

You can request assistance from Gemini at any point by creating a comment using either /gemini <command> or @gemini-code-assist <command>. Below is a summary of the supported commands on the current page.

Feature Command Description
Code Review /gemini review Performs a code review for the current pull request in its current state.
Pull Request Summary /gemini summary Provides a summary of the current pull request in its current state.
Comment @gemini-code-assist Responds in comments when explicitly tagged, both in pull request comments and review comments.
Help /gemini help Displays a list of available commands.

Customization

To customize Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a .gemini/ folder in the base of the repository. Detailed instructions can be found here.

Limitations & Feedback

Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counter productive. You can react with 👍 and 👎 on @gemini-code-assist comments. If you're interested in giving your feedback about your experience with Gemini Code Assist for Github and other Google products, sign up here.

You can also get AI-powered code generation, chat, as well as code reviews directly in the IDE at no cost with the Gemini Code Assist IDE Extension.

Footnotes

  1. Review the Privacy Notices, Generative AI Prohibited Use Policy, Terms of Service, and learn how to configure Gemini Code Assist in GitHub here. Gemini can make mistakes, so double check it and use code with caution.

@coderabbitai
Copy link
Contributor

coderabbitai bot commented Feb 25, 2026

Walkthrough

Three shell script linting files are updated to fix false positives in the shell-local-params rule. The pattern for detecting positional parameters ($[1-9]) is tightened by excluding matches containing pipe characters (markdown table boundaries) and common currency/pricing units (per, mo, month, year, etc.).

Changes

Cohort / File(s) Summary
Shell-Local-Params Rule Tightening
.agents/plugins/opencode-aidevops/index.mjs, .agents/scripts/linters-local.sh, .agents/scripts/pre-commit-hook.sh
Consistent pattern refinements across all three files to exclude false positives on currency/pricing text and markdown table syntax by rejecting lines containing pipe characters or common pricing unit keywords. Negative filters added to regex matching logic without altering core detection flow.

Estimated code review effort

🎯 2 (Simple) | ⏱️ ~8 minutes

Possibly related PRs

  • #2203: Modifies the same shell-local-params TTSR rule pattern in index.mjs to reduce false positives with aligned pattern tightening.
  • #2139: Directly affects the same shell-local-params rule and related filtering logic that this PR refines.

Poem

💰 No more false alarms on your pricing display,
Markdown tables pass through without delay,
Pipes and units now safely ignored,
Shell scripts clean—A-grade restored! ✨

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title directly and specifically describes the main change: fixing false-positives in the shell-local-params TTSR rule for currency/pricing patterns.
Linked Issues check ✅ Passed All coding requirements from issue #2194 are met: regex exclusions for currency/pricing patterns and markdown tables are implemented across all three modified files, with comprehensive test coverage.
Out of Scope Changes check ✅ Passed All changes are directly aligned with fixing false-positives in the shell-local-params rule; no unrelated modifications are present.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
  • 📝 Generate docstrings (stacked PR)
  • 📝 Generate docstrings (commit on current branch)
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch bugfix/ttsr-currency-false-positives

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

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

@github-actions
Copy link

🔍 Code Quality Report

�[0;35m[MONITOR]�[0m Code Review Monitoring Report

�[0;34m[INFO]�[0m Latest Quality Status:
SonarCloud: 0 bugs, 0 vulnerabilities, 90 code smells

�[0;34m[INFO]�[0m Recent monitoring activity:
Wed Feb 25 17:29:22 UTC 2026: Code review monitoring started
Wed Feb 25 17:29:22 UTC 2026: SonarCloud - Bugs: 0, Vulnerabilities: 0, Code Smells: 90

📈 Current Quality Metrics

  • BUGS: 0
  • CODE SMELLS: 90
  • VULNERABILITIES: 0

Generated on: Wed Feb 25 17:29:25 UTC 2026


Generated by AI DevOps Framework Code Review Monitoring

@sonarqubecloud
Copy link

Copy link

@gemini-code-assist gemini-code-assist bot left a comment

Choose a reason for hiding this comment

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

Code Review

This pull request effectively addresses false-positives in the shell-local-params rule by enhancing the detection regex to ignore common currency and pricing patterns. The changes are consistently applied across the TTSR plugin, local linter, and pre-commit hook. My review focuses on improving the maintainability of these new regular expressions and shell script logic, applying repository-specific optimization rules. I've identified opportunities to reduce code duplication and improve efficiency in linters-local.sh and pre-commit-hook.sh, which will make the code more efficient and easier to manage in the future. I've also suggested minor simplifications to the regular expressions themselves for conciseness.

Comment on lines +83 to 87
if [[ -f "$file" ]] && grep -n '\$[1-9]' "$file" | grep -v 'local.*=.*\$[1-9]' | grep -vE '\$[1-9][0-9.,/]' | grep -vE '\$[1-9]\s*\|' | grep -vE '\$[1-9]\s+(per|mo(nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)\b' >/dev/null; then
print_error "Direct positional parameter usage in $file"
grep -n '\$[1-9]' "$file" | grep -v 'local.*=.*\$[1-9]' | grep -vE '\$[1-9][0-9.,/]' | head -3
grep -n '\$[1-9]' "$file" | grep -v 'local.*=.*\$[1-9]' | grep -vE '\$[1-9][0-9.,/]' | grep -vE '\$[1-9]\s*\|' | grep -vE '\$[1-9]\s+(per|mo(nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)\b' | head -3
((violations++))
fi

Choose a reason for hiding this comment

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

high

The long grep pipeline is executed twice: once in the if condition to check for violations, and then again to print the first few violating lines. This is inefficient and creates significant code duplication, making the script harder to maintain. A better approach is to run the pipeline once, store its output in a variable, and then use that variable for both the check and the output. This improves performance and eliminates the duplicated code.

Suggested change
if [[ -f "$file" ]] && grep -n '\$[1-9]' "$file" | grep -v 'local.*=.*\$[1-9]' | grep -vE '\$[1-9][0-9.,/]' | grep -vE '\$[1-9]\s*\|' | grep -vE '\$[1-9]\s+(per|mo(nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)\b' >/dev/null; then
print_error "Direct positional parameter usage in $file"
grep -n '\$[1-9]' "$file" | grep -v 'local.*=.*\$[1-9]' | grep -vE '\$[1-9][0-9.,/]' | head -3
grep -n '\$[1-9]' "$file" | grep -v 'local.*=.*\$[1-9]' | grep -vE '\$[1-9][0-9.,/]' | grep -vE '\$[1-9]\s*\|' | grep -vE '\$[1-9]\s+(per|mo(nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)\b' | head -3
((violations++))
fi
if [[ -f "$file" ]]; then
local violations_output
violations_output=$(grep -n '\$[1-9]' "$file" | grep -v 'local.*=.*\$[1-9]' | grep -vE '\$[1-9][0-9.,/]' | grep -vE '\$[1-9]\s*\|' | grep -vE '\$[1-9]\s+(per|mo(nth)?|y(ea)?r|day|week|h(ou)?r|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)\b')
if [[ -n "$violations_output" ]]; then
print_error "Direct positional parameter usage in $file"
echo "$violations_output" | head -3
((violations++))
fi
fi
References
  1. The principle of consolidating multiple executions of a command/pipeline into a single pass to improve performance and efficiency applies here, even though it's a grep pipeline instead of jq.
  2. Storing the output of the grep pipeline in violations_output before using it multiple times is analogous to moving a loop-invariant calculation outside a loop, as it avoids redundant computation/execution and improves efficiency.

// - $[1-9] followed by digits, decimal, comma, or slash (e.g. $28/mo, $1.99, $1,000)
// - $[1-9] followed by pipe (markdown table cell boundary)
// - $[1-9] followed by common currency/pricing unit words (per, mo, month, flat, etc.)
pattern: "^\\s+(?:echo|printf|return|if|\\[\\[).*\\$[1-9](?![0-9.,/])(?!\\s*[|])(?!\\s+(?:per|mo(?:nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)\\b)(?!.*local\\s+\\w+=)",

Choose a reason for hiding this comment

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

medium

For improved readability and maintainability of this complex regular expression, you can make it more concise by grouping related alternatives. For example, year|yr can be combined into y(?:ea)?r, and hr|hour can be h(?:ou)?r. This makes the pattern slightly shorter and easier to parse visually.

Suggested change
pattern: "^\\s+(?:echo|printf|return|if|\\[\\[).*\\$[1-9](?![0-9.,/])(?!\\s*[|])(?!\\s+(?:per|mo(?:nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)\\b)(?!.*local\\s+\\w+=)",
pattern: "^\\s+(?:echo|printf|return|if|\\[\\[).*\\$[1-9](?![0-9.,/])(?!\\s*[|])(?!\\s+(?:per|mo(?:nth)?|y(?:ea)?r|day|week|h(?:ou)?r|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)\\b)(?!.*local\\s+\\w+=)",

Comment on lines +195 to +196
/\$[1-9][[:space:]]+(per|mo(nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)[[:space:][:punct:]]/ { next }
/\$[1-9][[:space:]]+(per|mo(nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)$/ { next }

Choose a reason for hiding this comment

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

medium

These two lines are nearly identical, with the only difference being the match at the end of the line ([[:space:][:punct:]] vs. $). You can combine them into a single, more maintainable rule by using an alternation ([[:space:][:punct:]]|$). This avoids duplicating the long list of keywords and makes future updates easier. I've also included a small simplification for the keywords themselves.

Suggested change
/\$[1-9][[:space:]]+(per|mo(nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)[[:space:][:punct:]]/ { next }
/\$[1-9][[:space:]]+(per|mo(nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)$/ { next }
/\$[1-9][[:space:]]+(per|mo(nth)?|y(ea)?r|day|week|h(ou)?r|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)([[:space:][:punct:]]|$)/ { next }

@augmentcode
Copy link

augmentcode bot commented Feb 25, 2026

🤖 Augment PR Summary

Summary: Reduces false-positives in the shell-local-params TTSR rule by expanding currency/pricing exclusions around bare $1$9 patterns.
Changes: Updates the plugin regex and both local/pre-commit enforcement scripts to ignore common pricing formats (decimals/slashes) plus table pipes and unit words (per/mo/month/year/etc.).

🤖 Was this summary useful? React with 👍 or 👎

Copy link

@augmentcode augmentcode bot left a comment

Choose a reason for hiding this comment

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

Review completed. 2 suggestions posted.

Fix All in Augment

Comment augment review to trigger a new review at any time.

// - $[1-9] followed by digits, decimal, comma, or slash (e.g. $28/mo, $1.99, $1,000)
// - $[1-9] followed by pipe (markdown table cell boundary)
// - $[1-9] followed by common currency/pricing unit words (per, mo, month, flat, etc.)
pattern: "^\\s+(?:echo|printf|return|if|\\[\\[).*\\$[1-9](?![0-9.,/])(?!\\s*[|])(?!\\s+(?:per|mo(?:nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)\\b)(?!.*local\\s+\\w+=)",
Copy link

Choose a reason for hiding this comment

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

The new (?!\\s*[|]) exclusion will also suppress matches for real shell pipelines like echo $1 | ..., potentially turning true violations into false negatives. Is that tradeoff intended, given | is common shell syntax and not unique to markdown tables?

Severity: medium

Other Locations
  • .agents/scripts/linters-local.sh:194
  • .agents/scripts/pre-commit-hook.sh:83

Fix This in Augment

🤖 Was this useful? React with 👍 or 👎, or 🚀 if it prevented an incident/outage.

if [[ -f "$file" ]] && grep -n '\$[1-9]' "$file" | grep -v 'local.*=.*\$[1-9]' | grep -vE '\$[1-9][0-9.,/]' >/dev/null; then
# slash (e.g. $28/mo, $1.99, $1,000), pipe (markdown table cell), or common
# currency/pricing unit words (per, mo, month, flat, etc.).
if [[ -f "$file" ]] && grep -n '\$[1-9]' "$file" | grep -v 'local.*=.*\$[1-9]' | grep -vE '\$[1-9][0-9.,/]' | grep -vE '\$[1-9]\s*\|' | grep -vE '\$[1-9]\s+(per|mo(nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)\b' >/dev/null; then
Copy link

Choose a reason for hiding this comment

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

grep -E (ERE/POSIX) doesn’t reliably support escapes like \\s and \\b, so these new exclusions may not work and could reintroduce the currency false-positives this PR is trying to eliminate. This affects both the if check and the diagnostic pipeline below.

Severity: high

Other Locations
  • .agents/scripts/pre-commit-hook.sh:85

Fix This in Augment

🤖 Was this useful? React with 👍 or 👎, or 🚀 if it prevented an incident/outage.

@marcusquinn marcusquinn merged commit bcf95b6 into main Feb 25, 2026
22 of 23 checks passed
Copy link
Contributor

@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: 1

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
.agents/plugins/opencode-aidevops/index.mjs (1)

787-811: ⚠️ Potential issue | 🟠 Major

validatePositionalParams is missing the new pipe and pricing-unit exclusions added to the TTSR rule.

The TTSR shell-local-params pattern now skips lines that contain $N | (pipe) and $N per/mo/month/… (pricing units), but the inline validatePositionalParams function (used by the hard quality gate in tool.execute.before) still only has the old digit/decimal exclusion on line 800:

if (/\$[1-9][0-9.,/]/.test(trimmed)) {
  continue;
}

The pipe and pricing-unit cases will continue to trigger false-positive violations in the inline gate even though they are now suppressed in the TTSR rule — the two enforcement paths are out of sync.

🐛 Proposed fix — bring validatePositionalParams in line with the TTSR rule
-        // Skip currency/pricing patterns: $[1-9] followed by digits, decimal, comma,
-        // or slash (e.g. $28/mo, $1.99, $1,000) — false-positives in markdown tables.
-        if (/\$[1-9][0-9.,/]/.test(trimmed)) {
-          continue;
-        }
+        // Skip currency/pricing patterns: $[1-9] followed by digits, decimal, comma, slash,
+        // pipe (markdown table boundary), or a common pricing-unit word (per, mo, month, …).
+        if (/\$[1-9][0-9.,/]/.test(trimmed)) continue;
+        if (/\$[1-9]\s*\|/.test(trimmed)) continue;
+        if (/\$[1-9]\s+(?:per|mo(?:nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)\b/.test(trimmed)) continue;
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In @.agents/plugins/opencode-aidevops/index.mjs around lines 787 - 811, The
inline validatePositionalParams function is out-of-sync with the TTSR rule:
replace the current exclusion that checks /\$[1-9][0-9.,/]/ (the check inside
validatePositionalParams) with an updated pattern that also ignores pipes and
pricing-unit suffixes (e.g. "$N |" and "$N per/mo/month/yr/year" variants) so
the function continues when a positional-parameter token is followed by digits,
decimal, comma, slash, a pipe character, or common pricing unit words; keep the
existing continue behavior and update only the regex used in
validatePositionalParams to mirror the TTSR shell-local-params exclusions.
🧹 Nitpick comments (1)
.agents/scripts/linters-local.sh (1)

194-196: LGTM — new awk exclusion rules are correct and idiomatic.

Using POSIX character classes ([[:space:]], [[:punct:]]) and the ERE mo(nth)? optional group is portable across macOS and Linux awk. The two-pattern approach (trailing space/punct vs. EOL) correctly handles both mid-line and end-of-line pricing phrases.

As a minor optional nicety, the two unit-word patterns could be merged into one:

♻️ Optional: collapse lines 195-196 into a single pattern
-            /\$[1-9][[:space:]]+(per|mo(nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)[[:space:][:punct:]]/ { next }
-            /\$[1-9][[:space:]]+(per|mo(nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)$/ { next }
+            /\$[1-9][[:space:]]+(per|mo(nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)([[:space:][:punct:]]|$)/ { next }
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In @.agents/scripts/linters-local.sh around lines 194 - 196, Merge the two awk
exclusion patterns that match dollar amounts with unit words (the two patterns
in .agents/scripts/linters-local.sh that begin with the price matcher for unit
words) into a single pattern: keep the same unit-word alternation and POSIX
classes ([[:space:]] and [[:punct:]]) but combine the "followed by space/punct"
and "end-of-line" cases into one expression by making the trailing separator a
single alternation/optional group (separator or EOL), then replace the two
separate / { next } rules with one consolidated / { next } rule so behavior is
unchanged but the rule is collapsed.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In @.agents/scripts/pre-commit-hook.sh:
- Around line 83-85: Replace the duplicated grep pipeline by capturing its
output into a variable (e.g., matches) and reusing that variable for the
existence check and printing; specifically, run the pipeline that starts with
grep -n '\$[1-9]' "$file" and the subsequent grep -v/grep -vE filters once,
assign its (possibly empty) result to matches (use "|| true" to avoid non-zero
exit), then change the if condition to check [[ -f "$file" ]] && [[ -n
"$matches" ]], call print_error "Direct positional parameter usage in $file",
echo "$matches" | head -3, and increment ((violations++)); update references to
the original duplicated pipeline locations to use matches instead.

---

Outside diff comments:
In @.agents/plugins/opencode-aidevops/index.mjs:
- Around line 787-811: The inline validatePositionalParams function is
out-of-sync with the TTSR rule: replace the current exclusion that checks
/\$[1-9][0-9.,/]/ (the check inside validatePositionalParams) with an updated
pattern that also ignores pipes and pricing-unit suffixes (e.g. "$N |" and "$N
per/mo/month/yr/year" variants) so the function continues when a
positional-parameter token is followed by digits, decimal, comma, slash, a pipe
character, or common pricing unit words; keep the existing continue behavior and
update only the regex used in validatePositionalParams to mirror the TTSR
shell-local-params exclusions.

---

Nitpick comments:
In @.agents/scripts/linters-local.sh:
- Around line 194-196: Merge the two awk exclusion patterns that match dollar
amounts with unit words (the two patterns in .agents/scripts/linters-local.sh
that begin with the price matcher for unit words) into a single pattern: keep
the same unit-word alternation and POSIX classes ([[:space:]] and [[:punct:]])
but combine the "followed by space/punct" and "end-of-line" cases into one
expression by making the trailing separator a single alternation/optional group
(separator or EOL), then replace the two separate / { next } rules with one
consolidated / { next } rule so behavior is unchanged but the rule is collapsed.

ℹ️ Review info

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 2e99667 and 17dbe70.

📒 Files selected for processing (3)
  • .agents/plugins/opencode-aidevops/index.mjs
  • .agents/scripts/linters-local.sh
  • .agents/scripts/pre-commit-hook.sh

Comment on lines +83 to +85
if [[ -f "$file" ]] && grep -n '\$[1-9]' "$file" | grep -v 'local.*=.*\$[1-9]' | grep -vE '\$[1-9][0-9.,/]' | grep -vE '\$[1-9]\s*\|' | grep -vE '\$[1-9]\s+(per|mo(nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)\b' >/dev/null; then
print_error "Direct positional parameter usage in $file"
grep -n '\$[1-9]' "$file" | grep -v 'local.*=.*\$[1-9]' | grep -vE '\$[1-9][0-9.,/]' | head -3
grep -n '\$[1-9]' "$file" | grep -v 'local.*=.*\$[1-9]' | grep -vE '\$[1-9][0-9.,/]' | grep -vE '\$[1-9]\s*\|' | grep -vE '\$[1-9]\s+(per|mo(nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)\b' | head -3
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

🧩 Analysis chain

🏁 Script executed:

# First, find and read the pre-commit-hook.sh file
find . -name "pre-commit-hook.sh" -type f

Repository: marcusquinn/aidevops

Length of output: 100


🏁 Script executed:

# Read the file around the reported lines
if [ -f ".agents/scripts/pre-commit-hook.sh" ]; then
  wc -l ".agents/scripts/pre-commit-hook.sh"
fi

Repository: marcusquinn/aidevops

Length of output: 102


🏁 Script executed:

# Get context around lines 80-85
if [ -f ".agents/scripts/pre-commit-hook.sh" ]; then
  sed -n '75,90p' ".agents/scripts/pre-commit-hook.sh"
fi

Repository: marcusquinn/aidevops

Length of output: 1083


🌐 Web query:

macOS BSD grep \s \b support extended regular expressions ERE compatibility

💡 Result:

On macOS’s default (BSD/Apple) grep, -E enables POSIX ERE, but grep also enables Apple’s “enhanced” regex features from re_format(7), which include the shortcuts and assertions you’re asking about:

  • \s / \S are supported as enhanced shortcuts (\s[[:space:]]). [1]
  • \b / \B are supported as enhanced word-boundary assertions (and \</\> are available too, with [[:<:]] / [[:>:]] equivalents). [1]
  • This is not POSIX ERE portability: many greps treat \s and \b as non-special (Autoconf explicitly warns they’re nonportable). [2]

If you need portable ERE, use:

  • whitespace: [[:space:]]
  • word boundaries (BSD-style): [[:<:]]word[[:>:]] (or use grep -w for whole words when that’s sufficient). [1]

Also note: other macOS tools (notably sed, find -E -regex) may not be compiled with the enhanced flag even though re_format(7) documents it, so \s/\b can fail there—grep is the common one that does work. [3]

Sources:
[1] macOS re_format(7) (“ENHANCED FEATURES”: \s, \b, \</\> and their [[:...:]] equivalents) https://www.unix.com/man-page/osx/7/re_format
[2] GNU Autoconf manual: portability warning to avoid \b, \s, etc. https://www.gnu.org/software/autoconf/manual/autoconf-2.65/html_node/Limitations-of-Usual-Tools.html
[3] Discussion of macOS enhanced vs extended support and that grep supports enhanced features while some other tools don’t https://stackoverflow.com/questions/12178924/os-x-sed-e-doesnt-accept-extended-regular-expressions


🏁 Script executed:

# Check if ShellCheck is available and run it on the file
which shellcheck || echo "ShellCheck not available"
if command -v shellcheck &> /dev/null; then
  shellcheck ".agents/scripts/pre-commit-hook.sh" || true
fi

Repository: marcusquinn/aidevops

Length of output: 149


🏁 Script executed:

# Also check the specific lines for context and verify the duplication more clearly
sed -n '76,90p' ".agents/scripts/pre-commit-hook.sh" | cat -n

Repository: marcusquinn/aidevops

Length of output: 1168


Refactor the grep pipeline to eliminate duplication and improve readability, but note that \s and \b work on macOS.

While \s and \b are supported by macOS BSD grep as enhanced regex features (per re_format(7)), the grep pipeline duplicated on lines 83 and 85 violates the DRY principle and creates a maintenance liability. If either line changes, the other must be manually updated or behavior diverges silently.

Extract the grep result into a variable to eliminate duplication:

local matches
matches=$(grep -n '\$[1-9]' "$file" \
	| grep -v 'local.*=.*\$[1-9]' \
	| grep -vE '\$[1-9][0-9.,/]' \
	| grep -vE '\$[1-9]\s*\|' \
	| grep -vE '\$[1-9]\s+(per|mo(nth)?|year|yr|day|week|hr|hour|flat|each|off|fee|plan|tier|user|seat|unit|addon|setup|trial|credit|annual|quarterly|monthly)\b' \
	|| true)
if [[ -f "$file" ]] && [[ -n "$matches" ]]; then
	print_error "Direct positional parameter usage in $file"
	echo "$matches" | head -3
	((violations++))
fi

This also improves readability by breaking the long pipeline into logical sections.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In @.agents/scripts/pre-commit-hook.sh around lines 83 - 85, Replace the
duplicated grep pipeline by capturing its output into a variable (e.g., matches)
and reusing that variable for the existence check and printing; specifically,
run the pipeline that starts with grep -n '\$[1-9]' "$file" and the subsequent
grep -v/grep -vE filters once, assign its (possibly empty) result to matches
(use "|| true" to avoid non-zero exit), then change the if condition to check [[
-f "$file" ]] && [[ -n "$matches" ]], call print_error "Direct positional
parameter usage in $file", echo "$matches" | head -3, and increment
((violations++)); update references to the original duplicated pipeline
locations to use matches instead.

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.

t1323: Fix TTSR shell-local-params rule false-positives on currency/pricing text

1 participant