diff --git a/marketing/drafts/agent-keeps-asking/copy.md b/marketing/drafts/agent-keeps-asking/copy.md new file mode 100644 index 0000000..9e5f934 --- /dev/null +++ b/marketing/drafts/agent-keeps-asking/copy.md @@ -0,0 +1,96 @@ +# Why does your coding agent keep stopping to ask you questions? + +> **Status: draft — awaiting sponsor fact-check** (FRE-199 pair 3, internal target +> Thu 2026-11-12). Not publishable from `drafts/`. +> This page never names a product of ours and never names a competitor. + +Most of the stopping is not the model being chatty — it is the permission system +doing what it was told. In the default mode, the agent prompts before the first +use of each tool; separately, its turn ends every time it finishes responding, +and ending a turn with a question is finishing a turn. You cannot and should not +eliminate every ask — but you can decide, once, which asks deserve an +interruption and let the routine ones pass without you. + +## Where the asks come from + +**Permission gates.** In the default mode the agent "prompts for permission on +first use of each tool" — so every new tool, and often every new command shape, +costs one prompt. The configuration decides who answers: + +- **`acceptEdits`** automatically accepts file edits and common filesystem + commands (like `mkdir`, `touch`, `mv`, `cp`) for paths in your working + directory — the single biggest ask category for most coding sessions, gone. +- **Permission rules** do the fine work: `deny` rules block a tool outright, + `allow` rules pass it silently, `ask` rules force the prompt. Order matters: + rules are evaluated deny, then ask, then allow — the first match wins, and an + allow rule cannot carve an exception out of a deny. +- **Modes set the floor.** `defaultMode` in your settings picks where every new + session starts. At the far end, `bypassPermissions` skips prompts entirely — + the docs' own warning is that it belongs only in isolated environments like + containers or VMs. + +One fact worth internalising: permission rules are enforced by the coding +agent's harness, not by the model. A line in your prompt asking it to "not ask" +changes nothing about what it is allowed to do — the configuration is the only +lever. + +**Turn ends.** A `Stop` hook fires when the agent finishes responding — every +turn, including the turns that end in a question. From the terminal's side of +the glass, "it finished", "it's asking me something" and "it's waiting on a +permission prompt" are the same silence. That is why the asking *feels* +endless: each ask costs a context switch, and nothing distinguishes the asks +from the completions. + +Practitioners describe the pattern in their own words. A developer who measured +why their sessions kept stopping found that the agent "just kept handing +control back" even with a permissive mode already on — the model's own habit of +ending turns to stay in the loop, on top of the permission asks. An operator +running a team of agents with per-agent autonomy levels put the other side: +"if every decision routes through you, you're the bottleneck agents were meant +to eliminate." + +## What to check or do + +1. **Sort the asks by kind before touching anything.** File edits in your + working directory: `acceptEdits` removes them wholesale. The same safe + command every session: an `allow` rule. The commands that must never run: a + `deny` rule. What is left is the set of questions only you can answer. +2. **Write the rules in the right order.** Deny, then ask, then allow; first + match wins. A broad deny stays broad — narrowing an allow elsewhere does not + soften it. +3. **Keep the genuinely ambiguous asks.** A mode that asks less is not a mode + that asks smarter. `bypassPermissions` in a throwaway container is a + documented pattern for unattended runs; using it on your daily machine is + the docs' own caution, not a recommendation. +4. **Make every stop visible.** Because every stop ends a turn, wire the + turn-end and notification moments (the `Stop` and `Notification` hooks) so + an ask reaches you where you actually are — and a permission wait is + distinguishable from a finished job. + +One next step: run one session with the asks tallied by kind — edits, known +commands, everything else. The first two usually turn out to be rules you +hadn't written yet; the third is the work. + +--- + +## Fact-check table (not part of the page) + +Every technical claim above, with its primary source. Claims about the +permission system and hooks were verified against the live docs on 2026-11-05. + +| # | Claim in the page | Source | +|---|---|---| +| 1 | Default mode "prompts for permission on first use of each tool" (labeled Manual; `manual` alias) | Claude Code permissions doc — https://code.claude.com/docs/en/permissions (permission modes table; fetched 2026-11-05) | +| 2 | `acceptEdits` "automatically accepts file edits and common filesystem commands such as mkdir, touch, mv, and cp for paths in the working directory or additionalDirectories" | same page (permission modes table) | +| 3 | Rules are evaluated in order deny, then ask, then allow; "the first match in that order determines the outcome"; "an allow rule can't carve an exception out of a deny rule" | same page (rule precedence section) | +| 4 | `bypassPermissions` "skips permission prompts"; docs' caution: "Only use this mode in isolated environments like containers or VMs where Claude Code can't cause damage" | same page (permission modes table) | +| 5 | `defaultMode` in settings files sets the default permission mode for new sessions | same page ("To change the default permission mode for new sessions, set defaultMode in your settings files") | +| 6 | "Permission rules are enforced by Claude Code, not by the model. Instructions in your prompt or CLAUDE.md shape what Claude tries to do, but they don't change what Claude Code allows." | same page (verbatim) | +| 7 | `Stop` fires when the agent finishes responding; hook cadence is per turn | Claude Code hooks reference — https://code.claude.com/docs/en/hooks (verified 2026-11-05 in FRE-199 round 1; unchanged) | +| 8 | Anecdote: "it just kept handing control back"; sessions kept stopping with a permissive mode on | r/ClaudeCode thread 1xlfqmo ("I measured why my Claude Code sessions kept stopping…", 2026-11-01, u/belovoj), logged in `drafts/listening.md` Scan 5 #1. Quoted as one developer's described experience; the thread's own measurement figures are deliberately **not** cited. | +| 9 | Anecdote: "if every decision routes through you, you're the bottleneck agents were meant to eliminate"; per-agent autonomy levels 0–5 | r/ClaudeCode thread 1xk0ghj ("multiple agents working on multiple projects", 2026-10-31, quote by u/iceydee), logged in `drafts/listening.md` Scan 4 #2. One operator's described practice. | + +**Ban compliance:** no product of ours named · no competitor named · no +superlatives · no benchmark numbers (the 1xlfqmo poster's measurement figures +are deliberately not cited) · no invented testimonials (anecdotes are real +threads, described without handles) · no price · no roadmap dates. diff --git a/marketing/drafts/agent-keeps-asking/rationale.md b/marketing/drafts/agent-keeps-asking/rationale.md new file mode 100644 index 0000000..03e62ea --- /dev/null +++ b/marketing/drafts/agent-keeps-asking/rationale.md @@ -0,0 +1,52 @@ +# Rationale — "Why does your coding agent keep stopping to ask you questions?" + +FRE-199 item 1, page 2 of the third pair. Drafted 2026-11-06 by CMO (internal +target Thu 2026-11-12 — six days early). + +## The phrase + +Primary: **"why does my coding agent keep stopping to ask me questions"** +(variants: "agent keeps handing control back", "claude code keeps asking for +permission"). The H1 carries the generic form; "handing control back" is the +backlog's own added phrase (Scan 5's phrase-list finding). + +## Why this phrase won the slot + +- **Backlog evidence.** r/ClaudeCode 1xlfqmo (2026-11-01, Scan 5 #1): "Auto mode + was already on, so permissions weren't the issue… it just kept handing + control back"; "the model was forcably trying to keep me in the loop." The + phrase-list finding from the same scan added "handing control back" as a + standing query. Corroborated by 1xlxw0q (turns ending with "nothing yet") and + the autonomy-ladder operator (Scan 4 #2, thread 1xk0ghj: "if every decision + routes through you, you're the bottleneck agents were meant to eliminate"). +- **Shortlist position (c)** in the plan's pair-3 shortlist, recorded at + revision 5 — the page extends the done-signal cluster (pair 1) with the + handback half. The distinction is kept deliberately: *agent-done-signal* + owns "how do I know it's done"; this page owns "why does it keep stopping on + me". Different question, different searcher. +- **Answerable honestly from verified sources only.** Every mechanism claim + re-reads to the permissions doc and hooks reference — the same pages and the + same claims the CTO verified in FRE-199 rounds 1–2 (mode ladder, precedence, + acceptEdits scope, enforced-by-harness sentence, Stop cadence). Nothing new + is asserted about agent behaviour. + +## What the page deliberately does not do + +- **Does not cite the 1xlfqmo poster's measurement figures** (the 28-of-73 + sample is the poster's own 18-day data, and the backlog row carries an + explicit do-not-cite flag). The anecdote is quoted as experience, not + measurement, and the fact-check table says so. +- Does not promise the asks can be eliminated. The honest answer is that the + asking is partly the permission system working as configured and partly the + agent ending turns to stay in the loop — the page sorts which is which. +- Does not touch environment contention (page 1 of this pair owns that half). + +## Evidence trail + +| Thread | Date | What it showed | +|---|---|---| +| r/ClaudeCode 1xlfqmo — "I measured why my Claude Code sessions kept stopping" | 2026-11-01 | "It just kept handing control back" with a permissive mode on; "forcibly trying to keep me in the loop" — the model-behaviour half | +| r/ClaudeCode 1xk0ghj — "multiple agents working on multiple projects" (quote by u/iceydee) | 2026-10-31 | "If every decision routes through you, you're the bottleneck agents were meant to eliminate"; per-agent autonomy levels 0–5 — the configuration half | +| r/ClaudeAI 1xlxw0q — "2,300 hours waiting" | 2026-11-02 | Turns ending in a one-word answer reload context each time — the per-ask cost, corroborating | + +All rows live in `drafts/listening.md` (The-Nook local master line). diff --git a/marketing/drafts/agent-worktree-contention/copy.md b/marketing/drafts/agent-worktree-contention/copy.md new file mode 100644 index 0000000..40e7cd2 --- /dev/null +++ b/marketing/drafts/agent-worktree-contention/copy.md @@ -0,0 +1,72 @@ +# How do you manage worktrees when your agents end up waiting on each other? + +> **Status: draft — awaiting sponsor fact-check** (FRE-199 pair 3, internal target +> Thu 2026-11-12). Not publishable from `drafts/`. +> This page never names a product of ours and never names a competitor. + +Usually, the worktrees are not what your agents are waiting on — the environment +they share is. Two agents can sit in two worktrees of the same repo and still +queue up behind one dev server, one test database, one `docker compose` stack. +The fix that scales is to multiply the environment per worktree, not to +orchestrate the waiting. + +## Why agents queue when the code doesn't + +Git supports parallel work out of the box: `git worktree add ` +creates a second working directory linked to the same repository — shared +history, but its own HEAD, its own index, its own checked-out branch. Git even +enforces the ownership half for you: it refuses to check out a branch into a +second worktree while the first one holds it. + +What git does not duplicate is everything the repo only *points at*: the dev +server bound to port 3000, the database named after the project directory, the +compose stack whose project name defaults to the folder you launched it from. +Two agents in two worktrees that both bring up the same stack are two agents +contending for one environment — and the queue looks like a worktree problem +when it is an environment problem. + +Practitioners who hit this converge on the same verdict. One, in a thread +asking this exact question: the queue "comes from having one test env, so I'd +multiply the env instead of orchestrating the waiting." + +## What to check or do + +1. **Give every worktree its own copy of the stack.** Docker Compose exists for + exactly this: it uses a *project name* to isolate environments from each + other, and names "multiple copies of a single environment, useful for + running stable copies for each feature branch" as a use case. Set a unique + one per worktree — the `-p` flag has top precedence, or use `name:` in the + compose file — and the port and container-name collisions disappear. +2. **Anything that cannot be multiplied, serialise on purpose.** One migration + runner, one deploy target, one flaky hardware-in-the-loop device: put it + behind a single serial step rather than letting two agents race it. A queue + you chose is a queue you can reason about. +3. **One branch, one worktree.** Git already refuses to check out the same + branch in two worktrees; keep it that way. Two agents on one branch is a + merge conflict waiting for both of them to finish. +4. **Remember a fresh worktree starts unconfigured.** Env files, generated + config and installed dependencies live in the worktree, not the repo — a new + worktree is a new environment to set up, which is exactly why the per-worktree + copy should be scripted, not hand-arranged. + +One next step: find the resource your agents contend for most often — usually +the test stack — and give it a per-worktree project name. The waiting usually +resolves before any queueing tool is needed. + +--- + +## Fact-check table (not part of the page) + +Every technical claim above, with its primary source. Claims about git and +Docker Compose were verified against the live docs on 2026-11-05. + +| # | Claim in the page | Source | +|---|---|---| +| 1 | `git worktree add []` creates a worktree "linked to the current repository, sharing everything except per-worktree files such as HEAD, index, etc." | git worktree docs — https://git-scm.com/docs/git-worktree (COMMANDS › add; fetched 2026-11-05) | +| 2 | `add` "refuses to create a new worktree when is a branch name and is already checked out by another worktree" | same page (OPTIONS › `--force`) | +| 3 | Compose "uses a project name to isolate environments from each other"; "multiple copies of a single environment, useful for running stable copies for each feature branch" is a named use case; precedence: `-p` flag > `COMPOSE_PROJECT_NAME` > `name:` attribute > directory basename | Docker Compose docs, "Specify a project name" — https://docs.docker.com/compose/how-tos/project-name/ (fetched 2026-11-05) | +| 4 | Anecdote: "The queue comes from having one test env, so I'd multiply the env instead of orchestrating the waiting" | r/ClaudeCode thread 1xlz2bs ("How do you manage worktrees when your agents end up waiting on each other?", 2026-11-02, u/Roland_culait / u/First-Painter7431), logged in `drafts/listening.md` Scan 6 #4. Quoted as one commenter's described practice, not a measurement. | + +**Ban compliance:** no product of ours named · no competitor named · no +superlatives · no benchmark numbers · no invented testimonials (the anecdote is +a real thread, described without handles) · no price · no roadmap dates. diff --git a/marketing/drafts/agent-worktree-contention/rationale.md b/marketing/drafts/agent-worktree-contention/rationale.md new file mode 100644 index 0000000..d80f6dd --- /dev/null +++ b/marketing/drafts/agent-worktree-contention/rationale.md @@ -0,0 +1,46 @@ +# Rationale — "How do you manage worktrees when your agents end up waiting on each other?" + +FRE-199 item 1, page 1 of the third pair. Drafted 2026-11-06 by CMO (internal +target Thu 2026-11-12 — six days early). + +## The phrase + +Primary: **"how do you manage worktrees when your agents end up waiting on each +other"** — carried verbatim as the H1, because it is already a complete search +phrase with the exact buying intent. + +## Why this phrase won the slot + +- **Backlog evidence.** r/ClaudeCode 1xlz2bs (2026-11-02, ~15 h old at scan time, + Scan 6 #4). The OP asked the question in its final words; the thread answered + itself (env per worktree, `docker compose -p`, preview deploys, one serial + step on main) — which is exactly what makes it page material: the demand is + proven, the answer is proven, and the answer is generic. +- **Shortlist position (a)** in the plan's pair-3 shortlist, recorded at + revision 5. Scan 9 (2026-11-05) produced no new queue item, so the + shortlist stands; selection finalised against that fresh scan as planned. +- **Answerable honestly and generically.** Both mechanisms are documented + primary sources (git worktree docs; Docker Compose project-name docs), both + fetched and read 2026-11-05. No agent-behaviour claim is needed — this page + is the lightest CTO-review lift of the shortlist. +- **Wedge-adjacent without a mention.** "Waiting" is the cost our wedge names + ("an agent blocked is the most expensive kind of idle"); this page owns the + agent-on-agent half of waiting, which no existing page covers. + +## What the page deliberately does not do + +- Does not cite the thread's own tooling (Orca, oyren.ai) or any workflow + product — category nouns only. +- Does not invent a measurement. The one quoted line is a commenter's described + practice, logged in the backlog with a do-not-interpret flag. +- Does not touch the approval surface (page 2 of this pair owns the + attention/handback half; this page is environment contention only). + +## Evidence trail + +| Thread | Date | What it showed | +|---|---|---| +| r/ClaudeCode 1xlz2bs — "How do you manage worktrees when your agents end up waiting on each other?" | 2026-11-02 | Exact phrase in the wild; self-answered with env-multiplication advice; "multiply the env instead of orchestrating the waiting" | +| Watched-table corroboration (Scans 5–9) | 2026-11-02 → 11-05 | Repobs ("which sessions were waiting for me"), Orca (worktree orchestration daily driver), Worktrunk, Conductor.build, Parallel Code — a shelf of builders around the same phrase; the demand is broad | + +All rows live in `drafts/listening.md` (The-Nook local master line). diff --git a/marketing/drafts/newsletter-postmortem-pitch/copy.md b/marketing/drafts/newsletter-postmortem-pitch/copy.md index f3d7747..f15f2b8 100644 --- a/marketing/drafts/newsletter-postmortem-pitch/copy.md +++ b/marketing/drafts/newsletter-postmortem-pitch/copy.md @@ -1,10 +1,12 @@ -# Newsletter pitch — post-mortem shape (placeholders; numbers gated) +# Newsletter pitch — post-mortem shape (narrowed; no conversion figure) -> **Status: draft — placeholders only. No figure in this file is a measurement.** -> FRE-199 item 2. Drafted 2026-11-05 by CMO; the plan's date was Fri 2026-11-06. -> **Send gate:** no figure ships until FRE-202 (weekly metrics job) or a direct -> read of the relay store provides it **and** the CTO confirms the query. Paid -> placements stay out (TLDR ≈ $3k/placement, no verifiable CPC to buy against). +> **Status: draft — narrowed 2026-11-06 per the CTO's reopening verdict on +> FRE-199.** The "X% trial→paid" half of the shape **cannot ship**: the +> FRE-202 snapshot (window 2026-10-22 → 10-29) reads trial started 2, purchase +> 0, activation 0, with 291 of 291 analytics rows predating the FRE-366 +> instrumentation — a trial→paid ratio from that cohort is not a metric. The +> ratio comes from FRE-197's mature Day 28–35 cohort read when it lands. +> **No figure in this file is a measurement.** Send gates at the bottom. ## Audience & channel @@ -16,9 +18,11 @@ No paid placements at any budget without a CoS + sponsor decision. A post-mortem pitch, not a product pitch: *here is what shipping a Mac utility alone actually broke, and what we changed because of it.* The product is the -setting; the breakage and the fix are the story. +setting; the breakage and the fix are the story. The story stands on its own +with zero funnel numbers — if no verified number exists on send day, the pitch +ships without one rather than with a placeholder. -## The pitch (shape — every figure is a placeholder) +## The pitch (shape — names and dates personalised; nothing else is a placeholder) **Subject:** What shipping a Mac utility alone broke (post-mortem) @@ -33,50 +37,60 @@ ways bigger teams don't hit: cleanly — while every delta it named 404'd, so users on older builds were being offered updates that didn't exist. The publish path deleted files before the feed that named them was live. Nothing alerted; the feed just - lied quietly. (Documented in our own changelog discipline: the fix — upload - the feed's enclosures, verify every URL, *then* prune — is now ordered so - the deletion can't run first.) -- **[PLACEHOLDER — second breakage: the launch-incident story with a real - number attached. Candidates from the engineering journal: the 0.13.x - appcast-item loss (changelog blanking on prune), or the relay regression - that shipped behind a passing suite. Pick the one FRE-202's data can - quantify.]** -- **The numbers, as they are.** activations and % trial→paid as of - — small numbers, real ones, and the interesting part is the funnel - shape, not the size. + lied quietly. The fix — upload the feed's enclosures, verify every enclosure + URL, copy the appcast up, and only *then* prune — is now ordered so the + deletion can't run first. +- **The green suite.** Weeks earlier, a regression in our public relay shipped + behind a passing test run — the suite that would have caught it existed but + nothing invoked it. A green checkmark that covers nothing looks identical to + one that covers everything. The suite is now wired into the standard test + entry point, and the relay's deploy patcher is tested alongside it. +- **What we're not going to quote you.** A growth number, right now, would be + theatre: our funnel is young and a conversion ratio from an immature cohort + is not a measurement. If we attach a count, it will be activations — one per + activated install, from our own relay store — and we will say exactly that, + because download counts (a different number, from a different store) flatter + nothing and confuse everyone. The receipts that matter here are the failure + modes above, not a traction line. The angle for your readers: solo distribution is a chain of quiet failure modes, each one invisible until it costs a user. We kept the receipts. -Happy to send the full write-up, screenshots of the broken feed, and the -exact publish-order change. +Happy to send the full write-up, screenshots of the broken feed, and the exact +publish-order and test-wiring changes. — , FrenoCorp -## Where the numbers come from (and the caveats that travel with them) +## Where a number could come from, and what disqualifies it -- **Preferred source:** FRE-202, the weekly metrics job (CTO owns the query). -- **Fallback:** a direct read of the relay store — `installs` (one row per - activated install, `created_at`) for activations; `admissions` - (`license_id` non-empty = licensed, empty = trial) for the trial→paid split. -- **Caveats that go in the pitch, not a footnote:** - - a conversion figure is per *install* (install cap is 3), not per person; - - DMG downloads (S3 side) and activations (relay store) are two different - numbers — the pitch says which one it quotes; - - "1,900 downloads, 6% trial→paid" is the *shape* of a pitch, never a figure - we hold. No number is estimated to fill a placeholder. +- **Trial→paid ratio: cannot ship today.** FRE-202's snapshot shows a cohort of + 2 trials, 0 purchases, pre-instrumentation rows. The ratio waits for + FRE-197's mature Day 28–35 read. If it lands before send day and the CTO + confirms the query, the ratio may be added — and it must say it is per + *install* (install cap 3), not per person. +- **Activations: the only count eligible to ship.** One row per activated + install (`installs`, `created_at`) in the relay store; CTO confirms the query + before any send. The pitch names it as activations, never as downloads. +- **Downloads (S3 side) are never quoted.** Different store, automation-heavy, + and the pitch that says "downloads" when it means activations burns the + credibility the post-mortem is built on. +- No number is estimated to fill any gap, ever. ## Gates before anything is sent -1. Figures exist (FRE-202 or CTO-confirmed direct read) — owner: CTO. -2. CTO confirms the query behind every figure quoted — owner: CTO. -3. Sponsor approves the send and holds the sending account (humans hold every +1. Any count quoted is activations, from a CTO-confirmed query — owner: CTO. +2. The trial→paid ratio ships only from FRE-197's mature cohort read with CTO + confirmation; otherwise the "what we're not going to quote you" paragraph + stands as written — owner: CTO. +3. Both breakage paragraphs are fact-checked against the engineering record + (FRE-542 publish-order incident; the NOOK-815 uninvited-suite relay + regression) before send — owner: CMO, evidence to CTO for verdict. +4. Sponsor approves the send and holds the sending account (humans hold every account) — owner: Michael Freno. -4. The second breakage paragraph is fact-checked against the engineering - journal before send — owner: CMO, evidence to CTO for verdict. ## Target dates (internal) -- Draft with placeholders: **done 2026-11-05** (plan date was 2026-11-06). -- Figures dropped in: when FRE-202 or the direct read exists — no date promised. -- Send: only after gates 1–4. Sponsor submits. +- Draft with placeholders: **done 2026-11-05**; narrowed to the no-figure shape + **2026-11-06** (CTO direction). +- Send: after gates 1–4 — with the no-figure shape, the only hard input left is + the CTO's query confirmation and the sponsor's send. diff --git a/marketing/drafts/newsletter-postmortem-pitch/rationale.md b/marketing/drafts/newsletter-postmortem-pitch/rationale.md index a6a6a82..469e10b 100644 --- a/marketing/drafts/newsletter-postmortem-pitch/rationale.md +++ b/marketing/drafts/newsletter-postmortem-pitch/rationale.md @@ -24,15 +24,38 @@ The lead paragraph is the 0.13.4 delta incident (FRE-542): the appcast stayed at 0.13.4 while its five delta files 404'd — the publish path pruned before the feed was up. The fix (upload enclosures, verify URLs, copy the appcast, then prune) is in `scripts/upload-release.sh` and is engineering-verified by -the FRE-542 record. The second breakage paragraph is a named placeholder with -two candidate incidents — it stays a placeholder until one can carry a real -number. +the FRE-542 record. + +**Second breakage, chosen 2026-11-06 (CTO direction):** the relay regression +that shipped behind a passing suite (NOOK-815) — the suite that would have +cought it existed but nothing invoked it; the fix wires it into the standard +test entry point. It was chosen over the changelog-blanking incident because +it is a complete story with no number needed and no overlap with the lead +(both remaining candidates were publish-path incidents; one story about the +publish path is enough). The placeholder is gone: no paragraph in the pitch +waits on a figure any more. + +## Narrowed 2026-11-06 — what the numbers can and cannot support + +The CTO's reopening verdict on FRE-199 confirmed **no figure for the pitch +today**: FRE-202's snapshot (trial started 2, purchase 0, activation 0; 291 of +291 rows predate the FRE-366 instrumentation) cannot yield a trial→paid ratio — +that waits for FRE-197's mature Day 28–35 cohort read. So the pitch narrowed: + +- the "X% trial→paid" placeholder is deleted, not held; +- if any count ships, it is **activations** (relay store, one row per activated + install), named as activations — downloads (S3 side) are never quoted; +- a new paragraph — "what we're not going to quote you" — turns the missing + number into part of the post-mortem's credibility instead of a gap; +- with the no-figure shape, the only inputs left before send are the CTO's + query confirmation (if a count is attached) and the sponsor's send. ## Hard rules honoured -- Every figure is `[PLACEHOLDER]` and labelled as such; the file says in its - header that no figure in it is a measurement. -- No invented number, no estimated conversion, no user counts. +- No figure in the file is a measurement; nothing is estimated to fill a gap. +- No conversion figure ships — the ratio is FRE-197's, gated and CTO-confirmed. +- Any count that ships is activations, named as activations; downloads are + never quoted. - The two caveats (per-install conversion with install cap 3; downloads ≠ activations) are written to travel inside the pitch, not a footnote. - Paid placements: out, per the issue text and the plan (TLDR ≈ $3k, no @@ -42,8 +65,9 @@ number. ## Gates before send -1. Figures from FRE-202 or a CTO-confirmed direct relay-store read — CTO. -2. CTO confirms the query behind every figure — CTO. -3. Sponsor approves the send; a human holds the account and sends — sponsor. -4. Second-breakage paragraph fact-checked against the journal — CMO drafts, - CTO verifies. +1. Any count quoted is activations, from a CTO-confirmed query — CTO. +2. Trial→paid ratio ships only from FRE-197's mature read, CTO-confirmed; + otherwise the no-figure paragraph stands — CTO. +3. Both breakage paragraphs fact-checked against the engineering record + (FRE-542; NOOK-815) — CMO drafts, CTO verifies. +4. Sponsor approves the send; a human holds the account and sends — sponsor.