Buying committee
Writes to 3 or more roles at each named company, one a week, and hands each engaged company to your AE within a day.
- Channel
- Contacts and companies
- Summary
- startupbuilder.dev
Be our SDR for our 60 biggest targets: property managers with 200 units or more. At each, find the owner, the operations lead, the leasing manager and the controller, and write to one a week with something for their job. I write to owners myself. Hold half back so we can tell. Anyone engaged goes to our AE within a day. Show me what’s missing; don’t send.
# Not live yet (gaps #2)
curl -X POST "https://api.sb/leaseline.app/campaigns?mode=try" \
-H "Authorization: Bearer $STARTUP_BUILDER_API_KEY" \
-H "Content-Type: application/json" \
-d '{"play":"buying-committee"}'import { $ } from 'startup-builder'
return await $.Campaign.create({ play: 'buying-committee' }, { mode: 'try' }) // dry run on the day-0 Startup, 2026-08-24 · Not live yet, gaps #2
npx startup-builder do Campaign.create --json '{"play":"buying-committee"}' --try # Not live yet (gaps #2){
"name": "do",
"arguments": {
"code": "return await $.Campaign.create({ play: 'buying-committee' }, { mode: 'try' }) // dry run on the day-0 Startup, 2026-08-24 · Not live yet, gaps #2",
"mode": "try"
}
}application/json{
"type": "https: //startupbuilder.dev/ errors/ refused",
"title": "Refused",
"status": 422,
"detail": "buying-committee can’t start yet: 1 check fails and 2 warn.",
"checks": [
{
"check": "owned-by-a-person",
"status": "warn",
"observed": "2 of the 60 named have an open Deal a person owns: they stay with that person",
"doc": "/plays/ buying-committee#check-owned-by-a-person",
"then": "Task.assign"
},
{
…
Hand our latest engaged member to the SDR agent and show me what it chose and why. Don’t send.
curl "https://api.sb/leaseline.app/events?where=name%20in%20(%22Company.funded%22%2C%20%22Visit.recorded%22%2C%20%22Visitor.identified%22%2C%20%22Prospect.engaged%22%2C%20%22Ad.clicked%22%2C%20%22Contact.enriched%22%2C%20%22Experiment.matured%22)&limit=1" \
-H "Authorization: Bearer $STARTUP_BUILDER_API_KEY"
# Not live yet (gaps #7)
curl -X POST "https://api.sb/leaseline.app/triggers/fire?mode=try" \
-H "Authorization: Bearer $STARTUP_BUILDER_API_KEY" \
-H "Content-Type: application/json" \
-d '{"like":"event_1426"}'
# Not live yet (gaps #7)
curl "https://api.sb/leaseline.app/decisions?where=on%20%3D%20%22organization_102%22" \
-H "Authorization: Bearer $STARTUP_BUILDER_API_KEY"
# Not live yet (gaps #7)
curl "https://api.sb/leaseline.app/actions?where=on%20%3D%20%22organization_102%22" \
-H "Authorization: Bearer $STARTUP_BUILDER_API_KEY"import { $ } from 'startup-builder'
const { events: [last] } = await $.Event.list({ where: 'name in ("Company.funded", "Visit.recorded", "Visitor.identified", "Prospect.engaged", "Ad.clicked", "Contact.enriched", "Experiment.matured")', limit: 1 }) // { play } compiled to this Play’s Trigger Events
const { subject } = await $.Trigger.fire({ like: last.$id }, { mode: 'try' }) // the same Event again, in try mode · Not live yet, gaps #7
const { decisions: [decision] } = await $.Decision.list({ where: `on = "${subject}"` }) // what it chose, and why · Not live yet, gaps #7
const { actions } = await $.Action.list({ where: `on = "${subject}"` }) // what it did, with its checks · Not live yet, gaps #7
return { decision, actions }
npx startup-builder do Event.list --json '{"where":"name in (\"Company.funded\", \"Visit.recorded\", \"Visitor.identified\", \"Prospect.engaged\", \"Ad.clicked\", \"Contact.enriched\", \"Experiment.matured\")","limit":1}'
npx startup-builder do Trigger.fire --json '{"like":"event_1426"}' --try # Not live yet (gaps #7)
npx startup-builder do Decision.list --json '{"where":"on = \"organization_102\""}' # Not live yet (gaps #7)
npx startup-builder do Action.list --json '{"where":"on = \"organization_102\""}' # Not live yet (gaps #7){
"name": "do",
"arguments": {
"code": "const { events: [last] } = await $.Event.list({ where: 'name in (\"Company.funded\", \"Visit.recorded\", \"Visitor.identified\", \"Prospect.engaged\", \"Ad.clicked\", \"Contact.enriched\", \"Experiment.matured\")', limit: 1 }) // { play } compiled to this Play’s Trigger Events\nconst { subject } = await $.Trigger.fire({ like: last.$id }, { mode: 'try' }) // the same Event again, in try mode · Not live yet, gaps #7\nconst { decisions: [decision] } = await $.Decision.list({ where: `on = \"${subject}\"` }) // what it chose, and why · Not live yet, gaps #7\nconst { actions } = await $.Action.list({ where: `on = \"${subject}\"` }) // what it did, with its checks · Not live yet, gaps #7\nreturn { decision, actions }",
"mode": "try"
}
}application/json{
"decision": {
"$id": "https: //api.sb/ leaseline.app/ decisions/ decision_503",
"$type": "Decision",
"choice": "to-the-ae",
"reason": "at Calloway Residential the operations lead replied to the renewals note and the controller viewed the committee page: 2 members engaged",
"stakes": "low",
"options": [
"map-the-committee",
"write-the-next-member",
"note-to-the-buyer",
"ads-only",
"to-the-ae",
"not-now"
…
sample · 4 Not live yetPreviewOn POST /{namespace}/processes/{process}/enableOff POST /{namespace}/processes/{process}/pauseTake this one POST /{namespace}/tasks/{task}/claim
action_3 is the Brief in AE · Priya Shah’s queue, due in 1 business day; once she claims, every member note at Calloway stops and replies go to her.
16.7 against 3.3 Deals per 100,
| Try another: the named company | Choice | Reason |
|---|---|---|
| Calloway Residential: the operations lead replied, the controller viewed the page | to-the-ae | 2 members engaged |
| Ridgeway Homes: 3 new owners announced; leasing manager not written to yet | write-the-next-member | a live reason, and a member due this week |
| Ashford Group: owner and principal, Priority 1 | note-to-the-buyer | the economic buyer at a Priority 1 company goes as Dana |
| Bayview Rentals: layoffs announced Oct 6 | not-now | a crisis holds every touch for 14 days |
- 45 min week 1, then 30 a week
- Your time
- Day 12: first member asks to meet
- First signal
Where it sits: Stranger → Lead → Trialing → Activated → At risk → Churned → Won back · Committee deal lift → Deals and trials opened → New Customers ↑ → ARR added each week → ARR
Worth’s formula: about +2.0 Deals per 100 named companies a quarter (Other Startups’ results; none of your own has matured) × 60 named ÷ 3 months × 0.30 Deals to paid × $2,400 first order ARR ≈ +$288. Under First signal: The leaf reads at day 90 and day 180; at 30 pairs, day 180 can tell only +14 Deals per 100 or more, so it pools with Other Startups’ draws in your category.
sample · api.sb/
Start it this week
npx startup-builder add play buying-committee # 1 · writes plays/buying-committee.mdx (Not live yet, gaps #5)
# 2 · dry run; below, its 422 on the day-0 Startup (clock at 2026-08-24)
curl -X POST "https://api.sb/leaseline.app/campaigns?mode=try" \
-H "Authorization: Bearer $STARTUP_BUILDER_API_KEY" \
-H "Content-Type: application/json" \
-d '{"play":"buying-committee"}'
# 3 · keep it, at You approve each one
curl -X POST https://api.sb/leaseline.app/campaigns \
-H "Authorization: Bearer $STARTUP_BUILDER_API_KEY" \
-H "Content-Type: application/json" \
-d '{"play":"buying-committee"}'
# on
curl -X POST https://api.sb/leaseline.app/processes/outbound/enable \
-H "Authorization: Bearer $STARTUP_BUILDER_API_KEY"
# off: no member note sends; the Ads layer pauses with it
curl -X POST https://api.sb/leaseline.app/processes/outbound/pause \
-H "Authorization: Bearer $STARTUP_BUILDER_API_KEY"| Check | Fix | Then |
|---|---|---|
owned-by-a-person warn · Not live yet, gaps #8 | Leave it to the person who owns it: the draft waits in their queue. | POST /{namespace}/tasks/{task}/assign |
use-when pass · Not live yet, gaps #8 | 60 named companies at 200+ units; 3.5 roles found a company | POST /{namespace}/metrics/query |
baseline pass · Not live yet, gaps #8 | 3.3 Deals opened per 100 of these companies in 90 days, n 60 | POST /{namespace}/metrics/query |
domain-authenticated pass | leaseline.app: 3 of 3 records resolve | POST /{namespace}/domains/{domain}/authenticate |
mailbox-warm fail · Not live yet, gaps #1 | Wait for the warm-up to finish, 14 days from day 0; mapping and the Ads layer run meanwhile. | POST /{namespace}/mailboxes/{mailbox}/warm |
role-unstaffed warn · Not live yet, gaps #8 | Staff the AE, or leave it: engaged companies come to you within a day. | POST /{namespace}/roles/{role}/staff |
JSON
{
"type": "https://startupbuilder.dev/errors/refused",
"title": "Refused",
"status": 422,
"detail": "buying-committee can’t start yet: 1 check fails and 2 warn.",
"checks": [
{
"check": "owned-by-a-person",
"status": "warn",
"observed": "2 of the 60 named have an open Deal a person owns: they stay with that person",
"doc": "/plays/buying-committee#check-owned-by-a-person",
"then": "Task.assign"
},
{
"check": "use-when",
"status": "pass",
"observed": "60 named companies at 200+ units; 3.5 roles found a company",
"doc": "/plays/buying-committee#check-use-when",
"then": "Metric.query"
},
{
"check": "baseline",
"status": "pass",
"observed": "3.3 Deals opened per 100 of these companies in 90 days, n 60",
"doc": "/plays/buying-committee#check-baseline",
"then": "Metric.query"
},
{
"check": "domain-authenticated",
"status": "pass",
"observed": "leaseline.app: 3 of 3 records resolve",
"doc": "/plays/buying-committee#check-domain-authenticated",
"then": "Domain.authenticate"
},
{
"check": "mailbox-warm",
"status": "fail",
"doc": "/plays/buying-committee#check-mailbox-warm",
"fix": "Wait for the warm-up to finish, 14 days from day 0; mapping and the Ads layer run meanwhile.",
"then": "Mailbox.warm"
},
{
"check": "role-unstaffed",
"status": "warn",
"roles": [
"sales-lead"
],
"owned": 2,
"doc": "/plays/buying-committee#check-role-unstaffed",
"fix": "Staff the AE, or leave it: engaged companies come to you within a day.",
"then": "Role.staff"
}
]
}It says no, says why, and names the fix.
| Check | Fix (one call) | Your time | Wait |
|---|---|---|---|
owned-by-a-person · warn (gaps #8): 2 of 60 have a person-owned Deal; they leave the draw | POST /{namespace}/tasks/{task}/assign drafts into that owner’s queue | 0 min | none |
use-when · baseline · pass: 60 named, 3.5 roles each · 3.3 per 100, n 60 | POST /{namespace}/metrics/query on committee-deal-lift | 1 min | none |
domain-authenticated · mailbox-warm · pass · fail: sdr@ warmed 0 of 14 days | POST /{namespace}/mailboxes/{mailbox}/warm | 2 min | 14 days |
role-unstaffed · warn (gaps #8): no AE, so engaged companies come to you | POST /{namespace}/roles/{role}/staff, or leave it | 0 min | none |
Your number · Before 3.3 Deals per 100 named · Now 16.7 per 100 treated,
Contact data costs $0.06 per member found (POST /{namespace}/contacts/{contact}/enrich), each note $0.04 from your Domain (Worker cost), and a printed note to a Priority 1 owner $4.80 with postage. That comes to about $20 a month at 30 treated companies; the Ads layer bills through account-ads.
When it starts
| When | Trigger id | Starts on | Window | How it gets in |
|---|---|---|---|---|
| A member asks for a meeting, a price or a pilot | member-hand-raise | event on Prospect.engaged where asks for a Meeting, a Price, a pilot or the security report | to the AE within 1 business day | the member’s reply, through POST /{namespace}/prospects/{prospect}/engage |
| A member replies, accepts a meeting or views the committee page | member-engaged | event on Prospect.engaged where replies, accepts a Meeting, or views the committee Page | 14 d | the same |
| Funding, hiring or a rival complaint at a treated company | named-organization-moment | event on Company.funded where funding, hiring, a technology change, a filing or a rival complaint at a treated company | a reason for 30 d | POST /{namespace}/monitors/{monitor}/check on each company’s public pages |
+ 5 more for pricing visits, surges, ad engagement, role changes and holdout reads (?lanes=) |
{
"$id": "https://api.sb/leaseline.app/events/event_1426" ,
"$type": "Event",
"name": "Prospect.engaged",
"at": "2026-10-19T15:12:48Z" ,
"seq": 1426,
"data": {
"organization": {
"$id": "https://api.sb/leaseline.app/organizations/organization_102" ,
"name": "Calloway Residential",
"list": "treated"
},
"prospect": {
"$id": "https://api.sb/leaseline.app/prospects/prospect_310" ,
"role": "operations lead"
},
"engaged": 2
}
}# each delivery is signed with the Watch’s secret
curl -X POST https://api.sb/leaseline.app/watches \
-H "Authorization: Bearer $STARTUP_BUILDER_API_KEY" \
-H "Content-Type: application/json" \
-d '{"selector":"Prospect.engaged","url":"https://leaseline.app/hooks/sb"}'
npx startup-builder trigger Prospect.engaged --like event_1426 # replays the second engaged member
npx startup-builder clock advance --by 1d # runs `sales-capacity` if the AE has not claimed itWho runs it
SDR · your agent (role:, worker_2) holds the Key Result, maps each committee and writes to its members. It hands engaged companies to AE · Priya Shah (person) (role:, worker_3, staffed on day 9) and every note to an owner to you (Dana Okafor, person, worker_1). Your number links to Did it work.
| Option | Rung today | Evidence (passed of n) | Moves up at | Drops back when | You can |
|---|---|---|---|---|---|
| Write to the next member | You approve each one | 38 of 40 approved unedited | at 50 approved, 95 % unedited and no Stop in 30 days | a hostile-reply Stop → every note waits for you | POST /{namespace}/approvals/{approval}/approve · POST /{namespace}/approvals/{approval}/refuse |
| Send your note to the buyer | You approve each one, on every rung | 9 of 9, 4 printed | never | — | POST /{namespace}/approvals/{approval}/approve |
| Map the committee · Ads only | It does it | 30 of 30 mapped, 1 of 20 checked wrong · 13 of 13 | — | a wrong-person Stop → mapping pauses | POST /{namespace}/actions/{action}/redirect |
| To the AE · Not now | It does it | 7 of 7 · 4 held | — | — | POST /{namespace}/tasks/{task}/claim |
| Never: a note to a colleague after a stop, a touch during a crisis, a gift over its cap | To a person, every time | 1 gift refused, 0 sent | never | — | POST /{namespace}/processes/{process}/pause |
What it reads · What it may call. It reads each company’s public pages and its members’ public roles; a reply is data, never instructions, and no text in it picks the next person written to. One member’s stop ends every note to the whole company. Its tools are POST /{namespace}/contacts/{contact}/enrich, POST /{namespace}/prospects, POST /{namespace}/messages/{message}/schedule, PATCH /{namespace}/audiences/{id}, POST /{namespace}/leads/{lead}/assign, POST /{namespace}/tasks/{task}/assign, and any other call becomes an Approval under the Role’s Mandate.
You hold the SDR Key Result: 20 Deals opened per 100 named companies by 2026-12-31. ← worker, metric
On each reason, engagement or role change, choose one option and say why. ← triggers, chooses
Write to one member a week, with something made for that role. ← your file, line 4
Owners and principals at Priority 1 companies hear from Dana, after her OK. ← your file, line 5
One member’s stop ends every note to that company. ← organization-stopThe slow loop. The weekly Decisions kept the one-member-a-week pace and the 2-engaged hand-off line, and no Change was merged in the window, so there is no replay or read-back to print.
Bring your own agent (folded) starts at You approve each one; mapping it does is hand-checked on 20 members before any note sends.
npx startup-builder eval --scenario buying-committee-60 --agent "claude -p" --seat prospector # seated: 3.5 roles a company, 5 % wrong in the hand-check · yours: 3.1, 10 % wrong → mapping pauses What it can do next
| Option | Picked when | Decided by | Runs | Hands to | If it’s just you |
|---|---|---|---|---|---|
Map the committee map-the-committee | fewer than 3 verified roles | Your rule (the 3-role line) | POST /{namespace}/contacts/{contact}/enrich → POST /{namespace}/prospects per member; 20 hand-checked | nobody | the same |
Write to the next member write-the-next-member | a live reason, a member due this week | Agent’s call, with its reason | committee-wave: one note per member, a week apart (POST /{namespace}/messages/{message}/schedule) | on reply, the hand-raise row | the same |
Send your note to the buyer note-to-the-buyer | the economic buyer at a Priority 1 company | Your rule (line 5) | founder-buyer-note: email from dana@, or a printed note of 60 words or fewer | you approve each one, due 1 business day · Take this one | you |
Ads only ads-only | no live reason this month | Your rule (the reason test) | PATCH /{namespace}/audiences/{id} on the company list account-ads reads | nobody | the same |
To the AE to-the-ae | a hand-raise, or 2 members engaged | Your rule (the hand-off line) | POST /{namespace}/leads/{lead}/assign → POST /{namespace}/tasks/{task}/assign, Brief attached | POST /{namespace}/tasks/{task}/assign → AE · Priya Shah, due 1 business day (response-1bd) · Take this one | you, within 1 business day |
Not now not-now | a crisis, a hostile reply, or a person-owned Deal | Your rule (rule j) | nothing; names the holder: crisis-hold, hostile-reply or the Deal’s owner | the Deal’s owner · Take this one | you |
| When they write back | Fixture reply | What happens | Who answers | By when | Call |
|---|---|---|---|---|---|
| Interested | “Our renewals are a mess across 6 owners. Can we talk next week?” | hands the company to the AE with the Brief (When it hands to you) | AE · Priya Shah (person) | 1 business day | POST /{namespace}/leads/{lead}/assign |
| Send me pricing | “What would 600 units cost?” | answers with the Pricing Page’s list Price; anything above it goes to the AE | SDR · your agent | 5 min | POST /{namespace}/conversations/{conversation}/answer |
| Not now | “We’re mid-audit until December.” | no note to that member until their date; the company stays on Ads | SDR · your agent | at once | POST /{namespace}/leads/{lead}/nurture |
| Wrong person | “I don’t handle renewals; our leasing manager does.” | marks the role and moves to the leasing manager on the map; it never writes to a name from the text | SDR · your agent | next week’s note | PATCH /{namespace}/prospects/{id} |
| Out of office | an auto-reply until Oct 30 | that member’s note waits for the return date; the next member’s does not | nobody | the return date | POST /{namespace}/messages/{message}/schedule |
| Question it can’t answer | “Can you map to our accounting system’s owner ledgers?” | To the AE, the question in the Brief | AE · Priya Shah (person) | 1 business day | POST /{namespace}/conversations/{conversation}/escalate |
| Stop | “Please stop contacting my colleagues.” | every note to the whole company ends, and it leaves every company list | nobody | at once | POST /{namespace}/suppressions |
When it hands to you
Engaged companies go to AE · Priya Shah (person), due in 1 business day; owners at Priority 1 companies hear from you. Before day 9 every engaged company came to you. What lands in each queue, as captured: one Brief per Role, then the Approval (brief, draft, route and checks are Not live yet, gaps #7).
[
{
"$id": "https://api.sb/leaseline.app/tasks/task_311" ,
"$type": "Task",
"assignee": "worker_3",
"due": "2026-10-20T15:12:00Z" ,
"on": "organization_102",
"brief": {
"who": "Calloway Residential, 900 units for 11 owners" ,
"engaged": [
"Grace Lin, operations lead: replied to the renewals note" ,
"the controller: viewed the committee page"
],
"chose": "to-the-ae",
"why": "2 members engaged",
"reason": "their news page: 3 new owners this year" ,
"notWrittenTo": [
"the owner",
"the leasing manager"
],
"never": [
"a price beyond the list",
"a discount"
]
}
},
{
"$id": "https://api.sb/leaseline.app/tasks/task_287" ,
"$type": "Task",
"assignee": "worker_1",
"due": "2026-10-08T17:00:00Z" ,
"on": "organization_163",
"brief": {
"who": "Ashford Group, owner and principal" ,
"chose": "note-to-the-buyer",
"why": "the economic buyer at a Priority 1 company",
"note": "printed, 52 words, to the verified work address"
}
},
{
"$id": "https://api.sb/leaseline.app/approvals/approval_83" ,
"$type": "Approval",
"verdict": null,
"deadline": "2026-10-08T17:00:00Z" ,
"draft": "Tom, Ashford renews 1,400 leases a year across 9 owners. I built Leaseline to send every notice 60 days out, per owner…" ,
"route": "note-to-the-buyer",
"checks": [
{
"check": "gift-cap",
"status": "pass"
},
{
"check": "crisis-hold",
"status": "pass"
}
]
}
]Each receiver answers with POST /{namespace}/tasks/{task}/claim (Take this one), POST /{namespace}/tasks/{task}/return with a reason, POST /{namespace}/actions/{action}/redirect, POST /{namespace}/approvals/{approval}/approve or POST /{namespace}/approvals/{approval}/refuse, each a one-call window, and an Approval unanswered by its deadline expires and the note never sends. Once the AE claims a company, every member note there stops and replies go to her. A company nobody claims within 1 business day pauses every new first touch (sales-capacity) and goes up through POST /{namespace}/tasks/{task}/escalate.
On time: AE · Priya Shah, 6 of 7 claimed within 1 business day, median 3 h, ■□□□ Too early to tell, n 7 (the 7th waited 27 h and paused new first touches for a day). Your queue: counted by kind: in weeks 1 to 3, 40 note approvals and the 20-member hand-check; since, about 1 hand-off and 1 owner note a week.
The fixed line: POST /{namespace}/deals/{deal}/assign sets owner to the receiving person, the agent is never a Deal’s owner, and Meetings land on the owner’s calendar under the owner’s name.
When it won’t send
| Check (refuses one send) | Refuses | Fix | Then |
|---|---|---|---|
owned-by-a-person (rule j; Not live yet, gaps #8) | a note to a member of a company whose Lead or open Deal a person owns | Leave it to the person who owns it: the draft waits in their queue. | POST /{namespace}/tasks/{task}/assign |
organization-stop | any note to a company where one member asked to stop, or asked you to stop writing colleagues | Leave them off; the stop holds at Company scope. | GET /{namespace}/suppressions |
crisis-hold | any touch for 14 days after a layoff, breach or leadership crisis at the company | Wait the 14 days; the Ads layer pauses too. | GET /{namespace}/events |
gift-cap (printed notes) | a gift over its buyer-class cap, or any gift to a public-sector or healthcare company | Send the note without the gift, or under the cap. | POST /{namespace}/messages/{message}/schedule |
mailbox-warm | a first note from a Mailbox still warming | Wait for the warm-up to finish, 14 days from day 0; mapping runs meanwhile. | POST /{namespace}/mailboxes/{mailbox}/warm |
| Stop (pauses the Play) | Pauses when | Then |
|---|---|---|
bounce | bounces over 2 % of a day’s notes | that Mailbox pauses; POST /{namespace}/mailboxes/{mailbox}/rest |
complaint | complaints near 0.1 % | notes pause on every Mailbox |
reply-floor | interested replies under 1 % after 300 member notes | outreach stops; Ads continue under their own Stops |
hostile-reply | one hostile reply | that company gets nothing for 90 days and the reply goes to you; 3 in 30 days drop a rung |
wrong-person | over 10 % wrong person or role in a hand-check | mapping and unchecked first notes pause |
thin-map | under half the treated companies hold 3 verified roles | outreach pauses and reports the List as hard to map |
sales-capacity | an engaged company waits over 1 business day | every new first touch pauses |
holdout-integrity | held-back companies touched by more than 5 % of the holdout | the draw’s Readout is void and promotion freezes |
spend-limit | Ads, notes, data or model spend at its monthly Limit | that part pauses until the month turns |
kill-switch | you press it | every Tactic and the Ads layer pause; POST /{namespace}/processes/{process}/enable after review |
The captured refusal, then the Stop that fired as a Campaign.paused reason (Not live yet, gaps #2); the company it held is the third thread in Example.
| Check | Fix | Then |
|---|---|---|
crisis-hold fail | Wait the 14 days; the Ads layer pauses too. | GET /{namespace}/events |
owned-by-a-person pass · Not live yet, gaps #8 | — | POST /{namespace}/tasks/{task}/assign |
JSON
{
"type": "https://startupbuilder.dev/errors/refused",
"title": "Refused",
"status": 422,
"detail": "The note to Bayview’s controller did not send: Bayview announced layoffs on Oct 6.",
"checks": [
{
"check": "crisis-hold",
"status": "fail",
"observed": "layoffs announced 2026-10-06",
"doc": "/plays/buying-committee#check-crisis-hold",
"fix": "Wait the 14 days; the Ads layer pauses too.",
"then": "Event.list"
},
{
"check": "owned-by-a-person",
"status": "pass"
}
]
}It says no, says why, and names the fix.
[
{
"reason": {
"limit": "sales-capacity",
"observed": "Ridgeway Homes waited 27 h for a claim",
"bound": "1 business day",
"window": "1 company"
},
"doc": "/plays/buying-committee#stop-sales-capacity" ,
"task": "task_296"
}
]Did it work
The 60 companies were paired by size and split at random, 30 treated and 30 held back (rules m–o). The leaf reads at day 90, on 2026-11-22, so no company has matured: every row is an interim count, and nothing prints as Added. Each figure’s call is POST /{namespace}/metrics/query by node and by arm; every node above the leaf is Not live yet (gaps #4).
16.7 against 3.3 Deals per 100,
- Chose
- to-the-ae
- Why
- at Calloway Residential the operations lead replied to the renewals note and the controller viewed the committee page: 2 members engaged
- From
- map-the-committee · write-the-next-member · note-to-the-buyer · ads-only · to-the-ae · not-now
- Expects
- a Meeting held with Calloway within 14d
- Reopens when
- no Meeting.booked at organization_102 within 14d
- By
- worker_2
JSON
{
"$id": "decisions/decision_503",
"$type": "Decision",
"choice": "to-the-ae",
"reason": "at Calloway Residential the operations lead replied to the renewals note and the controller viewed the committee page: 2 members engaged",
"stakes": "low",
"options": [
"map-the-committee",
"write-the-next-member",
"note-to-the-buyer",
"ads-only",
"to-the-ae",
"not-now"
],
"by": "worker_2",
"on": "organization_102",
"expected": "a Meeting held with Calloway within 14d",
"reopensWhen": "no Meeting.booked at organization_102 within 14d"
}| Node | Agent half | Your half | Added | Confidence | Basis |
|---|---|---|---|---|---|
committee-deal-lift | 16.7 Deals per 100 treated (5 of 30), interim | 3.3 per 100 held back (1 of 30) | — (0 matured; the day-90 read lands 2026-11-22) | ■□□□ Too early to tell | held back at random, in pairs · n 60 · 0 matured · Other Startups’ results +2.0 per 100, ■■□□ Early sign, n 1,240 |
opened-deals-and-trials | 5 Deals | 1 | — | ■□□□ Too early to tell | the same assignment, interim |
new-arr ↑ | $2,393, 1 Customer on the $2,400 plan · Booked: credited, not all caused by this Play | $0 | — · Worth about +$290 a month | ■□□□ Too early to tell (1 vs 0 Customers) | the same · 4 Deals still deciding |
net-new-arr · arr | +$2,393 | $0 | — | ■□□□ Too early to tell | carried from new-arr |
The leaf counts Deals opened after a held Meeting or a written request, per 100 named companies, treated minus held back, at day 90 and day 180; held-back companies get Ads and outreach from no Play but inbound answers.
How it moves it: each treated company heard from a median of 3 roles, a week apart, each opening on a reason of its own, where before one person per company heard a general pitch.
Guardrails: treated against held back, interim: Meetings held per Deal opened, 1.0 against 1.0, and stop requests, 1 of 30 companies against 0.
{
"$id": "https://api.sb/leaseline.app/campaigns/buying-committee" ,
"$type": "Campaign",
"play": "play:buying-committee@1" ,
"path": [
"committee-deal-lift",
"opened-deals-and-trials",
"new-arr",
"net-new-arr",
"arr"
],
"experiment": {
"metric": "committee-deal-lift",
"unit": "per-100",
"heldBack": 30,
"decision": null
},
"readout": {
"value": null,
"n": 60,
"maturing": 60,
"interval": null,
"readability": "inadmissible",
"basis": "held-back",
"pooled": false
},
"ledger": {
"spend": 37,
"workerCost": 4,
"hours": 4.6,
"wonArr": 2393,
"projectedArr": 288,
"paybackDays": 1
}
}Outside benchmark: deals with 3 or more engaged buyer contacts closed at about twice the rate of single-threaded deals (a revenue-intelligence firm’s 2025 study of 1.8M opportunities).
Before it · After it. Before it: account-ads runs its Ads layer, and account-visits and cold-email bring the visits and first replies. After it: the AE’s Meetings start Deals, and champion-follow hears a mapped member who changes jobs.
Example
Leaseline ran it from 2026-08-24 to 2026-10-19 (56 days). 60 named property managers, paired by size: 30 treated and 30 held back. Mapping found 104 members across 4 roles; the hand-check of 20 found 1 wrong role. 17 treated companies held a live reason by day 56; the other 13 got Ads only. Read every captured thread at ?threads=; three follow the tables.
| What happened, treated companies, by option | Decisions | Done | Engaged (what happened) |
|---|---|---|---|
| Map the committee · Write to the next member | 30 · 61 | 104 members · 61 notes | 9 members at 7 companies |
| Send your note to the buyer | 9 | 9 sent, 4 printed | 2 owners replied |
| Ads only · To the AE · Not now | 13 · 7 · 4 | — · 7 handed over · held | 5 Deals opened, 1 won |
| Treated · held back | 30 · 30 | 61 notes · none | 5 Deals, interim · 1 · $2,393 won (credited, not all caused by this Play) |
| At 50 named (the Use it when volume) | about 25 pairs | held back at random; pools at day 180 | Other Startups’ results: +2.0 per 100, ■■□□ Early sign, n 1,240 |
| Day | Event | What happened | Your time |
|---|---|---|---|
| 0 | event_1125 Campaign.created | the 60 named, paired and drawn; the dry run fails mailbox-warm | 30 min |
| 2 | event_1132 Prospect.created, first of 104 | mapping; you hand-checked 20, 1 wrong | 25 min |
| 9 | event_1164 Role.staffed | AE · Priya Shah (person) takes role: | — |
| 14 | event_1192 Mailbox.warmed | the first member notes | — |
| 16 | event_1204 Message.created | the first owner note, printed, to Ashford Group | 5 min |
| 26 | event_1270 Prospect.engaged | the first hand-raise: Ridgeway’s operations lead asked to meet | — |
| 27 | event_1278 Campaign.paused | sales-capacity: Ridgeway waited 27 h; Priya claimed it, and first touches resumed | — |
| 1–56 | event_1141 Approval.created, first of 49 | 40 member notes and 9 owner notes you approved, from the POST /{namespace}/tasks/next log | 3.1 h · total 4.6 h measured, 5 h asked |
Leaseline → Grace Lin, operations lead, Calloway Residential, Oct 13 · Your news page says Calloway took on 3 new owners this year.¹ For an operations lead, that usually means 3 more renewal calendars to keep in step. Leaseline sends every notice 60 days out, per owner, from your own lease dates.² Worth 20 minutes? *Signed with the Role’s disclosure line.*³
Grace, Oct 17 · “Yes, our renewals are a mess across owners.” Oct 19 · the controller viewed the committee page; To the AE sent the Brief to Priya (
task_311), due Oct 20, 15:12.
- With your team getting leaner, Leaseline can take renewals off your plate.
+ Bayview renews about 400 leases a year; Leaseline sends each notice 60 days out, per owner. Ridgeway Homes, 2026-09-19 10:20 · the operations lead: “Can we see it with our 6 owners’ leases?” To the AE went to Priya (
task_296, due Sep 22, 10:20). She claimed it 27 h later, past the line, which paused new first touches for a day;⁴ she held the call on Sep 24, and the Deal is still deciding.
¹ It opens on the company’s own public page. ² Every claim maps to an approved Page. ³ The fixed signature line, compiled from the Role’s disclosure Setting. ⁴ An engaged company that waits over a business day pauses every new first touch.
Your settings
---
holdout: 0.5 # in pairs by size: half the named companies hear only inbound answers
---
Write to one member a week at each named company, with something for their role.
Owners and principals at Priority 1 companies hear from Dana, after her OK. $ npx startup-builder show plays/buying-committee
holdout 0.5 in pairs · one member a week · owners as Dana your file plays/buying-committee.mdx:2,4,5 (Ask 2026-08-24)
family demand · process outbound · worker role:prospector, owns never · chooses 6 (5 rule, 1 read) · sequences committee-wave, founder-buyer-note · Ads layer account-ads · approval every-send · checks owned-by-a-person, organization-stop, crisis-hold, mailbox-warm · stops 10 catalog play:buying-committee@1 Every key from the catalog
Compiled, not written: edit the Play record buying-committee and its Leaseline run, then regenerate. Every step runs from a sentence or a line of code. In your words: the CRM words you know, and where each lives here.