bitfab 0.36.12 → 0.38.0

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/dist/node.cjs CHANGED
@@ -97,7 +97,7 @@ var __version__;
97
97
  var init_version_generated = __esm({
98
98
  "src/version.generated.ts"() {
99
99
  "use strict";
100
- __version__ = "0.36.12";
100
+ __version__ = "0.38.0";
101
101
  }
102
102
  });
103
103
 
@@ -2541,12 +2541,15 @@ async function processItem(httpClient, serverItem, fn, testRunId, mockStrategy,
2541
2541
  let lease = includeDbBranchLease ? serverItem.dbBranchLease : void 0;
2542
2542
  let leaseError = includeDbBranchLease ? serverItem.dbBranchLeaseError : void 0;
2543
2543
  let dbSnapshotRef = serverItem.dbSnapshotRef;
2544
+ let dbBranchTimings = includeDbBranchLease ? serverItem.dbBranchTimings : void 0;
2544
2545
  let inputs = [];
2545
2546
  let originalOutput;
2546
2547
  let result;
2547
2548
  let error = null;
2548
2549
  let traceError = null;
2549
2550
  let replayError = null;
2551
+ let replayDurationMs = null;
2552
+ let replayStarted = null;
2550
2553
  const originalTraceId = serverItem.originalTraceId ?? serverItem.sourceTraceId;
2551
2554
  const originalSpanId = serverItem.originalSpanId ?? serverItem.sourceSpanId;
2552
2555
  try {
@@ -2569,6 +2572,7 @@ async function processItem(httpClient, serverItem, fn, testRunId, mockStrategy,
2569
2572
  lease = resolved.lease ?? void 0;
2570
2573
  leaseError = resolved.leaseError ?? void 0;
2571
2574
  dbSnapshotRef = resolved.dbSnapshotRef ?? dbSnapshotRef;
2575
+ dbBranchTimings = resolved.timings ?? dbBranchTimings;
2572
2576
  }
2573
2577
  if (leaseError) {
2574
2578
  throw new DbBranchReplayError(
@@ -2602,20 +2606,17 @@ async function processItem(httpClient, serverItem, fn, testRunId, mockStrategy,
2602
2606
  includeOutputs,
2603
2607
  includeRootOutput: false
2604
2608
  });
2605
- if (treeResponse.root) {
2606
- mockTree = buildMockTree(treeResponse.root);
2607
- } else if (mockStrategy === "all" || hasOverrides) {
2609
+ if (!treeResponse.root) {
2608
2610
  throw new BitfabError(
2609
2611
  `Replay mock strategy "${mockStrategy}"${hasOverrides ? " with overrides" : ""} requires a span tree root for original span ${originalSpanId}.`
2610
2612
  );
2611
- } else {
2612
- mockTree = void 0;
2613
2613
  }
2614
- } catch (e) {
2615
- if (mockStrategy === "all" || hasOverrides) {
2616
- throw e;
2614
+ mockTree = buildMockTree(treeResponse.root);
2615
+ } catch (error2) {
2616
+ if (mockStrategy !== "marked" || hasOverrides) {
2617
+ throw error2;
2617
2618
  }
2618
- mockTree = void 0;
2619
+ mockTree = { spans: /* @__PURE__ */ new Map() };
2619
2620
  }
2620
2621
  }
2621
2622
  const outputCache = /* @__PURE__ */ new Map();
@@ -2632,6 +2633,7 @@ async function processItem(httpClient, serverItem, fn, testRunId, mockStrategy,
2632
2633
  return pending;
2633
2634
  } : void 0;
2634
2635
  try {
2636
+ replayStarted = performance.now();
2635
2637
  const maybePromise = runWithReplayContext(
2636
2638
  {
2637
2639
  testRunId,
@@ -2644,16 +2646,24 @@ async function processItem(httpClient, serverItem, fn, testRunId, mockStrategy,
2644
2646
  mockStrategy,
2645
2647
  mockOverrides: hasOverrides ? resolvedOverrides : void 0,
2646
2648
  fetchSpanOutput,
2647
- dbBranchLease: lease
2649
+ dbBranchLease: lease,
2650
+ dbBranchTimings
2648
2651
  },
2649
2652
  () => fn(...inputs)
2650
2653
  );
2651
2654
  result = maybePromise instanceof Promise ? await maybePromise : maybePromise;
2655
+ replayDurationMs = Math.round(performance.now() - replayStarted);
2652
2656
  } catch (e) {
2657
+ if (replayStarted !== null) {
2658
+ replayDurationMs = Math.round(performance.now() - replayStarted);
2659
+ }
2653
2660
  traceError = e;
2654
2661
  error = errorMessage(e);
2655
2662
  }
2656
2663
  } catch (e) {
2664
+ if (replayStarted !== null) {
2665
+ replayDurationMs = Math.round(performance.now() - replayStarted);
2666
+ }
2657
2667
  replayError = e;
2658
2668
  error = replayItemErrorMessage(e);
2659
2669
  } finally {
@@ -2670,6 +2680,8 @@ async function processItem(httpClient, serverItem, fn, testRunId, mockStrategy,
2670
2680
  }
2671
2681
  }
2672
2682
  }
2683
+ const originalDurationMs = serverItem.originalDurationMs ?? serverItem.durationMs ?? null;
2684
+ const originalModel = serverItem.originalModel ?? serverItem.model ?? null;
2673
2685
  return {
2674
2686
  // Written in by replay() from the complete-replay response once the server
2675
2687
  // has minted this replay trace's row. Null until then: the client-side
@@ -2686,13 +2698,17 @@ async function processItem(httpClient, serverItem, fn, testRunId, mockStrategy,
2686
2698
  error,
2687
2699
  traceError,
2688
2700
  replayError,
2689
- durationMs: serverItem.durationMs ?? null,
2701
+ durationMs: replayDurationMs,
2702
+ originalDurationMs,
2703
+ originalTokens: serverItem.originalTokens ?? serverItem.tokens ?? null,
2704
+ originalModel,
2690
2705
  // Filled in by replay() from the complete-replay response once the
2691
2706
  // replay traces are persisted and their spans aggregated server-side.
2692
2707
  // Null here (and on older servers) means "replay tokens not known".
2693
2708
  tokens: null,
2694
- model: serverItem.model ?? null,
2695
- dbSnapshotRef: dbSnapshotRef ?? null
2709
+ model: originalModel,
2710
+ dbSnapshotRef: dbSnapshotRef ?? null,
2711
+ dbBranchTimings: dbBranchTimings ?? null
2696
2712
  };
2697
2713
  }
2698
2714
  async function waitForReplayPersistence(httpClient, testRunId, replayedTraceIds) {
@@ -2919,9 +2935,13 @@ async function replay(httpClient, serviceUrl, traceFunctionKey, fn, options, reg
2919
2935
  traceError: item.traceError,
2920
2936
  replayError: item.replayError,
2921
2937
  durationMs: item.durationMs,
2938
+ originalDurationMs: item.originalDurationMs,
2939
+ originalTokens: item.originalTokens,
2940
+ originalModel: item.originalModel,
2922
2941
  tokens: item.tokens,
2923
2942
  model: item.model,
2924
- dbSnapshotRef: item.dbSnapshotRef
2943
+ dbSnapshotRef: item.dbSnapshotRef,
2944
+ dbBranchTimings: item.dbBranchTimings
2925
2945
  }
2926
2946
  });
2927
2947
  } catch {
@@ -6107,7 +6127,8 @@ var Bitfab = class {
6107
6127
  snapshotTimestamp: replayCtx.dbBranchLease.snapshotTimestamp,
6108
6128
  region: replayCtx.dbBranchLease.region,
6109
6129
  originalTraceId: replayCtx.sourceBitfabTraceId,
6110
- accessed: replayCtx.dbSnapshotAccessed === true
6130
+ accessed: replayCtx.dbSnapshotAccessed === true,
6131
+ timings: replayCtx.dbBranchTimings
6111
6132
  }
6112
6133
  }
6113
6134
  });
@@ -6197,7 +6218,12 @@ var Bitfab = class {
6197
6218
  }
6198
6219
  }
6199
6220
  const shouldMock = replayCtxForMock.mockStrategy === "all" || replayCtxForMock.mockStrategy === "marked" && options.mockOnReplay === true;
6200
- if (shouldMock && mockSpan) {
6221
+ if (shouldMock && !mockSpan) {
6222
+ throw new BitfabError(
6223
+ `Replay selected span "${traceFunctionKey}:${baseSpanParams.spanName}" for mocking, but recorded occurrence ${callIndex + 1} is unavailable. The real span was not executed.`
6224
+ );
6225
+ }
6226
+ if (shouldMock) {
6201
6227
  const recorded = resolveRecordedOutput();
6202
6228
  if (recorded instanceof Promise) {
6203
6229
  return emitMockAsync(recorded, "recorded");
@@ -6434,7 +6460,13 @@ var Bitfab = class {
6434
6460
  // against servers that predate the rename.
6435
6461
  source_trace_id: params.dbSnapshotUsage.originalTraceId
6436
6462
  },
6437
- accessed: params.dbSnapshotUsage.accessed
6463
+ accessed: params.dbSnapshotUsage.accessed,
6464
+ // Echoed verbatim (camelCase inside) rather than re-cased into this
6465
+ // record's snake_case: it is the server's own object coming back, and
6466
+ // a translation layer here is one more thing to drift.
6467
+ ...params.dbSnapshotUsage.timings && {
6468
+ timings: params.dbSnapshotUsage.timings
6469
+ }
6438
6470
  };
6439
6471
  }
6440
6472
  this.httpClient.sendExternalTrace({