@sellable/mcp 0.1.151 → 0.1.152
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/README.md +4 -3
- package/agents/post-find-leads-filter-scout.md +5 -4
- package/agents/post-find-leads-message-scout.md +15 -14
- package/agents/source-scout-linkedin-engagement.md +6 -5
- package/agents/source-scout-prospeo-contact.md +4 -4
- package/agents/source-scout-sales-nav.md +4 -4
- package/dist/index-dev.js +0 -0
- package/dist/index.js +0 -0
- package/dist/tools/cells.js +1 -1
- package/dist/tools/leads.d.ts +36 -3
- package/dist/tools/leads.js +83 -71
- package/dist/tools/prompts.js +9 -9
- package/dist/tools/registry.d.ts +17 -0
- package/dist/tools/rubrics.js +23 -20
- package/package.json +1 -1
- package/skills/create-campaign/SKILL.md +59 -56
- package/skills/create-campaign-v2/SKILL.md +43 -42
- package/skills/create-campaign-v2/SOUL.md +16 -13
- package/skills/create-campaign-v2/core/auto-execute.README.md +16 -17
- package/skills/create-campaign-v2/core/auto-execute.yaml +8 -7
- package/skills/create-campaign-v2/core/flow.v2.json +81 -149
- package/skills/create-campaign-v2/core/policy.md +13 -12
- package/skills/create-campaign-v2/references/approval-gate-framing.md +4 -3
- package/skills/create-campaign-v2/references/filter-leads.md +5 -4
- package/skills/create-campaign-v2/references/lead-validation-preview.md +2 -2
- package/skills/create-campaign-v2/references/sample-validation-loop.md +32 -27
- package/skills/create-campaign-v2/references/step-13-import-leads.md +29 -28
- package/skills/create-campaign-v2/references/watch-guide-narration.md +27 -28
- package/skills/create-campaign-v2-tail/SKILL.md +44 -44
- package/skills/create-rubric/SKILL.md +5 -5
- package/skills/find-leads/SKILL.md +2 -2
- package/skills/generate-messages/SKILL.md +2 -1
- package/skills/providers/prospeo.md +3 -3
- package/skills/providers/sales-nav.md +7 -7
- package/skills/providers/signal-discovery.md +11 -11
package/dist/tools/rubrics.js
CHANGED
|
@@ -95,16 +95,16 @@ async function fetchCampaignOffer(campaignOfferId) {
|
|
|
95
95
|
leadScoringRubrics: v3.rubrics,
|
|
96
96
|
};
|
|
97
97
|
}
|
|
98
|
-
const
|
|
98
|
+
const filterRulesSavedForReviewWatchNarration = {
|
|
99
99
|
stage: "fit-message",
|
|
100
|
-
headline: "Filter rules saved",
|
|
101
|
-
visibleState: "The browser is
|
|
102
|
-
agentIntent: "Codex is
|
|
103
|
-
nextAction: "
|
|
100
|
+
headline: "Filter rules saved for review",
|
|
101
|
+
visibleState: "The browser is showing Filter Rules with the saved criteria.",
|
|
102
|
+
agentIntent: "Codex is waiting for filter approval before the review batch is enriched or scored.",
|
|
103
|
+
nextAction: "Approve or revise the filters",
|
|
104
104
|
progressLabel: "Fit + message",
|
|
105
|
-
safety: "
|
|
105
|
+
safety: "Saved rules are ready to review; downstream row processing remains gated.",
|
|
106
106
|
};
|
|
107
|
-
function
|
|
107
|
+
function shouldKeepFilterRulesVisible(campaign) {
|
|
108
108
|
const currentStep = campaign.currentStep;
|
|
109
109
|
if (!currentStep)
|
|
110
110
|
return true;
|
|
@@ -116,16 +116,15 @@ function shouldMoveToFilterLeads(campaign) {
|
|
|
116
116
|
"filter-choice",
|
|
117
117
|
"create-icp-rubric",
|
|
118
118
|
"filter-rules",
|
|
119
|
-
"apply-icp-rubric",
|
|
120
119
|
].includes(currentStep);
|
|
121
120
|
}
|
|
122
121
|
function buildEnableIcpFiltersPayload(campaign) {
|
|
123
122
|
const payload = {
|
|
124
123
|
enableICPFilters: true,
|
|
125
124
|
};
|
|
126
|
-
if (
|
|
127
|
-
payload.currentStep = "
|
|
128
|
-
payload.watchNarration =
|
|
125
|
+
if (shouldKeepFilterRulesVisible(campaign)) {
|
|
126
|
+
payload.currentStep = "create-icp-rubric";
|
|
127
|
+
payload.watchNarration = filterRulesSavedForReviewWatchNarration;
|
|
129
128
|
}
|
|
130
129
|
return payload;
|
|
131
130
|
}
|
|
@@ -245,7 +244,7 @@ export const rubricToolDefinitions = [
|
|
|
245
244
|
},
|
|
246
245
|
{
|
|
247
246
|
name: "save_rubrics",
|
|
248
|
-
description: "Persist rubric criteria to the campaign. Pass leadScoringRubrics directly to save without drafting. Saving active rubrics enables ICP filtering and
|
|
247
|
+
description: "Persist rubric criteria to the campaign. Pass leadScoringRubrics directly to save without drafting. Saving active rubrics enables ICP filtering and keeps the watched client on Filter Rules for user approval; it does not move to Filter Leads or run filtering by itself.",
|
|
249
248
|
inputSchema: {
|
|
250
249
|
type: "object",
|
|
251
250
|
properties: {
|
|
@@ -580,12 +579,16 @@ export async function saveRubrics(input) {
|
|
|
580
579
|
// cascade blocked.
|
|
581
580
|
let enableICPFiltersSet = false;
|
|
582
581
|
let currentStepSet = false;
|
|
582
|
+
let savedCurrentStep = null;
|
|
583
583
|
try {
|
|
584
584
|
const api = getApi();
|
|
585
585
|
const payload = buildEnableIcpFiltersPayload(campaign);
|
|
586
586
|
await api.put(`/api/v2/campaign-offers/${input.campaignOfferId}`, payload);
|
|
587
587
|
enableICPFiltersSet = true;
|
|
588
|
-
|
|
588
|
+
if (typeof payload.currentStep === "string") {
|
|
589
|
+
savedCurrentStep = payload.currentStep;
|
|
590
|
+
currentStepSet = true;
|
|
591
|
+
}
|
|
589
592
|
}
|
|
590
593
|
catch (error) {
|
|
591
594
|
// Non-fatal: the rubric save already succeeded. Retry the minimum
|
|
@@ -604,17 +607,17 @@ export async function saveRubrics(input) {
|
|
|
604
607
|
}
|
|
605
608
|
return {
|
|
606
609
|
success: true,
|
|
607
|
-
message:
|
|
608
|
-
? `Saved ${normalizedDraft.length} rubric criteria, ICP filtering is ON, and the campaign is
|
|
609
|
-
:
|
|
610
|
+
message: savedCurrentStep === "create-icp-rubric"
|
|
611
|
+
? `Saved ${normalizedDraft.length} rubric criteria, ICP filtering is ON, and the campaign is waiting for filter approval.`
|
|
612
|
+
: currentStepSet
|
|
610
613
|
? `Saved ${normalizedDraft.length} rubric criteria and ICP filtering is ON.`
|
|
611
|
-
:
|
|
614
|
+
: enableICPFiltersSet || campaign.enableICPFilters === true
|
|
615
|
+
? `Saved ${normalizedDraft.length} rubric criteria and ICP filtering is ON.`
|
|
616
|
+
: `Saved ${normalizedDraft.length} rubric criteria to the campaign. WARNING: could not auto-enable ICP filtering — call update_campaign({ campaignId, enableICPFilters: true }) to activate rubric-based filtering.`,
|
|
612
617
|
criteriaCount: normalizedDraft.length,
|
|
613
618
|
deletedCount: deletedRubricIds.length,
|
|
614
619
|
enableICPFiltersSet,
|
|
615
|
-
currentStep:
|
|
616
|
-
? "apply-icp-rubric"
|
|
617
|
-
: (campaign.currentStep ?? null),
|
|
620
|
+
currentStep: savedCurrentStep ?? campaign.currentStep ?? null,
|
|
618
621
|
currentStepSet,
|
|
619
622
|
rubrics: result?.rubrics ?? normalizedDraft,
|
|
620
623
|
activeRubrics: result?.rubrics ?? normalizedDraft,
|
package/package.json
CHANGED
|
@@ -72,10 +72,10 @@ not create, link, or surface local draft files unless the user explicitly asks
|
|
|
72
72
|
for them. Resume, gating, and handoff read campaign state first. The
|
|
73
73
|
watchable campaign exists after the short brief; lead import is bounded to the
|
|
74
74
|
first review batch. After that, the user chooses whether to use filters or skip.
|
|
75
|
-
When filters are chosen, save rubrics,
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
75
|
+
When filters are chosen, save rubrics, get filter approval, then wait for
|
|
76
|
+
message-template approval before enrichment/filtering or Generate Message cells.
|
|
77
|
+
Use Template is the default message path; AI Generated is only an explicit
|
|
78
|
+
opt-out.
|
|
79
79
|
|
|
80
80
|
## Opening Turn Contract
|
|
81
81
|
|
|
@@ -124,9 +124,10 @@ data, compare sources by source volume, sampled ICP fit, activity/warmth
|
|
|
124
124
|
signals, cleanup risk, and confidence basis. If a user asks for a forecast,
|
|
125
125
|
label it explicitly as not estimated from this run.
|
|
126
126
|
|
|
127
|
-
Before any provider prompt, search, source scout, or signal-discovery call,
|
|
128
|
-
|
|
129
|
-
authorizes scouting/search only. The gate
|
|
127
|
+
Before any provider prompt, search, source scout, or signal-discovery call, show
|
|
128
|
+
one source-plan gate and ask for approval. The plan must be visible before the
|
|
129
|
+
question, and this first approval authorizes scouting/search only. The gate
|
|
130
|
+
should say:
|
|
130
131
|
|
|
131
132
|
- given this campaign, the viable source options
|
|
132
133
|
- the recommended first lane
|
|
@@ -143,6 +144,10 @@ why. Do not call `search_signals`, `search_sales_nav`, `search_prospeo`,
|
|
|
143
144
|
`fetch_post_engagers`, or provider-scoped subagents until the user approves this
|
|
144
145
|
source plan or explicitly chooses a different source.
|
|
145
146
|
|
|
147
|
+
If the user already answered a provider approval such as "Approve Prospeo plan",
|
|
148
|
+
that answer satisfies the source-plan gate. Persist the approved provider and
|
|
149
|
+
run the scouting/search next; do not ask a second source-plan approval question.
|
|
150
|
+
|
|
146
151
|
For hiring-led campaigns, do not default to Sales Nav just because the target is
|
|
147
152
|
a role search. Prospeo is the primary lane when the brief asks for companies
|
|
148
153
|
actively hiring specific roles, open-role signals, account/contact coverage, or
|
|
@@ -153,41 +158,42 @@ are likely. Sales Nav is useful for recent LinkedIn activity, role/title
|
|
|
153
158
|
precision, and referral paths, but it does not provide hiring-by-role filters;
|
|
154
159
|
say that distinction plainly in the source-plan gate.
|
|
155
160
|
|
|
156
|
-
After scouting, ask for a second approval on the concrete source action. For
|
|
157
|
-
Signal Discovery, name how many selected posts will be scraped, the target
|
|
158
|
-
engager/source-candidate volume, and the
|
|
159
|
-
Nav or Prospeo, name the specific approved import lane and source lead count.
|
|
161
|
+
After scouting, ask for a second approval on the concrete source action. For
|
|
162
|
+
Signal Discovery, name how many selected posts will be scraped, the target
|
|
163
|
+
engager/source-candidate volume, and the 15-row review/process sample size. For Sales
|
|
164
|
+
Nav or Prospeo, name the specific approved import lane and source lead count.
|
|
165
|
+
|
|
160
166
|
Do not call `import_leads` or `confirm_lead_list` until this second approval is
|
|
161
167
|
granted.
|
|
162
168
|
|
|
163
|
-
For Sales Nav and Prospeo, the second gate approves materializing the source
|
|
164
|
-
lead list, not importing only the review batch. Use the first-page/sample review
|
|
165
|
-
to calculate projected good fits: sampled fit rate after conservative cleanup,
|
|
166
|
-
raw pool size, source target, and expected good-fit count. If the projected
|
|
167
|
-
good-fit pool is below the campaign target
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
169
|
+
For Sales Nav and Prospeo, the second gate approves materializing the source
|
|
170
|
+
lead list, not importing only the review batch. Use the first-page/sample review
|
|
171
|
+
to calculate projected good fits: sampled fit rate after conservative cleanup,
|
|
172
|
+
raw pool size, source target, and expected good-fit count. If the projected
|
|
173
|
+
good-fit pool is below the campaign target, keep refining/broadening filters
|
|
174
|
+
before asking for import approval. Once it clears target, approve `import_leads`
|
|
175
|
+
with a source-list `targetLeadCount` around 1,000 by default (provider cap is
|
|
176
|
+
internal when the raw pool is larger). Only after the source list is ready
|
|
177
|
+
should `confirm_lead_list({ reviewBatchLimit: 15 })` copy confirmed rows into
|
|
178
|
+
the campaign table and return the first 15 review/process rows.
|
|
173
179
|
|
|
174
180
|
For Signal Discovery, the customer-facing approval card must use the exact
|
|
175
181
|
action shape "Approve scraping N Signal Discovery posts?" and the chat summary
|
|
176
182
|
should be a compact `## Source Recommendation` block with:
|
|
177
183
|
|
|
178
|
-
-
|
|
179
|
-
- source-candidate plan: about 1,
|
|
180
|
-
|
|
184
|
+
- goal: about 300 good-fit prospects after cleanup, enrichment, and filters
|
|
185
|
+
- source-candidate plan: about 1,500 raw engagers using a 20% working fit-rate
|
|
186
|
+
assumption unless sampled data supports a different number
|
|
181
187
|
- planning floor: continue with Signal Discovery only when sampled/projected
|
|
182
188
|
fit is at least 10% after cleanup; below that, move to Sales Nav recent
|
|
183
189
|
activity instead of scraping noisy engagers
|
|
184
|
-
- review checkpoint: after the source list exists,
|
|
185
|
-
|
|
190
|
+
- review checkpoint: after the source list exists, copy confirmed source rows
|
|
191
|
+
into the campaign and process only the first 15 for fit and message review
|
|
186
192
|
- a selected-post table with post author/topic, why it fits, and visible
|
|
187
193
|
engagement
|
|
188
194
|
- total visible pool and estimated good-fit pool
|
|
189
|
-
- first pass: build the source list
|
|
190
|
-
|
|
195
|
+
- first pass: build the source list, copy it into the campaign, then process
|
|
196
|
+
only the first 15 leads before scaling
|
|
191
197
|
- fallback: switch to Sales Nav recent activity if sampled/projected fit falls
|
|
192
198
|
below 10%, or if the review batch is vendor-heavy, agency-heavy, or off-ICP
|
|
193
199
|
|
|
@@ -217,17 +223,19 @@ which posts are being sampled in the watched app. The watch guide should say
|
|
|
217
223
|
that we are pulling sample engagers from these posts to confirm the ICP is
|
|
218
224
|
actually engaging and the source is viable.
|
|
219
225
|
|
|
220
|
-
After
|
|
226
|
+
After confirmed source rows exist in the campaign table, use the same registry pattern for
|
|
227
|
+
|
|
221
228
|
post-lead work, but do not load that registry or any deep filter/message prompt
|
|
222
229
|
before the filter-choice question. After `confirm_lead_list`, ask add filters
|
|
223
230
|
vs skip filters immediately. Once the user answers, launch the message scout
|
|
224
231
|
from the same campaign/table basis. If the user chooses filters, also launch the
|
|
225
|
-
filter-leads scout, move to Filter Rules, save rubrics, then
|
|
226
|
-
|
|
227
|
-
filters, move to Messages/message
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
232
|
+
filter-leads scout, move to Filter Rules, save rubrics, then ask for filter
|
|
233
|
+
approval. After approval, keep the browser on Filter Leads while the message
|
|
234
|
+
recommendation is reviewed. If the user skips filters, move to Messages/message
|
|
235
|
+
review. Enrichment/filtering and Generate Message cells wait for message
|
|
236
|
+
approval. AI Generated is an explicit opt-out from the template path. If the
|
|
237
|
+
post-lead agents are absent, the main thread still orchestrates the same
|
|
238
|
+
branches from compact MCP context.
|
|
231
239
|
|
|
232
240
|
Use rendered Markdown for user review surfaces, not fenced code blocks. Keep
|
|
233
241
|
lines short, use indexed section labels and bullets, and translate internal
|
|
@@ -643,29 +651,23 @@ updates.
|
|
|
643
651
|
until `hasMore=false`. Message review requires Message Draft Builder output:
|
|
644
652
|
do not draft from a checklist, local markdown artifact, or parent-thread
|
|
645
653
|
intuition. Use campaign state, campaign brief content, selected source state, and
|
|
646
|
-
|
|
654
|
+
first review/process sample rows as the source of truth; do not read stale local
|
|
647
655
|
markdown such as `message-validation.md`, inspect the database directly, or
|
|
648
656
|
synthesize local validation artifacts from general knowledge.
|
|
649
657
|
5. Create the campaign shell early with the v1 brief so the user can open the
|
|
650
|
-
watch link and see useful setup state immediately.
|
|
651
|
-
|
|
652
|
-
|
|
653
|
-
|
|
654
|
-
are approved
|
|
655
|
-
is synced into the campaign brief. When filters are approved, immediately
|
|
658
|
+
watch link and see useful setup state immediately. Materialize the approved
|
|
659
|
+
source list, copy confirmed rows into the campaign, and process only the
|
|
660
|
+
first 15 review rows after the source is attached to the campaign; do not
|
|
661
|
+
queue workflow cells, attach a sequence, or start until saved filters and the
|
|
662
|
+
message template/token rules are approved. When filters are chosen, immediately
|
|
656
663
|
call `mcp__sellable__update_campaign({ campaignId, enableICPFilters: true, currentStep: "create-icp-rubric", watchNarration })`
|
|
657
664
|
so the watched app moves to Filter Rules while rubrics are drafted/saved.
|
|
658
|
-
After rubrics save,
|
|
659
|
-
|
|
660
|
-
|
|
661
|
-
|
|
662
|
-
Messages
|
|
663
|
-
|
|
664
|
-
`enrichCellId` cells to kick off enrichment/filtering. Move to Messages only
|
|
665
|
-
after at least one review row passes and Generate Message cells are running or
|
|
666
|
-
ready.
|
|
667
|
-
Product Generate Message cells must not run before that template/token
|
|
668
|
-
approval.
|
|
665
|
+
After rubrics save, keep Filter Rules visible for approval; after approval,
|
|
666
|
+
move to Filter Leads and wait there for the background message recommendation.
|
|
667
|
+
If filters are skipped, move to Messages/message review. Queue the bounded
|
|
668
|
+
review-batch `enrichCellId` cells only after message approval. Move to
|
|
669
|
+
Messages only after at least one review row passes and one generated message
|
|
670
|
+
is ready.
|
|
669
671
|
Do not ask the user to approve the brief before shell creation unless they
|
|
670
672
|
explicitly requested a no-write draft; the shell itself is the review surface.
|
|
671
673
|
6. The main thread owns watch navigation. Call
|
|
@@ -673,9 +675,10 @@ updates.
|
|
|
673
675
|
visible work so the user can watch progress in the app: `create-offer` for
|
|
674
676
|
the brief, `pick-provider` or the selected provider step while sourcing,
|
|
675
677
|
`filter-choice` after the review batch, `create-icp-rubric` as soon
|
|
676
|
-
as filters are
|
|
677
|
-
|
|
678
|
-
|
|
678
|
+
as filters are chosen and while saved filters await approval,
|
|
679
|
+
`apply-icp-rubric` after filter approval and message approval while bounded
|
|
680
|
+
enrichment/filter scoring runs, `validate-sample` only as a recovery/legacy
|
|
681
|
+
observation state,
|
|
679
682
|
`auto-execute-messaging` after at least one row passes and review-batch
|
|
680
683
|
messages are being generated or reviewed, `awaiting-user-greenlight` only
|
|
681
684
|
after generated review-batch messages are approved, `settings` for sender
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: create-campaign-v2
|
|
3
|
-
description: Execute the compact JSON-gated shell-first campaign flow: resolve campaign identity, create a watchable CampaignOffer shell with the brief, attach and approve the source,
|
|
3
|
+
description: Execute the compact JSON-gated shell-first campaign flow: resolve campaign identity, create a watchable CampaignOffer shell with the brief, attach and approve the source, copy the confirmed source list into the campaign, process the first 15 review rows, persist rubrics and approved message template, validate the first passing generated message, then hand off to Settings, sequence, and start.
|
|
4
4
|
visibility: internal
|
|
5
5
|
---
|
|
6
6
|
|
|
@@ -40,19 +40,17 @@ for debug output.
|
|
|
40
40
|
4. Create the watchable campaign shell with `create_campaign` and the v1 brief.
|
|
41
41
|
5. Surface the direct watch link.
|
|
42
42
|
6. Choose and approve the lead source.
|
|
43
|
-
7.
|
|
43
|
+
7. Materialize the approved source list, confirm/copy it into the campaign, and
|
|
44
|
+
use only the first 15 rows as the initial review/process sample.
|
|
44
45
|
8. Ask whether to use filters or skip them.
|
|
45
|
-
9. Persist lead rubrics when filters are enabled
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
11. Review and approve/revise the message.
|
|
49
|
-
12. Sync the approved template into the
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
message is ready for review. Do not wait for a stronger sample once that
|
|
54
|
-
first passing message exists; review it, then hand off to Settings, sender,
|
|
55
|
-
sequence, and explicit launch greenlight.
|
|
46
|
+
9. Persist lead rubrics when filters are enabled, then ask approval while the
|
|
47
|
+
app remains on Filter Rules.
|
|
48
|
+
10. Move to Filter Leads only after saved filters are approved.
|
|
49
|
+
11. Review and approve/revise the message template.
|
|
50
|
+
12. Sync the approved template into the brief, then queue bounded
|
|
51
|
+
enrichment/filtering.
|
|
52
|
+
13. Move to Messages after one row passes and one generated message is ready;
|
|
53
|
+
review it, then hand off to Settings, sender, sequence, and launch.
|
|
56
54
|
|
|
57
55
|
There is no normal approval-packet, commit-gate, atomic-mint, or local
|
|
58
56
|
artifact-validation step. Those belong only to legacy validation/rehearsal
|
|
@@ -136,9 +134,9 @@ can be a conversation-signal check if relevant hiring posts are likely, and
|
|
|
136
134
|
Sales Nav is a LinkedIn activity/referral fallback rather than the main hiring
|
|
137
135
|
filter.
|
|
138
136
|
|
|
139
|
-
Before any provider prompt, search, source scout, or signal-discovery call,
|
|
140
|
-
|
|
141
|
-
authorizes source scouting/search only
|
|
137
|
+
Before any provider prompt, search, source scout, or signal-discovery call, show
|
|
138
|
+
one source-plan gate and ask for approval. The gate must include the plan before
|
|
139
|
+
the question, and this first approval authorizes source scouting/search only:
|
|
142
140
|
|
|
143
141
|
- given this campaign, the viable source options
|
|
144
142
|
- the recommended first lane
|
|
@@ -151,7 +149,9 @@ Do not surface blanket source heuristics as product copy. Make the recommendatio
|
|
|
151
149
|
specific to the campaign. If Signal Discovery is recommended, name the exact
|
|
152
150
|
post themes you will search. If the campaign looks unlikely to have relevant
|
|
153
151
|
public conversations, recommend the specific Sales Nav or Prospeo lane instead
|
|
154
|
-
and say why.
|
|
152
|
+
and say why. An approval like "Approve Prospeo plan" satisfies this gate; persist
|
|
153
|
+
the provider and search next. Do not ask a second source-plan question. Do not
|
|
154
|
+
call `search_signals`, `search_sales_nav`, `search_prospeo`,
|
|
155
155
|
`fetch_post_engagers`, or provider-scoped subagents until the user approves this
|
|
156
156
|
source plan or explicitly chooses a different source.
|
|
157
157
|
|
|
@@ -176,17 +176,17 @@ name the specific search/import lane and source lead count. Do not call
|
|
|
176
176
|
`import_leads` or `confirm_lead_list` until this second source-action approval
|
|
177
177
|
is granted.
|
|
178
178
|
|
|
179
|
-
For Sales Nav and Prospeo, do not ask to import only the
|
|
179
|
+
For Sales Nav and Prospeo, do not ask to import only the 15-row review sample at
|
|
180
180
|
the source-action gate. First-page samples are for source math: compute sampled
|
|
181
181
|
fit after conservative cleanup, project how many good-fit prospects the raw
|
|
182
182
|
pool can yield, and keep refining filters while the projected good-fit pool is
|
|
183
|
-
below the campaign target
|
|
184
|
-
campaign/source defaults say otherwise). Once the lane clears the target, ask
|
|
183
|
+
below the campaign target. Once the lane clears the target, ask
|
|
185
184
|
approval to materialize the source list with
|
|
186
|
-
`targetLeadCount
|
|
187
|
-
|
|
188
|
-
`confirm_lead_list
|
|
189
|
-
table for fit and
|
|
185
|
+
`targetLeadCount` around 1,000 source contacts by default (use the provider cap
|
|
186
|
+
internally when the raw pool is larger). After that source list is ready,
|
|
187
|
+
`confirm_lead_list({ reviewBatchLimit: 15 })` copies confirmed source rows into
|
|
188
|
+
the campaign table and returns the first 15 review/process row ids for fit and
|
|
189
|
+
message review.
|
|
190
190
|
|
|
191
191
|
After the user approves this concrete source-action gate, do not show the
|
|
192
192
|
Source Recommendation again and do not ask another source approval question.
|
|
@@ -205,10 +205,11 @@ selected posts exist:
|
|
|
205
205
|
|
|
206
206
|
Use Signal Discovery first.
|
|
207
207
|
|
|
208
|
-
**
|
|
209
|
-
**
|
|
208
|
+
**Goal:** ~300 good-fit prospects after cleanup, enrichment, and filters<br>
|
|
209
|
+
**Working assumption:** ~20% of raw post engagers become good-fit prospects<br>
|
|
210
|
+
**Engagers needed:** ~1,500 raw engagers<br>
|
|
210
211
|
**Planning floor:** continue only when sampled/projected fit is at least 10% after cleanup; below that, switch to Sales Nav recent activity<br>
|
|
211
|
-
**Review checkpoint:** after the source list exists,
|
|
212
|
+
**Review checkpoint:** after the source list exists, copy the confirmed source list into the campaign and process only the first 15 leads for fit and message review<br>
|
|
212
213
|
|
|
213
214
|
### Selected posts
|
|
214
215
|
|
|
@@ -219,19 +220,18 @@ Use Signal Discovery first.
|
|
|
219
220
|
| Divyanshi Sharma | LinkedIn lead-gen system built with Claude Code | ~508 |
|
|
220
221
|
|
|
221
222
|
**Total visible pool:** ~2,813 engagers<br>
|
|
222
|
-
**Estimated good-fit pool at
|
|
223
|
+
**Estimated good-fit pool at 20%:** ~560 prospects before dedupe/risk cleanup
|
|
223
224
|
|
|
224
225
|
### Recommendation
|
|
225
226
|
|
|
226
227
|
Approve scraping these 3 posts.
|
|
227
228
|
|
|
228
|
-
This gives enough volume to
|
|
229
|
+
This gives enough volume to target ~300 good-fit prospects after cleanup, while
|
|
229
230
|
keeping the source tied to people already engaging with Claude Code outbound /
|
|
230
231
|
AI-native sales workflows.
|
|
231
232
|
|
|
232
|
-
**First pass:** build the source list
|
|
233
|
-
|
|
234
|
-
fit and messages before sending.
|
|
233
|
+
**First pass:** build the source list, copy it into the campaign, then process
|
|
234
|
+
only the first 15 leads so we can inspect quality before scaling.
|
|
235
235
|
|
|
236
236
|
**Fallback:** if sampled/projected fit falls below 10%, or if the review batch
|
|
237
237
|
is too vendor-heavy, agency-heavy, or off-ICP, switch to Sales Nav recent
|
|
@@ -245,7 +245,7 @@ authorizes. For Sales Nav/Prospeo it must also show source export math:
|
|
|
245
245
|
`rawResultCount`, `sampledFitRate`, conservative projected fit rate,
|
|
246
246
|
`targetLeadCount` for the source list, and projected good-fit count from that
|
|
247
247
|
export. If projected good-fit count is below target, the recommendation is to
|
|
248
|
-
refine or broaden filters, not to
|
|
248
|
+
refine or broaden filters, not to run a 15-row review sample.
|
|
249
249
|
|
|
250
250
|
Supplied profile CSVs, company/domain CSVs, pasted domains, and existing
|
|
251
251
|
Sellable lead lists are supported, but keep provider mechanics out of the first
|
|
@@ -253,7 +253,7 @@ customer-facing source-choice labels.
|
|
|
253
253
|
|
|
254
254
|
## Post-Lead Workstreams
|
|
255
255
|
|
|
256
|
-
After `confirm_lead_list`
|
|
256
|
+
After `confirm_lead_list` copies a non-empty confirmed source into the campaign and
|
|
257
257
|
`get_rows_minimal({ tableId: workflowTableId })` proves rows exist, ask the
|
|
258
258
|
filter-choice question immediately. Do not call
|
|
259
259
|
`get_post_find_leads_scout_registry`, load filter/message subskill prompts, or
|
|
@@ -271,11 +271,12 @@ are optional only.
|
|
|
271
271
|
When the user chooses filters, immediately call
|
|
272
272
|
`update_campaign({ campaignId, enableICPFilters: true, currentStep: "create-icp-rubric", watchNarration })`
|
|
273
273
|
before rubric thinking or branch work. The watched app should move to Filter
|
|
274
|
-
Rules quickly. After `save_rubrics`, the
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
274
|
+
Rules quickly. After `save_rubrics`, keep the app on Filter Rules so the user
|
|
275
|
+
can read and approve the saved criteria. Only after that approval should
|
|
276
|
+
`update_campaign` move to `apply-icp-rubric` / Filter Leads, where the run waits
|
|
277
|
+
for the message template approval before enrichment, filtering, or Generate
|
|
278
|
+
Message cells are queued. Tell the user the Message Draft Builder is preparing
|
|
279
|
+
the template in the background.
|
|
279
280
|
|
|
280
281
|
Lead Fit Builder persists production rubrics with `save_rubrics` when filters
|
|
281
282
|
are enabled. It must not require `brief.md`, `lead-review.md`, or
|
|
@@ -311,11 +312,11 @@ state before drafting. Do not render message review until
|
|
|
311
312
|
|
|
312
313
|
Load references only when needed:
|
|
313
314
|
|
|
314
|
-
- `references/watch-link-handoff.md` for watch-link
|
|
315
|
-
- `references/watch-guide-narration.md` for
|
|
315
|
+
- `references/watch-link-handoff.md` for watch-link handoff.
|
|
316
|
+
- `references/watch-guide-narration.md` for watch narration.
|
|
316
317
|
- `references/lead-validation-preview.md` for legacy/debug preview shapes.
|
|
317
318
|
- `references/filter-leads.md` for rubric design and `save_rubrics` rules.
|
|
318
|
-
- `references/step-13-import-leads.md` before
|
|
319
|
+
- `references/step-13-import-leads.md` before source copy.
|
|
319
320
|
- `references/sample-validation-loop.md` before review-batch validation.
|
|
320
321
|
- `references/final-handoff-contract.md` for Settings, sender, sequence, and
|
|
321
322
|
start.
|
|
@@ -51,9 +51,11 @@ turn anchored to that:
|
|
|
51
51
|
3. Turn that into a campaign brief and create the watchable campaign shell.
|
|
52
52
|
4. Ask for brief approval before any lead import or sending-adjacent work.
|
|
53
53
|
5. Find likely responders and approve the source.
|
|
54
|
-
6.
|
|
54
|
+
6. Copy the confirmed source list into the campaign and use the first 15 rows as
|
|
55
|
+
the review/process sample.
|
|
55
56
|
7. Filter for fit and draft the reusable message template from the same sample.
|
|
56
|
-
8.
|
|
57
|
+
8. Queue the bounded fit cascade from saved rubrics/run conditions only after the
|
|
58
|
+
message template is approved.
|
|
57
59
|
9. Use Settings for sender selection, sequence attach, and final launch handoff.
|
|
58
60
|
|
|
59
61
|
Approvals only feel safe when the user can see what they are approving. Before
|
|
@@ -81,12 +83,13 @@ example, like `omit the noticed... line` or `use "operators"`. Missing data
|
|
|
81
83
|
should never produce robotic or creepy copy.
|
|
82
84
|
|
|
83
85
|
Approved token guidance is part of the campaign, not just the review. After the
|
|
84
|
-
|
|
85
|
-
campaign brief should carry forward the token fill rules and examples before any
|
|
86
|
+
first review/process sample exists and message generation has a selected
|
|
87
|
+
template, the campaign brief should carry forward the token fill rules and examples before any
|
|
86
88
|
workflow-table cascade is queued: good fills, good omits, bad fills, fallback
|
|
87
89
|
rules, and why the bad fills are blocked.
|
|
88
90
|
The campaign brief must carry forward the token fill rules from review into the
|
|
89
|
-
live campaign state before enrichment, filtering,
|
|
91
|
+
live campaign state before enrichment, filtering, Generate Message cells, sender
|
|
92
|
+
setup, sequence attach, or launch.
|
|
90
93
|
|
|
91
94
|
## Progress Updates
|
|
92
95
|
|
|
@@ -275,17 +278,17 @@ surface install status to the customer.
|
|
|
275
278
|
|
|
276
279
|
For post-lead work, call `get_post_find_leads_scout_registry` after
|
|
277
280
|
the user chooses filters, not before the filter-choice question. After
|
|
278
|
-
`confirm_lead_list`
|
|
279
|
-
|
|
281
|
+
`confirm_lead_list` copies source rows and `get_rows_minimal` proves the first
|
|
282
|
+
review/process sample exists, ask add-filters vs skip-filters
|
|
280
283
|
immediately. Once the user answers, start `post-find-leads-message-scout` /
|
|
281
284
|
message generation from the same campaign/table basis. If the user chooses
|
|
282
285
|
filters, also start `post-find-leads-filter-scout`, move the browser to Filter
|
|
283
|
-
Rules, save rubrics, then
|
|
284
|
-
recommendation is reviewed. If the user
|
|
285
|
-
Messages/message review. The join gate is
|
|
286
|
-
or a resolved skip-filter choice, plus a message
|
|
287
|
-
same campaign/table basis. Enrichment, filtering,
|
|
288
|
-
cells
|
|
286
|
+
Rules, save rubrics, then ask for filter approval. After approval, keep the
|
|
287
|
+
browser on Filter Leads while the message recommendation is reviewed. If the user
|
|
288
|
+
skips filters, move the browser to Messages/message review. The join gate is
|
|
289
|
+
saved-filter approval or a resolved skip-filter choice, plus a message
|
|
290
|
+
recommendation grounded in the same campaign/table basis. Enrichment, filtering,
|
|
291
|
+
and Generate Message cells wait for template approval on the Use Template path.
|
|
289
292
|
|
|
290
293
|
Only promise parallel post-lead work when parallel work actually started. If the
|
|
291
294
|
host cannot or should not launch background branches, say the real sequence:
|
|
@@ -11,19 +11,19 @@ autonomous tail (Step 13, `auto-execute-leads`). All subsequent steps (14
|
|
|
11
11
|
validate-sample, 15 auto-execute-messaging, 16 awaiting-user-greenlight)
|
|
12
12
|
read the already-parsed config; they do not re-load the YAML mid-run.
|
|
13
13
|
|
|
14
|
-
Config values are NOT written to DB. They live on the skill side and
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
the
|
|
14
|
+
Config values are NOT written to DB. They live on the skill side and influence
|
|
15
|
+
tool arguments (e.g. `importLimit` / `sampleSize` controls the first N
|
|
16
|
+
review/process rows after `confirm_lead_list` copies the confirmed source rows
|
|
17
|
+
into the campaign).
|
|
18
18
|
|
|
19
19
|
## Sections
|
|
20
20
|
|
|
21
21
|
### `import`
|
|
22
22
|
|
|
23
|
-
- **`importLimit`** — Review
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
23
|
+
- **`importLimit`** — Review/process sample size used after Step 13 copies the
|
|
24
|
+
confirmed source rows into the campaign. The tail MUST NOT exceed this cap
|
|
25
|
+
before the message template is approved and at least one generated passing
|
|
26
|
+
message is reviewed.
|
|
27
27
|
- **`provider`** — Inherited from the Phase 84 commit decision (saved in
|
|
28
28
|
the committed brief / campaign metadata). Present here so the tail can
|
|
29
29
|
narrate which provider it's running against; it does NOT override the
|
|
@@ -31,19 +31,18 @@ the imported review batch for validation).
|
|
|
31
31
|
|
|
32
32
|
### `sample`
|
|
33
33
|
|
|
34
|
-
- **`sampleSize`** — How many rows the validation loop pulls from the
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
34
|
+
- **`sampleSize`** — How many rows the validation loop pulls from the first
|
|
35
|
+
review/process sample. In v2 this matches the process cap (default 15), so the
|
|
36
|
+
user sees enough real rows to judge the campaign without spending credits on
|
|
37
|
+
hundreds more.
|
|
38
38
|
- **`minProjectedPass`** — Passing-message floor required before handoff.
|
|
39
|
-
The default requires
|
|
39
|
+
The default requires one passing example from the 15-row review sample.
|
|
40
40
|
Math:
|
|
41
41
|
```text
|
|
42
42
|
projectedPass = round(passInSample / sampleSize * importLimit)
|
|
43
43
|
```
|
|
44
|
-
With defaults (sampleSize=
|
|
45
|
-
|
|
46
|
-
floor.
|
|
44
|
+
With defaults (sampleSize=15, importLimit=15), `projectedPass` equals the
|
|
45
|
+
actual review sample pass count. One passing row is exactly at the floor.
|
|
47
46
|
- **`maxRevisionRounds`** — Hard cap before escalating to the user. A
|
|
48
47
|
revision round is one full sample pass that triggered brief revision
|
|
49
48
|
and retried. On stale resume the counter does NOT reset.
|
|
@@ -128,7 +127,7 @@ logs and adjust:
|
|
|
128
127
|
|
|
129
128
|
- `importLimit` higher only if users consistently ask for larger review
|
|
130
129
|
batches and credit spend is acceptable.
|
|
131
|
-
- `sampleSize` higher if a
|
|
130
|
+
- `sampleSize` higher if a 15-row review sample is not enough to judge
|
|
132
131
|
quality for a specific market.
|
|
133
132
|
- `minProjectedPass` lower only if fewer than 3 passing examples is still
|
|
134
133
|
enough for a confident user decision.
|