@bitfab/sdk 0.54.8 → 0.54.10

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.
Files changed (35) hide show
  1. package/dist/{chunk-L4SB4W3Z.js → chunk-3F7SICKD.js} +609 -8
  2. package/dist/chunk-3F7SICKD.js.map +1 -0
  3. package/dist/{chunk-LMKQBRSP.js → chunk-6KVKJQNH.js} +4 -3
  4. package/dist/chunk-6KVKJQNH.js.map +1 -0
  5. package/dist/{chunk-GJWKOJGJ.js → chunk-NDWA6QLU.js} +3 -3
  6. package/dist/chunk-NDWA6QLU.js.map +1 -0
  7. package/dist/{chunk-M2AEKEZE.js → chunk-VJOLQ7UY.js} +85 -40
  8. package/dist/chunk-VJOLQ7UY.js.map +1 -0
  9. package/dist/{chunk-4LMLPCYL.js → chunk-XREH4NJT.js} +6 -4
  10. package/dist/chunk-XREH4NJT.js.map +1 -0
  11. package/dist/{http-JPJBWD5Z.js → http-NPOFVS25.js} +2 -2
  12. package/dist/{http-3WCRPXRQ.js → http-NVPWO4TN.js} +2 -2
  13. package/dist/index.cjs +669 -8
  14. package/dist/index.cjs.map +1 -1
  15. package/dist/index.d.cts +175 -4
  16. package/dist/index.d.ts +175 -4
  17. package/dist/index.js +5 -3
  18. package/dist/node.cjs +669 -8
  19. package/dist/node.cjs.map +1 -1
  20. package/dist/node.d.cts +1 -1
  21. package/dist/node.d.ts +1 -1
  22. package/dist/node.js +5 -3
  23. package/dist/node.js.map +1 -1
  24. package/dist/{replay-2JBBAJUG.js → replay-OMXCRECR.js} +3 -3
  25. package/dist/replayCli.js +2 -2
  26. package/dist/seedCli.js +2 -2
  27. package/package.json +1 -1
  28. package/dist/chunk-4LMLPCYL.js.map +0 -1
  29. package/dist/chunk-GJWKOJGJ.js.map +0 -1
  30. package/dist/chunk-L4SB4W3Z.js.map +0 -1
  31. package/dist/chunk-LMKQBRSP.js.map +0 -1
  32. package/dist/chunk-M2AEKEZE.js.map +0 -1
  33. /package/dist/{http-3WCRPXRQ.js.map → http-NPOFVS25.js.map} +0 -0
  34. /package/dist/{http-JPJBWD5Z.js.map → http-NVPWO4TN.js.map} +0 -0
  35. /package/dist/{replay-2JBBAJUG.js.map → replay-OMXCRECR.js.map} +0 -0
package/dist/index.cjs CHANGED
@@ -42,7 +42,7 @@ var __version__, __packageName__;
42
42
  var init_version_generated = __esm({
43
43
  "src/version.generated.ts"() {
44
44
  "use strict";
45
- __version__ = "0.54.8";
45
+ __version__ = "0.54.10";
46
46
  __packageName__ = "@bitfab/sdk";
47
47
  }
48
48
  });
@@ -827,8 +827,8 @@ function encodePayloadBody(payload) {
827
827
  const marker = { error: `payload_serialize_failed: ${message}` };
828
828
  return { body: JSON.stringify(marker), dropped, value: marker };
829
829
  }
830
- const isRecord4 = typeof sanitized === "object" && sanitized !== null && !Array.isArray(sanitized);
831
- if (dropped.length > 0 && isRecord4) {
830
+ const isRecord6 = typeof sanitized === "object" && sanitized !== null && !Array.isArray(sanitized);
831
+ if (dropped.length > 0 && isRecord6) {
832
832
  const obj = sanitized;
833
833
  const existing = Array.isArray(obj.errors) ? obj.errors : [];
834
834
  obj.errors = [
@@ -845,7 +845,7 @@ function encodePayloadBody(payload) {
845
845
  return {
846
846
  body: JSON.stringify(sanitized),
847
847
  dropped,
848
- value: isRecord4 ? sanitized : void 0
848
+ value: isRecord6 ? sanitized : void 0
849
849
  };
850
850
  }
851
851
  }
@@ -947,13 +947,15 @@ var init_spanOrigin = __esm({
947
947
  "openai-agents",
948
948
  "langgraph",
949
949
  "claude-agent-sdk",
950
- "vercel-ai"
950
+ "vercel-ai",
951
+ "rivet"
951
952
  ];
952
953
  FRAMEWORK_INSTRUMENTATIONS = [
953
954
  "openai-agents",
954
955
  "langgraph",
955
956
  "claude-agent-sdk",
956
- "vercel-ai"
957
+ "vercel-ai",
958
+ "rivet"
957
959
  ];
958
960
  FRAMEWORK_INSTRUMENTATION_SET = new Set(
959
961
  FRAMEWORK_INSTRUMENTATIONS
@@ -3457,6 +3459,55 @@ var init_codeChange = __esm({
3457
3459
  }
3458
3460
  });
3459
3461
 
3462
+ // src/integrationFixture.ts
3463
+ function isRecord4(value) {
3464
+ return typeof value === "object" && value !== null && !Array.isArray(value);
3465
+ }
3466
+ function createIntegrationFixtureContext(name, value) {
3467
+ const serialized = serializeValue(value);
3468
+ return {
3469
+ [INTEGRATION_FIXTURE_CONTEXT_KEY]: {
3470
+ version: INTEGRATION_FIXTURE_VERSION,
3471
+ name,
3472
+ value: serialized.json,
3473
+ ...serialized.meta !== void 0 && { valueMeta: serialized.meta }
3474
+ }
3475
+ };
3476
+ }
3477
+ function extractIntegrationFixtures(spanData) {
3478
+ const contexts = spanData.contexts;
3479
+ if (!Array.isArray(contexts)) {
3480
+ return void 0;
3481
+ }
3482
+ const fixtures = /* @__PURE__ */ new Map();
3483
+ for (const context of contexts) {
3484
+ if (!isRecord4(context)) {
3485
+ continue;
3486
+ }
3487
+ const fixture = context[INTEGRATION_FIXTURE_CONTEXT_KEY];
3488
+ if (!isRecord4(fixture) || fixture.version !== INTEGRATION_FIXTURE_VERSION || typeof fixture.name !== "string") {
3489
+ continue;
3490
+ }
3491
+ fixtures.set(
3492
+ fixture.name,
3493
+ deserializeValue({
3494
+ json: fixture.value,
3495
+ ...fixture.valueMeta !== void 0 && { meta: fixture.valueMeta }
3496
+ })
3497
+ );
3498
+ }
3499
+ return fixtures.size > 0 ? fixtures : void 0;
3500
+ }
3501
+ var INTEGRATION_FIXTURE_CONTEXT_KEY, INTEGRATION_FIXTURE_VERSION;
3502
+ var init_integrationFixture = __esm({
3503
+ "src/integrationFixture.ts"() {
3504
+ "use strict";
3505
+ init_serialize();
3506
+ INTEGRATION_FIXTURE_CONTEXT_KEY = "__bitfabIntegrationFixture";
3507
+ INTEGRATION_FIXTURE_VERSION = 1;
3508
+ }
3509
+ });
3510
+
3460
3511
  // src/replay.ts
3461
3512
  var replay_exports = {};
3462
3513
  __export(replay_exports, {
@@ -3681,6 +3732,7 @@ async function processItem(httpClient, serverItem, fn, testRunId, mockStrategy,
3681
3732
  const spanData = span.rawData?.span_data ?? {};
3682
3733
  inputs = deserializeInputs(spanData);
3683
3734
  originalOutput = deserializeOutput(spanData);
3735
+ const integrationFixtures = extractIntegrationFixtures(spanData);
3684
3736
  if (adaptInputs) {
3685
3737
  const originalMetadata = serverItem.originalMetadata;
3686
3738
  inputs = adaptInputs(inputs, {
@@ -3772,6 +3824,7 @@ async function processItem(httpClient, serverItem, fn, testRunId, mockStrategy,
3772
3824
  mockStrategy,
3773
3825
  mockOverrides: hasOverrides ? resolvedOverrides : void 0,
3774
3826
  fetchSpanOutput,
3827
+ integrationFixtures,
3775
3828
  dbBranchLease: lease,
3776
3829
  dbBranchTimings
3777
3830
  },
@@ -4252,6 +4305,7 @@ var init_replay = __esm({
4252
4305
  init_codeChange();
4253
4306
  init_errors();
4254
4307
  init_http();
4308
+ init_integrationFixture();
4255
4309
  init_mockOverride();
4256
4310
  init_randomUuid();
4257
4311
  init_replayContext();
@@ -4295,6 +4349,7 @@ __export(index_exports, {
4295
4349
  BitfabLangGraphIntegration: () => BitfabLangGraphIntegration,
4296
4350
  BitfabOpenAIAgentHandler: () => BitfabOpenAIAgentHandler,
4297
4351
  BitfabOpenAITracingProcessor: () => BitfabOpenAITracingProcessor,
4352
+ BitfabRivetIntegration: () => BitfabRivetIntegration,
4298
4353
  BitfabVercelAiHandler: () => BitfabVercelAiHandler,
4299
4354
  DEFAULT_SERVICE_URL: () => DEFAULT_SERVICE_URL,
4300
4355
  DatasetsClient: () => DatasetsClient,
@@ -6969,6 +7024,533 @@ _context = new WeakMap();
6969
7024
  // src/client.ts
6970
7025
  init_replayContext();
6971
7026
 
7027
+ // src/rivetIntegration.ts
7028
+ init_errors();
7029
+ init_integrationFixture();
7030
+ init_replayContext();
7031
+
7032
+ // src/rivetContext.ts
7033
+ init_asyncStorage();
7034
+ var storage = null;
7035
+ var browserBinding = null;
7036
+ var STORAGE_SYMBOL = /* @__PURE__ */ Symbol.for("bitfab.rivetContextStorage");
7037
+ function initializeStorage() {
7038
+ if (storage) {
7039
+ return;
7040
+ }
7041
+ const shared = globalThis;
7042
+ const existing = shared[STORAGE_SYMBOL];
7043
+ if (existing) {
7044
+ storage = existing;
7045
+ return;
7046
+ }
7047
+ const created = createAsyncLocalStorage();
7048
+ if (created) {
7049
+ shared[STORAGE_SYMBOL] = created;
7050
+ storage = created;
7051
+ }
7052
+ }
7053
+ var rivetContextReady = asyncStorageReady.then(() => {
7054
+ initializeStorage();
7055
+ });
7056
+ function getRivetContextBinding() {
7057
+ initializeStorage();
7058
+ return storage?.getStore() ?? browserBinding ?? void 0;
7059
+ }
7060
+ function runWithBrowserBinding(binding, fn) {
7061
+ const previous = browserBinding;
7062
+ browserBinding = binding;
7063
+ try {
7064
+ const result = fn();
7065
+ if (result instanceof Promise) {
7066
+ return result.finally(() => {
7067
+ browserBinding = previous;
7068
+ });
7069
+ }
7070
+ browserBinding = previous;
7071
+ return result;
7072
+ } catch (error) {
7073
+ browserBinding = previous;
7074
+ throw error;
7075
+ }
7076
+ }
7077
+ function runWithRivetContext(binding, fn) {
7078
+ initializeStorage();
7079
+ if (!storage && !isAsyncStorageInitDone()) {
7080
+ return rivetContextReady.then(() => runWithRivetContext(binding, fn));
7081
+ }
7082
+ if (storage) {
7083
+ return storage.run(binding, fn);
7084
+ }
7085
+ return runWithBrowserBinding(binding, fn);
7086
+ }
7087
+
7088
+ // src/rivetIntegration.ts
7089
+ var RIVET_DOCS_URL = "https://docs.bitfab.ai/frameworks/rivet";
7090
+ var RIVET_GROUP_EFFECT_METHODS = {
7091
+ db: ["execute", "nativeMetrics", "close"],
7092
+ kv: [
7093
+ "get",
7094
+ "put",
7095
+ "delete",
7096
+ "batchPut",
7097
+ "batchGet",
7098
+ "batchDelete",
7099
+ "deleteRange",
7100
+ "listPrefix",
7101
+ "listRange",
7102
+ "list"
7103
+ ],
7104
+ schedule: ["after", "at", "cancel", "get", "list"],
7105
+ cron: ["set", "every", "get", "list", "delete", "history"],
7106
+ queue: [
7107
+ "send",
7108
+ "next",
7109
+ "nextBatch",
7110
+ "waitForNames",
7111
+ "waitForAvailable",
7112
+ "complete",
7113
+ "enqueueAndWait",
7114
+ "tryNext",
7115
+ "tryNextBatch"
7116
+ ],
7117
+ run: ["setWakeAt"]
7118
+ };
7119
+ var RIVET_TOP_LEVEL_EFFECTS = [
7120
+ "broadcast",
7121
+ "saveState",
7122
+ "sleep",
7123
+ "destroy"
7124
+ ];
7125
+ var TOP_LEVEL_UNAVAILABLE_CAPABILITIES = /* @__PURE__ */ new Set([
7126
+ "conn",
7127
+ "conns",
7128
+ "log",
7129
+ "request",
7130
+ "actorRuntimeSocket",
7131
+ "keepAwake",
7132
+ "waitUntil",
7133
+ "client"
7134
+ ]);
7135
+ var SYNC_VOID_EFFECTS = /* @__PURE__ */ new Set([
7136
+ "broadcast",
7137
+ "sleep",
7138
+ "destroy"
7139
+ ]);
7140
+ var QUEUE_MESSAGE_EFFECTS = /* @__PURE__ */ new Set([
7141
+ "queue.next",
7142
+ "queue.nextBatch",
7143
+ "queue.waitForNames",
7144
+ "queue.tryNext",
7145
+ "queue.tryNextBatch"
7146
+ ]);
7147
+ function isRecord5(value) {
7148
+ return typeof value === "object" && value !== null;
7149
+ }
7150
+ function readProperty(value, property) {
7151
+ try {
7152
+ return Reflect.get(value, property, value);
7153
+ } catch {
7154
+ return void 0;
7155
+ }
7156
+ }
7157
+ function snapshotContext(context) {
7158
+ const source = context;
7159
+ const snapshot = {};
7160
+ for (const property of [
7161
+ "state",
7162
+ "vars",
7163
+ "actorId",
7164
+ "name",
7165
+ "key",
7166
+ "region",
7167
+ "aborted"
7168
+ ]) {
7169
+ const value = readProperty(source, property);
7170
+ if (value !== void 0) {
7171
+ snapshot[property] = value;
7172
+ }
7173
+ }
7174
+ return snapshot;
7175
+ }
7176
+ function unavailableCapability(path) {
7177
+ return new BitfabError(
7178
+ `Rivet context capability "${path}" is unavailable during replay. Add first-class support for that public context path before replaying code that uses it.`,
7179
+ RIVET_DOCS_URL
7180
+ );
7181
+ }
7182
+ function effectNode(traceFunctionKey, effect, mockSpanId) {
7183
+ return {
7184
+ traceFunctionKey,
7185
+ spanName: effect,
7186
+ type: "function",
7187
+ originalSpanId: mockSpanId
7188
+ };
7189
+ }
7190
+ function replayEffectStatus(replay2, traceFunctionKey, effect, marked) {
7191
+ const counterKey = `${traceFunctionKey}:${effect}`;
7192
+ const callIndex = replay2.callCounters?.get(counterKey) ?? 0;
7193
+ const mockSpan = replay2.mockTree?.spans.get(`${counterKey}:${callIndex}`);
7194
+ const hasOverride = replay2.mockOverrides?.some(
7195
+ (override) => override.match(
7196
+ effectNode(traceFunctionKey, effect, mockSpan?.sourceSpanId)
7197
+ )
7198
+ ) ?? false;
7199
+ return {
7200
+ willMock: hasOverride || replay2.mockStrategy === "all" || replay2.mockStrategy === "marked" && marked,
7201
+ hasRecordedSpan: mockSpan !== void 0,
7202
+ hasOverride,
7203
+ callIndex
7204
+ };
7205
+ }
7206
+ function assertReplayEffectAvailable(replay2, traceFunctionKey, effect, marked) {
7207
+ if (!replay2) {
7208
+ return;
7209
+ }
7210
+ const status = replayEffectStatus(replay2, traceFunctionKey, effect, marked);
7211
+ if (!status.willMock) {
7212
+ throw new BitfabError(
7213
+ `Rivet effect "${effect}" has no live actor context during replay. Add "${effect}" to mockOnReplay or provide a replay override.`,
7214
+ RIVET_DOCS_URL
7215
+ );
7216
+ }
7217
+ if (!status.hasRecordedSpan && !status.hasOverride) {
7218
+ throw new BitfabError(
7219
+ `No recorded Rivet effect "${effect}" exists at call ${status.callIndex + 1}; the live effect was not executed.`,
7220
+ RIVET_DOCS_URL
7221
+ );
7222
+ }
7223
+ }
7224
+ function fixtureName(traceFunctionKey) {
7225
+ return `rivet:${traceFunctionKey}`;
7226
+ }
7227
+ function snapshotFromReplay(traceFunctionKey, replay2) {
7228
+ const fixture = replay2.integrationFixtures?.get(fixtureName(traceFunctionKey));
7229
+ if (!isRecord5(fixture)) {
7230
+ throw new BitfabError(
7231
+ `Trace "${traceFunctionKey}" has no Rivet context fixture. Capture a fresh trace with the Rivet integration before replaying it.`,
7232
+ RIVET_DOCS_URL
7233
+ );
7234
+ }
7235
+ return fixture;
7236
+ }
7237
+ var BitfabRivetIntegration = class {
7238
+ /** @internal Constructed by `Bitfab.getRivetIntegration()`. */
7239
+ constructor(traceFunctionKey, runtime, options = {}) {
7240
+ this.traceFunctionKey = traceFunctionKey;
7241
+ this.runtime = runtime;
7242
+ this.replayProxies = /* @__PURE__ */ new WeakMap();
7243
+ this.markedEffects = new Set(options.mockOnReplay ?? []);
7244
+ }
7245
+ /**
7246
+ * Run a callback with a live Rivet context bound to the current async chain.
7247
+ * This binds context only; it creates no trace or span.
7248
+ */
7249
+ withContext(context, fn) {
7250
+ if (!isRecord5(context)) {
7251
+ throw new BitfabError("Rivet withContext requires a context object");
7252
+ }
7253
+ const binding = {
7254
+ context,
7255
+ fixtureContext: createIntegrationFixtureContext(
7256
+ fixtureName(this.traceFunctionKey),
7257
+ snapshotContext(context)
7258
+ ),
7259
+ recordedRoots: /* @__PURE__ */ new Set()
7260
+ };
7261
+ return runWithRivetContext(binding, fn);
7262
+ }
7263
+ /**
7264
+ * Adapt a traced function into a Rivet handler whose first argument is the
7265
+ * live actor context. The context is not added to the traced root's inputs.
7266
+ */
7267
+ bind(fn) {
7268
+ const integration = this;
7269
+ return function(context, ...args) {
7270
+ return integration.withContext(context, () => fn.apply(this, args));
7271
+ };
7272
+ }
7273
+ /**
7274
+ * Return the current Rivet context proxy. In production it delegates to the
7275
+ * bound live context. During replay it hydrates recorded actor state and
7276
+ * intercepts supported effects without requiring a live Rivet actor.
7277
+ */
7278
+ getContext() {
7279
+ const replay2 = getReplayContext();
7280
+ if (replay2) {
7281
+ const existing = this.replayProxies.get(replay2);
7282
+ if (existing) {
7283
+ return existing;
7284
+ }
7285
+ const proxy = this.createContextProxy(
7286
+ snapshotFromReplay(this.traceFunctionKey, replay2),
7287
+ void 0
7288
+ );
7289
+ this.replayProxies.set(replay2, proxy);
7290
+ return proxy;
7291
+ }
7292
+ const binding = getRivetContextBinding();
7293
+ if (!binding) {
7294
+ throw new BitfabError(
7295
+ "No Rivet context is bound. Call rivet.bind(handler) or rivet.withContext(context, callback) at the Rivet boundary.",
7296
+ RIVET_DOCS_URL
7297
+ );
7298
+ }
7299
+ this.runtime.recordRootFixture(
7300
+ binding.fixtureContext,
7301
+ binding.recordedRoots
7302
+ );
7303
+ if (!binding.proxy) {
7304
+ binding.proxy = this.createContextProxy(
7305
+ binding.context,
7306
+ binding
7307
+ );
7308
+ }
7309
+ return binding.proxy;
7310
+ }
7311
+ createContextProxy(target, binding) {
7312
+ const replay2 = getReplayContext();
7313
+ const dbProxy = this.createDbProxy(binding, replay2);
7314
+ const groupProxies = /* @__PURE__ */ new Map();
7315
+ for (const group of Object.keys(
7316
+ RIVET_GROUP_EFFECT_METHODS
7317
+ )) {
7318
+ if (group !== "db") {
7319
+ groupProxies.set(group, this.createGroupProxy(group, binding, replay2));
7320
+ }
7321
+ }
7322
+ const topLevelEffects = /* @__PURE__ */ new Map();
7323
+ for (const effect of RIVET_TOP_LEVEL_EFFECTS) {
7324
+ topLevelEffects.set(
7325
+ effect,
7326
+ this.createEffect(
7327
+ effect,
7328
+ () => binding?.context,
7329
+ effect,
7330
+ replay2
7331
+ )
7332
+ );
7333
+ }
7334
+ const replayTarget = replay2 ? { ...target } : target;
7335
+ if (replay2) {
7336
+ const controller = new AbortController();
7337
+ if (target.aborted === true) {
7338
+ controller.abort();
7339
+ }
7340
+ replayTarget.abortSignal = controller.signal;
7341
+ }
7342
+ return new Proxy(replayTarget, {
7343
+ get: (source, property) => {
7344
+ if (property === "db") {
7345
+ return dbProxy;
7346
+ }
7347
+ if (typeof property === "string") {
7348
+ const group = groupProxies.get(property);
7349
+ if (group) {
7350
+ return group;
7351
+ }
7352
+ const effect = topLevelEffects.get(property);
7353
+ if (effect) {
7354
+ return effect;
7355
+ }
7356
+ }
7357
+ if (property === "setPreventSleep" && replay2) {
7358
+ return (_preventSleep) => void 0;
7359
+ }
7360
+ if (replay2 && typeof property === "string" && TOP_LEVEL_UNAVAILABLE_CAPABILITIES.has(property)) {
7361
+ throw unavailableCapability(property);
7362
+ }
7363
+ const value = Reflect.get(source, property, source);
7364
+ return typeof value === "function" ? value.bind(source) : value;
7365
+ }
7366
+ });
7367
+ }
7368
+ createDbProxy(binding, replay2) {
7369
+ const proxy = this.createGroupProxy("db", binding, replay2);
7370
+ return new Proxy(proxy, {
7371
+ get: (source, property) => property === "transaction" ? this.createTransaction(binding, replay2) : Reflect.get(source, property, source)
7372
+ });
7373
+ }
7374
+ createGroupProxy(group, binding, replay2) {
7375
+ const targetProvider = () => {
7376
+ if (!binding) {
7377
+ return void 0;
7378
+ }
7379
+ const context = binding.context;
7380
+ const target = readProperty(context, group);
7381
+ return isRecord5(target) ? target : void 0;
7382
+ };
7383
+ const proxy = this.createMethodProxy(
7384
+ targetProvider,
7385
+ group,
7386
+ RIVET_GROUP_EFFECT_METHODS[group],
7387
+ replay2
7388
+ );
7389
+ if (group !== "queue") {
7390
+ return proxy;
7391
+ }
7392
+ return new Proxy(proxy, {
7393
+ get: (source, property) => property === "iter" ? (options) => this.createQueueIterator(source, options) : Reflect.get(source, property, source)
7394
+ });
7395
+ }
7396
+ createMethodProxy(targetProvider, prefix, methods, replay2) {
7397
+ const effects = /* @__PURE__ */ new Map();
7398
+ for (const method of methods) {
7399
+ const effect = `${prefix}.${method}`;
7400
+ effects.set(
7401
+ method,
7402
+ this.createEffect(effect, targetProvider, method, replay2)
7403
+ );
7404
+ }
7405
+ return new Proxy(
7406
+ {},
7407
+ {
7408
+ get: (_source, property) => {
7409
+ if (typeof property === "string") {
7410
+ const effect = effects.get(property);
7411
+ if (effect) {
7412
+ return effect;
7413
+ }
7414
+ if (replay2) {
7415
+ throw unavailableCapability(`${prefix}.${property}`);
7416
+ }
7417
+ }
7418
+ const target = targetProvider();
7419
+ if (!target) {
7420
+ return void 0;
7421
+ }
7422
+ const value = Reflect.get(target, property, target);
7423
+ return typeof value === "function" ? value.bind(target) : value;
7424
+ }
7425
+ }
7426
+ );
7427
+ }
7428
+ createEffect(effect, targetProvider, methodName, replay2) {
7429
+ const marked = this.markedEffects.has(effect);
7430
+ const invoke = (...args) => {
7431
+ assertReplayEffectAvailable(
7432
+ getReplayContext(),
7433
+ this.traceFunctionKey,
7434
+ effect,
7435
+ marked
7436
+ );
7437
+ const target = targetProvider();
7438
+ const method = target ? readProperty(target, methodName) : void 0;
7439
+ if (typeof method !== "function") {
7440
+ throw unavailableCapability(effect);
7441
+ }
7442
+ return method.apply(target, args);
7443
+ };
7444
+ const wrapped = SYNC_VOID_EFFECTS.has(effect) ? this.runtime.wrapEffect(
7445
+ effect,
7446
+ marked,
7447
+ invoke,
7448
+ replay2 ? () => void 0 : void 0
7449
+ ) : this.runtime.wrapEffect(effect, marked, async (...args) => {
7450
+ return await invoke(...args);
7451
+ });
7452
+ return (...args) => {
7453
+ if (replay2) {
7454
+ assertReplayEffectAvailable(
7455
+ replay2,
7456
+ this.traceFunctionKey,
7457
+ effect,
7458
+ marked
7459
+ );
7460
+ }
7461
+ const result = wrapped(...args);
7462
+ if (!QUEUE_MESSAGE_EFFECTS.has(effect) || !(result instanceof Promise)) {
7463
+ return result;
7464
+ }
7465
+ return result.then(
7466
+ (value) => this.decorateQueueMessages(value, effect, args, replay2)
7467
+ );
7468
+ };
7469
+ }
7470
+ createTransaction(binding, replay2) {
7471
+ return async (callback, options) => {
7472
+ if (typeof callback !== "function") {
7473
+ throw new BitfabError("Rivet db.transaction requires a callback");
7474
+ }
7475
+ if (replay2) {
7476
+ return await callback(
7477
+ this.createMethodProxy(
7478
+ () => void 0,
7479
+ "db.transaction",
7480
+ ["execute"],
7481
+ replay2
7482
+ )
7483
+ );
7484
+ }
7485
+ const context = binding?.context;
7486
+ const db = context ? readProperty(context, "db") : void 0;
7487
+ const transaction = isRecord5(db) ? readProperty(db, "transaction") : void 0;
7488
+ if (!isRecord5(db) || typeof transaction !== "function") {
7489
+ throw unavailableCapability("db.transaction");
7490
+ }
7491
+ return await transaction.call(
7492
+ db,
7493
+ async (transactionDb) => {
7494
+ if (!isRecord5(transactionDb)) {
7495
+ throw unavailableCapability("db.transaction.execute");
7496
+ }
7497
+ return await callback(
7498
+ this.createMethodProxy(
7499
+ () => transactionDb,
7500
+ "db.transaction",
7501
+ ["execute"],
7502
+ replay2
7503
+ )
7504
+ );
7505
+ },
7506
+ options
7507
+ );
7508
+ };
7509
+ }
7510
+ decorateQueueMessages(value, effect, args, replay2) {
7511
+ if (!this.queueCallIsCompletable(effect, args)) {
7512
+ return value;
7513
+ }
7514
+ if (Array.isArray(value)) {
7515
+ return value.map((message) => this.decorateQueueMessage(message, replay2));
7516
+ }
7517
+ return this.decorateQueueMessage(value, replay2);
7518
+ }
7519
+ decorateQueueMessage(value, replay2) {
7520
+ if (!isRecord5(value)) {
7521
+ return value;
7522
+ }
7523
+ const originalComplete = readProperty(value, "complete");
7524
+ const complete = this.createEffect(
7525
+ "queue.message.complete",
7526
+ () => typeof originalComplete === "function" ? { complete: originalComplete.bind(value) } : void 0,
7527
+ "complete",
7528
+ replay2
7529
+ );
7530
+ return { ...value, complete };
7531
+ }
7532
+ queueCallIsCompletable(effect, args) {
7533
+ const options = effect === "queue.waitForNames" ? args[1] : args[0];
7534
+ return isRecord5(options) && options.completable === true;
7535
+ }
7536
+ createQueueIterator(queue, options) {
7537
+ return {
7538
+ async *[Symbol.asyncIterator]() {
7539
+ for (; ; ) {
7540
+ const next = Reflect.get(queue, "next", queue);
7541
+ if (typeof next !== "function") {
7542
+ throw unavailableCapability("queue.next");
7543
+ }
7544
+ const message = await next.call(queue, options);
7545
+ if (message !== void 0 && message !== null) {
7546
+ yield message;
7547
+ }
7548
+ }
7549
+ }
7550
+ };
7551
+ }
7552
+ };
7553
+
6972
7554
  // src/seedContext.ts
6973
7555
  init_asyncStorage();
6974
7556
  var seedContextStorage = null;
@@ -8678,6 +9260,47 @@ var Bitfab = class {
8678
9260
  options
8679
9261
  });
8680
9262
  }
9263
+ /**
9264
+ * Get the first-class Rivet actor-context integration for an existing trace
9265
+ * root. The integration binds context and records effect spans; it never
9266
+ * creates another root.
9267
+ *
9268
+ * @param traceFunctionKey - Key used by the enclosing `withTrace()` root
9269
+ * @param options - Explicit per-context-path replay mocking policy
9270
+ * @experimental This API may change before it is stable.
9271
+ */
9272
+ getRivetIntegration(traceFunctionKey, options) {
9273
+ return new BitfabRivetIntegration(
9274
+ traceFunctionKey,
9275
+ {
9276
+ wrapEffect: (effect, mockOnReplay, fn, replayOutput) => {
9277
+ const spanOptions = {
9278
+ name: effect,
9279
+ type: "function",
9280
+ captureWhen: "nested",
9281
+ mockOnReplay,
9282
+ surface: "inherit",
9283
+ instrumentation: "rivet",
9284
+ ...replayOutput !== void 0 && { replayOutput }
9285
+ };
9286
+ return this.withSpan(traceFunctionKey, spanOptions, fn);
9287
+ },
9288
+ recordRootFixture: (context, recordedRoots) => {
9289
+ const root = getSpanStack()[0];
9290
+ if (!root) {
9291
+ return;
9292
+ }
9293
+ const rootId = `${root.traceId}:${root.spanId}`;
9294
+ if (recordedRoots.has(rootId)) {
9295
+ return;
9296
+ }
9297
+ root.contexts.push(context);
9298
+ recordedRoots.add(rootId);
9299
+ }
9300
+ },
9301
+ options
9302
+ );
9303
+ }
8681
9304
  /**
8682
9305
  * Get a Claude Agent SDK handler for tracing.
8683
9306
  *
@@ -9176,6 +9799,7 @@ var Bitfab = class {
9176
9799
  }
9177
9800
  return output;
9178
9801
  };
9802
+ const resolveBaseOutput = () => options.replayOutput !== void 0 ? options.replayOutput() : resolveRecordedOutput();
9179
9803
  const shouldMockWithBaseStrategy = replayCtxForMock.mockStrategy === "all" || replayCtxForMock.mockStrategy === "marked" && options.mockOnReplay === true;
9180
9804
  if (replayCtxForMock.mockOverrides?.length) {
9181
9805
  const nodeMeta = {
@@ -9232,7 +9856,7 @@ var Bitfab = class {
9232
9856
  }
9233
9857
  if (shouldMockWithBaseStrategy) {
9234
9858
  const output = await resolveMockOrAbort(
9235
- () => resolveRecordedOutput()
9859
+ () => resolveBaseOutput()
9236
9860
  );
9237
9861
  void sendSpan({
9238
9862
  result: output,
@@ -9255,7 +9879,7 @@ var Bitfab = class {
9255
9879
  );
9256
9880
  }
9257
9881
  if (shouldMockWithBaseStrategy) {
9258
- const recorded = resolveRecordedOutput();
9882
+ const recorded = resolveBaseOutput();
9259
9883
  if (recorded instanceof Promise) {
9260
9884
  return emitMockAsync(recorded, "recorded");
9261
9885
  }
@@ -9857,6 +10481,28 @@ var BitfabFunction = class {
9857
10481
  span(options = {}) {
9858
10482
  return this.client.span(this.traceFunctionKey, options);
9859
10483
  }
10484
+ withTrace(optionsOrFn, maybeFn) {
10485
+ if (typeof optionsOrFn === "function") {
10486
+ return this.client.withTrace(this.traceFunctionKey, optionsOrFn);
10487
+ }
10488
+ if (!maybeFn) {
10489
+ throw new BitfabError("BitfabFunction.withTrace requires a function");
10490
+ }
10491
+ return this.client.withTrace(this.traceFunctionKey, optionsOrFn, maybeFn);
10492
+ }
10493
+ /**
10494
+ * Create a trace method decorator bound to this function's key.
10495
+ *
10496
+ * Equivalent to `client.trace(key, options)` but reuses the key bound on
10497
+ * this handle.
10498
+ *
10499
+ * @param options - Trace configuration applied to the decorated method
10500
+ * @returns A method decorator configured for this key
10501
+ * @experimental Automatic child-call instrumentation is experimental.
10502
+ */
10503
+ trace(options = {}) {
10504
+ return this.client.trace(this.traceFunctionKey, options);
10505
+ }
9860
10506
  /**
9861
10507
  * Get a Vercel AI SDK language-model middleware bound to this function's key.
9862
10508
  *
@@ -9954,6 +10600,20 @@ var BitfabFunction = class {
9954
10600
  getLangGraphIntegration(options) {
9955
10601
  return this.client.getLangGraphIntegration(this.traceFunctionKey, options);
9956
10602
  }
10603
+ /**
10604
+ * Get the first-class Rivet actor-context integration bound to this key.
10605
+ * Use its `bind()` or `withContext()` outside this handle's `withTrace()`
10606
+ * root, then call `getContext()` inside the root.
10607
+ *
10608
+ * @param options - Explicit per-context-path replay mocking policy
10609
+ * @experimental This API may change before it is stable.
10610
+ */
10611
+ getRivetIntegration(options) {
10612
+ return this.client.getRivetIntegration(
10613
+ this.traceFunctionKey,
10614
+ options
10615
+ );
10616
+ }
9957
10617
  /**
9958
10618
  * Wrap a BAML client method to automatically capture prompt and LLM metadata.
9959
10619
  * Delegates to the parent client's wrapBAML method.
@@ -10115,6 +10775,7 @@ function resolveTraceFunctionKey(registration) {
10115
10775
  BitfabLangGraphIntegration,
10116
10776
  BitfabOpenAIAgentHandler,
10117
10777
  BitfabOpenAITracingProcessor,
10778
+ BitfabRivetIntegration,
10118
10779
  BitfabVercelAiHandler,
10119
10780
  DEFAULT_SERVICE_URL,
10120
10781
  DatasetsClient,