@sellable/mcp 0.1.506 → 0.1.508

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.
@@ -10,6 +10,13 @@ const SAFE_PACKET_ACTION_TYPES = new Set([
10
10
  "approve_messages",
11
11
  "start_paused_campaign",
12
12
  "wait_for_scheduler",
13
+ "wait_for_active_work",
14
+ "wait_for_source_import",
15
+ "copy_selected_source_rows",
16
+ "continue_signal_discovery_source",
17
+ "continue_sales_nav_source",
18
+ "continue_prospeo_source",
19
+ "manual_source_replenishment",
13
20
  "refresh_paid_inmail_credits",
14
21
  "lower_paid_inmail_threshold",
15
22
  "switch_to_connection_lane",
@@ -19,6 +26,14 @@ const MANUAL_ONLY_PACKET_ACTION_TYPES = new Set([
19
26
  "lower_paid_inmail_threshold",
20
27
  "switch_to_connection_lane",
21
28
  "create_connection_campaign",
29
+ "continue_sales_nav_source",
30
+ "continue_prospeo_source",
31
+ "manual_source_replenishment",
32
+ ]);
33
+ const TERMINAL_NO_ACTION_BLOCKER_CODES = new Set([
34
+ "paid_inmail_below_threshold",
35
+ "paid_inmail_credit_missing",
36
+ "paid_inmail_credit_stale",
22
37
  ]);
23
38
  const SOURCE_PLAN_STATES = new Set([
24
39
  "not_needed",
@@ -27,6 +42,8 @@ const SOURCE_PLAN_STATES = new Set([
27
42
  "needs_signal_import",
28
43
  "waiting_for_import",
29
44
  "needs_confirm",
45
+ "needs_same_source_copy",
46
+ "needs_provider_continuation",
30
47
  "source_shortfall",
31
48
  "provider_exhausted",
32
49
  "provider_missing",
@@ -156,6 +173,16 @@ function sanitizeActionCandidate(candidate) {
156
173
  tableId: stringValue(candidate.tableId),
157
174
  tableName: stringValue(candidate.tableName) ?? null,
158
175
  columnId: stringValue(candidate.columnId) ?? null,
176
+ sourceLeadListId: stringValue(candidate.sourceLeadListId) ?? null,
177
+ leadSourceProvider: stringValue(candidate.leadSourceProvider) ?? null,
178
+ sourceFingerprint: stringValue(candidate.sourceFingerprint) ?? null,
179
+ sourceInventoryStatus: stringValue(candidate.sourceInventoryStatus) ?? null,
180
+ sourceRowIds: stringArray(candidate.sourceRowIds),
181
+ sourceRowLimit: typeof candidate.sourceRowLimit === "number"
182
+ ? candidate.sourceRowLimit
183
+ : undefined,
184
+ activeJobId: stringValue(candidate.activeJobId) ?? null,
185
+ activeImportStatus: stringValue(candidate.activeImportStatus) ?? null,
159
186
  targetRows: typeof candidate.targetRows === "number" ? candidate.targetRows : undefined,
160
187
  columnRole: stringValue(candidate.columnRole),
161
188
  rowSelector: sanitizeRowSelector(candidate.rowSelector),
@@ -190,9 +217,25 @@ function sanitizeToolInput(value) {
190
217
  return {};
191
218
  return {
192
219
  senderId: stringValue(value.senderId),
220
+ actionType: allowedActionType(value.actionType),
193
221
  campaignId: stringValue(value.campaignId),
194
222
  tableId: stringValue(value.tableId),
195
223
  columnId: stringValue(value.columnId) ?? null,
224
+ sourceLeadListId: stringValue(value.sourceLeadListId) ?? null,
225
+ leadSourceProvider: stringValue(value.leadSourceProvider) ?? null,
226
+ sourceFingerprint: stringValue(value.sourceFingerprint) ?? null,
227
+ activeJobId: stringValue(value.activeJobId) ?? null,
228
+ activeImportStatus: stringValue(value.activeImportStatus) ?? null,
229
+ sourceInventoryStatus: stringValue(value.sourceInventoryStatus) ?? null,
230
+ sourceRowIds: stringArray(value.sourceRowIds),
231
+ sourceRowLimit: typeof value.sourceRowLimit === "number"
232
+ ? value.sourceRowLimit
233
+ : undefined,
234
+ campaignOfferId: stringValue(value.campaignOfferId),
235
+ provider: stringValue(value.provider),
236
+ allowDifferentSourceLeadList: typeof value.allowDifferentSourceLeadList === "boolean"
237
+ ? value.allowDifferentSourceLeadList
238
+ : undefined,
196
239
  targetPreparedMessages: typeof value.targetPreparedMessages === "number"
197
240
  ? value.targetPreparedMessages
198
241
  : undefined,
@@ -219,6 +262,10 @@ function sanitizePacketIds(value) {
219
262
  campaignId: stringValue(value.campaignId),
220
263
  tableId: stringValue(value.tableId),
221
264
  columnId: stringValue(value.columnId) ?? null,
265
+ sourceLeadListId: stringValue(value.sourceLeadListId) ?? null,
266
+ leadSourceProvider: stringValue(value.leadSourceProvider) ?? null,
267
+ sourceFingerprint: stringValue(value.sourceFingerprint) ?? null,
268
+ activeJobId: stringValue(value.activeJobId) ?? null,
222
269
  };
223
270
  }
224
271
  function sanitizeStructuredAction(action, selectedBySender, mode, rank) {
@@ -241,6 +288,7 @@ function sanitizeStructuredAction(action, selectedBySender, mode, rank) {
241
288
  return {
242
289
  rank,
243
290
  type: action.type,
291
+ actionType: allowedActionType(action.actionType),
244
292
  toolName: stringValue(action.toolName) ?? null,
245
293
  sideEffectClass: stringValue(action.sideEffectClass),
246
294
  ids,
@@ -338,6 +386,9 @@ function sanitizeSourcePlan(value) {
338
386
  reason: stringValue(value.reason),
339
387
  campaignId: stringValue(value.campaignId),
340
388
  tableId: stringValue(value.tableId),
389
+ sourceLeadListId: stringValue(value.sourceLeadListId) ?? null,
390
+ leadSourceProvider: stringValue(value.leadSourceProvider) ?? null,
391
+ sourceFingerprint: stringValue(value.sourceFingerprint) ?? null,
341
392
  remainingRowsNeeded: typeof value.remainingRowsNeeded === "number"
342
393
  ? value.remainingRowsNeeded
343
394
  : undefined,
@@ -586,14 +637,16 @@ function sanitizeRefillTargetPlanResult(result) {
586
637
  const eligibleSenderLedger = sanitizeEligibleSenderLedger(target.eligibleSenderLedger, selectedBySender);
587
638
  const senderRefillPlans = sanitizeStructuredSenderPlans(target.senderRefillPlans, selectedBySender);
588
639
  const globalActionQueue = buildSanitizedGlobalActionQueue(senderRefillPlans);
589
- const status = blockers.some((blocker) => ["sender_disconnected", "sender_sales_nav_disconnected"].includes(String(blocker.code)))
590
- ? "blocked"
591
- : remainingProjectedGap === 0
592
- ? "complete"
593
- : grossTarget <= 0
594
- ? "blocked"
595
- : remainingReadyOrProjectedGap === 0
596
- ? "awaiting_scheduler_after_ready_buffer"
640
+ const hasTerminalNoActionBlocker = globalActionQueue.length === 0 &&
641
+ blockers.some((blocker) => TERMINAL_NO_ACTION_BLOCKER_CODES.has(String(blocker.code)));
642
+ const status = remainingProjectedGap === 0
643
+ ? "complete"
644
+ : grossTarget <= 0
645
+ ? "blocked"
646
+ : remainingReadyOrProjectedGap === 0
647
+ ? "awaiting_scheduler_after_ready_buffer"
648
+ : hasTerminalNoActionBlocker
649
+ ? "blocked"
597
650
  : "needs_refill";
598
651
  return {
599
652
  ...result,
@@ -584,89 +584,6 @@ export declare const allTools: ({
584
584
  required: string[];
585
585
  additionalProperties: boolean;
586
586
  };
587
- } | {
588
- name: string;
589
- description: string;
590
- inputSchema: {
591
- type: string;
592
- properties: {
593
- campaignId: {
594
- type: string;
595
- description: string;
596
- };
597
- tableId: {
598
- type: string;
599
- };
600
- targetPreparedMessages: {
601
- type: string;
602
- minimum: number;
603
- maximum: number;
604
- };
605
- maxRowsToCheck: {
606
- type: string;
607
- minimum: number;
608
- maximum: number;
609
- description: string;
610
- };
611
- batchSize: {
612
- type: string;
613
- minimum: number;
614
- maximum: number;
615
- description: string;
616
- };
617
- maxBatchRows: {
618
- type: string;
619
- minimum: number;
620
- maximum: number;
621
- description: string;
622
- };
623
- approvalMode: {
624
- type: string;
625
- enum: string[];
626
- description: string;
627
- };
628
- autoContinue: {
629
- type: string;
630
- };
631
- disableLowPassRateStop: {
632
- type: string;
633
- description: string;
634
- };
635
- rowSelector: {
636
- type: string;
637
- description: string;
638
- properties: {
639
- type: {
640
- type: string;
641
- enum: string[];
642
- };
643
- basisHash: {
644
- type: string;
645
- };
646
- rowIds: {
647
- type: string;
648
- items: {
649
- type: string;
650
- };
651
- };
652
- limit: {
653
- type: string;
654
- minimum: number;
655
- maximum: number;
656
- };
657
- };
658
- required: string[];
659
- additionalProperties: boolean;
660
- };
661
- workspaceId: {
662
- type: string;
663
- description: string;
664
- };
665
- jobId?: undefined;
666
- };
667
- required: string[];
668
- additionalProperties: boolean;
669
- };
670
587
  } | {
671
588
  name: string;
672
589
  description: string;
@@ -692,9 +609,11 @@ export declare const allTools: ({
692
609
  batchSize?: undefined;
693
610
  maxBatchRows?: undefined;
694
611
  approvalMode?: undefined;
612
+ rowSelector?: undefined;
695
613
  autoContinue?: undefined;
614
+ senderId?: undefined;
615
+ actionType?: undefined;
696
616
  disableLowPassRateStop?: undefined;
697
- rowSelector?: undefined;
698
617
  };
699
618
  additionalProperties: boolean;
700
619
  required?: undefined;
@@ -3131,6 +3050,8 @@ export declare const allTools: ({
3131
3050
  keepInSync?: undefined;
3132
3051
  jobId?: undefined;
3133
3052
  reviewBatchLimit?: undefined;
3053
+ sourceRowIds?: undefined;
3054
+ sourceRowLimit?: undefined;
3134
3055
  allowPartialSourceList?: undefined;
3135
3056
  includeRawImportResult?: undefined;
3136
3057
  selections?: undefined;
@@ -3325,6 +3246,8 @@ export declare const allTools: ({
3325
3246
  keepInSync?: undefined;
3326
3247
  jobId?: undefined;
3327
3248
  reviewBatchLimit?: undefined;
3249
+ sourceRowIds?: undefined;
3250
+ sourceRowLimit?: undefined;
3328
3251
  allowPartialSourceList?: undefined;
3329
3252
  includeRawImportResult?: undefined;
3330
3253
  selections?: undefined;
@@ -3418,6 +3341,8 @@ export declare const allTools: ({
3418
3341
  keepInSync?: undefined;
3419
3342
  jobId?: undefined;
3420
3343
  reviewBatchLimit?: undefined;
3344
+ sourceRowIds?: undefined;
3345
+ sourceRowLimit?: undefined;
3421
3346
  allowPartialSourceList?: undefined;
3422
3347
  includeRawImportResult?: undefined;
3423
3348
  selections?: undefined;
@@ -3583,6 +3508,8 @@ export declare const allTools: ({
3583
3508
  keepInSync?: undefined;
3584
3509
  jobId?: undefined;
3585
3510
  reviewBatchLimit?: undefined;
3511
+ sourceRowIds?: undefined;
3512
+ sourceRowLimit?: undefined;
3586
3513
  allowPartialSourceList?: undefined;
3587
3514
  includeRawImportResult?: undefined;
3588
3515
  selections?: undefined;
@@ -3690,6 +3617,8 @@ export declare const allTools: ({
3690
3617
  keepInSync?: undefined;
3691
3618
  jobId?: undefined;
3692
3619
  reviewBatchLimit?: undefined;
3620
+ sourceRowIds?: undefined;
3621
+ sourceRowLimit?: undefined;
3693
3622
  allowPartialSourceList?: undefined;
3694
3623
  includeRawImportResult?: undefined;
3695
3624
  selections?: undefined;
@@ -3806,6 +3735,8 @@ export declare const allTools: ({
3806
3735
  keepInSync?: undefined;
3807
3736
  jobId?: undefined;
3808
3737
  reviewBatchLimit?: undefined;
3738
+ sourceRowIds?: undefined;
3739
+ sourceRowLimit?: undefined;
3809
3740
  allowPartialSourceList?: undefined;
3810
3741
  includeRawImportResult?: undefined;
3811
3742
  selections?: undefined;
@@ -3911,6 +3842,8 @@ export declare const allTools: ({
3911
3842
  keepInSync?: undefined;
3912
3843
  jobId?: undefined;
3913
3844
  reviewBatchLimit?: undefined;
3845
+ sourceRowIds?: undefined;
3846
+ sourceRowLimit?: undefined;
3914
3847
  allowPartialSourceList?: undefined;
3915
3848
  includeRawImportResult?: undefined;
3916
3849
  selections?: undefined;
@@ -4021,6 +3954,8 @@ export declare const allTools: ({
4021
3954
  keepInSync?: undefined;
4022
3955
  jobId?: undefined;
4023
3956
  reviewBatchLimit?: undefined;
3957
+ sourceRowIds?: undefined;
3958
+ sourceRowLimit?: undefined;
4024
3959
  allowPartialSourceList?: undefined;
4025
3960
  includeRawImportResult?: undefined;
4026
3961
  selections?: undefined;
@@ -4119,6 +4054,8 @@ export declare const allTools: ({
4119
4054
  keepInSync?: undefined;
4120
4055
  jobId?: undefined;
4121
4056
  reviewBatchLimit?: undefined;
4057
+ sourceRowIds?: undefined;
4058
+ sourceRowLimit?: undefined;
4122
4059
  allowPartialSourceList?: undefined;
4123
4060
  includeRawImportResult?: undefined;
4124
4061
  selections?: undefined;
@@ -5009,6 +4946,8 @@ export declare const allTools: ({
5009
4946
  keepInSync?: undefined;
5010
4947
  jobId?: undefined;
5011
4948
  reviewBatchLimit?: undefined;
4949
+ sourceRowIds?: undefined;
4950
+ sourceRowLimit?: undefined;
5012
4951
  allowPartialSourceList?: undefined;
5013
4952
  includeRawImportResult?: undefined;
5014
4953
  selections?: undefined;
@@ -5116,6 +5055,8 @@ export declare const allTools: ({
5116
5055
  keepInSync?: undefined;
5117
5056
  jobId?: undefined;
5118
5057
  reviewBatchLimit?: undefined;
5058
+ sourceRowIds?: undefined;
5059
+ sourceRowLimit?: undefined;
5119
5060
  allowPartialSourceList?: undefined;
5120
5061
  includeRawImportResult?: undefined;
5121
5062
  selections?: undefined;
@@ -6161,6 +6102,8 @@ export declare const allTools: ({
6161
6102
  keepInSync?: undefined;
6162
6103
  jobId?: undefined;
6163
6104
  reviewBatchLimit?: undefined;
6105
+ sourceRowIds?: undefined;
6106
+ sourceRowLimit?: undefined;
6164
6107
  allowPartialSourceList?: undefined;
6165
6108
  includeRawImportResult?: undefined;
6166
6109
  selections?: undefined;
@@ -6315,6 +6258,8 @@ export declare const allTools: ({
6315
6258
  keepInSync?: undefined;
6316
6259
  jobId?: undefined;
6317
6260
  reviewBatchLimit?: undefined;
6261
+ sourceRowIds?: undefined;
6262
+ sourceRowLimit?: undefined;
6318
6263
  allowPartialSourceList?: undefined;
6319
6264
  includeRawImportResult?: undefined;
6320
6265
  selections?: undefined;
@@ -6456,6 +6401,8 @@ export declare const allTools: ({
6456
6401
  keepInSync?: undefined;
6457
6402
  jobId?: undefined;
6458
6403
  reviewBatchLimit?: undefined;
6404
+ sourceRowIds?: undefined;
6405
+ sourceRowLimit?: undefined;
6459
6406
  allowPartialSourceList?: undefined;
6460
6407
  includeRawImportResult?: undefined;
6461
6408
  selections?: undefined;
@@ -6552,6 +6499,8 @@ export declare const allTools: ({
6552
6499
  keepInSync?: undefined;
6553
6500
  jobId?: undefined;
6554
6501
  reviewBatchLimit?: undefined;
6502
+ sourceRowIds?: undefined;
6503
+ sourceRowLimit?: undefined;
6555
6504
  allowPartialSourceList?: undefined;
6556
6505
  includeRawImportResult?: undefined;
6557
6506
  selections?: undefined;
@@ -6598,6 +6547,17 @@ export declare const allTools: ({
6598
6547
  type: string;
6599
6548
  description: string;
6600
6549
  };
6550
+ sourceRowIds: {
6551
+ type: string;
6552
+ items: {
6553
+ type: string;
6554
+ };
6555
+ description: string;
6556
+ };
6557
+ sourceRowLimit: {
6558
+ type: string;
6559
+ description: string;
6560
+ };
6601
6561
  allowPartialSourceList: {
6602
6562
  type: string;
6603
6563
  description: string;
@@ -6807,6 +6767,8 @@ export declare const allTools: ({
6807
6767
  keepInSync?: undefined;
6808
6768
  jobId?: undefined;
6809
6769
  reviewBatchLimit?: undefined;
6770
+ sourceRowIds?: undefined;
6771
+ sourceRowLimit?: undefined;
6810
6772
  allowPartialSourceList?: undefined;
6811
6773
  includeRawImportResult?: undefined;
6812
6774
  };
@@ -6904,6 +6866,8 @@ export declare const allTools: ({
6904
6866
  keepInSync?: undefined;
6905
6867
  jobId?: undefined;
6906
6868
  reviewBatchLimit?: undefined;
6869
+ sourceRowIds?: undefined;
6870
+ sourceRowLimit?: undefined;
6907
6871
  allowPartialSourceList?: undefined;
6908
6872
  includeRawImportResult?: undefined;
6909
6873
  selections?: undefined;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@sellable/mcp",
3
- "version": "0.1.506",
3
+ "version": "0.1.508",
4
4
  "type": "module",
5
5
  "description": "Sellable MCP server for Claude Code and Codex campaign workflows",
6
6
  "main": "dist/index.js",
@@ -92,10 +92,16 @@ When the host can call typed MCP tools, start with:
92
92
  refill_sends({ yolo?: boolean, executionMode?: "manual" | "scheduled" | "yolo", requireWorkspace?: boolean, workspaceId?: string, senders?: string[], senderIds?: string[], senderNames?: string[], horizonSendDays?: number, untilDate?: "YYYY-MM-DD", targetDate?: "YYYY-MM-DD" })
93
93
  ```
94
94
 
95
- That command helper only normalizes arguments and returns the execution
96
- contract. It does not mutate. Continue with the workflow below for route
97
- selection, state rereads, approval gating, source import, preparation, and
98
- bounded approval.
95
+ That command helper normalizes arguments and returns the execution contract. In
96
+ non-yolo mode it does not mutate. In `--yolo`, it may execute exactly one safe
97
+ bounded primitive from the fresh `target.globalActionQueue[0]`, then reread and
98
+ return the new target plan; currently safe primitives are paid-credit refresh,
99
+ existing-row message preparation, same-source row copy, and read-only wait
100
+ rereads. It does not run unbounded approval, lower
101
+ paid-InMail thresholds, switch source families, create campaigns, launch, send,
102
+ or write scheduler rows. Continue with the workflow below for route selection,
103
+ state rereads, approval gating, source import, preparation, and bounded
104
+ approval.
99
105
 
100
106
  ## Workspace Contract
101
107
 
@@ -199,12 +205,20 @@ Structured planner packet:
199
205
  - `manualAlternates` are not yolo actions. Threshold lowering and campaign
200
206
  creation are manual continuations only.
201
207
 
208
+ Refill action ladder: approve generated rows only when an explicit bounded
209
+ approval gate exists, process all existing same-campaign unenriched/unprepared
210
+ rows in bounded batches before any source work, then copy bounded net-new rows
211
+ from the selected source (`selectedLeadListId`, provider, and source
212
+ fingerprint preserved), then use provider-aligned source-more. A new source or
213
+ provider switch changes the reply-rate baseline and is a manual alternate, not a
214
+ `--yolo` side effect.
215
+
202
216
  Run-local paid-credit guard: in `--yolo`, the `refill_sends` MCP command
203
217
  automatically maintains a `refreshedPaidInmailSenderIds` set for the current
204
218
  command call. If its first target plan has stale/missing paid-InMail credit
205
219
  facts, it refreshes each selected sender at most once, reruns
206
220
  `get_refill_target_plan`, and returns the post-refresh `targetPlan` before
207
- choosing the next prep/approval/start action. If fresh facts are still below
221
+ choosing the next prep/source-copy/bounded-approval/read-only wait action. If fresh facts are still below
208
222
  threshold, below-threshold paid-InMail facts fall back to an existing connection
209
223
  lane, the same Sales Nav cascade campaign's connection branch, or a manual
210
224
  continuation.
@@ -238,10 +252,7 @@ next action in `--yolo`. Do not present paid-credit refresh as the next operator
238
252
  action after `refill_sends` returns `autoPaidInmailRefresh` and the
239
253
  post-refresh `targetPlan`. Trust `refill_sends.autoPaidInmailRefresh`: it should
240
254
  show the exact sender ids refreshed once, sender-credit-cache write receipts,
241
- and a returned post-refresh `targetPlan`. Also inspect
242
- `refill_sends.yoloExecution`: if it applied a supported yolo action, continue
243
- from the final returned `targetPlan`; otherwise continue from the post-refresh
244
- packet or `targetPlanBeforeYoloAction`.
255
+ and a returned post-refresh `targetPlan`. Continue from that post-refresh packet.
245
256
  If paid InMail is below threshold after the fresh credit read, report the exact
246
257
  campaign/table/column threshold action or same-campaign connection fallback;
247
258
  `--yolo` does not lower paid-InMail thresholds or create campaigns.
@@ -296,7 +307,7 @@ they change `stateRevision`, not `targetShapeRevision`, and do not require a
296
307
  second approval.
297
308
 
298
309
  In `--yolo`, continue as far as the rendered packet safely allows. After each
299
- apply/prep/start result, reread state, settle processing when needed, and move to
310
+ apply/prep/source-copy/bounded-approval/read-only wait result, reread state, settle processing when needed, and move to
300
311
  the next selected sender or start-eligible same-packet campaign instead of
301
312
  stopping after the first partial result. If no in-packet safe action remains,
302
313
  return concrete continuation options with campaign names, exact ids, which option
@@ -310,7 +321,7 @@ selected sender: selected send days, gross capacity, actual sent cells, future
310
321
  scheduler-owned scheduled cells with non-null `scheduledFor`, projected count,
311
322
  ready-to-schedule buffer, remaining projected gap, paid-InMail feasibility,
312
323
  `targetShapeRevision`, `stateRevision`, and the next MCP primitive that can
313
- reduce the gap. After every apply/prep/start result, wait for processing, reread
324
+ reduce the gap. After every apply/prep/source-copy/bounded-approval/read-only wait result, wait for processing, reread
314
325
  the target plan/refill state, recompute the ledger, then keep applying safe
315
326
  bounded actions until projected coverage fills the target window or a concrete
316
327
  non-scheduler blocker is proven.
@@ -120,12 +120,19 @@ in-progress wait state, not a reason to mark the goal complete or blocked.
120
120
  - `nextActions[0]` is the current sender's smallest safe primitive.
121
121
  - `manualAlternates` are not yolo actions. Threshold lowering and campaign
122
122
  creation are manual continuations only.
123
+ Refill action ladder: approve generated rows only when an explicit bounded
124
+ approval gate exists, process all existing same-campaign
125
+ unenriched/unprepared rows in bounded batches before any source work, then
126
+ copy bounded net-new rows from the selected source (`selectedLeadListId`,
127
+ provider, and source fingerprint preserved), then use provider-aligned
128
+ source-more. A new source or provider switch changes the reply-rate baseline
129
+ and is a manual alternate, not a `--yolo` side effect.
123
130
  Run-local paid-credit guard: in `--yolo`, the `refill_sends` MCP command
124
131
  automatically maintains a `refreshedPaidInmailSenderIds` set for the current
125
132
  command call. If its first target plan has stale/missing paid-InMail credit
126
133
  facts, it refreshes each selected sender at most once, reruns
127
134
  `get_refill_target_plan`, and returns the post-refresh `targetPlan` before
128
- choosing the next prep/approval/start action. If fresh facts are still below
135
+ choosing the next prep/source-copy/bounded-approval/read-only wait action. If fresh facts are still below
129
136
  threshold, below-threshold paid-InMail facts fall back to an existing
130
137
  connection lane, the same Sales Nav cascade campaign's connection branch, or
131
138
  a manual continuation.
@@ -161,10 +168,8 @@ in-progress wait state, not a reason to mark the goal complete or blocked.
161
168
  operator action after `refill_sends` returns `autoPaidInmailRefresh` and the
162
169
  post-refresh `targetPlan`. Trust `refill_sends.autoPaidInmailRefresh`: it
163
170
  should show the exact sender ids refreshed once, sender-credit-cache write
164
- receipts, and a returned post-refresh `targetPlan`. Also inspect
165
- `refill_sends.yoloExecution`: if it applied a supported yolo action,
166
- continue from the final returned `targetPlan`; otherwise continue from the
167
- post-refresh packet or `targetPlanBeforeYoloAction`. If paid InMail is below threshold after the fresh credit read, report
171
+ receipts, and a returned post-refresh `targetPlan`. Continue from that
172
+ post-refresh packet. If paid InMail is below threshold after the fresh credit read, report
168
173
  the exact campaign/table/column threshold action or same-campaign
169
174
  connection fallback; `--yolo` does not lower paid-InMail thresholds or create campaigns.
170
175
  2. Call `resolve_campaign_fill_route`. Use `intent:"plain"` for generic
@@ -566,7 +571,7 @@ same refill request, do not ask the `Accept` / `Decline` question. Instead:
566
571
  caps/dates, approval mode, blockers, and side-effect class still match the
567
572
  packet;
568
573
  4. execute only the exact packet;
569
- 5. after each terminal credit-refresh/apply/prep/start result, rerun
574
+ 5. after each terminal credit-refresh/apply/prep/source-copy/bounded-approval/read-only wait result, rerun
570
575
  `get_refill_target_plan`, reread state, settle processing when needed,
571
576
  recompute the target-window saturation ledger, and continue with the next smallest
572
577
  safe action inside the same bounded packet until every selected sender is