@sellable/mcp 0.1.526 → 0.1.528

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.
@@ -1316,6 +1316,14 @@ function normalizeImportProvider(provider) {
1316
1316
  return "signal-discovery";
1317
1317
  return undefined;
1318
1318
  }
1319
+ function inferImportProviderFromLeadListConfig(config) {
1320
+ const provider = normalizeImportProvider(config?.importProvider);
1321
+ if (provider)
1322
+ return provider;
1323
+ if (config?.type === "signal_lead_list")
1324
+ return "signal-discovery";
1325
+ return undefined;
1326
+ }
1319
1327
  function assertPhase126ImportProvider(provider, campaignOfferId) {
1320
1328
  if (!provider) {
1321
1329
  throw new Error(`import_leads requires a supported leadSourceProvider for campaign ${campaignOfferId}. Provide provider or set campaign.leadSourceProvider to sales-nav, prospeo, or signal-discovery, then call get_provider_prompt({ provider, campaignOfferId }).`);
@@ -4202,7 +4210,8 @@ export async function confirmLeadList(input) {
4202
4210
  });
4203
4211
  let resolvedLeadListId = sourceLeadListId;
4204
4212
  let resolvedProvider;
4205
- if (!resolvedLeadListId || currentStep === undefined) {
4213
+ const isSameSourceRefillCopy = currentStep === null && Array.isArray(sourceRowIds) && sourceRowIds.length > 0;
4214
+ if (!resolvedLeadListId || currentStep === undefined || !isSameSourceRefillCopy) {
4206
4215
  const campaign = requestOptions
4207
4216
  ? await api.get(`/api/v2/campaign-offers/${campaignOfferId}`, requestOptions)
4208
4217
  : await api.get(`/api/v2/campaign-offers/${campaignOfferId}`);
@@ -4258,7 +4267,7 @@ export async function confirmLeadList(input) {
4258
4267
  : await api.get(`/api/v3/workflow-tables/${resolvedLeadListId}?mode=meta`);
4259
4268
  const leadListConfig = leadListMeta.table?.config ?? null;
4260
4269
  if (!resolvedProvider) {
4261
- resolvedProvider = normalizeImportProvider(leadListConfig?.importProvider);
4270
+ resolvedProvider = inferImportProviderFromLeadListConfig(leadListConfig);
4262
4271
  }
4263
4272
  const leadListRowCount = leadListMeta.rowCount ?? 0;
4264
4273
  const importProgress = leadListConfig?.importProgress ?? null;
@@ -55,6 +55,24 @@ const SOURCE_PLAN_STATES = new Set([
55
55
  "provider_missing",
56
56
  "blocked",
57
57
  ]);
58
+ const PREP_FAILURE_STATUSES = new Set(["ok", "zero_yield", "low_yield"]);
59
+ const PREP_FAILURE_STAGES = new Set([
60
+ "enrichment_fetch_failure",
61
+ "icp_or_rubric_rejection",
62
+ "message_generation_failure",
63
+ "dependency_blocked",
64
+ "approval_blocked",
65
+ "mixed_or_unknown",
66
+ ]);
67
+ const PREP_FAILURE_RECOMMENDED_ACTIONS = new Set([
68
+ "skip_errored_rows_and_continue_frontier",
69
+ "retry_repairable_cells",
70
+ "review_rubric_or_source_quality",
71
+ "repair_message_generation",
72
+ "wait_for_dependencies",
73
+ "approve_or_repair_approval_cells",
74
+ "inspect_rows",
75
+ ]);
58
76
  async function postRefillTargetPlan(body, workspaceId) {
59
77
  const api = getApi();
60
78
  const requestOptions = workspaceRequestOptions(workspaceId);
@@ -111,6 +129,38 @@ function stringArray(value) {
111
129
  return [];
112
130
  return value.filter((item) => typeof item === "string");
113
131
  }
132
+ function sanitizePrepFailureDiagnosis(value) {
133
+ if (!isRecord(value))
134
+ return undefined;
135
+ const status = stringValue(value.status);
136
+ const stage = stringValue(value.stage);
137
+ const recommendedAction = stringValue(value.recommendedAction);
138
+ if (!status ||
139
+ !PREP_FAILURE_STATUSES.has(status) ||
140
+ !stage ||
141
+ !PREP_FAILURE_STAGES.has(stage) ||
142
+ !recommendedAction ||
143
+ !PREP_FAILURE_RECOMMENDED_ACTIONS.has(recommendedAction)) {
144
+ return undefined;
145
+ }
146
+ const evidence = isRecord(value.evidence) ? value.evidence : {};
147
+ return {
148
+ status,
149
+ stage,
150
+ retryable: booleanValue(value.retryable) ?? false,
151
+ recommendedAction,
152
+ evidence: {
153
+ checkedRows: numberValue(evidence.checkedRows),
154
+ preparedRows: numberValue(evidence.preparedRows),
155
+ affectedRows: numberValue(evidence.affectedRows),
156
+ sampleRowIds: stringArray(evidence.sampleRowIds).slice(0, 10),
157
+ counts: numericRecord(evidence.counts),
158
+ dominantReason: stringValue(evidence.dominantReason) ?? null,
159
+ dominantDetail: stringValue(evidence.dominantDetail) ?? null,
160
+ httpStatus: stringValue(evidence.httpStatus) ?? null,
161
+ },
162
+ };
163
+ }
114
164
  function evidenceLatestMs(evidence) {
115
165
  const latestAt = evidence.latestAt;
116
166
  if (typeof latestAt !== "string")
@@ -301,6 +351,7 @@ function sanitizeExistingRowFrontier(value) {
301
351
  stuckActiveCells: sanitizeStuckActiveCells(value.stuckActiveCells),
302
352
  approvedNotDispatched: sanitizeApprovedNotDispatched(value.approvedNotDispatched),
303
353
  wait: sanitizeWait(value.wait),
354
+ failureDiagnosis: sanitizePrepFailureDiagnosis(value.failureDiagnosis),
304
355
  };
305
356
  }
306
357
  function sanitizeSkippedRungs(value) {
@@ -413,6 +464,7 @@ function sanitizeToolInput(value) {
413
464
  operations: sanitizeRerunErroredCellsOperations(value.operations),
414
465
  wait: sanitizeWait(value.wait),
415
466
  refillReceipt: sanitizeRefillReceipt(value.refillReceipt),
467
+ capSaturated: booleanValue(value.capSaturated) === true ? true : undefined,
416
468
  };
417
469
  }
418
470
  function sanitizePacketIds(value) {
@@ -463,6 +515,8 @@ function sanitizeStructuredAction(action, selectedBySender, mode, rank) {
463
515
  : null,
464
516
  stopCondition: stringValue(action.stopCondition) ?? "",
465
517
  yoloEligible,
518
+ capSaturated: booleanValue(action.capSaturated) === true ? true : undefined,
519
+ prepFailureDiagnosis: sanitizePrepFailureDiagnosis(action.prepFailureDiagnosis),
466
520
  };
467
521
  }
468
522
  function sanitizeLedgerBlockers(value) {
@@ -551,9 +605,11 @@ function sanitizeSourcePlan(value) {
551
605
  sourceLeadListId: stringValue(value.sourceLeadListId) ?? null,
552
606
  leadSourceProvider: stringValue(value.leadSourceProvider) ?? null,
553
607
  sourceFingerprint: stringValue(value.sourceFingerprint) ?? null,
608
+ capSaturated: booleanValue(value.capSaturated) === true ? true : undefined,
554
609
  remainingRowsNeeded: typeof value.remainingRowsNeeded === "number"
555
610
  ? value.remainingRowsNeeded
556
611
  : undefined,
612
+ prepFailureDiagnosis: sanitizePrepFailureDiagnosis(value.prepFailureDiagnosis),
557
613
  };
558
614
  }
559
615
  function sanitizePaidInmail(value) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@sellable/mcp",
3
- "version": "0.1.526",
3
+ "version": "0.1.528",
4
4
  "type": "module",
5
5
  "description": "Sellable MCP server for Claude Code and Codex campaign workflows",
6
6
  "main": "dist/index.js",