@sellable/mcp 0.1.132 → 0.1.134

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -190,7 +190,7 @@ export const campaignToolDefinitions = [
190
190
  },
191
191
  watchNarration: {
192
192
  type: "object",
193
- description: "Single structured watch-guide narration object to send with currentStep changes. Include stage, headline, visibleState, agentIntent, and nextAction so the browser guide mirrors Codex progress.",
193
+ description: "Single structured watch-guide narration object to send with currentStep changes. Include what just happened, what the browser is showing now, what Codex is doing next, and nextAction so the browser guide mirrors Codex progress.",
194
194
  properties: {
195
195
  stage: {
196
196
  type: "string",
@@ -211,7 +211,13 @@ export const campaignToolDefinitions = [
211
211
  blockedReason: { type: ["string", "null"] },
212
212
  workerStatuses: { type: "object" },
213
213
  },
214
- required: ["stage", "headline", "visibleState", "agentIntent"],
214
+ required: [
215
+ "stage",
216
+ "headline",
217
+ "visibleState",
218
+ "agentIntent",
219
+ "nextAction",
220
+ ],
215
221
  },
216
222
  leadSourceType: {
217
223
  type: ["string", "null"],
@@ -283,7 +289,7 @@ export const campaignToolDefinitions = [
283
289
  },
284
290
  watchNarration: {
285
291
  type: "object",
286
- description: "Single structured watch-guide narration object to send with currentStep changes. Include stage, headline, visibleState, agentIntent, and nextAction so the browser guide mirrors Codex progress. Do not send separate guideHeadline/guideBody fields.",
292
+ description: "Single structured watch-guide narration object to send with currentStep changes. Include what just happened, what the browser is showing now, what Codex is doing next, and nextAction so the browser guide mirrors Codex progress. Do not send separate guideHeadline/guideBody fields.",
287
293
  properties: {
288
294
  stage: {
289
295
  type: "string",
@@ -304,7 +310,13 @@ export const campaignToolDefinitions = [
304
310
  blockedReason: { type: ["string", "null"] },
305
311
  workerStatuses: { type: "object" },
306
312
  },
307
- required: ["stage", "headline", "visibleState", "agentIntent"],
313
+ required: [
314
+ "stage",
315
+ "headline",
316
+ "visibleState",
317
+ "agentIntent",
318
+ "nextAction",
319
+ ],
308
320
  },
309
321
  interactionMode: {
310
322
  type: "string",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@sellable/mcp",
3
- "version": "0.1.132",
3
+ "version": "0.1.134",
4
4
  "type": "module",
5
5
  "description": "Sellable MCP server for Claude Code and Codex campaign workflows",
6
6
  "main": "dist/index.js",
@@ -93,11 +93,15 @@ Optional debug/UAT draft directory, disabled in normal customer runs:
93
93
  campaign. If shell creation fails, stop and surface the error. There is no
94
94
  no-shell mint fallback in the active shell-first flow.
95
95
  - The main thread owns watch navigation. Before expensive work in each major
96
- stage, call `update_campaign({ campaignId, currentStep })` with the visible UI
97
- step the user should be watching, then continue the work from MCP/product
98
- state. Use `create-offer` for the brief, `pick-provider` or the selected
99
- provider step while sourcing, `filter-choice` after the 15-row review batch is
100
- imported, `messages`/`auto-execute-messaging` for message work,
96
+ stage, call `update_campaign({ campaignId, currentStep, watchNarration })`
97
+ with the visible UI step the user should be watching, then continue the work
98
+ from MCP/product state. Every currentStep switch in a watched run must refresh
99
+ `watchNarration` in the same visible beat. The copy must say what just
100
+ happened, what the browser is showing now, what Codex is doing next, and what
101
+ the user should do next. Use `create-offer` for the brief, `pick-provider` or
102
+ the selected provider step while sourcing, `filter-choice` after the 15-row
103
+ review batch is imported, `apply-icp-rubric` while template approval is
104
+ pending on Filter Leads, `auto-execute-messaging` for approved message work,
101
105
  `awaiting-user-greenlight` for Settings, and `validate-sample` only for
102
106
  recovery/legacy validation if reached. Do not advance `currentStep` backward.
103
107
  - After the shell is minted, normal resume paths read the CampaignOffer first.
@@ -423,13 +427,18 @@ brief`, `Revise target`, `Revise offer/proof`, and `Other / custom`.
423
427
  not visible in this session, use `Approve brief + compare source paths`
424
428
  instead. The customer approves the sourcing decision, not the host
425
429
  implementation detail.
426
- Include a `Watch link:` line before the approval question once
427
- `create_campaign` has returned `watchUrl`. The visible brief must come before
428
- any optional debug persistence. After the brief is synthesized, render the
429
- approval-ready brief in chat and create/update the campaign shell before any
430
- visible `mkdir`, `Write`, artifact-copy, or similar local draft setup. In
431
- normal customer runs, skip local draft setup entirely. File/folder creation is
432
- not the user's value moment; the live campaign brief is.
430
+ Include a `Watch link:` line in the normal chat text immediately before the
431
+ brief approval question once `create_campaign` has returned `watchUrl`. This
432
+ is a hard gate for `AskUserQuestion` / `request_user_input`: do not ask
433
+ `Approve this brief before I start finding leads?` until the user has already
434
+ seen the watch link for the live campaign shell. If the question panel would
435
+ appear without a preceding `Watch link:` line, stop and send the link first.
436
+ The visible brief must come before any optional debug persistence. After the
437
+ brief is synthesized, render the approval-ready brief in chat and
438
+ create/update the campaign shell before any visible `mkdir`, `Write`,
439
+ artifact-copy, or similar local draft setup. In normal customer runs, skip
440
+ local draft setup entirely. File/folder creation is not the user's value
441
+ moment; the live campaign brief is.
433
442
 
434
443
  The approval question can be based on the rendered brief in chat and the live
435
444
  campaign brief. Do not wait for file-write chrome before asking for approval.
@@ -8,6 +8,30 @@
8
8
  "requiredArtifactsApplyWhen": "legacy resume, fixture validation, or explicit debug/UAT mode only",
9
9
  "customerFacingAccess": "Watch link, live campaign currentStep, and concise watchNarration"
10
10
  },
11
+ "watchNarrationTransitionContract": {
12
+ "rule": "Every watched currentStep switch must update watchNarration in the same visible beat. The narration must clearly say what just happened, what page or state the browser is showing now, what Codex is doing next, and what the user should do next. Do not persist optimistic future-step copy; if the step cannot be shown yet, keep the previous currentStep and narrate the current work instead.",
13
+ "requiredFields": [
14
+ "stage",
15
+ "headline",
16
+ "visibleState",
17
+ "agentIntent",
18
+ "nextAction"
19
+ ],
20
+ "copyMustInclude": [
21
+ "what just happened",
22
+ "current visible page/state",
23
+ "next user action",
24
+ "safety boundary when work is gated"
25
+ ],
26
+ "appliesToTools": [
27
+ "create_campaign",
28
+ "update_campaign",
29
+ "update_campaign_brief when it unlocks a step",
30
+ "attach_selected_sender",
31
+ "attach_recommended_sequence",
32
+ "start_campaign"
33
+ ]
34
+ },
11
35
  "commitGateChoices": [
12
36
  "approve",
13
37
  "revise-brief",
@@ -419,6 +443,8 @@
419
443
  "watchUrl"
420
444
  ],
421
445
  "campaignLinkTiming": "before_approval_question",
446
+ "questionToolGate": "Do not call AskUserQuestion or request_user_input for brief approval until the immediately preceding customer-visible chat text includes `Watch link:` with the create_campaign.watchUrl for this campaign shell.",
447
+ "missingWatchLinkRecovery": "If the brief approval question would appear before the watch link, stop and send the rendered brief checkpoint plus `Watch link: {watchUrl}` first; then ask the approve/revise question.",
422
448
  "forbiddenNormalCustomerLinks": [
423
449
  "brief.md",
424
450
  "local draft path",
@@ -428,6 +454,12 @@
428
454
  },
429
455
  {
430
456
  "action": "ask_continue_or_revise_only_if_needed",
457
+ "requiresPriorVisibleContent": [
458
+ "full readable brief",
459
+ "live campaign shell orientation",
460
+ "Watch link: {watchUrl}"
461
+ ],
462
+ "mustNotCallQuestionToolUntil": "The watch link has already been shown in normal chat text after create_campaign returned watchUrl.",
431
463
  "autoContinueWhen": {
432
464
  "artifactStatus": "confirmed",
433
465
  "confidenceIn": [
@@ -1252,6 +1284,7 @@
1252
1284
  }
1253
1285
  ],
1254
1286
  "earlyMessageStartRule": "After auto-execute-leads confirms the 15-row review batch, workflowTableId is ready, and get_rows_minimal proves rows exist, the Message Draft Builder must start immediately from campaignBrief, selected source state, selectedLeadListId, and imported campaign table rows. post-lead-workstreams must reuse that in-flight message branch; if it is missing, launch it before saving rubrics or claiming message progress. This background template draft is provisional speed work only. The message worker must load the full generate-messages prompt; parent-thread fallback loads the same prompt and may use references/message-review-safety-gate.md only as a supplemental approval checklist. It may run beside filter-leads, but no enrichment, ICP scoring, filtering, or product Generate Message cells can queue until save_rubrics and update_campaign_brief both succeed.",
1287
+ "workerStatusContract": "Only show Lead Fit Builder or Message Draft Builder as In Progress when a Task/spawn_agent branch actually started and returned a live branch id, or when the parent-thread fallback is actively doing that branch before the next user-visible step. If a branch is completed in the parent thread, show it as Ready. After update_campaign_brief saves the approved template, Message Draft Builder is Ready even if row-level Generate Message cells have not completed.",
1255
1288
  "finalMessageReconcileRule": "The message recommendation may start before lead-filter.md exists, but before message-review it must cite only imported review-batch rows that still pass the saved rubric/filter results. If the selected winner depends on a row later excluded by saved filters, revise message-generation before message review.",
1256
1289
  "finalTemplateReviewLockRule": "template review does not require a Use Template vs AI Generated mode choice. After filters are enabled, lock template review until saved rubrics exist and the draft reconciles to the approved brief, selected source, and imported review batch. Keep the watched browser on Filter Leads while approval is pending. After approval writes the Approved Message Template into campaignBrief, queue enrichment/ICP scoring for the bounded review batch; prefer at least 2 usable passing/probably passing rows before moving the watched browser to Messages, with weak-sample escalation if only 1 passes.",
1257
1290
  "claudeRule": "In Claude Code, launch the returned message-generation scout immediately after post-import rows exist, then launch/reuse the filter-leads scout when the user chooses filters. When both named agents are available and both branches are ready in the same assistant message, use Task/Agent subagents in parallel; otherwise never claim background message progress until message-generation actually started.",
@@ -1566,7 +1599,7 @@
1566
1599
  {
1567
1600
  "action": "run_or_reconcile_subskill",
1568
1601
  "target": "generate-messages",
1569
- "mode": "DRY MODE",
1602
+ "mode": "approved_template_builder",
1570
1603
  "sampleSource": "imported review-batch rows from selectedLeadListId",
1571
1604
  "toolCallRequiredBeforeArtifacts": [
1572
1605
  "get_subskill_prompt({ subskillName: \"generate-messages\", offset, limit }) until hasMore=false",
@@ -1787,6 +1820,25 @@
1787
1820
  "requiredBeforeCascade": true,
1788
1821
  "writesCampaignState": "campaignBrief.Approved Message Template"
1789
1822
  },
1823
+ {
1824
+ "action": "advance_watch_after_template_saved_before_cascade",
1825
+ "tool": "update_campaign",
1826
+ "requires": [
1827
+ "campaignId",
1828
+ "campaignBrief.Approved Message Template",
1829
+ "leadScoringRubrics"
1830
+ ],
1831
+ "requiredValues": {
1832
+ "currentStep": "apply-icp-rubric",
1833
+ "enableICPFilters": true,
1834
+ "watchNarration.stage": "fit-message",
1835
+ "watchNarration.headline": "Template saved",
1836
+ "watchNarration.workerStatuses.leadFitBuilder": "ready",
1837
+ "watchNarration.workerStatuses.messageDraftBuilder": "ready"
1838
+ },
1839
+ "when": "immediately_after_update_campaign_brief_succeeds_before_get_rows_or_queue_cells",
1840
+ "watchNarrationRule": "Say the approved message template was saved into the campaign brief, the browser is staying on Filter Leads, and Codex is now queueing only the bounded review-batch enrichment/ICP scoring cascade. The Message Draft Builder must be shown as Ready, not In Progress, after this point."
1841
+ },
1790
1842
  {
1791
1843
  "tool": "get_rows_minimal",
1792
1844
  "purpose": "read_bounded_review_batch_cell_ids_after_message_approval",
@@ -2480,7 +2532,8 @@
2480
2532
  "requiredValues": {
2481
2533
  "currentStep": "awaiting-user-greenlight",
2482
2534
  "watchNarration.stage": "review-ready"
2483
- }
2535
+ },
2536
+ "watchNarrationRule": "Say the approved-template cascade has produced reviewable messages and the browser is moving to Settings. Include what just happened, that Settings is now visible for sender selection, and that nothing launches until the user greenlights the final send."
2484
2537
  }
2485
2538
  ],
2486
2539
  "allowedTools": [
@@ -2536,9 +2589,11 @@
2536
2589
  {
2537
2590
  "tool": "update_campaign",
2538
2591
  "requiredValues": {
2539
- "currentStep": "settings"
2592
+ "currentStep": "settings",
2593
+ "watchNarration.stage": "review-ready"
2540
2594
  },
2541
- "purpose": "park the watched UI on Settings before sender selection"
2595
+ "purpose": "park the watched UI on Settings before sender selection",
2596
+ "watchNarrationRule": "Say message review is complete and the browser is now on Settings so the user can connect or choose a sender. Include the safety boundary that no launch happens from Settings."
2542
2597
  },
2543
2598
  {
2544
2599
  "tool": "get_campaign_navigation_state",
@@ -2576,8 +2631,10 @@
2576
2631
  "senderIds": [
2577
2632
  "{selectedSenderId}"
2578
2633
  ],
2579
- "currentStep": "sequence"
2580
- }
2634
+ "currentStep": "sequence",
2635
+ "watchNarration.stage": "review-ready"
2636
+ },
2637
+ "watchNarrationRule": "Say the sender was attached and the browser is moving to Sequence. Explain that Codex is binding the recommended sequence next and that launch still needs explicit greenlight."
2581
2638
  },
2582
2639
  {
2583
2640
  "tool": "get_campaign_navigation_state",
@@ -2591,15 +2648,18 @@
2591
2648
  "campaignId": "{campaignId}",
2592
2649
  "currentStep": "send"
2593
2650
  },
2594
- "purpose": "bind the tier-aware recommended sequence before the launch decision"
2651
+ "purpose": "bind the tier-aware recommended sequence before the launch decision",
2652
+ "watchNarrationRule": "The sequence tool may persist currentStep. If it does, the same visible beat must still explain that the recommended sequence is attached and Send is next; otherwise follow with update_campaign and watchNarration before asking for launch greenlight."
2595
2653
  },
2596
2654
  {
2597
2655
  "tool": "update_campaign",
2598
- "when": "sequence attach response does not persist currentStep",
2656
+ "when": "after recommended sequence attach; required if sequence attach did not persist watchNarration with currentStep",
2599
2657
  "requiredValues": {
2600
- "currentStep": "send"
2658
+ "currentStep": "send",
2659
+ "watchNarration.stage": "review-ready"
2601
2660
  },
2602
- "purpose": "show the Send tab once sender and sequence are ready"
2661
+ "purpose": "show the Send tab once sender and sequence are ready",
2662
+ "watchNarrationRule": "Say the sender and sequence are ready and the browser is now on Send. The next action is the final launch greenlight; do not imply anything has sent yet."
2603
2663
  },
2604
2664
  {
2605
2665
  "tool": "get_campaign_navigation_state",
@@ -2720,7 +2780,8 @@
2720
2780
  "requiredFields": [
2721
2781
  "campaignId"
2722
2782
  ],
2723
- "persistsCurrentStep": "running"
2783
+ "persistsCurrentStep": "running",
2784
+ "watchNarrationRule": "After start_campaign succeeds, the running state must say the final greenlight was accepted, the campaign is now live/running, and the user can watch progress from the campaign."
2724
2785
  },
2725
2786
  {
2726
2787
  "action": "surface_watch_link",
@@ -28,6 +28,9 @@ stage labels. The driver label comes from the watch URL mode (`mode=claude` or
28
28
  - One primary user action per frame.
29
29
  - Headline under 8 words.
30
30
  - Body is 1-2 short sentences total.
31
+ - Every watched step switch must refresh `watchNarration` with current-tense
32
+ copy that says what just happened, what the browser is showing now, what
33
+ Codex is doing next, and what the user should do next.
31
34
  - Say where the user acts: usually `in Claude Code`, `in Codex`, or `in chat`,
32
35
  matching the host that created the watch URL.
33
36
  - `Find Leads` is only the static progress label. The copy must name the active
@@ -46,6 +46,9 @@ real-time updates from your signed-in session.
46
46
 
47
47
  Command-Enter or click that link to watch it in Sellable.
48
48
 
49
+ Now ask the brief approval question. Do not show the approve/revise question
50
+ panel until this `Watch link:` line has appeared in normal chat text.
51
+
49
52
  Cool, let's find leads.
50
53
  ```
51
54