Skip to content

Address Codacy security findings#107

Open
mason-sharp wants to merge 4 commits intomainfrom
fix/SPOC-467/codacy-security
Open

Address Codacy security findings#107
mason-sharp wants to merge 4 commits intomainfrom
fix/SPOC-467/codacy-security

Conversation

@mason-sharp
Copy link
Copy Markdown
Member

  • Sanitize SQL identifiers in merkle tree queries using pgx.Identifier.Sanitize() instead
    of interpolating raw table names
  • Replace fragile manual string escaping of resolvedAgainstOrigin with strconv.Atoi
    validation
  • Add // nosemgrep annotations to false-positive SQL injection findings (all use
    parameterized queries or sanitized identifiers)
  • Bump Go 1.25.4 → 1.25.9 (CVE-2025-61730, CVE-2026-27142, CVE-2025-61727, CVE-2026-32281,
    CVE-2026-32289, CVE-2026-32288)
  • Bump moby/buildkit v0.27.1 → v0.28.1 (CVE-2026-33747, CVE-2026-33748)
  • Bump grpc v1.79.1 → v1.80.0 (CVE-2026-33186)
  • Bump otel exporters v1.38–1.41 → v1.43.0 (CVE-2026-39882)
  • Pin GitHub Actions to full commit SHAs
  • Add explicit USER nonroot to Dockerfile

Not addressed

Test plan

  • Unit tests pass (go test ./... -short)
  • TestBuildRowHashQuery passes (validates merkle identifier quoting change)
  • Codacy re-scan shows reduced findings

mason-sharp and others added 4 commits April 10, 2026 15:07
…ilter

- buildRowHashQuery, buildFetchRowsSQLSimple, buildFetchRowsSQLComposite
  now take separate schema/table args and quote them with
  pgx.Identifier.Sanitize() instead of interpolating a raw
  QualifiedTableName string.

- buildEffectiveFilter: replace fragile strings.ReplaceAll("'","''")
  escaping of resolvedAgainstOrigin with strconv.Atoi validation. Spock
  node IDs are integers; reject non-numeric values instead of escaping.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
All flagged query sites use pgx.Identifier.Sanitize() for identifiers
and parameterized placeholders ($N) for values. Annotate each with the
specific reason so opengrep suppressions survive line shifts.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
…cies

- go.mod: 1.25.4 → 1.25.9
- release.yaml: goreleaser-cross 1.25.4 → 1.25.8
- test.yml: go-version 1.24 → 1.25
- Pin docker/setup-qemu-action, docker/setup-buildx-action, and
  docker/login-action to full commit SHAs (Codacy supply-chain finding)
- github.com/moby/buildkit v0.27.1 → v0.28.1 (CVE-2026-33747,
  CVE-2026-33748)
- google.golang.org/grpc v1.79.1 → v1.80.0 (CVE-2026-33186)
- go.opentelemetry.io/otel/* v1.38-1.41 → v1.43.0 (CVE-2026-39882)

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@coderabbitai
Copy link
Copy Markdown

coderabbitai bot commented Apr 11, 2026

📝 Walkthrough

Walkthrough

The changes update CI/CD workflows with pinned action versions and Go 1.25, bump Go dependencies including OpenTelemetry and gRPC, add container security hardening with nonroot user, refactor SQL query functions to accept separate schema/table parameters, and suppress static-analysis warnings on database operations.

Changes

Cohort / File(s) Summary
CI/CD Workflows & Toolchain Updates
.github/workflows/release.yaml, .github/workflows/test.yml
Updated Docker setup action pins to specific commit SHAs, bumped GoReleaser cross image from v1.25.4 to v1.25.8, and updated Go version from 1.24 to 1.25.
Go Version and Dependencies
go.mod
Upgraded Go toolchain from 1.25.4 to 1.25.9; updated 15+ indirect dependencies including OpenTelemetry stack (v1.41.0→v1.43.0), gRPC (v1.78.0→v1.80.0), in-toto, sigstore, and golang.org/* packages.
Container Security Hardening
Dockerfile
Added explicit USER nonroot instruction in the runtime stage to enforce non-root execution.
Database Query Security Annotations
db/queries/queries.go, internal/consistency/diff/table_diff.go, internal/consistency/diff/table_rerun.go, internal/consistency/repair/stale_repair.go, internal/consistency/repair/table_repair.go, internal/infra/cdc/listen.go, internal/infra/db/auth.go
Added // nosemgrep inline comments to database execution sites to suppress static-analysis warnings; updated buildEffectiveFilter() to validate numeric node IDs with strconv.Atoi.
SQL Query Refactoring
internal/consistency/mtree/merkle.go, internal/consistency/mtree/merkle_test.go
Refactored buildRowHashQuery, buildFetchRowsSQLSimple, and buildFetchRowsSQLComposite to accept separate schema and table parameters instead of qualified table name strings; updated test cases to match new function signatures.

Poem

🐰 A rabbit's tale of updates spun with care:
From one to nine-point-five, our Go climbs through the air,
Dependencies refresh, security's tight (nonroot for might!),
Schemas and tables now split just right—
With semgrep suppressed, our queries take flight! 🚀

🚥 Pre-merge checks | ✅ 2 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 11.11% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (2 passed)
Check name Status Explanation
Title check ✅ Passed The title accurately summarizes the main change: addressing Codacy security findings through code fixes, dependency updates, and configuration changes across the codebase.
Description check ✅ Passed The description is comprehensive and directly related to the changeset, detailing SQL sanitization improvements, CVE fixes, dependency version bumps, GitHub Actions pinning, and Dockerfile changes that match the file summaries.

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

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch fix/SPOC-467/codacy-security

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.

@codacy-production
Copy link
Copy Markdown

Up to standards ✅

🟢 Issues 0 issues

Results:
0 new issues

View in Codacy

🟢 Metrics 0 complexity · 0 duplication

Metric Results
Complexity 0
Duplication 0

View in Codacy

TIP This summary will be updated as you push new changes. Give us feedback

@mason-sharp mason-sharp changed the title Fix/spoc 467/codacy security Address Codacy security findings Apr 11, 2026
Copy link
Copy Markdown

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

🧹 Nitpick comments (3)
internal/consistency/mtree/merkle.go (1)

379-388: Scope no semgrep suppressions to specific rule IDs.

Line 379/388/442/451/474/483 use broad suppression comments. Prefer rule-targeted suppressions plus a short reason so future unrelated findings on these lines aren’t accidentally masked.

Example refinement
- rowsH1, err := pool1.Query(m.Ctx, rowHashQuery, args...) // nosemgrep
+ rowsH1, err := pool1.Query(m.Ctx, rowHashQuery, args...) // nosemgrep: go.lang.security.sql-injection -- identifiers are sanitized with pgx.Identifier.Sanitize and values are parameterized

Also applies to: 442-452, 474-484

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

In `@internal/consistency/mtree/merkle.go` around lines 379 - 388, The broad "//
nosemgrep" suppressions on the pool1.Query and pool2.Query calls (and the other
occurrences noted) should be scoped to specific rule IDs and include a short
reason; replace each bare "// nosemgrep" comment with a targeted form like "//
nosemgrep:<RULE-ID> -- <short reason>" (e.g., reference the call sites
pool1.Query, pool2.Query, the m.Ctx usage, and the rowHashQuery/readRowHashes
logic) so only the intended Semgrep rule is suppressed and future findings
aren’t masked; update all occurrences mentioned (the lines around the
pool1.Query/pool2.Query blocks and the similar places referenced) to follow this
pattern.
internal/consistency/mtree/merkle_test.go (1)

37-160: Add one regression case for identifier-quoting behavior.

Given the security goal of this change, add a test that asserts schema/table identifiers are always quoted/sanitized (e.g., mixed-case or embedded quotes) to lock this behavior in.

Example test case addition
 tests := []struct {
   name           string
   schema         string
   table          string
@@
 }{
+  {
+    name:        "schema/table identifiers are sanitized",
+    schema:      `Public`,
+    table:       `Order"Items`,
+    key:         []string{"id"},
+    cols:        []string{"id"},
+    whereClause: "TRUE",
+    colTypes:    nil,
+    wantContains: []string{
+      `FROM "Public"."Order""Items"`,
+    },
+    wantOrderBy: `"id"`,
+  },
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@internal/consistency/mtree/merkle_test.go` around lines 37 - 160, Add a
regression test case to TestBuildRowHashQuery that verifies schema/table
identifiers are always quoted and sanitized: add a test entry (e.g., name
"identifier quoting", schema with mixed-case and an embedded quote like
`MiXeD"Sch`, table like `weird"Table`, key e.g., ["id"], cols include "id") and
assert the returned query contains the properly double-quoted/escaped schema and
table (e.g., quotes around identifiers and internal quotes doubled), that ORDER
BY uses the quoted key, and that buildRowHashQuery is used to generate the query
and orderBy to validate the exact quoted identifiers.
.github/workflows/test.yml (1)

20-20: Use go-version-file: go.mod to keep workflow Go version in sync with the module.

Currently pinning 1.25 while go.mod requires 1.25.9. This allows patch drift and reduces reproducibility. Either use go-version-file: go.mod or explicitly pin to 1.25.9.

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

In @.github/workflows/test.yml at line 20, The workflow currently pins
go-version: '1.25' which can drift from the module's exact runtime; update the
step to either use go-version-file: go.mod so the runner reads the Go version
from your module or explicitly pin go-version to '1.25.9' to match go.mod;
change the key from go-version to go-version-file: go.mod (or set go-version:
'1.25.9') in the job that defines the Go setup.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In @.github/workflows/release.yaml:
- Line 34: Update the GoReleaser cross image tag to match the Go version in
go.mod: replace the goreleaser image tag "v1.25.8" with "v1.25.9" (the tag shown
as goreleaser/goreleaser-cross:v1.25.8) so the workflow's toolchain aligns with
the Go version declared in go.mod (Go 1.25.9); ensure the updated tag appears
wherever goreleaser/goreleaser-cross is referenced in the workflow.

In `@internal/consistency/diff/table_diff.go`:
- Line 338: The nosemgrep suppressions hide a real SQL injection:
buildEffectiveFilter() currently constructs EffectiveFilter by
string-concatenating user-provided TableFilter and that raw string is embedded
into SQL via templates and fmt.Sprintf in the queries executed (see the
pool.QueryRow/Query calls that reference EffectiveFilter and the templates in
db/queries/templates.go). Fix by removing the suppressions and replacing string
embedding with a safe approach: change buildEffectiveFilter() to either (A)
parse/validate the incoming TableFilter against a strict
whitelist/SQL-expression grammar (or build an AST) and produce a parameterized
predicate plus a slice of parameters, or (B) refactor the API to accept
structured filter objects (column/operator/value) and build the WHERE clause
using placeholders. Then update the query templates and the code paths that call
pool.QueryRow / pool.Query (the functions that currently fmt.Sprintf
EffectiveFilter into SQL) to use prepared/parameterized queries and pass the
parameters instead of injecting the raw string. Also add input validation in the
HTTP handler that accepts TableFilter to reject anything not matching the
allowed grammar/whitelist.

---

Nitpick comments:
In @.github/workflows/test.yml:
- Line 20: The workflow currently pins go-version: '1.25' which can drift from
the module's exact runtime; update the step to either use go-version-file:
go.mod so the runner reads the Go version from your module or explicitly pin
go-version to '1.25.9' to match go.mod; change the key from go-version to
go-version-file: go.mod (or set go-version: '1.25.9') in the job that defines
the Go setup.

In `@internal/consistency/mtree/merkle_test.go`:
- Around line 37-160: Add a regression test case to TestBuildRowHashQuery that
verifies schema/table identifiers are always quoted and sanitized: add a test
entry (e.g., name "identifier quoting", schema with mixed-case and an embedded
quote like `MiXeD"Sch`, table like `weird"Table`, key e.g., ["id"], cols include
"id") and assert the returned query contains the properly double-quoted/escaped
schema and table (e.g., quotes around identifiers and internal quotes doubled),
that ORDER BY uses the quoted key, and that buildRowHashQuery is used to
generate the query and orderBy to validate the exact quoted identifiers.

In `@internal/consistency/mtree/merkle.go`:
- Around line 379-388: The broad "// nosemgrep" suppressions on the pool1.Query
and pool2.Query calls (and the other occurrences noted) should be scoped to
specific rule IDs and include a short reason; replace each bare "// nosemgrep"
comment with a targeted form like "// nosemgrep:<RULE-ID> -- <short reason>"
(e.g., reference the call sites pool1.Query, pool2.Query, the m.Ctx usage, and
the rowHashQuery/readRowHashes logic) so only the intended Semgrep rule is
suppressed and future findings aren’t masked; update all occurrences mentioned
(the lines around the pool1.Query/pool2.Query blocks and the similar places
referenced) to follow this pattern.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 27132716-a2e4-4d98-a891-f4ede8ee17bf

📥 Commits

Reviewing files that changed from the base of the PR and between cf8794d and 419381a.

⛔ Files ignored due to path filters (1)
  • go.sum is excluded by !**/*.sum
📒 Files selected for processing (13)
  • .github/workflows/release.yaml
  • .github/workflows/test.yml
  • Dockerfile
  • db/queries/queries.go
  • go.mod
  • internal/consistency/diff/table_diff.go
  • internal/consistency/diff/table_rerun.go
  • internal/consistency/mtree/merkle.go
  • internal/consistency/mtree/merkle_test.go
  • internal/consistency/repair/stale_repair.go
  • internal/consistency/repair/table_repair.go
  • internal/infra/cdc/listen.go
  • internal/infra/db/auth.go

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.

1 participant