This is the contract everything reads. SPICED-tagged, speaker-resolved call segments from Grain, joined to HubSpot deals on the deal id, scored in Claude against the SPICED rubric, and every score anchored to a verbatim customer quote. Each rep gets one object per account per week. The coaching card renders it, the manager rollup aggregates it, the Deal Pulse forecasts against it, and the query box answers over it. This document is the spine the engineer builds against.
Derived directly from the real analysis output the scorer already produces. The object joins to the pipeline on the account and deal id, carries the seven SPICED sub-dimensions plus sentiment and call structure, and pairs each dimension score with the customer line, the rep's actual response, and the ideal response that grounds it. No score exists without evidence.
| Field | Type | Description |
|---|---|---|
| Identity and join keys | ||
account | string | Account domain, the join key to HubSpot. Example: cbre.com. |
account_name | string | Human-readable account label, may carry the opportunity thread context. |
rep | string | Deal owner, resolved from the HubSpot owner at ingest and denormalized onto every segment. |
manager | string | The rep's frontline manager, drives the coaching-card routing and the access scope. |
deal_stage | string | Current bowtie stage for the deal. Example: Discovery. |
deal_stage_basis | string | The evidence for the stage call: call types logged, latest activity, days dormant. |
| SPICED, seven sub-dimensions | ||
spiced.situation | {score,state,gap} | score 1 to 5, state (weak, solid, strong), gap boolean. Situation understanding. |
spiced.pain | {score,state,gap} | Same shape. Buyer-articulated pain in their own words. |
spiced.impact | {score,state,gap} | Same shape. The quantified business consequence of the pain. |
spiced.critical_event | {score,state,gap} | Same shape. A dated compelling event with a consequence. |
spiced.decision_criteria | {score,state,gap} | Same shape. What the buyer will judge the decision on. |
spiced.decision_process | {score,state,gap} | Same shape. Who decides, the approval path, multi-threading. |
spiced.engagement | {score,state,gap} | Same shape. Depth and reciprocity of buyer engagement. |
| Impact review, the evidence bundle | ||
impact_review.asked_impact_question | boolean | Did the rep actually ask an impact question. The behavioral binary underneath the score. |
impact_review.basis | string | Why the score is what it is, in plain language tied to what was and was not said. |
impact_review.old_score / new_score | number | Score before and after the review pass, so re-scans are auditable. |
impact_review.best_moment.call | string | Which call the evidence quote comes from, deep-links to the Grain moment. |
impact_review.best_moment.customer_line | string | The verbatim customer quote. The trust anchor, the buyer's actual words. |
impact_review.best_moment.rep_actual | string | What the rep actually said in response, verbatim. |
impact_review.best_moment.ideal_response | string | What a top rep could have said. The rewrite the coaching card renders. |
| Sentiment and call structure | ||
sentiment.score | number | Buyer warmth index, 1 to 5. |
sentiment.trajectory | string | Direction across the call sequence. Example: warming. |
sentiment.note | string | The nuance, including when warmth rides on low-authority champions and inflates true deal health. |
call_structure.score | number | Call-flow discipline, 1 to 5, with a gap boolean. |
call_structure.note | string | Process observations: next-step discipline, talk ratio, ACE opening quality. |
| Diagnosis and coaching | ||
headline_gap | string | The single most deal-limiting gap, named with its dimension and score. |
top_gaps[] | {dimension,score,why}[] | The ranked shortlist of gaps, each with the reason it scored where it did. |
best_coaching_moment | {dimension,call,customer_line,rep_actual,ideal_response,why} | The single moment that best teaches the coachable point, fully sourced. |
recommendation.rep_pattern | string | The rep's recurring pattern across deals, the coaching thesis. |
recommendation.playbook_section | string | The matching Managing for Impact play to run. |
recommendation.one_on_one_focus | string | The concrete agenda for the Tuesday 1:1, tied to the gaps. |
recommendation.primary_prompt / secondary_prompts[] | {label,url} | The coaching prompt links (question bank, role-play, 1:1 agenda) the manager runs. |
| Deal outlook | ||
recommended_next_step | string | The single next action to advance the deal. |
deal_risk.at_risk | boolean | Risk flag for the Deal Pulse row. |
deal_risk.level | string | low, medium, or high. |
deal_risk.reason | string | Why the deal is flagged: dormancy, single-threading, missing Critical Event, unquantified Impact. |
rolling_note | string | The running deal narrative, carried across weekly runs. |
Field names and shapes are lifted verbatim from the live analysis output (cbre.com.result.json). The engineer treats this object as the canonical record; every surface downstream is a projection of it.
Every dimension carries a 1 to 5 quality score, but the object also resolves to a binary Completion for the two dimensions that move revenue: Impact and Critical Event. Completion drives the ELT Deal Pulse and the goal metric. Quality drives the week-over-week growth a rep watches. Both are shown; together they teach the framework at two levels, did you do it and how well.
Did the rep capture a validated Impact and an identified Critical Event at all. This is the revenue-linked headline that drives the completion-lift goal metric and every Deal Pulse row. It is a binary the scorer detects against the locked definitions below.
How well they did it, the depth score already in the object as score per dimension. This is the coaching signal and the week-over-week delta a rep watches. Growth trajectory is the frame, not a static grade.
These two definitions are the exact binary the scorer detects and the bar the completion-lift goal metric is measured against. In the CBRE object, both fail: Impact scores 2 (a named pain with no cost number the buyer owns) and Critical Event scores 1.5 (a Q3 budget cue with no dated consequence). Neither is complete.
The deal moves through the bowtie stages the Deal Pulse already tracks: Educate, Orchestrate, Define, and Trade or SOW. Each transition has a SPICED completion that must hold before the deal earns the next stage. A deal sitting in a stage without its gating element complete is a forecast risk and a coaching trigger on the same row.
| Bowtie stage | SPICED elements in play | Completion that gates the transition out |
|---|---|---|
| Educate | Situation, Pain | Situation understood and buyer-articulated Pain captured in the buyer's own words. Front-half SPICED is the entry bar to Orchestrate. |
| Orchestrate | Impact, Engagement | Impact complete: a quantified consequence tied to a metric the buyer owns. Without it, the deal is warm but unqualified and should not advance to Define. |
| Define | Critical Event, Decision Criteria, Decision Process | Critical Event complete: a dated event with a consequence, plus a mapped decision process reaching the economic buyer. This is the gate most deals fail silently. |
| Trade / SOW | Decision Process, Decision Criteria | Confirmed approval path, criteria the buyer will judge on, and a mutual action plan. The deal is defensible in the forecast. |
The object stages CBRE at Discovery inside Educate to Orchestrate. Situation (3.5) and Pain (3.8) clear the Educate gate, but Impact (2) is incomplete, so the deal has not truly earned Orchestrate to Define. Critical Event (1.5) and single-threaded Decision Process (2.2) mean the Define gate is nowhere close. The completion binaries make the stall structural and visible, not a matter of rep optimism.
The weekly run is a batch dispatch of five stages. Stage 0 is deterministic TypeScript; stages 1 through 4 are Claude skills. The extract stage fans out one task per rep and runs full SPICED in a single pass, which is what kills the corpus-reload and quote-misattribution problems that broke prior attempts. Each agent below declares its inputs, outputs, entry condition, exit condition, and handoff.
deal_risk plus single-threading and staleness rules.Between compute (Layer 2, where the data lives) and the app (Layer 3), a single one-way gate serializes derived artifacts to a versioned JSON schema and pushes them out over one allowlistable endpoint. Nothing inbound to the customer environment is opened. This is the most security-load-bearing artifact in the system; its schema is designed first. What crosses is bounded below.
// The versioned payload that crosses Layer 2 to Layer 3. // The ingest Worker rejects anything that does not match this schema. { "schema_version": "ws2.1", "generated_at": "<ISO 8601 timestamp>", "scope": { "account": "string", "rep": "string", "manager": "string" }, // 1. Derived insight and scores (the object, minus raw) "spiced": { "situation": {"score": 1..5, "state": "string", "gap": bool}, /* + 6 dims */ }, "completion": { "impact": bool, "critical_event": bool }, "headline_gap": "string", "recommendation": { "one_on_one_focus": "string", "playbook_section": "string" }, "deal_risk": { "at_risk": bool, "level": "string", "reason": "string" }, // 2. Exactly ONE short attributed quote per coaching point // bounded to a rolling 120-day window (lookback AND retention) "evidence_quote": { "customer_line": "string", // short excerpt, derived-OK "call_date": "<must be within 120 days>", "deep_link": "<points back into Grain, recording stays there>" }, // 3. Usage telemetry only "telemetry": { "event": "string", "timestamp": "string", "behavior_tag": "string", "actor": "anonymized" } // 4. NEVER crosses: raw transcripts, full recordings, utterance logs, // any quote from a call older than 120 days. }
Derived insight and scores cross. Exactly one short attributed quote per coaching point crosses, bounded to a rolling 120-day window as both lookback and retention. Usage telemetry crosses. Raw transcripts and full recordings never cross; the deep link points back into the customer's own environment, where the recording stays.
This data model and agent handoff is a working draft built from the live analysis output and the locked pre-build decisions. The bowtie stage mapping in section 3 is the piece most likely to move: it should be reconciled with Dan's bowtie workflow slides once they are available, so the stage names, the gating completions, and the transition logic match the canonical WbD bowtie exactly. Everything else, the object schema, the two scores, the five-stage agent decomposition, and the derived-only egress gate, is stable and buildable as written.