@sellable/install 0.1.220 → 0.1.222
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.
package/bin/sellable-install.mjs
CHANGED
|
@@ -991,8 +991,8 @@ const CREATE_CAMPAIGN_ALLOWED_TOOLS = [
|
|
|
991
991
|
"mcp__sellable__record_campaign_review_batch",
|
|
992
992
|
"mcp__sellable__queue_campaign_cells",
|
|
993
993
|
"mcp__sellable__wait_for_campaign_processing",
|
|
994
|
-
"mcp__sellable__refill_campaign_sends",
|
|
995
994
|
"mcp__sellable__resolve_campaign_fill_route",
|
|
995
|
+
"mcp__sellable__get_campaign_refill_state",
|
|
996
996
|
"mcp__sellable__fill_campaign_horizon",
|
|
997
997
|
"mcp__sellable__start_campaign_message_preparation",
|
|
998
998
|
"mcp__sellable__get_campaign_message_preparation_status",
|
package/lib/runtime-verify.mjs
CHANGED
|
@@ -28,14 +28,16 @@ export const REQUIRED_SELLABLE_MCP_TOOLS = [
|
|
|
28
28
|
"get_campaign_messages_preview",
|
|
29
29
|
"attach_sequence",
|
|
30
30
|
"attach_recommended_sequence",
|
|
31
|
-
"refill_campaign_sends",
|
|
32
31
|
"resolve_campaign_fill_route",
|
|
32
|
+
"get_campaign_refill_state",
|
|
33
33
|
"start_campaign_message_preparation",
|
|
34
34
|
"get_campaign_message_preparation_status",
|
|
35
35
|
"cancel_campaign_message_preparation",
|
|
36
36
|
"start_campaign",
|
|
37
37
|
];
|
|
38
38
|
|
|
39
|
+
export const FORBIDDEN_SELLABLE_MCP_TOOLS = ["refill_campaign_sends"];
|
|
40
|
+
|
|
39
41
|
export const CREATE_CAMPAIGN_SMOKE_CALLS = [
|
|
40
42
|
{
|
|
41
43
|
name: "get_auth_status",
|
|
@@ -59,6 +61,14 @@ export const CREATE_CAMPAIGN_SMOKE_CALLS = [
|
|
|
59
61
|
limit: 1200,
|
|
60
62
|
},
|
|
61
63
|
},
|
|
64
|
+
{
|
|
65
|
+
name: "get_subskill_prompt",
|
|
66
|
+
arguments: {
|
|
67
|
+
subskillName: "refill-sends-workflow",
|
|
68
|
+
offset: 0,
|
|
69
|
+
limit: 1200,
|
|
70
|
+
},
|
|
71
|
+
},
|
|
62
72
|
{
|
|
63
73
|
name: "get_subskill_asset",
|
|
64
74
|
arguments: {
|
|
@@ -310,6 +320,7 @@ function summarizeAttempt(result, attempt) {
|
|
|
310
320
|
ok: result.ok === true,
|
|
311
321
|
availableToolCount: result.availableTools?.length || 0,
|
|
312
322
|
missingToolCount: result.missingTools?.length || 0,
|
|
323
|
+
forbiddenToolCount: result.forbiddenTools?.length || 0,
|
|
313
324
|
error: result.error || null,
|
|
314
325
|
createCampaignSmoke: result.createCampaignSmoke
|
|
315
326
|
? {
|
|
@@ -379,6 +390,7 @@ async function verifySellableMcpRuntimeOnce({
|
|
|
379
390
|
|
|
380
391
|
let availableTools = [];
|
|
381
392
|
let missingTools = [...requiredTools];
|
|
393
|
+
let forbiddenTools = [];
|
|
382
394
|
let createCampaignSmoke = null;
|
|
383
395
|
let error = null;
|
|
384
396
|
|
|
@@ -390,7 +402,19 @@ async function verifySellableMcpRuntimeOnce({
|
|
|
390
402
|
});
|
|
391
403
|
availableTools = toolList.tools.map((tool) => tool.name).sort();
|
|
392
404
|
missingTools = missingRequiredTools(toolList.tools, requiredTools);
|
|
393
|
-
|
|
405
|
+
forbiddenTools = availableTools.filter((tool) =>
|
|
406
|
+
FORBIDDEN_SELLABLE_MCP_TOOLS.includes(tool)
|
|
407
|
+
);
|
|
408
|
+
if (forbiddenTools.length > 0) {
|
|
409
|
+
createCampaignSmoke = {
|
|
410
|
+
ok: false,
|
|
411
|
+
missingTools: [],
|
|
412
|
+
calls: [],
|
|
413
|
+
error: `Forbidden MCP tool(s) exposed: ${forbiddenTools.join(", ")}`,
|
|
414
|
+
startedAt: new Date().toISOString(),
|
|
415
|
+
completedAt: new Date().toISOString(),
|
|
416
|
+
};
|
|
417
|
+
} else if (missingTools.length === 0) {
|
|
394
418
|
createCampaignSmoke = await verifyCreateCampaignSmoke({
|
|
395
419
|
client,
|
|
396
420
|
availableTools,
|
|
@@ -420,13 +444,18 @@ async function verifySellableMcpRuntimeOnce({
|
|
|
420
444
|
}
|
|
421
445
|
|
|
422
446
|
return {
|
|
423
|
-
ok:
|
|
447
|
+
ok:
|
|
448
|
+
!error &&
|
|
449
|
+
missingTools.length === 0 &&
|
|
450
|
+
forbiddenTools.length === 0 &&
|
|
451
|
+
createCampaignSmoke?.ok === true,
|
|
424
452
|
skipped: false,
|
|
425
453
|
command,
|
|
426
454
|
args,
|
|
427
455
|
requiredTools,
|
|
428
456
|
availableTools,
|
|
429
457
|
missingTools,
|
|
458
|
+
forbiddenTools,
|
|
430
459
|
createCampaignSmoke,
|
|
431
460
|
stderrTail: stderrLines,
|
|
432
461
|
error: error ? redact(error) : null,
|
package/package.json
CHANGED
|
@@ -47,8 +47,8 @@ allowed-tools:
|
|
|
47
47
|
- mcp__sellable__record_campaign_review_batch
|
|
48
48
|
- mcp__sellable__queue_campaign_cells
|
|
49
49
|
- mcp__sellable__wait_for_campaign_processing
|
|
50
|
-
- mcp__sellable__refill_campaign_sends
|
|
51
50
|
- mcp__sellable__resolve_campaign_fill_route
|
|
51
|
+
- mcp__sellable__get_campaign_refill_state
|
|
52
52
|
- mcp__sellable__fill_campaign_horizon
|
|
53
53
|
- mcp__sellable__start_campaign_message_preparation
|
|
54
54
|
- mcp__sellable__get_campaign_message_preparation_status
|
|
@@ -118,44 +118,38 @@ The default path stays the existing first campaign-table execution slice:
|
|
|
118
118
|
review the normal `reviewBatchLimit:15`, approve reviewed draft rows, then move
|
|
119
119
|
to Settings/sequence/final greenlight. For any plain post-mint fill request
|
|
120
120
|
such as "fill campaigns", "fill up", "refill sends", "max out sends", or
|
|
121
|
-
"load sends",
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
121
|
+
"load sends", hand off to the skill-led refill workflow:
|
|
122
|
+
|
|
123
|
+
```text
|
|
124
|
+
get_subskill_prompt({ subskillName: "refill-sends-workflow" })
|
|
125
|
+
resolve_campaign_fill_route({ intent:"plain" })
|
|
126
|
+
get_campaign_refill_state
|
|
127
|
+
```
|
|
128
|
+
|
|
129
|
+
Plain fill is not an alias for `fill_campaign_horizon` or campaign creation.
|
|
130
|
+
`fill_campaign_horizon` is evergreen-only and must not be used for regular
|
|
131
|
+
campaign refill. Route outcomes are `route:"evergreen_horizon"`,
|
|
132
|
+
`route:"active_campaigns"`, and `route:"ask_create"`; stay in the same `campaignOfferId`/`campaignId` context after minting. If route resolution
|
|
133
|
+
returns `route:"ask_create"`, ask whether to create a normal campaign or
|
|
134
|
+
evergreen campaigns. Campaign creation is allowed only after this route and
|
|
135
|
+
explicit user selection; it is never the default response to plain fill. When
|
|
136
|
+
more leads are needed, the refill workflow must recommend same-campaign
|
|
137
|
+
source-ladder replenishment; do not create warm-post-engager side campaigns,
|
|
138
|
+
on-demand campaigns, or unrelated campaigns. Surface sender-health blockers
|
|
139
|
+
separately from prepared/approved/scheduled counts.
|
|
140
|
+
|
|
137
141
|
Treat active fills as capacity-fill preparation: calculate the bounded target
|
|
138
|
-
from sender capacity when needed, then
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
`
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
`maxRowsToCheck` at 300, then continues in batches capped at 100 newly checked
|
|
150
|
-
rows. It will not pull another row batch while the current checked batch still
|
|
151
|
-
has queueable or active cells. If the user says "approve X messages", use
|
|
152
|
-
`approvalMode:"approve"` but still do not launch. If the user says "schedule X
|
|
153
|
-
sends" or asks to fill sender sends, use `approvalMode:"approve"` only when
|
|
154
|
-
the user explicitly asked for approval, approve exactly the bounded X-message
|
|
155
|
-
cohort during preparation, then re-read scheduled counts; if scheduler-owned
|
|
156
|
-
cells are not present, report prepared/approved/ready awaiting scheduler
|
|
157
|
-
instead of success. Final launch remains a separate explicit user greenlight
|
|
158
|
-
and must verify that bounded cohort and must not broad approve-all.
|
|
142
|
+
from sender capacity when needed, then use the refill workflow to decide source
|
|
143
|
+
replenishment, enrichment/prep, approval policy, and scheduler proof. Mutation
|
|
144
|
+
requires exact visible approval and a fresh `get_campaign_refill_state` reread.
|
|
145
|
+
If the user says "prepare/generate X messages", use message-prep primitives with
|
|
146
|
+
`targetPreparedMessages:X` and default `approvalMode:"mark_ready"`. If the user
|
|
147
|
+
says "approve X messages", use `approvalMode:"approve"` only for the bounded
|
|
148
|
+
cohort and still do not launch. If the user says "schedule X sends", approve
|
|
149
|
+
only when explicitly requested, then reread scheduled counts; if
|
|
150
|
+
scheduler-owned cells are not present, report prepared/approved/ready awaiting
|
|
151
|
+
scheduler instead of success. Final launch remains a separate explicit user
|
|
152
|
+
greenlight and must not broad approve-all.
|
|
159
153
|
When approving reviewed draft rows in the campaign table, resolve the actual
|
|
160
154
|
visible `Approved` cells with `select_campaign_cells({ columnRole: "approved",
|
|
161
155
|
rowSelector: { type: "rowIds", rowIds } })` and `update_cell` those returned
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: refill-sends
|
|
3
|
+
description: Plan regular campaign and evergreen campaign send refill work through the skill-led refill workflow.
|
|
4
|
+
visibility: public
|
|
5
|
+
allowed-tools:
|
|
6
|
+
- mcp__sellable__get_subskill_prompt
|
|
7
|
+
- mcp__sellable__search_subskill_prompts
|
|
8
|
+
- mcp__sellable__resolve_campaign_fill_route
|
|
9
|
+
- mcp__sellable__get_campaign_refill_state
|
|
10
|
+
- mcp__sellable__fill_campaign_horizon
|
|
11
|
+
- mcp__sellable__get_campaign
|
|
12
|
+
- mcp__sellable__get_campaign_message_preparation_status
|
|
13
|
+
- mcp__sellable__start_campaign_message_preparation
|
|
14
|
+
- mcp__sellable__cancel_campaign_message_preparation
|
|
15
|
+
- mcp__sellable__import_leads
|
|
16
|
+
- mcp__sellable__wait_for_lead_list_ready
|
|
17
|
+
- mcp__sellable__confirm_lead_list
|
|
18
|
+
- mcp__sellable__search_signals
|
|
19
|
+
- mcp__sellable__fetch_post_engagers
|
|
20
|
+
- mcp__sellable__search_sales_nav
|
|
21
|
+
- mcp__sellable__lookup_sales_nav_filter
|
|
22
|
+
- mcp__sellable__search_prospeo
|
|
23
|
+
- mcp__sellable__search_prospeo_companies
|
|
24
|
+
- mcp__sellable__confirm_prospeo_company_accounts
|
|
25
|
+
- mcp__sellable__load_csv_linkedin_leads
|
|
26
|
+
- mcp__sellable__load_csv_domains
|
|
27
|
+
- mcp__sellable__list_dnc_entries
|
|
28
|
+
- mcp__sellable__load_csv_dnc_entries
|
|
29
|
+
- mcp__sellable__get_rows
|
|
30
|
+
- mcp__sellable__get_rows_minimal
|
|
31
|
+
- mcp__sellable__get_table_rows
|
|
32
|
+
---
|
|
33
|
+
|
|
34
|
+
# Refill Sends
|
|
35
|
+
|
|
36
|
+
Use this public wrapper for plain operator requests such as "fill", "refill sends",
|
|
37
|
+
"max out sends", "load everyone up", or "fill horizon sends".
|
|
38
|
+
|
|
39
|
+
Load the internal workflow prompt before taking any operational step:
|
|
40
|
+
|
|
41
|
+
```text
|
|
42
|
+
get_subskill_prompt({ subskillName: "refill-sends-workflow" })
|
|
43
|
+
```
|
|
44
|
+
|
|
45
|
+
Then follow that workflow exactly. The default path is read-only research:
|
|
46
|
+
resolve the route, read target refill state, report the next safe step, and stop
|
|
47
|
+
before mutation unless the user has explicitly approved the exact workspace,
|
|
48
|
+
campaign/table/source ids, caps/dates, approval mode, expected side effects,
|
|
49
|
+
and stop/rollback condition.
|
|
50
|
+
|
|
51
|
+
Public concepts are regular campaign and evergreen campaign. Internal direct
|
|
52
|
+
campaign types are unsupported refill targets. `fill_campaign_horizon` is only a
|
|
53
|
+
legacy evergreen-only lower-level primitive after route and refill-state
|
|
54
|
+
evidence proves an evergreen target.
|