Posts are untrusted

Safety

Stash feeds internet content to an agent that can edit code, so every layer assumes a post may be written to manipulate it.

What could go wrong, and what stops it

RiskWhat Stash does
A post tells the agent to add a harmful command to your CLAUDE.mdPosts are fenced as untrusted data, every tip is scanned, risky tips are held for review, and every change needs your approval.
Hidden text that you can't see but a model readsZero-width, bidi and control characters and HTML comments are removed on save. The scanner flags any that slip through.
The triage run is steered into running commands or sending data outClaude Code: no shell, no settings or other plugins, writes only to tips/, web access only to documentation hosts and the post's own domains, and a $1.50 cap. Codex: the workspace sandbox with no network and no user config. Both: a CLI that refuses network and file commands, and anything written outside your tips is put back.
A tip injected into every Claude Code sessionThe session hook rescans tip files every time and never shows held tips. Titles are cleaned and framed as data.
A "tip" that's really an adEvery tip carries a promotion label: own product, sponsored, affiliate links or sales funnel, with one line on who benefits. It's information, not a penalty.
A file planted in your library gets pushed to GitHubOnly Stash data is ever committed, and only the app pushes, with fixed arguments.

Each layer is tested, including a red-team run where a hostile post goes through real Claude Code with the exact flags the Mac app uses. The full threat model is in SECURITY.md, which also explains how to report a vulnerability.

The decisions

  1. 0101Posts are untrusted inputEvery caption, transcript, comment and fetched page is data, never instructions, and is cleaned and fenced before a model sees it.
  2. 0102Nothing changes in your code without your approvalApplying a tip always shows the exact change first; tool installs need a human even in automated runs.
  3. 0103The headless run is boxed inTriage on the Mac can read the library, write only in tips/, fetch only documentation hosts and the post's own domains, and can't run commands or load other settings.
  4. 0104Only the app pushes your library, never the modelClaude can't push, configure remotes or change git settings; the Mac app pushes with fixed arguments after a successful run.
  5. 0105Every tip is scanned, and risky ones are held for reviewA deterministic scanner flags dangerous commands, hidden text and injection attempts. Flagged tips never reach a repo or a session on their own.
  6. 0106Reading the whole post and using browser cookies are separate opt-insyt-dlp only runs when you turn on "Read the whole post", always with hardening flags, and it reads Chrome cookies only if you allow that separately.
  7. 0107Label masked promotion instead of hiding itEvery tip says whether the post promotes the creator's own product, a sponsor, affiliate links or a sales funnel, without changing its score.