The problem
ICP research tells you who fits. Signal monitoring tells you when to act. Neither tells you what to say. Most “AI for sales” briefs ship one of two ways: a bullet-list summary the rep reads once and forgets, or a deck pitched at them that they have to rewrite. Both miss the actual job — give the rep something they can lead with verbatim, anchored on evidence they can audit if pushed.
The other two repos in the pre-outbound stack answered who and when. This one answers what.
What it does
Input: a YAML file with {name, company, meeting_datetime, meeting_type} and an optional prior_context_file. Output: a 7-section markdown brief between 300 and 650 words, plus a structured JSON sidecar for downstream consumers.
Sections (seven; section 2 is omitted when no prior context is provided):
| § | Section | Source |
|---|---|---|
| 1 | Header — who, when, meeting type | input YAML |
| 2 | Last-touch context | manual prior_context_file paste (V1.2 wires Gmail MCP auto-fetch) |
| 3 | ICP fit — score, sector, override reasoning | Account Research Agent via subprocess |
| 4 | Why now — dated, sourced, evidence-verified signals | Signal Monitor via subprocess |
| 5 | Talking points — exactly 3, each tied to evidence | Sonnet synthesizer |
| 6 | Likely objections — 2-3 with response stubs | Sonnet synthesizer |
| 7 | Open with — single sentence | Sonnet synthesizer |
Every §5 talking point is required to cite at least one evidence ID from §3 or §4. The talking_point_provenance clamp rejects floating talking points before the brief ships.
Architectural decisions worth defending
1. Four code-enforced clamps, not four prompt-asked-nicely rules. The brief has four commitments that can’t be talked around because they live in Python, not prose:
evidence_traceable— for every signal in §4, the critic fetches thesource_urland substring-matches the verbatimevidence_quote. Hallucinated quotes attributed to real URLs raiseEvidenceTraceabilityFailedand the brief is not shipped. Same architectural move as the disqualifier clamp in the Account Research Agent and the evidence-traceable clamp in the Signal Monitor.length_compliance— total brief word count must land between 300 and 650. The compiler word-counts the rendered markdown; out-of-band emits aCriticGapwith a concrete word delta and the synthesizer retries with a length hint. Same pattern as the autonomous-blog-autopilot length gate.talking_point_provenance— every §5 talking point must cite at least one evidence ID from the registry built from ARA + SM. Missing or invalid IDs emit aCriticGap; the synthesizer retries. No floating talking points reach the rendered brief.- Spend cap — per-brief budget cap (default $0.50). The
SpendTrackerwraps every API call, charges optimistically, and raisesBudgetExceededbefore the next call would push the run total over the cap.
2. Modular composition via subprocess + stable JSON contracts. MPA calls ARA and SM as separate Python processes — not as imported libraries. Each sibling’s --json flag (shipped in v1.1.0) produces a schema_version-pinned payload on stdout; diagnostic prints route to stderr. MPA refuses to proceed if a sibling returns a schema_version it wasn’t built against — explicit upgrade discipline beats silent breakage. A future repo or external pipeline can compose the same way without importing any of this codebase’s Python.
3. Sequential composition under Anthropic Tier 1 rate limits. Both ARA and SM have their own internal parallel super-steps (ARA: 4 nodes, SM: 6 producers). Firing them concurrently in MPA’s super-step bursts 10+ concurrent Anthropic API calls in the first minute and reliably triggers 429s on Haiku 4.5’s 50k input-tokens/min cap. MPA’s graph runs loader → ARA → SM → synthesizer → critic fully sequentially. Total wall-clock ~3-4 minutes per brief; rate-limit-safe; reversible on Tier 2+. This is the third repo in the trilogy applying the code-over-prompt rule pattern to rate-limit enforcement — different scope (graph-layer vs. SDK-layer vs. semaphore-layer), same architectural commitment.
First live brief
Generated 2026-06-09 against retool.com for a hypothetical first-touch with Jonathan Krangel (Head of RevOps, named in the Account Research Agent’s published Retool sample brief). Wall-clock 4:09. Total cost $0.40 across all three repos’ budgets (MPA’s own spend was $0.017 of its $0.50 cap; ARA spent ~$0.30 on the ICP-fit pass; SM spent $0.095 surfacing one verified signal). Five-of-five critic dimensions passed: evidence=10, length=10, provenance=10, recency_genuine=10, actionability=9.
Pre-meeting brief — Jonathan Krangel @ retool.com
When: 2026-06-23T14:00:00-07:00 | Type: discovery | Role: Head of RevOps
ICP fit: 4.5/5 (Series C · B2B SaaS — enterprise app platform / low-code tooling)
[icp_2]Pitch hook: Hiring first dedicated GTM Engineer — offer RevOps stack audit to align sales tools with Retool’s aggressive AI/enterprise scaling motion[icp_3]Pitch hook: 68 quota-carrying reps but no public GTM tooling disclosure suggests greenfield opportunity[icp_4]Pitch hook: AWS strategic partnership (Dec 2025) signals enterprise go-to-market at scaleWhy now:
[signal_1][relevant_jd] retool.com (2026-05-30) — “As a GTM Engineer, you will build technical solutions for GTM teams, improve internal tools, and experiment with AI to enhance workflows…” — verified verbatim against the live builtinnyc.com source URL by theevidence_traceableclampTalking points:
- You’re hiring your first GTM Engineer — before that hire shapes your stack, a quick audit can prevent them inheriting technical debt on day one. (evidence: icp_2, signal_1)
- 68 quota-carrying reps with no disclosed GTM tooling is a rare greenfield moment — what does your current RevOps stack actually look like under the hood? (evidence: icp_3)
- The AWS partnership signals you’re pushing enterprise at scale now — most RevOps motions aren’t built to operationalize that velocity. (evidence: icp_4)
Likely objections:
- We’re already building our own internal GTM tools — Retool is the product. → That’s exactly why the GTM Engineer JD is interesting — building internal tools is the plan, but the stack those tools sit on still needs architecture decisions. We’re not replacing what you build; we’re the layer underneath it.
- We just posted the GTM Engineer role — we want to let them define the stack. → A pre-hire audit actually gives that person a clean brief to inherit rather than a discovery project. We can hand them findings, not problems.
Open with: You posted the GTM Engineer role three weeks ago — I’m curious what problem finally made that hire feel urgent.
Every quote in §4 was verified against its live source URL by the evidence_traceable clamp before the brief shipped. Every §5 talking point references a specific evidence ID by the talking_point_provenance clamp. The brief came in at 388 words — inside the 300-650 band by the length_compliance clamp.
Eval discipline
Six offline goldens run on every commit: three replays of historical engagements (Bellwether, Felipe@Revert, Saída de Emergência), three edge-case clamp tests. The hallucinated-quote test is the load-bearing one — it deliberately pairs a fabricated evidence_quote with a real-URL HTML fixture that doesn’t contain the quote, and asserts that EvidenceTraceabilityFailed is raised before the brief ships. If that test ever goes green by accident, the architectural commitment is broken.
$ pytest evals/ -v
22 passed in 0.18s
The pre-outbound stack
| Repo | Answers | Output contract |
|---|---|---|
| Account Research Agent | Who fits | JSON via python run.py <domain> --json |
| Signal Monitor | When to act | JSON via python run.py --only <domain> --json |
| Meeting Prep Agent (this tool) | What to say | Markdown + JSON sidecar via python run.py <input.yaml> |
Downstream, Outbound Campaign Crew (CrewAI) extends the stack from pre-outbound into outbound — same governance thesis, second framework.
And the discipline layer above all of them:
| Repo | Role |
|---|---|
| eval-watch | How do you know your agents — all of them — are right? Monthly GH Actions cron, regression gate vs anchored baseline, STATUS.md auto-committed to the repo. |
Three MIT repos. Three tool pages. One architectural thesis: code-enforced rules over prompt-asked-nicely rules, critic-driven self-correction, modular composition through stable CLI contracts.
The pattern shows up seven times across the portfolio — disqualifier clamp in ARA, three clamps in SM, four clamps in MPA, eval discipline in CI (eval-watch), Flow gates + task guardrails in CrewAI (Outbound Campaign Crew). The thesis isn’t a one-shot; it’s a way of thinking that shows up across surfaces — and across frameworks.
Use it
The agent is MIT licensed. Install ARA + SM + MPA all three; configure each .env with API keys; run:
git clone https://github.com/aehirota/meeting-prep-agent
cd meeting-prep-agent
python -m venv .venv && source .venv/bin/activate
pip install -r requirements.txt
cp .env.example .env # fill in ANTHROPIC_API_KEY + ARA_REPO_PATH + SM_REPO_PATH
python -m pytest evals/ # 22/22 offline goldens
python run.py inputs/samples/retool.yaml --print # live composition
Architecture deep-dive in docs/architecture.md. Honest limitations in KNOWN_ISSUES.md — including the explicit rationale for why Tier 3 manual replay scoring is not shipped in V1, the deferred V1.1/V1.2 features, and the trade-offs that come with the strict evidence_traceable clamp (predictable false negatives on JS-rendered pages, same as Signal Monitor).