Snapshots

Every jam ends in a brief someone else can work from

Settled
  • Three documents: the jam brief, a team brief per deliverable, and a signed read only page.
  • The Send to sheet names one of seven recipients.
  • Brew emails a brief only to our team; it never posts or runs anything.
  • Also a PDF, a publish pack, and Gmail, Mail or Outlook drafts.
  • Bump TB_V when briefs are written differently, and all saved ones rewrite.
Your call

Should shared links expire? Proposal: 30 days by default, with revoke on the jam.

Engineering · 5.9

Briefs and hand-off

DraftLast checked Mon Oct 26Owner Param

Answer

Every jam ends in a brief someone else works from: the jam brief (the working document), the team brief (one per deliverable, written for a named recipient), a signed read-only page, a PDF and a publish pack; Brew sends the brief only to our team by email and never posts or runs anything itself.

Today

Three documents

Document What it is Where it lives Source
Jam brief One Markdown document per jam (w.doc): starts as the card, grows as people jam, AI edits on request, replies fold in; readiness is a checklist, never a score the jam brew/jam-brief.js:1-6
Team brief One AI pass turns the card, proof, plan, jam brief and final package into a brief with fixed editable sections and evidence per claim; final words verbatim; creatives attached w.teamBriefs[changeId], one per deliverable tab (?ch=) brew/team-brief.js:1-7, 196-200 git 9fd1de4
Hand-off Everything about a jam for someone outside: card, options, Plays, brief, versions, assets, chats, open questions /h/<token> read-only page, signed brew/handoff.js:1-10

TB_V 4: bump it when the team brief starts being written differently; every saved one is rewritten. brew/team-brief.js:17

Recipients

The "Send to…" sheet names a real recipient: your team, your agency, a designer, a media buyer, a creator, a video editor, or our team. brew/team-brief.js:20 memory brew-jam-rca-2026-10-26

Send routes

Route What happens Source
Share with my team Freezes the brief (BR-n, numbered per brand), copies it with the read-only link; nothing sent brew/SCOPE.md brew/docs/handover/engineering/11-known-issues-and-debt.md
Send to our team Freezes and emails the whole brief to SHOPOS_EMAIL (default hello@joinsquareup.com) every time; tracked status brew/jam-mail.js:104 brew/brief-status.js:1-6
Download PDF Chromium render, gen/brief-*.pdf memory brew-brief-mode
Open in Gmail, Mail or Outlook Downloads the files and opens a compose page or an .eml draft from the person's own email; no Gmail scope memory brew-brief-mode
Slack Posts to the channel picked at connect with an Approve button; thread replies fold into the brief memory brew-real-connectors
Publish pack A zip per version for the team to post or apply by hand brew/publish-pack.js:1-5

Status of a brief sent to our team

sent → received → in_progress → delivered, or needs_info (needs a note) and back. Only staff move it (POST /api/work/:wid/brief/status). Each move writes a jam line, a notification and an email to the sender; the top bar shows "N with the team". If the email did not go, the jam says "ready, paste it", never "sent". brew/brief-status.js:1-10 brew/docs/handover/engineering/12-ui2-service-api.md

Editing a brief

The team brief writes itself once the first draft is in. Selecting text or tapping a section opens "Change with AI"; there are no hand-edit boxes. Chat edits the brief only when the message is about the brief. Every change stamps a revision so teammates reload it. memory brew-team-brief-ai-edit In the Brief tab, people can comment on words and press "Fix with AI". memory brew-brief-mode

Link signing

Hand-off and ready links are HMAC-signed with HANDOFF_SECRET (production uses its own and opens nothing signed with the Anthropic key). The signature is 12 base64url characters. Links do not expire. brew/handoff.js:14-20 brew/jam2/ready.js:10-11

Guests

Guests cannot share, send or move a brief. The demo site sends no email. brew/SCOPE.md

Tomorrow

Item Version Tag
One team brief per deliverable with a named recipient v1 Stays
Brew never sends to a brand's customers v1 Stays
Links that expire and can be revoked v2 New
Sending a brief to an agency by email from Brew v2 New, needs a send decision
Posting the final asset to the channel v3 New, only behind a person's yes

How we do it

  1. A new brief kind gets its own sections in team-brief.js and a test in test/team-brief.test.js.
  2. Never let the fact sheet or team-only card words into a shared brief; unleak() and publicView guard this. memory brew-brief-mode memory brew-shopify-connector-qa
  3. Check a status change end to end on staging with a staff account before relying on it.

Numbers

Metric Definition Where measured
Briefs shared Frozen briefs per brand per week w.jamBrief (Proposed to count)
With our team Briefs sent and not yet delivered withTeam.n on /feed and /work brew/docs/handover/engineering/12-ui2-service-api.md
Time to delivered Sent to delivered, per brief w.jamBrief.history (Proposed)

Open

  1. Should shared links expire? Proposal: 30 days by default, with revoke on the jam.
  2. Does the recipient "our team" stay now that Brew is kept independent? Proposal: keep it as is, add nothing new tied to it. memory brew-qa-round2-2026-10-24
Sources
  • brew origin/main: jam-brief.js:1-8; team-brief.js:1-20, 196-223; handoff.js:1-20; brief-status.js:1-10; jam-mail.js:1-8, 104, 117; jam2/ready.js:10-11; publish-pack.js:1-5
  • brew origin/main: SCOPE.md (Share the brief, Brew's emails); DUMMY.md (closing paragraph)
  • brew origin/main: docs/handover/engineering/12-ui2-service-api.md section 1, 13-jam-chip-api.md
  • brew origin/main git log: 9fd1de4 (per-tab briefs with recipients)
  • memory brew-brief-mode, brew-team-brief-ai-edit, brew-jam-rca-2026-10-26, brew-real-connectors

Source file content/engineering/briefs-and-hand-off.md · For agents: Markdown · JSON