zeitlich 0.2.49 → 0.2.50
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/README.md +26 -23
- package/dist/{activities-zG_FBoY2.d.ts → activities-IuOIvPHO.d.ts} +6 -6
- package/dist/{activities-7OcT_vdR.d.cts → activities-cIlq1y1y.d.cts} +6 -6
- package/dist/adapters/sandbox/daytona/index.cjs.map +1 -1
- package/dist/adapters/sandbox/daytona/index.d.cts +3 -3
- package/dist/adapters/sandbox/daytona/index.d.ts +3 -3
- package/dist/adapters/sandbox/daytona/index.js.map +1 -1
- package/dist/adapters/sandbox/daytona/workflow.d.cts +2 -2
- package/dist/adapters/sandbox/daytona/workflow.d.ts +2 -2
- package/dist/adapters/sandbox/e2b/index.cjs.map +1 -1
- package/dist/adapters/sandbox/e2b/index.d.cts +1 -1
- package/dist/adapters/sandbox/e2b/index.d.ts +1 -1
- package/dist/adapters/sandbox/e2b/index.js.map +1 -1
- package/dist/adapters/sandbox/e2b/workflow.d.cts +1 -1
- package/dist/adapters/sandbox/e2b/workflow.d.ts +1 -1
- package/dist/adapters/thread/anthropic/index.cjs +45 -42
- package/dist/adapters/thread/anthropic/index.cjs.map +1 -1
- package/dist/adapters/thread/anthropic/index.d.cts +10 -10
- package/dist/adapters/thread/anthropic/index.d.ts +10 -10
- package/dist/adapters/thread/anthropic/index.js +45 -42
- package/dist/adapters/thread/anthropic/index.js.map +1 -1
- package/dist/adapters/thread/anthropic/workflow.d.cts +7 -7
- package/dist/adapters/thread/anthropic/workflow.d.ts +7 -7
- package/dist/adapters/thread/google-genai/index.cjs +117 -54
- package/dist/adapters/thread/google-genai/index.cjs.map +1 -1
- package/dist/adapters/thread/google-genai/index.d.cts +27 -23
- package/dist/adapters/thread/google-genai/index.d.ts +27 -23
- package/dist/adapters/thread/google-genai/index.js +117 -54
- package/dist/adapters/thread/google-genai/index.js.map +1 -1
- package/dist/adapters/thread/google-genai/workflow.d.cts +8 -8
- package/dist/adapters/thread/google-genai/workflow.d.ts +8 -8
- package/dist/adapters/thread/langchain/index.cjs +45 -42
- package/dist/adapters/thread/langchain/index.cjs.map +1 -1
- package/dist/adapters/thread/langchain/index.d.cts +10 -10
- package/dist/adapters/thread/langchain/index.d.ts +10 -10
- package/dist/adapters/thread/langchain/index.js +45 -42
- package/dist/adapters/thread/langchain/index.js.map +1 -1
- package/dist/adapters/thread/langchain/workflow.d.cts +7 -7
- package/dist/adapters/thread/langchain/workflow.d.ts +7 -7
- package/dist/{cold-store-CkWoNtMh.d.cts → cold-store-C0uvYTSi.d.cts} +1 -1
- package/dist/{cold-store-DKMAO1Dd.d.ts → cold-store-CCnZYWjx.d.ts} +1 -1
- package/dist/index.cjs +15050 -420
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +79 -83
- package/dist/index.d.ts +79 -83
- package/dist/index.js +15051 -417
- package/dist/index.js.map +1 -1
- package/dist/{proxy-B7CWEV-T.d.cts → proxy-BVznA2_p.d.cts} +1 -1
- package/dist/{proxy-ByFHMVRX.d.ts → proxy-C4J1pNUk.d.ts} +1 -1
- package/dist/{thread-manager-Cibe0X5m.d.cts → thread-manager-BqjzWsP7.d.ts} +4 -4
- package/dist/{thread-manager-B9rtMEVn.d.cts → thread-manager-CzIs47uG.d.cts} +4 -4
- package/dist/{thread-manager-nK-WcFzM.d.ts → thread-manager-Dzl1fHhV.d.cts} +4 -4
- package/dist/{thread-manager-7AW4rhfu.d.ts → thread-manager-SkSWRPRc.d.ts} +4 -4
- package/dist/{types-gVa5XCWD.d.ts → types-BQvXWcft.d.ts} +1 -1
- package/dist/{types-DO4Tkwxo.d.ts → types-CbPnU4RM.d.ts} +3 -3
- package/dist/{types-CJ7tCdl6.d.ts → types-D8W5TnSa.d.cts} +3 -3
- package/dist/{types-CJ7tCdl6.d.cts → types-D8W5TnSa.d.ts} +3 -3
- package/dist/{types-DeVNWqlb.d.ts → types-DZnUqCAP.d.cts} +709 -709
- package/dist/{types-CjY93AWZ.d.cts → types-OEN1xrFg.d.cts} +1 -1
- package/dist/{types-XUUFvrJ9.d.cts → types-YNesmGKV.d.ts} +709 -709
- package/dist/{types-BR-k7h0e.d.cts → types-d2RvEP6v.d.cts} +3 -3
- package/dist/{workflow-uhOIj9D-.d.ts → workflow-B3oTe2_D.d.cts} +34 -3
- package/dist/{workflow-KbGsxpfh.d.cts → workflow-Bkzg0cjB.d.ts} +34 -3
- package/dist/workflow.cjs +15008 -377
- package/dist/workflow.cjs.map +1 -1
- package/dist/workflow.d.cts +3 -3
- package/dist/workflow.d.ts +3 -3
- package/dist/workflow.js +15009 -374
- package/dist/workflow.js.map +1 -1
- package/package.json +10 -37
- package/src/adapters/thread/anthropic/activities.ts +1 -1
- package/src/adapters/thread/anthropic/fork-transform.test.ts +17 -11
- package/src/adapters/thread/anthropic/model-invoker.test.ts +4 -3
- package/src/adapters/thread/anthropic/model-invoker.ts +1 -1
- package/src/adapters/thread/anthropic/thread-manager.test.ts +2 -2
- package/src/adapters/thread/anthropic/thread-manager.ts +1 -1
- package/src/adapters/thread/google-genai/activities.ts +1 -1
- package/src/adapters/thread/google-genai/fork-transform.test.ts +17 -11
- package/src/adapters/thread/google-genai/model-invoker.test.ts +337 -0
- package/src/adapters/thread/google-genai/model-invoker.ts +107 -23
- package/src/adapters/thread/google-genai/thread-manager.test.ts +2 -2
- package/src/adapters/thread/google-genai/thread-manager.ts +1 -1
- package/src/adapters/thread/langchain/activities.ts +1 -1
- package/src/adapters/thread/langchain/fork-transform.test.ts +17 -11
- package/src/adapters/thread/langchain/model-invoker.ts +1 -1
- package/src/adapters/thread/langchain/thread-manager.test.ts +2 -2
- package/src/adapters/thread/langchain/thread-manager.ts +1 -1
- package/src/index.ts +2 -2
- package/src/lib/sandbox/capability-types.test.ts +2 -2
- package/src/lib/sandbox/manager.ts +2 -6
- package/src/lib/sandbox/sandbox.test.ts +1 -1
- package/src/lib/sandbox/types.ts +2 -2
- package/src/lib/session/session.integration.test.ts +92 -0
- package/src/lib/session/session.ts +23 -11
- package/src/lib/thread/keys.test.ts +9 -9
- package/src/lib/thread/keys.ts +1 -1
- package/src/lib/thread/manager.test.ts +24 -14
- package/src/lib/thread/manager.ts +19 -23
- package/src/lib/thread/snapshot.test.ts +51 -43
- package/src/lib/thread/snapshot.ts +54 -32
- package/src/lib/thread/test-utils.ts +106 -59
- package/src/lib/thread/tiered.test.ts +1 -1
- package/src/lib/thread/types.ts +2 -2
- package/src/lib/tool-router/router.integration.test.ts +44 -0
- package/src/lib/tool-router/router.ts +140 -32
- package/src/lib/workflow.ts +49 -0
- package/src/{adapters/sandbox/inmemory/proxy.ts → test-utils/in-memory-sandbox-proxy.ts} +5 -16
- package/src/{adapters/sandbox/inmemory/index.ts → test-utils/in-memory-sandbox.ts} +11 -3
- package/src/tools/bash/bash.test.ts +1 -1
- package/src/tools/edit/handler.test.ts +1 -1
- package/tsup.config.ts +2 -4
- package/dist/adapters/sandbox/inmemory/index.cjs +0 -214
- package/dist/adapters/sandbox/inmemory/index.cjs.map +0 -1
- package/dist/adapters/sandbox/inmemory/index.d.cts +0 -40
- package/dist/adapters/sandbox/inmemory/index.d.ts +0 -40
- package/dist/adapters/sandbox/inmemory/index.js +0 -211
- package/dist/adapters/sandbox/inmemory/index.js.map +0 -1
- package/dist/adapters/sandbox/inmemory/workflow.cjs +0 -36
- package/dist/adapters/sandbox/inmemory/workflow.cjs.map +0 -1
- package/dist/adapters/sandbox/inmemory/workflow.d.cts +0 -27
- package/dist/adapters/sandbox/inmemory/workflow.d.ts +0 -27
- package/dist/adapters/sandbox/inmemory/workflow.js +0 -34
- package/dist/adapters/sandbox/inmemory/workflow.js.map +0 -1
|
@@ -1,16 +1,16 @@
|
|
|
1
1
|
import { ActivityInterfaceFor } from '@temporalio/workflow';
|
|
2
|
-
import { T as ThreadOps } from '../../../types-
|
|
3
|
-
import { A as AnthropicContent } from '../../../thread-manager-
|
|
4
|
-
import { c as createThreadOpsProxy } from '../../../proxy-
|
|
5
|
-
export { T as ThreadOpsProxyOptions } from '../../../proxy-
|
|
2
|
+
import { T as ThreadOps } from '../../../types-YNesmGKV.js';
|
|
3
|
+
import { A as AnthropicContent } from '../../../thread-manager-SkSWRPRc.js';
|
|
4
|
+
import { c as createThreadOpsProxy } from '../../../proxy-C4J1pNUk.js';
|
|
5
|
+
export { T as ThreadOpsProxyOptions } from '../../../proxy-C4J1pNUk.js';
|
|
6
6
|
export { A as ADAPTER_ID, a as AdapterId } from '../../../adapter-id-CMwVrVqv.js';
|
|
7
7
|
import '@temporalio/common/lib/interfaces';
|
|
8
8
|
import 'zod';
|
|
9
|
-
import '../../../types-
|
|
9
|
+
import '../../../types-D8W5TnSa.js';
|
|
10
10
|
import '@temporalio/common';
|
|
11
|
-
import '
|
|
11
|
+
import 'redis';
|
|
12
12
|
import '@anthropic-ai/sdk';
|
|
13
|
-
import '../../../types-
|
|
13
|
+
import '../../../types-CbPnU4RM.js';
|
|
14
14
|
|
|
15
15
|
/**
|
|
16
16
|
* Workflow-safe proxy for Anthropic thread operations.
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
+
var crypto = require('crypto');
|
|
3
4
|
var activity = require('@temporalio/activity');
|
|
4
5
|
|
|
5
6
|
// src/adapters/thread/google-genai/adapter-id.ts
|
|
@@ -55,11 +56,11 @@ function createThreadManager(config) {
|
|
|
55
56
|
return {
|
|
56
57
|
async initialize() {
|
|
57
58
|
await redis.del(redisKey);
|
|
58
|
-
await redis.set(metaKey, "1",
|
|
59
|
+
await redis.set(metaKey, "1", { EX: ttlSeconds });
|
|
59
60
|
},
|
|
60
61
|
async load() {
|
|
61
62
|
await assertThreadExists();
|
|
62
|
-
const data = await redis.
|
|
63
|
+
const data = await redis.lRange(redisKey, 0, -1);
|
|
63
64
|
return data.map(deserialize);
|
|
64
65
|
},
|
|
65
66
|
async append(messages) {
|
|
@@ -67,22 +68,18 @@ function createThreadManager(config) {
|
|
|
67
68
|
await assertThreadExists();
|
|
68
69
|
if (idOf) {
|
|
69
70
|
const dedupId = messages.map(idOf).join(":");
|
|
70
|
-
await redis.eval(
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
redisKey,
|
|
75
|
-
String(ttlSeconds),
|
|
76
|
-
...messages.map(serialize)
|
|
77
|
-
);
|
|
71
|
+
await redis.eval(APPEND_IDEMPOTENT_SCRIPT, {
|
|
72
|
+
keys: [dedupKey(dedupId), redisKey],
|
|
73
|
+
arguments: [String(ttlSeconds), ...messages.map(serialize)]
|
|
74
|
+
});
|
|
78
75
|
} else {
|
|
79
|
-
await redis.
|
|
76
|
+
await redis.rPush(redisKey, messages.map(serialize));
|
|
80
77
|
await redis.expire(redisKey, ttlSeconds);
|
|
81
78
|
}
|
|
82
79
|
},
|
|
83
80
|
async fork(newThreadId) {
|
|
84
81
|
await assertThreadExists();
|
|
85
|
-
const data = await redis.
|
|
82
|
+
const data = await redis.lRange(redisKey, 0, -1);
|
|
86
83
|
const stateRaw = await redis.get(stateKey);
|
|
87
84
|
const forked = createThreadManager({
|
|
88
85
|
...config,
|
|
@@ -91,12 +88,12 @@ function createThreadManager(config) {
|
|
|
91
88
|
await forked.initialize();
|
|
92
89
|
if (data.length > 0) {
|
|
93
90
|
const newKey = getThreadListKey(key, newThreadId);
|
|
94
|
-
await redis.
|
|
91
|
+
await redis.rPush(newKey, data);
|
|
95
92
|
await redis.expire(newKey, ttlSeconds);
|
|
96
93
|
}
|
|
97
94
|
if (stateRaw != null) {
|
|
98
95
|
const newStateKey = getThreadStateKey(key, newThreadId);
|
|
99
|
-
await redis.set(newStateKey, stateRaw,
|
|
96
|
+
await redis.set(newStateKey, stateRaw, { EX: ttlSeconds });
|
|
100
97
|
}
|
|
101
98
|
return forked;
|
|
102
99
|
},
|
|
@@ -107,20 +104,20 @@ function createThreadManager(config) {
|
|
|
107
104
|
"replaceAll requires the thread manager to be configured with `idOf`"
|
|
108
105
|
);
|
|
109
106
|
}
|
|
110
|
-
const existing = await redis.
|
|
107
|
+
const existing = await redis.lRange(redisKey, 0, -1);
|
|
111
108
|
const existingIds = existing.map((raw) => idOf(deserialize(raw))).filter((id) => typeof id === "string");
|
|
112
109
|
await redis.del(redisKey);
|
|
113
110
|
if (existingIds.length > 0) {
|
|
114
|
-
await redis.del(
|
|
111
|
+
await redis.del(existingIds.map(dedupKey));
|
|
115
112
|
}
|
|
116
113
|
if (messages.length > 0) {
|
|
117
|
-
await redis.
|
|
114
|
+
await redis.rPush(redisKey, messages.map(serialize));
|
|
118
115
|
await redis.expire(redisKey, ttlSeconds);
|
|
119
116
|
}
|
|
120
117
|
await redis.expire(metaKey, ttlSeconds);
|
|
121
118
|
},
|
|
122
119
|
async delete() {
|
|
123
|
-
await redis.del(redisKey, metaKey, stateKey);
|
|
120
|
+
await redis.del([redisKey, metaKey, stateKey]);
|
|
124
121
|
},
|
|
125
122
|
async loadState() {
|
|
126
123
|
const raw = await redis.get(stateKey);
|
|
@@ -129,14 +126,14 @@ function createThreadManager(config) {
|
|
|
129
126
|
},
|
|
130
127
|
async saveState(state) {
|
|
131
128
|
await assertThreadExists();
|
|
132
|
-
await redis.set(stateKey, JSON.stringify(state),
|
|
129
|
+
await redis.set(stateKey, JSON.stringify(state), { EX: ttlSeconds });
|
|
133
130
|
},
|
|
134
131
|
async deleteState() {
|
|
135
132
|
await redis.del(stateKey);
|
|
136
133
|
},
|
|
137
134
|
async length() {
|
|
138
135
|
await assertThreadExists();
|
|
139
|
-
return redis.
|
|
136
|
+
return redis.lLen(redisKey);
|
|
140
137
|
},
|
|
141
138
|
async truncateFromId(messageId) {
|
|
142
139
|
await assertThreadExists();
|
|
@@ -145,7 +142,7 @@ function createThreadManager(config) {
|
|
|
145
142
|
"truncateFromId requires the thread manager to be configured with `idOf`"
|
|
146
143
|
);
|
|
147
144
|
}
|
|
148
|
-
const data = await redis.
|
|
145
|
+
const data = await redis.lRange(redisKey, 0, -1);
|
|
149
146
|
let idx = -1;
|
|
150
147
|
const removedIds = [];
|
|
151
148
|
for (let i = 0; i < data.length; i++) {
|
|
@@ -160,11 +157,11 @@ function createThreadManager(config) {
|
|
|
160
157
|
await redis.del(redisKey);
|
|
161
158
|
await redis.expire(metaKey, ttlSeconds);
|
|
162
159
|
} else {
|
|
163
|
-
await redis.
|
|
160
|
+
await redis.lTrim(redisKey, 0, idx - 1);
|
|
164
161
|
await redis.expire(redisKey, ttlSeconds);
|
|
165
162
|
}
|
|
166
163
|
if (removedIds.length > 0) {
|
|
167
|
-
await redis.del(
|
|
164
|
+
await redis.del(removedIds.map(dedupKey));
|
|
168
165
|
}
|
|
169
166
|
}
|
|
170
167
|
};
|
|
@@ -179,7 +176,7 @@ async function encodeSnapshot(config) {
|
|
|
179
176
|
}
|
|
180
177
|
const listKey = getThreadListKey(threadKey, threadId);
|
|
181
178
|
const stateKey = getThreadStateKey(threadKey, threadId);
|
|
182
|
-
const messages = await redis.
|
|
179
|
+
const messages = await redis.lRange(listKey, 0, -1);
|
|
183
180
|
const stateRaw = await redis.get(stateKey);
|
|
184
181
|
const state = stateRaw == null ? null : JSON.parse(stateRaw);
|
|
185
182
|
const dedupIds = idOf ? messages.map(idOf) : [];
|
|
@@ -199,31 +196,38 @@ async function applySnapshot(config) {
|
|
|
199
196
|
}
|
|
200
197
|
const listKey = getThreadListKey(threadKey, threadId);
|
|
201
198
|
const stateKey = getThreadStateKey(threadKey, threadId);
|
|
202
|
-
await redis.del(listKey, stateKey);
|
|
203
|
-
const pipeline = redis.
|
|
199
|
+
await redis.del([listKey, stateKey]);
|
|
200
|
+
const pipeline = redis.multi();
|
|
204
201
|
if (snapshot.messages.length > 0) {
|
|
205
|
-
pipeline.
|
|
202
|
+
pipeline.rPush(listKey, snapshot.messages);
|
|
206
203
|
pipeline.expire(listKey, ttlSeconds);
|
|
207
204
|
}
|
|
208
205
|
if (snapshot.state != null) {
|
|
209
|
-
pipeline.set(stateKey, JSON.stringify(snapshot.state),
|
|
206
|
+
pipeline.set(stateKey, JSON.stringify(snapshot.state), { EX: ttlSeconds });
|
|
210
207
|
}
|
|
211
208
|
for (const id of snapshot.dedupIds) {
|
|
212
|
-
pipeline.set(getThreadDedupKey(threadId, id), "1",
|
|
209
|
+
pipeline.set(getThreadDedupKey(threadId, id), "1", { EX: ttlSeconds });
|
|
213
210
|
}
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
throw firstErr;
|
|
224
|
-
}
|
|
211
|
+
try {
|
|
212
|
+
await pipeline.execAsPipeline();
|
|
213
|
+
} catch (err) {
|
|
214
|
+
await redis.del([
|
|
215
|
+
listKey,
|
|
216
|
+
stateKey,
|
|
217
|
+
...snapshot.dedupIds.map((id) => getThreadDedupKey(threadId, id))
|
|
218
|
+
]).catch(() => void 0);
|
|
219
|
+
throw firstPipelineError(err);
|
|
225
220
|
}
|
|
226
|
-
await redis.set(metaKey, "1",
|
|
221
|
+
await redis.set(metaKey, "1", { EX: ttlSeconds });
|
|
222
|
+
}
|
|
223
|
+
function firstPipelineError(err) {
|
|
224
|
+
if (err != null && typeof err === "object" && "replies" in err && Array.isArray(err.replies)) {
|
|
225
|
+
const firstErr = err.replies.find(
|
|
226
|
+
(r) => r instanceof Error
|
|
227
|
+
);
|
|
228
|
+
if (firstErr) return firstErr;
|
|
229
|
+
}
|
|
230
|
+
return err;
|
|
227
231
|
}
|
|
228
232
|
async function clearHotTier(config) {
|
|
229
233
|
const { redis, threadKey, threadId, dedupIds = [] } = config;
|
|
@@ -233,7 +237,7 @@ async function clearHotTier(config) {
|
|
|
233
237
|
getThreadStateKey(threadKey, threadId),
|
|
234
238
|
...dedupIds.map((id) => getThreadDedupKey(threadId, id))
|
|
235
239
|
];
|
|
236
|
-
await redis.del(
|
|
240
|
+
await redis.del(keys);
|
|
237
241
|
}
|
|
238
242
|
|
|
239
243
|
// src/lib/thread/tiered.ts
|
|
@@ -431,7 +435,9 @@ function createGoogleGenAIModelInvoker({
|
|
|
431
435
|
redis,
|
|
432
436
|
client,
|
|
433
437
|
model,
|
|
434
|
-
hooks
|
|
438
|
+
hooks,
|
|
439
|
+
config: generationConfig,
|
|
440
|
+
cache: cacheConfig
|
|
435
441
|
}) {
|
|
436
442
|
return async function invokeGoogleGenAIModel2(config) {
|
|
437
443
|
const { threadId, threadKey, state, assistantMessageId } = config;
|
|
@@ -446,12 +452,57 @@ function createGoogleGenAIModelInvoker({
|
|
|
446
452
|
const { contents, systemInstruction } = await thread.prepareForInvocation();
|
|
447
453
|
const functionDeclarations = toFunctionDeclarations(state.tools);
|
|
448
454
|
const tools = functionDeclarations.length > 0 ? [{ functionDeclarations }] : void 0;
|
|
455
|
+
const {
|
|
456
|
+
systemInstruction: _si,
|
|
457
|
+
tools: _t,
|
|
458
|
+
abortSignal: _as,
|
|
459
|
+
cachedContent: callerCachedContent,
|
|
460
|
+
toolConfig: callerToolConfig,
|
|
461
|
+
...callerConfig
|
|
462
|
+
} = generationConfig ?? {};
|
|
463
|
+
let liveContents = contents;
|
|
464
|
+
let cachedContentName;
|
|
465
|
+
let cachedWriteTokens;
|
|
466
|
+
if (cacheConfig && cacheConfig.splitIndex > 0 && contents.length > cacheConfig.splitIndex) {
|
|
467
|
+
liveContents = contents.slice(cacheConfig.splitIndex);
|
|
468
|
+
const ttl = cacheConfig.ttlSeconds ?? 300;
|
|
469
|
+
const cacheRedisKey = `${threadKey ?? "messages"}:gemini-cache:${model}:${cacheConfig.splitIndex}:thread:${threadId}`;
|
|
470
|
+
cachedContentName = await redis.get(cacheRedisKey) ?? void 0;
|
|
471
|
+
if (!cachedContentName) {
|
|
472
|
+
const cacheInstance = await client.caches.create({
|
|
473
|
+
model,
|
|
474
|
+
config: {
|
|
475
|
+
contents: contents.slice(0, cacheConfig.splitIndex),
|
|
476
|
+
...systemInstruction ? { systemInstruction } : {},
|
|
477
|
+
...tools ? { tools } : {},
|
|
478
|
+
...callerToolConfig ? { toolConfig: callerToolConfig } : {},
|
|
479
|
+
ttl: `${ttl}s`,
|
|
480
|
+
abortSignal: signal
|
|
481
|
+
}
|
|
482
|
+
});
|
|
483
|
+
if (!cacheInstance?.name) {
|
|
484
|
+
throw new Error("Gemini cache creation did not return a cache name");
|
|
485
|
+
}
|
|
486
|
+
cachedContentName = cacheInstance.name;
|
|
487
|
+
cachedWriteTokens = cacheInstance.usageMetadata?.totalTokenCount ?? void 0;
|
|
488
|
+
const redisTtl = ttl - 5;
|
|
489
|
+
if (redisTtl > 0) {
|
|
490
|
+
await redis.set(cacheRedisKey, cachedContentName, { EX: redisTtl });
|
|
491
|
+
}
|
|
492
|
+
}
|
|
493
|
+
}
|
|
449
494
|
const stream = await client.models.generateContentStream({
|
|
450
495
|
model,
|
|
451
|
-
contents,
|
|
496
|
+
contents: liveContents,
|
|
452
497
|
config: {
|
|
453
|
-
...
|
|
454
|
-
...
|
|
498
|
+
...callerConfig,
|
|
499
|
+
...cachedContentName ? { cachedContent: cachedContentName } : {
|
|
500
|
+
...callerCachedContent ? { cachedContent: callerCachedContent } : {
|
|
501
|
+
...systemInstruction ? { systemInstruction } : {},
|
|
502
|
+
...tools ? { tools } : {}
|
|
503
|
+
},
|
|
504
|
+
...callerToolConfig ? { toolConfig: callerToolConfig } : {}
|
|
505
|
+
},
|
|
455
506
|
abortSignal: signal
|
|
456
507
|
}
|
|
457
508
|
});
|
|
@@ -465,19 +516,27 @@ function createGoogleGenAIModelInvoker({
|
|
|
465
516
|
if (!lastChunk) {
|
|
466
517
|
throw new Error("Google GenAI stream ended without producing any chunks");
|
|
467
518
|
}
|
|
519
|
+
for (const part of allParts) {
|
|
520
|
+
if (part.functionCall && !part.functionCall.id) {
|
|
521
|
+
part.functionCall.id = crypto.randomBytes(8).toString("hex");
|
|
522
|
+
}
|
|
523
|
+
}
|
|
468
524
|
const modelContent = { role: "model", parts: allParts };
|
|
469
|
-
const functionCalls = lastChunk.functionCalls ?? [];
|
|
470
525
|
return {
|
|
471
526
|
message: modelContent,
|
|
472
|
-
rawToolCalls:
|
|
473
|
-
|
|
474
|
-
|
|
475
|
-
|
|
527
|
+
rawToolCalls: allParts.filter(
|
|
528
|
+
(p) => !!p.functionCall
|
|
529
|
+
).map((p) => ({
|
|
530
|
+
id: p.functionCall.id,
|
|
531
|
+
name: p.functionCall.name ?? "",
|
|
532
|
+
args: p.functionCall.args ?? {}
|
|
476
533
|
})),
|
|
477
534
|
usage: {
|
|
478
535
|
inputTokens: lastChunk.usageMetadata?.promptTokenCount,
|
|
479
536
|
outputTokens: lastChunk.usageMetadata?.candidatesTokenCount,
|
|
480
|
-
|
|
537
|
+
cachedWriteTokens,
|
|
538
|
+
cachedReadTokens: lastChunk.usageMetadata?.cachedContentTokenCount,
|
|
539
|
+
reasonTokens: lastChunk.usageMetadata?.thoughtsTokenCount
|
|
481
540
|
}
|
|
482
541
|
};
|
|
483
542
|
};
|
|
@@ -487,13 +546,17 @@ async function invokeGoogleGenAIModel({
|
|
|
487
546
|
client,
|
|
488
547
|
model,
|
|
489
548
|
hooks,
|
|
490
|
-
config
|
|
549
|
+
config,
|
|
550
|
+
generationConfig,
|
|
551
|
+
cache
|
|
491
552
|
}) {
|
|
492
553
|
const invoker = createGoogleGenAIModelInvoker({
|
|
493
554
|
redis,
|
|
494
555
|
client,
|
|
495
556
|
model,
|
|
496
|
-
hooks
|
|
557
|
+
hooks,
|
|
558
|
+
config: generationConfig,
|
|
559
|
+
cache
|
|
497
560
|
});
|
|
498
561
|
return invoker(config);
|
|
499
562
|
}
|