@abelxiaoxing/cadence 1.0.11 → 1.0.13

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.
@@ -46,6 +46,7 @@ export class ParentPayloadBridgeError extends Error {
46
46
 
47
47
  export interface ParentProviderRegistry {
48
48
  getProvider(provider: string): Provider | undefined;
49
+ getRegisteredNativeProvider?(provider: string): Provider | undefined;
49
50
  registerProvider(provider: Provider): void;
50
51
  }
51
52
 
@@ -198,9 +199,12 @@ export class ParentPayloadBridge {
198
199
  model: Model<string>,
199
200
  registry: ParentProviderRegistry,
200
201
  ): Provider | undefined {
201
- const current = registry.getProvider(model.provider);
202
+ const current = this.nativeCarrier(model.provider, registry);
202
203
  if (!current) return undefined;
203
204
  const delegate = this.unwrapProvider(current);
205
+ const wrapped = this.isWrappedProvider(current)
206
+ ? current
207
+ : this.wrapProvider(delegate);
204
208
  const state = this.state;
205
209
  if (state?.active) {
206
210
  const key = modelKeyId(modelKeyFor(model));
@@ -210,14 +214,18 @@ export class ParentPayloadBridge {
210
214
  state.ready.delete(key);
211
215
  }
212
216
  }
213
- const wrapped = this.wrapProvider(delegate);
214
- registry.registerProvider(wrapped);
217
+ if (wrapped !== current) {
218
+ registry.registerProvider(wrapped);
219
+ }
215
220
  return wrapped;
216
221
  }
217
222
 
218
223
  capture(
219
224
  modelKey: ParentModelKey,
220
- registry?: Pick<ParentProviderRegistry, "getProvider">,
225
+ registry?: Pick<
226
+ ParentProviderRegistry,
227
+ "getProvider" | "getRegisteredNativeProvider"
228
+ >,
221
229
  ): ParentPayloadCapture | undefined {
222
230
  const state = this.state;
223
231
  if (!state?.active) return undefined;
@@ -226,7 +234,7 @@ export class ParentPayloadBridge {
226
234
  return undefined;
227
235
  }
228
236
  if (registry) {
229
- const current = registry.getProvider(modelKey.provider);
237
+ const current = this.nativeCarrier(modelKey.provider, registry);
230
238
  if (!current || this.unwrapProvider(current) !== capture.delegate) {
231
239
  return undefined;
232
240
  }
@@ -236,11 +244,14 @@ export class ParentPayloadBridge {
236
244
 
237
245
  diagnoseCapture(
238
246
  modelKey: ParentModelKey,
239
- registry: Pick<ParentProviderRegistry, "getProvider">,
247
+ registry: Pick<
248
+ ParentProviderRegistry,
249
+ "getProvider" | "getRegisteredNativeProvider"
250
+ >,
240
251
  ): ParentBridgeFailureCode | undefined {
241
252
  const state = this.state;
242
253
  if (!state?.active) return "parent-bridge-session-unavailable";
243
- const current = registry.getProvider(modelKey.provider);
254
+ const current = this.nativeCarrier(modelKey.provider, registry);
244
255
  if (!current || !this.isWrappedProvider(current)) {
245
256
  return "parent-bridge-provider-not-installed";
246
257
  }
@@ -468,6 +479,19 @@ export class ParentPayloadBridge {
468
479
  return state;
469
480
  }
470
481
 
482
+ private nativeCarrier(
483
+ providerId: string,
484
+ registry: Pick<
485
+ ParentProviderRegistry,
486
+ "getProvider" | "getRegisteredNativeProvider"
487
+ >,
488
+ ): Provider | undefined {
489
+ const registered = registry.getRegisteredNativeProvider?.(providerId);
490
+ return registered && this.isWrappedProvider(registered)
491
+ ? registered
492
+ : registry.getProvider(providerId);
493
+ }
494
+
471
495
  private isWrappedProvider(provider: Provider): boolean {
472
496
  return Reflect.get(provider, PROVIDER_WRAPPER) !== undefined;
473
497
  }
package/src/patch.ts CHANGED
@@ -199,7 +199,11 @@ export async function applyAgentsCheckpoint(
199
199
  ): Promise<AgentsCheckpointResult> {
200
200
  const validation = validateAgentsCheckpointRequest(value);
201
201
  if (!validation.ok) {
202
- return failure({ kind: "artifact", code: "invalid-checkpoint-contract" });
202
+ return failure({
203
+ kind: "artifact",
204
+ code: "invalid-checkpoint-contract",
205
+ stage: "agents-checkpoint",
206
+ });
203
207
  }
204
208
  const request = validation.value;
205
209
  if (signal?.aborted) {
@@ -207,19 +211,35 @@ export async function applyAgentsCheckpoint(
207
211
  }
208
212
  const before = regularText(root, request.agentsTarget);
209
213
  if (before === NONREGULAR_AGENTS_TARGET) {
210
- return failure({ kind: "artifact", code: "nonregular-mode" });
214
+ return failure({
215
+ kind: "artifact",
216
+ code: "nonregular-mode",
217
+ stage: "agents-checkpoint",
218
+ });
211
219
  }
212
220
  if (!isCurrent(root, request.snapshot as Bound)) {
213
- return failure({ kind: "stale", code: "stale-snapshot" });
221
+ return failure({
222
+ kind: "stale",
223
+ code: "stale-snapshot",
224
+ stage: "agents-checkpoint",
225
+ });
214
226
  }
215
227
  let targets: string[];
216
228
  try {
217
229
  targets = diffWritePaths(request.diff).paths;
218
230
  } catch {
219
- return failure({ kind: "artifact", code: "invalid-diff" });
231
+ return failure({
232
+ kind: "artifact",
233
+ code: "invalid-diff",
234
+ stage: "agents-checkpoint",
235
+ });
220
236
  }
221
237
  if (targets.length !== 1 || targets[0] !== request.agentsTarget) {
222
- return failure({ kind: "artifact", code: "agents-target-mismatch" });
238
+ return failure({
239
+ kind: "artifact",
240
+ code: "agents-target-mismatch",
241
+ stage: "agents-checkpoint",
242
+ });
223
243
  }
224
244
 
225
245
  let temp: string | undefined;
@@ -228,7 +248,11 @@ export async function applyAgentsCheckpoint(
228
248
  (request.agentsImpact === "create-index" && before !== null) ||
229
249
  (request.agentsImpact !== "create-index" && before === null)
230
250
  ) {
231
- return failure({ kind: "artifact", code: "agents-impact-mismatch" });
251
+ return failure({
252
+ kind: "artifact",
253
+ code: "agents-impact-mismatch",
254
+ stage: "agents-checkpoint",
255
+ });
232
256
  }
233
257
  temp = mkdtempSync(path.join(tmpdir(), "cadence-agents-checkpoint-"));
234
258
  if (before !== null) {
@@ -247,7 +271,11 @@ export async function applyAgentsCheckpoint(
247
271
  return cancellationFailure();
248
272
  }
249
273
  if (candidateCheck.code !== 0) {
250
- return failure({ kind: "artifact", code: "git-apply-check-failed" });
274
+ return failure({
275
+ kind: "artifact",
276
+ code: "git-apply-check-failed",
277
+ stage: "agents-checkpoint",
278
+ });
251
279
  }
252
280
  const candidateApply = await git(
253
281
  temp,
@@ -259,17 +287,33 @@ export async function applyAgentsCheckpoint(
259
287
  return cancellationFailure();
260
288
  }
261
289
  if (candidateApply.code !== 0) {
262
- return failure({ kind: "artifact", code: "git-apply-failed" });
290
+ return failure({
291
+ kind: "artifact",
292
+ code: "git-apply-failed",
293
+ stage: "agents-checkpoint",
294
+ });
263
295
  }
264
296
  const after = regularText(temp, request.agentsTarget);
265
297
  if (after === NONREGULAR_AGENTS_TARGET) {
266
- return failure({ kind: "artifact", code: "nonregular-mode" });
298
+ return failure({
299
+ kind: "artifact",
300
+ code: "nonregular-mode",
301
+ stage: "agents-checkpoint",
302
+ });
267
303
  }
268
304
  if (!checkpointContentIsScoped(request.agentsImpact, before, after)) {
269
- return failure({ kind: "artifact", code: "outside-managed-region" });
305
+ return failure({
306
+ kind: "artifact",
307
+ code: "outside-managed-region",
308
+ stage: "agents-checkpoint",
309
+ });
270
310
  }
271
311
  if (!isCurrent(root, request.snapshot as Bound)) {
272
- return failure({ kind: "stale", code: "stale-snapshot" });
312
+ return failure({
313
+ kind: "stale",
314
+ code: "stale-snapshot",
315
+ stage: "agents-checkpoint",
316
+ });
273
317
  }
274
318
  const check = await git(
275
319
  root,
@@ -281,7 +325,11 @@ export async function applyAgentsCheckpoint(
281
325
  return cancellationFailure();
282
326
  }
283
327
  if (check.code !== 0) {
284
- return failure({ kind: "stale", code: "git-apply-check-failed" });
328
+ return failure({
329
+ kind: "stale",
330
+ code: "git-apply-check-failed",
331
+ stage: "agents-checkpoint",
332
+ });
285
333
  }
286
334
  const apply = await git(
287
335
  root,
@@ -307,6 +355,7 @@ export async function applyRetainedPatch(input: {
307
355
  root: string;
308
356
  id: string;
309
357
  store: ResultStore;
358
+ candidateOutputsAvailable?: (checkoutRoot: string) => boolean;
310
359
  signal?: AbortSignal;
311
360
  }): Promise<ApplyCandidateResult> {
312
361
  if (input.signal?.aborted) return cancellationFailure();
@@ -314,16 +363,28 @@ export async function applyRetainedPatch(input: {
314
363
  if (retained.root !== input.root)
315
364
  throw new Error("retained result root mismatch");
316
365
  if (!retained.verification && !isCurrent(input.root, retained.snapshot))
317
- return failure({ kind: "stale", code: "stale-snapshot" });
366
+ return failure({
367
+ kind: "stale",
368
+ code: "stale-snapshot",
369
+ stage: "candidate-retention",
370
+ });
318
371
 
319
372
  let targets: string[];
320
373
  try {
321
374
  targets = diffWritePaths(retained.diff.toString("utf8")).paths;
322
375
  } catch {
323
- return failure({ kind: "artifact", code: "invalid-diff" });
376
+ return failure({
377
+ kind: "artifact",
378
+ code: "invalid-diff",
379
+ stage: "candidate-diff",
380
+ });
324
381
  }
325
382
  if (targets.some((path) => !retained.writeSet.includes(path))) {
326
- return failure({ kind: "artifact", code: "write-set-mismatch" });
383
+ return failure({
384
+ kind: "artifact",
385
+ code: "write-set-mismatch",
386
+ stage: "candidate-diff",
387
+ });
327
388
  }
328
389
 
329
390
  if (retained.verification) {
@@ -345,6 +406,7 @@ export async function applyRetainedPatch(input: {
345
406
  packageManifest: retained.packageManifest,
346
407
  lockfile: retained.lockfile,
347
408
  dependencyTarget: retained.dependencyTarget,
409
+ candidateOutputsAvailable: input.candidateOutputsAvailable,
348
410
  signal: input.signal,
349
411
  });
350
412
  if (!preflight.ok) {
@@ -353,10 +415,14 @@ export async function applyRetainedPatch(input: {
353
415
  return failure({
354
416
  kind: preflight.kind,
355
417
  code: preflight.code,
356
- ...(preflight.excerpt ? { evidence: [preflight.excerpt] } : {}),
418
+ stage: "candidate-preflight",
357
419
  });
358
420
  case "stale":
359
- return failure({ kind: preflight.kind, code: preflight.code });
421
+ return failure({
422
+ kind: preflight.kind,
423
+ code: preflight.code,
424
+ stage: "candidate-preflight",
425
+ });
360
426
  case "environment":
361
427
  return failure({ kind: preflight.kind, code: preflight.code });
362
428
  case "verification-adapter":
@@ -368,7 +434,11 @@ export async function applyRetainedPatch(input: {
368
434
  }
369
435
  }
370
436
  if (!isCurrent(input.root, retained.snapshot)) {
371
- return failure({ kind: "stale", code: "stale-snapshot" });
437
+ return failure({
438
+ kind: "stale",
439
+ code: "stale-snapshot",
440
+ stage: "candidate-preflight",
441
+ });
372
442
  }
373
443
  }
374
444
  if (input.signal?.aborted) return cancellationFailure();
@@ -381,7 +451,11 @@ export async function applyRetainedPatch(input: {
381
451
  );
382
452
  if (numstat.cancelled || input.signal?.aborted) return cancellationFailure();
383
453
  if (numstat.code !== 0 || numstat.stdout.includes(Buffer.from("-\t-\t"))) {
384
- return failure({ kind: "artifact", code: "invalid-diff" });
454
+ return failure({
455
+ kind: "artifact",
456
+ code: "invalid-diff",
457
+ stage: "candidate-diff",
458
+ });
385
459
  }
386
460
  const summary = await git(
387
461
  input.root,
@@ -396,7 +470,11 @@ export async function applyRetainedPatch(input: {
396
470
  summary.stdout.toString("utf8"),
397
471
  )
398
472
  ) {
399
- return failure({ kind: "artifact", code: "invalid-diff" });
473
+ return failure({
474
+ kind: "artifact",
475
+ code: "invalid-diff",
476
+ stage: "candidate-diff",
477
+ });
400
478
  }
401
479
  const check = await git(
402
480
  input.root,
@@ -406,7 +484,11 @@ export async function applyRetainedPatch(input: {
406
484
  );
407
485
  if (check.cancelled || input.signal?.aborted) return cancellationFailure();
408
486
  if (check.code !== 0)
409
- return failure({ kind: "artifact", code: "git-apply-check-failed" });
487
+ return failure({
488
+ kind: "artifact",
489
+ code: "git-apply-check-failed",
490
+ stage: "candidate-apply",
491
+ });
410
492
  if (input.signal?.aborted) return cancellationFailure();
411
493
  const apply = await git(
412
494
  input.root,