Skip to content

SonarCloud: JavaScript code-quality modernization (×68) #421

Open

Description

@don-petry

JavaScript code-quality modernization

SonarCloud open findings in petry-projects/google-app-scripts — 68 issue(s) grouped as one workstream. Part of the org SonarCloud tuning initiative combsmith/.github#593.

Findings

Rule Count Representative message
javascript:S6582 10 Prefer using an optional chain expression instead, as it's more concise and easier to read
javascript:S7781 9 Prefer String#replaceAll() over String#replace().
javascript:S7764 8 Prefer globalThis over window.
javascript:S7773 5 Prefer Number.parseInt over parseInt.
javascript:S7772 4 Prefer node:fs over fs.
javascript:S8786 4 Simplify this regular expression to reduce its runtime, as it has super-linear performance
javascript:S2486 3 Handle this exception or don't catch it at all.
javascript:S5869 3 Remove duplicates in this character class.
javascript:S3358 2 Extract this nested ternary operation into an independent statement.
javascript:S7735 2 Unexpected negated condition.
css:S7924 2 Text does not meet the minimal contrast requirement with its background.
javascript:S6557 2 Use the 'String#endsWith' method instead.
javascript:S6644 2 Unnecessary use of conditional expression for default assignment.
javascript:S7759 2 Prefer Date.now() over Date#getTime().
javascript:S4624 1 Refactor this code to not use nested template literals.
javascript:S1788 1 Default parameters should be last.
javascript:S1481 1 Remove the declaration of the unused 'safeId' variable.
javascript:S1854 1 Remove this useless assignment to variable "safeId".
javascript:S6353 1 Use concise character class syntax '\w' instead of '[a-zA-Z0-9_]'.
javascript:S7744 1 The empty object is useless.
javascript:S7786 1 new Error() is too unspecific for a type check. Use new TypeError() instead.
javascript:S4138 1 Expected a for-of loop instead of a for loop with this simple iteration.
javascript:S4043 1 Move this array "sort" operation to a separate statement or replace it with "toSorted".
javascript:S7765 1 Use .includes(), rather than .lastIndexOf(), when checking for existence.

Affected files

  • deploy/index.html (20)
  • src/gmail-to-drive-by-labels/src/index.js (9)
  • src/gas-utils.js (8)
  • src/calendar-to-briefing-doc/src/index.js (6)
  • test-utils/setup.js (6)
  • gas-installer/Index.html (5)
  • src/calendar-to-sheets/src/index.js (4)
  • test-utils/mocks.js (3)
  • gas-installer/src/index.js (3)
  • scripts/check-coverage.js (3)
  • src/deploy/index.js (1)

Approach

Apply the flagged idiom fixes: optional chaining (S6582), replaceAll (S7781), globalThis over window (S7764), Number.parseInt (S7773), and the other per-line suggestions. Each carries SonarCloud's exact recommendation. Mechanical; behavior identical.

Acceptance

  • All listed SonarCloud findings for this repo/workstream resolved to zero
  • No behavior change; existing tests/CI green
  • Fixes are real (no blanket NOSONAR unless a confirmed false positive, noted inline)

Filed from the 2026-07-03 org SonarCloud review.

Activity

  1. don-petry commented on Jul 3, 2026

    @don-petry
    CollaboratorAuthor

    Dev-Lead Implementation Plan

    Issue: #421 — SonarCloud: JavaScript code-quality modernization (×68)

    Scope

    Apply SonarCloud's exact per-rule idiom modernizations across the 11 affected files — all behavior-preserving refactors (optional chaining, replaceAll, globalThis, Number.parseInt, node: builtins, TypeError, Date.now, for-of, toSorted, regex simplification, nested-ternary extraction, unused-var removal, conditional-default simplification, endsWith, CSS contrast).

    Implementation Checklist

    • src/gas-utils.js — node:crypto, replaceAll, TypeError, regex super-linear simplification (S8786)
    • src/gmail-to-drive-by-labels/src/index.js — Date.now(), char-class dedupe [\w-], conditional-default ||, toSorted
    • src/calendar-to-briefing-doc/src/index.js — optional chaining / idiom fixes
    • src/calendar-to-sheets/src/index.js — toSorted, char-class / idiom fixes
    • src/deploy/index.js — idiom fix
    • test-utils/setup.js — globalThis, node:crypto
    • test-utils/mocks.js — optional chaining fixes
    • scripts/check-coverage.js — node:fs, node:path, for-of
    • gas-installer/src/index.js — idiom fixes
    • gas-installer/Index.html — replaceAll, optional chaining
    • deploy/index.html — globalThis, Number.parseInt, replaceAll, optional chaining, nested-ternary extraction, remove unused safeId, CSS contrast

    Tests to Write

    • No new tests: these are behavior-preserving refactors (Phase 2 TDD exception). The existing Jest suite + Playwright specs are the regression guard; all must remain green.

    Test Command

    npm test (Jest, includes coverage) and npm run check (prettier + eslint)

  2. don-petry commented on Jul 3, 2026

    @don-petry
    CollaboratorAuthor

    Dev-Lead: issue #421 implementation failed — will retry

    The engine failed (engine-error — e.g. a timeout or transient engine error). This was attempt 1 of 3; dev-lead will retry automatically. You can also re-apply the dev-lead label to retry now.

  3. don-petry commented on Jul 3, 2026

    @don-petry
    CollaboratorAuthor

    Dev-Lead: issue #421 implementation failed — will retry

    The engine failed (engine-error — e.g. a timeout or transient engine error). This was attempt 2 of 3; dev-lead will retry automatically. You can also re-apply the dev-lead label to retry now.

    Last 40 lines of engine output (redacted)
        [copilot] calling gh copilot (model=openai/o4-mini, timeout=600s, flags=--yolo)
    Error: Model "openai/o4-mini" from --model flag is not available.
    
    
  4. don-petry commented on Jul 4, 2026

    @don-petry
    CollaboratorAuthor

    Dev-Lead Implementation Plan

    Issue: #421 — SonarCloud: JavaScript code-quality modernization (×68)

    Scope

    Apply the flagged SonarCloud idiom modernizations (optional chaining, String#replaceAll, globalThis, Number.parseInt, Date.now(), endsWith, concise/dedup char classes, TypeError, no-nested-ternary/template, unused-var removal, etc.) across the 11 affected files. Mechanical, behavior-preserving.

    Implementation Checklist

    • src/gas-utils.js — replaceAll, optional chaining, TypeError
    • src/gmail-to-drive-by-labels/src/index.js — default-assignment, Date.now(), dedup char class
    • src/calendar-to-briefing-doc/src/index.js — optional chaining, misc idioms
    • src/calendar-to-sheets/src/index.js — toSorted, misc idioms
    • src/deploy/index.js — idiom fix
    • gas-installer/src/index.js — endsWith, optional chaining
    • scripts/check-coverage.js — node:fs, for-of
    • test-utils/setup.js, test-utils/mocks.js — optional chaining, misc
    • deploy/index.html — replaceAll, optional chaining, globalThis, Number.parseInt, nested ternary/template, unused safeId
    • gas-installer/Index.html — replaceAll, optional chaining

    Tests to Write

    • Behavior-preserving refactor: no new tests. Existing Jest suite (301 tests) plus prettier/eslint act as the regression guard. .gs files are intentionally untouched (outside the affected-file scope and not scanned).

    Test Command

    npm test (Jest), npm run check (prettier + eslint), bash .dev-lead/scripts/dev-lead-lint.sh

  5. don-petry commented on Jul 4, 2026

    @don-petry
    CollaboratorAuthor

    Dev-Lead: cannot implement issue #421 — needs human attention

    Automatic retries are exhausted (attempt 3 of 3). The most recent failure was engine-error.

    Please review the failures above. To retry anyway, remove the dev-lead:needs-human label and re-apply the dev-lead label.

  6. removed
    dev-leadFor dev-lead agent pickup
    dev-lead:needs-humandev-lead could not complete this issue; needs human attention
    on Jul 15, 2026
  7. don-petry commented on Jul 15, 2026

    @don-petry
    CollaboratorAuthor

    Re-scoped as a parent tracker. The single ×68 issue exhausted dev-lead's 3 retries on 2026-07-04 (mislabeled `engine-error` — the pre-fix deep-impl timeout, since resolved by #1018/#1021 + follow-ups now live on `dev-lead/v1-stable`). Per the split+rescope guidance for oversized issues, this is now broken into three single-concern stories routed to dev-lead individually:

    Routing #442 first to validate the split on the stabilized engine; #443/#444 follow once it lands. dev-lead/dev-lead:needs-human cleared from this tracker so it isn't picked up directly.

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

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions