Skip to content

docs: record prompt injection hardening (2026-03-06) - #7

Merged
twistedmelonman merged 2 commits into
mainfrom
claude/security-prompt-injection-hardening-docs-20260306
Mar 7, 2026
Merged

twistedmelonman merged 2 commits into
mainfrom
claude/security-prompt-injection-hardening-docs-20260306

Conversation

@twistedmelonman

Copy link
Copy Markdown
Member

Summary

  • Adds docs/plans/2026-03-06-prompt-injection-hardening.md documenting the security audit and remediation applied across 11 repos on 2026-03-06
  • Links to the clinejection article that triggered the audit
  • Records the vulnerability (no author_association guard on claude.yml issue triggers), the fix, and commit SHAs for all patched repos

Context

The actual security fixes were applied directly to each repo's main branch via the GitHub API (owner-authorized, no CI gating). This PR is documentation only — it records what was done and why for audit trail purposes.

Repos patched (10 × claude.yml, 1 × claude-assistant.yml):

  • smartwatermelon: github-workflows, claude-wrapper
  • nightowlstudiollc: juliet-cleaning, vpn-lan-bridge, yesteryear, financial-agent, amelia-boone, kebab-tax, kebab-tax-netlify, night-owl-studio, photo-game-poc

Test plan

  • Verify the linked article URL resolves
  • Spot-check one or two commit SHAs from the table against the respective repos

🤖 Generated with Claude Code

Records the 2026-03-06 security audit triggered by the clinejection
article, the vulnerability analysis across smartwatermelon and
nightowlstudiollc repos, the fix applied (author_association guard +
id-token: write removal), and commit SHAs for all 11 patched repos.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Comment thread docs/plans/2026-03-06-prompt-injection-hardening.md
@twistedmelonman

Copy link
Copy Markdown
Member Author

Seer finding is a false positive. The live .github/workflows/claude.yml in this repo was patched on 2026-03-06 (commit 7c70a2b) — directly to main via the GitHub API as part of the security remediation this PR documents. Verified: author_association appears 4× in the current file and id-token: write is absent. This PR adds only the audit trail documentation; the fix predates the PR.

@twistedmelonman
twistedmelonman merged commit ce62149 into main Mar 7, 2026
4 checks passed
@twistedmelonman
twistedmelonman deleted the claude/security-prompt-injection-hardening-docs-20260306 branch March 7, 2026 00:13
twistedmelonman pushed a commit that referenced this pull request Apr 30, 2026
Two fixes from pre-push review:

Closes #71: command substitution \$() strips trailing newlines
from captured file content. Both CANONICAL_CONTENT and
current_content lose their trailing \n, so the PUT-uploaded
content was missing a final newline — every install/bump PR
would produce a file failing yamllint's
no-new-line-at-end-of-file rule. Same issue I just fixed in
smartwatermelon/.github PR #7. Fixed by switching the upload
encoder from `printf "%s"` to `printf "%s\n"`.

Closes #70: install branch was named `claude/install-blocking-
review` with no version suffix. If a re-run encountered an
already-open install PR, the git ref creation would fail.
Renamed to `claude/install-blocking-review-\${TARGET_VERSION}`
to match the bump-branch convention and let re-runs slide past
existing same-version PRs.

Issues #67, #72, #73 remain open as tracked tech-debt — they
are real but lower-priority edge cases that can be addressed
in follow-up PRs (mixed local/remote actions caller, transient
gh-API-failure misclassification, .github meta-repo opt-out).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
twistedmelonman added a commit that referenced this pull request Apr 30, 2026
* feat: add bulk-install-claude-review.sh for smartwatermelon fleet

Closes the workflow-templates gap for the smartwatermelon user
account. Since GitHub's `workflow-templates/` picker is
organization-only, repos under `smartwatermelon` (a user
account) never see the org-default stub in their Actions UI.
The script opens install/refresh PRs to roll the canonical
caller stub across the fleet.

Behavior:
- Dry-run by default; --apply to actually open PRs.
- Classifies each repo: CURRENT / STALE / MISSING / CUSTOMIZED /
  LOCAL. CUSTOMIZED and LOCAL are skipped automatically.
- Idempotent: re-running on a clean fleet produces no PRs.
- Target version is derived from the @v… pin in
  smartwatermelon/.github/workflow-templates/claude-blocking-review.yml,
  so bumping that file is the single fleet-wide trigger.
- PRs carry the [skip-claude-review: bulk-install] tag so the
  blocking-review workflow doesn't gate its own install/bump PR.

Tested via dry-run against the live fleet:
- 14 CURRENT, 4 STALE (mix of @V3 floating and @v2.0.2),
  1 LOCAL (github-workflows itself), 1 MISSING (.github).

Plan: docs/plans/2026-04-30-bulk-install-smartwatermelon-fleet.md

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

* fix: address code-reviewer findings on bulk-install script

Five issues raised by code-reviewer on the prior commit:

1. Validate fetch_file output for the per-repo caller file
   (mirrors the canonical-fetch validation that already existed).
   Empty content now classifies as ERROR instead of falling
   through and misclassifying as "no @Version pin found".

2. Reorder customization check before pin comparison. Previously,
   a repo with caller-side customizations on a stale pin would
   get its pin sed-bumped without flagging the customizations.
   New behavior matches what the README claimed: any customized
   caller is skipped for human review regardless of pin status.

3. Tighten extract_pin regex from `[^[:space:]]+` to
   `[A-Za-z0-9._/-]+` so trailing punctuation (commas, quotes
   from quoted YAML values) doesn't get captured into the pin.
   Same fix applied to the canonical-version extraction.

4. Validate --only argument: error when missing or starts with
   `--`. Previously `./script --only --apply` would silently
   iterate every repo because ONLY="" fell through to the
   list-all-repos branch.

5. Exit non-zero when REPOS_ERROR is non-empty. Surfaces fetch
   failures to CI/cron/automation callers. CUSTOMIZED is
   intentionally not an error — it's a human-review signal.

README CUSTOMIZED row updated to reflect "regardless of pin"
behavior.

All verified via shellcheck -S info clean and live --dry-run
against the smartwatermelon fleet.

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

* style: use [[:space:]] for consistency with rest of codebase

Closes #68. The `has_customization` regex used `\s` while the
rest of the script and `claude-review-audit.sh` consistently
use POSIX `[[:space:]]`. Replaced for portability and to match
the convention. Classification still produces identical results
on the live fleet.

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

* fix: strip_comments before canonical version extraction

Closes #66. TARGET_VERSION extraction skipped strip_comments
while extract_pin used it — inconsistent. A commented-out
@Version in the canonical stub could be picked up as the
target. No real-world hit (the canonical file has no such
comment), but the inconsistency is a footgun.

Hoists strip_comments to before the canonical-fetch block and
reuses it. Removes the duplicate definition from the helpers
section.

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

* fix: preserve trailing newline + version-suffix install branch

Two fixes from pre-push review:

Closes #71: command substitution \$() strips trailing newlines
from captured file content. Both CANONICAL_CONTENT and
current_content lose their trailing \n, so the PUT-uploaded
content was missing a final newline — every install/bump PR
would produce a file failing yamllint's
no-new-line-at-end-of-file rule. Same issue I just fixed in
smartwatermelon/.github PR #7. Fixed by switching the upload
encoder from `printf "%s"` to `printf "%s\n"`.

Closes #70: install branch was named `claude/install-blocking-
review` with no version suffix. If a re-run encountered an
already-open install PR, the git ref creation would fail.
Renamed to `claude/install-blocking-review-\${TARGET_VERSION}`
to match the bump-branch convention and let re-runs slide past
existing same-version PRs.

Issues #67, #72, #73 remain open as tracked tech-debt — they
are real but lower-priority edge cases that can be addressed
in follow-up PRs (mixed local/remote actions caller, transient
gh-API-failure misclassification, .github meta-repo opt-out).

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

---------

Co-authored-by: Claude Code Bot <claude-code@smartwatermelon.github>
Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
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