Skip to content

FM Consulting

Scopecraft

AI-assisted proposal drafting for consultants — turns a rough client brief into a client-ready statement of work in minutes, then tracks it from draft to signed decision.

Gallery

Case study

The problem

Every consulting engagement starts with the same repetitive task: turning a rough, informal client brief into a polished, phased statement of work with a timeline and pricing tiers. Most tools built for this (PandaDoc, Proposify, Bonsai) charge an ongoing subscription for what is fundamentally a well-understood document shape, and none of them draft the first version for you — they're templating tools, not drafting tools.

The solution

A consultant pastes in their own rough notes — a paraphrased call, a few bullet points, an informal email — and Claude drafts a complete proposal: a specific problem statement, 3-5 scope phases each with concrete deliverables, a realistic timeline, 2-3 differentiated pricing tiers, and explicit assumptions and exclusions to guard against scope creep. The consultant reviews the draft in a fully editable form — adding or removing scope phases, timeline rows, or pricing tiers, editing any text — before sending. Sending generates a public, unauthenticated share link; a proposal is only editable before it's sent, matching how a real statement of work actually works. When the client opens the link, the proposal automatically flips from "sent" to "viewed" — a real signal, not a guess — and the client can accept (typing their name, captured with a timestamp) or decline (with an optional reason), all without an account. A dashboard tracks every proposal's status at a glance, and an analytics view surfaces win rate, average days from sent to responded, and a full status funnel.

How it was built

One Anthropic call (Claude Opus 4.8, adaptive thinking, structured output via a Zod schema) does the entire drafting job — the schema itself encodes the discipline (2-3 pricing tiers, non-empty assumptions and exclusions, at least one deliverable per scope phase), and the system prompt is tuned specifically against placeholder text ("TBD", "[Client Name]") so every draft reads as genuinely specific to the brief given. The AI-drafted document is stored as validated JSON on the proposal row and re-validated against the same schema on every read, since it's round-tripping through plain string columns rather than native JSON fields. The client-facing share page calls a status-transition function directly from its own Server Component render rather than through a form action — which surfaced a real Next.js 16 constraint during development: revalidatePath can only be called from an actual mutation (a Server Action triggered by a client interaction, or a route handler), not as a side effect of a page's own render. The fix was to drop the revalidatePath call from that specific transition and rely on every route being force-dynamic for freshness instead, keeping the other, genuinely interaction-triggered mutations (send, accept, decline) using revalidatePath as normal.

More projects