@langgraph-js/pure-graph 1.2.0 → 1.4.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/README.md +22 -14
- package/dist/adapter/hono/runs.js +18 -1
- package/dist/adapter/nextjs/router.js +18 -7
- package/dist/adapter/zod.d.ts +15 -8
- package/dist/adapter/zod.js +8 -0
- package/dist/global.d.ts +3 -2
- package/dist/storage/index.d.ts +4 -3
- package/dist/storage/index.js +13 -1
- package/dist/storage/memory/threads.d.ts +3 -2
- package/dist/storage/memory/threads.js +29 -2
- package/dist/storage/pg/checkpoint.d.ts +2 -0
- package/dist/storage/pg/checkpoint.js +9 -0
- package/dist/storage/pg/threads.d.ts +43 -0
- package/dist/storage/pg/threads.js +304 -0
- package/dist/storage/sqlite/threads.d.ts +3 -2
- package/dist/storage/sqlite/threads.js +37 -3
- package/dist/threads/index.d.ts +3 -2
- package/dist/threads/index.js +1 -26
- package/dist/tsconfig.tsbuildinfo +1 -0
- package/dist/types.d.ts +2 -1
- package/package.json +38 -5
- package/.prettierrc +0 -11
- package/bun.lock +0 -209
- package/dist/adapter/nextjs/zod.d.ts +0 -203
- package/dist/adapter/nextjs/zod.js +0 -60
- package/examples/nextjs/README.md +0 -36
- package/examples/nextjs/app/api/langgraph/[...path]/route.ts +0 -10
- package/examples/nextjs/app/favicon.ico +0 -0
- package/examples/nextjs/app/globals.css +0 -26
- package/examples/nextjs/app/layout.tsx +0 -34
- package/examples/nextjs/app/page.tsx +0 -211
- package/examples/nextjs/next.config.ts +0 -26
- package/examples/nextjs/package.json +0 -24
- package/examples/nextjs/postcss.config.mjs +0 -5
- package/examples/nextjs/tsconfig.json +0 -27
- package/packages/agent-graph/demo.json +0 -35
- package/packages/agent-graph/package.json +0 -18
- package/packages/agent-graph/src/index.ts +0 -47
- package/packages/agent-graph/src/tools/tavily.ts +0 -9
- package/packages/agent-graph/src/tools.ts +0 -38
- package/packages/agent-graph/src/types.ts +0 -42
- package/pnpm-workspace.yaml +0 -4
- package/src/adapter/hono/assistants.ts +0 -24
- package/src/adapter/hono/endpoint.ts +0 -3
- package/src/adapter/hono/index.ts +0 -14
- package/src/adapter/hono/runs.ts +0 -65
- package/src/adapter/hono/threads.ts +0 -37
- package/src/adapter/nextjs/endpoint.ts +0 -2
- package/src/adapter/nextjs/index.ts +0 -2
- package/src/adapter/nextjs/router.ts +0 -193
- package/src/adapter/nextjs/zod.ts +0 -66
- package/src/adapter/zod.ts +0 -135
- package/src/createEndpoint.ts +0 -116
- package/src/e.d.ts +0 -3
- package/src/global.ts +0 -11
- package/src/graph/stream.ts +0 -263
- package/src/graph/stringify.ts +0 -219
- package/src/index.ts +0 -6
- package/src/queue/JsonPlusSerializer.ts +0 -143
- package/src/queue/event_message.ts +0 -30
- package/src/queue/stream_queue.ts +0 -237
- package/src/storage/index.ts +0 -52
- package/src/storage/memory/checkpoint.ts +0 -2
- package/src/storage/memory/queue.ts +0 -91
- package/src/storage/memory/threads.ts +0 -154
- package/src/storage/redis/queue.ts +0 -148
- package/src/storage/sqlite/DB.ts +0 -16
- package/src/storage/sqlite/checkpoint.ts +0 -503
- package/src/storage/sqlite/threads.ts +0 -366
- package/src/storage/sqlite/type.ts +0 -12
- package/src/threads/index.ts +0 -51
- package/src/types.ts +0 -116
- package/src/utils/createEntrypointGraph.ts +0 -20
- package/src/utils/getGraph.ts +0 -44
- package/src/utils/getLangGraphCommand.ts +0 -21
- package/test/graph/entrypoint.ts +0 -21
- package/test/graph/index.ts +0 -60
- package/test/hono.ts +0 -15
- package/tsconfig.json +0 -20
|
@@ -1,37 +0,0 @@
|
|
|
1
|
-
import { zValidator } from '@hono/zod-validator';
|
|
2
|
-
import { Hono } from 'hono';
|
|
3
|
-
import { client } from './endpoint';
|
|
4
|
-
import { ThreadIdParamSchema, ThreadCreatePayloadSchema, ThreadSearchPayloadSchema } from '../zod';
|
|
5
|
-
|
|
6
|
-
const api = new Hono();
|
|
7
|
-
|
|
8
|
-
// Threads Routes
|
|
9
|
-
api.post('/threads', zValidator('json', ThreadCreatePayloadSchema), async (c) => {
|
|
10
|
-
const payload = c.req.valid('json');
|
|
11
|
-
const thread = await client.threads.create(payload);
|
|
12
|
-
|
|
13
|
-
return c.json(thread);
|
|
14
|
-
});
|
|
15
|
-
|
|
16
|
-
api.post('/threads/search', zValidator('json', ThreadSearchPayloadSchema), async (c) => {
|
|
17
|
-
// Search Threads
|
|
18
|
-
const payload = c.req.valid('json');
|
|
19
|
-
const result = await client.threads.search(payload as any);
|
|
20
|
-
c.res.headers.set('X-Pagination-Total', result.length.toString());
|
|
21
|
-
return c.json(result);
|
|
22
|
-
});
|
|
23
|
-
|
|
24
|
-
api.get('/threads/:thread_id', zValidator('param', ThreadIdParamSchema), async (c) => {
|
|
25
|
-
// Get Thread
|
|
26
|
-
const { thread_id } = c.req.valid('param');
|
|
27
|
-
return c.json(await client.threads.get(thread_id));
|
|
28
|
-
});
|
|
29
|
-
|
|
30
|
-
api.delete('/threads/:thread_id', zValidator('param', ThreadIdParamSchema), async (c) => {
|
|
31
|
-
// Delete Thread
|
|
32
|
-
const { thread_id } = c.req.valid('param');
|
|
33
|
-
await client.threads.delete(thread_id);
|
|
34
|
-
return new Response(null, { status: 204 });
|
|
35
|
-
});
|
|
36
|
-
|
|
37
|
-
export default api;
|
|
@@ -1,193 +0,0 @@
|
|
|
1
|
-
/** @ts-ignore */
|
|
2
|
-
import { NextRequest, NextResponse } from 'next/server';
|
|
3
|
-
import { client } from './endpoint';
|
|
4
|
-
import {
|
|
5
|
-
AssistantsSearchSchema,
|
|
6
|
-
AssistantGraphQuerySchema,
|
|
7
|
-
RunStreamPayloadSchema,
|
|
8
|
-
RunListQuerySchema,
|
|
9
|
-
RunCancelQuerySchema,
|
|
10
|
-
ThreadCreatePayloadSchema,
|
|
11
|
-
ThreadSearchPayloadSchema,
|
|
12
|
-
} from '../zod';
|
|
13
|
-
import { serialiseAsDict } from '../../graph/stream';
|
|
14
|
-
|
|
15
|
-
// Next.js App Router 的 SSE 响应实现
|
|
16
|
-
async function sseResponse(generator: AsyncGenerator<{ event: string; data: unknown }>): Promise<Response> {
|
|
17
|
-
const encoder = new TextEncoder();
|
|
18
|
-
const stream = new ReadableStream({
|
|
19
|
-
async start(controller) {
|
|
20
|
-
try {
|
|
21
|
-
for await (const { event, data } of generator) {
|
|
22
|
-
const line = `event: ${event}\n` + `data: ${serialiseAsDict(data, 0)}\n\n`;
|
|
23
|
-
controller.enqueue(encoder.encode(line));
|
|
24
|
-
}
|
|
25
|
-
} catch (err) {
|
|
26
|
-
// ignore
|
|
27
|
-
} finally {
|
|
28
|
-
controller.close();
|
|
29
|
-
}
|
|
30
|
-
},
|
|
31
|
-
});
|
|
32
|
-
return new Response(stream, {
|
|
33
|
-
headers: {
|
|
34
|
-
'Content-Type': 'text/event-stream; charset=utf-8',
|
|
35
|
-
'Cache-Control': 'no-cache, no-transform',
|
|
36
|
-
Connection: 'keep-alive',
|
|
37
|
-
},
|
|
38
|
-
});
|
|
39
|
-
}
|
|
40
|
-
|
|
41
|
-
// 统一路由处理器
|
|
42
|
-
export async function GET(req: NextRequest) {
|
|
43
|
-
const url = new URL(req.url);
|
|
44
|
-
const pathname = url.pathname;
|
|
45
|
-
|
|
46
|
-
// Assistants routes
|
|
47
|
-
if (pathname.match(/\/assistants\/[^/]+\/graph$/)) {
|
|
48
|
-
const match = pathname.match(/\/assistants\/([^/]+)\/graph$/);
|
|
49
|
-
if (match) {
|
|
50
|
-
const assistant_id = match[1];
|
|
51
|
-
const xrayParam = url.searchParams.get('xray');
|
|
52
|
-
const queryParams = { xray: xrayParam };
|
|
53
|
-
const { xray } = AssistantGraphQuerySchema.parse(queryParams);
|
|
54
|
-
const data = await client.assistants.getGraph(assistant_id, {
|
|
55
|
-
xray: xray !== undefined ? xray === 'true' : undefined,
|
|
56
|
-
});
|
|
57
|
-
return NextResponse.json(data);
|
|
58
|
-
}
|
|
59
|
-
}
|
|
60
|
-
|
|
61
|
-
// Threads routes
|
|
62
|
-
if (pathname.match(/\/threads\/[0-9a-fA-F-]{36}$/)) {
|
|
63
|
-
const match = pathname.match(/\/threads\/([0-9a-fA-F-]{36})$/);
|
|
64
|
-
if (match) {
|
|
65
|
-
const thread_id = match[1];
|
|
66
|
-
const data = await client.threads.get(thread_id);
|
|
67
|
-
return NextResponse.json(data);
|
|
68
|
-
}
|
|
69
|
-
}
|
|
70
|
-
|
|
71
|
-
// Runs routes
|
|
72
|
-
if (pathname.match(/\/threads\/[0-9a-fA-F-]{36}\/runs$/)) {
|
|
73
|
-
const match = pathname.match(/\/threads\/([0-9a-fA-F-]{36})\/runs$/);
|
|
74
|
-
if (match) {
|
|
75
|
-
const thread_id = match[1];
|
|
76
|
-
const limit = url.searchParams.get('limit');
|
|
77
|
-
const offset = url.searchParams.get('offset');
|
|
78
|
-
const status = url.searchParams.get('status');
|
|
79
|
-
const queryParams = { limit, offset, status };
|
|
80
|
-
const {
|
|
81
|
-
limit: parsedLimit,
|
|
82
|
-
offset: parsedOffset,
|
|
83
|
-
status: parsedStatus,
|
|
84
|
-
} = RunListQuerySchema.parse(queryParams);
|
|
85
|
-
const runs = await client.runs.list(thread_id, {
|
|
86
|
-
limit: parsedLimit,
|
|
87
|
-
offset: parsedOffset,
|
|
88
|
-
status: parsedStatus,
|
|
89
|
-
});
|
|
90
|
-
return Response.json(runs);
|
|
91
|
-
}
|
|
92
|
-
}
|
|
93
|
-
|
|
94
|
-
return new NextResponse('Not Found', { status: 404 });
|
|
95
|
-
}
|
|
96
|
-
|
|
97
|
-
export async function POST(req: NextRequest) {
|
|
98
|
-
const url = new URL(req.url);
|
|
99
|
-
const pathname = url.pathname;
|
|
100
|
-
|
|
101
|
-
// Assistants routes
|
|
102
|
-
if (pathname.endsWith('/assistants/search')) {
|
|
103
|
-
const body = await req.json();
|
|
104
|
-
const payload = AssistantsSearchSchema.parse(body);
|
|
105
|
-
const data = await client.assistants.search({
|
|
106
|
-
graphId: payload.graph_id,
|
|
107
|
-
metadata: payload.metadata as any,
|
|
108
|
-
limit: payload.limit,
|
|
109
|
-
offset: payload.offset,
|
|
110
|
-
} as any);
|
|
111
|
-
return NextResponse.json(data, {
|
|
112
|
-
headers: { 'X-Pagination-Total': String(data.length) },
|
|
113
|
-
});
|
|
114
|
-
}
|
|
115
|
-
|
|
116
|
-
// Threads routes
|
|
117
|
-
if (pathname.endsWith('/threads')) {
|
|
118
|
-
const body = await req.json();
|
|
119
|
-
const payload = ThreadCreatePayloadSchema.parse(body);
|
|
120
|
-
const thread = await client.threads.create({
|
|
121
|
-
thread_id: payload.thread_id,
|
|
122
|
-
metadata: payload.metadata as any,
|
|
123
|
-
if_exists: (payload.if_exists as any) ?? undefined,
|
|
124
|
-
});
|
|
125
|
-
return NextResponse.json(thread);
|
|
126
|
-
}
|
|
127
|
-
|
|
128
|
-
if (pathname.endsWith('/threads/search')) {
|
|
129
|
-
const body = await req.json();
|
|
130
|
-
const payload = ThreadSearchPayloadSchema.parse(body);
|
|
131
|
-
const result = await client.threads.search({
|
|
132
|
-
metadata: payload.metadata as any,
|
|
133
|
-
status: payload.status as any,
|
|
134
|
-
limit: payload.limit,
|
|
135
|
-
offset: payload.offset,
|
|
136
|
-
sortBy: (payload.sort_by as any) ?? undefined,
|
|
137
|
-
sortOrder: (payload.sort_order as any) ?? undefined,
|
|
138
|
-
});
|
|
139
|
-
return NextResponse.json(result, {
|
|
140
|
-
headers: { 'X-Pagination-Total': String(result.length) },
|
|
141
|
-
});
|
|
142
|
-
}
|
|
143
|
-
|
|
144
|
-
// Runs routes - stream
|
|
145
|
-
if (pathname.match(/\/threads\/[0-9a-fA-F-]{36}\/runs\/stream$/)) {
|
|
146
|
-
const match = pathname.match(/\/threads\/([0-9a-fA-F-]{36})\/runs\/stream$/);
|
|
147
|
-
if (match) {
|
|
148
|
-
const thread_id = match[1];
|
|
149
|
-
const body = await req.json();
|
|
150
|
-
const payload = RunStreamPayloadSchema.parse(body);
|
|
151
|
-
const generator = client.runs.stream(thread_id, payload.assistant_id as string, payload as any);
|
|
152
|
-
return sseResponse(generator as any);
|
|
153
|
-
}
|
|
154
|
-
}
|
|
155
|
-
|
|
156
|
-
// Runs routes - cancel
|
|
157
|
-
if (pathname.match(/\/threads\/[0-9a-fA-F-]{36}\/runs\/[0-9a-fA-F-]{36}\/cancel$/)) {
|
|
158
|
-
const match = pathname.match(/\/threads\/([0-9a-fA-F-]{36})\/runs\/([0-9a-fA-F-]{36})\/cancel$/);
|
|
159
|
-
if (match) {
|
|
160
|
-
const thread_id = match[1];
|
|
161
|
-
const run_id = match[2];
|
|
162
|
-
const waitParam = url.searchParams.get('wait');
|
|
163
|
-
const actionParam = url.searchParams.get('action');
|
|
164
|
-
const queryParams = {
|
|
165
|
-
wait: waitParam ? waitParam === 'true' : false,
|
|
166
|
-
action: actionParam ?? 'interrupt',
|
|
167
|
-
};
|
|
168
|
-
const { wait, action } = RunCancelQuerySchema.parse(queryParams);
|
|
169
|
-
const promise = client.runs.cancel(thread_id, run_id, wait, action);
|
|
170
|
-
if (wait) await promise;
|
|
171
|
-
return new Response(null, { status: wait ? 204 : 202 });
|
|
172
|
-
}
|
|
173
|
-
}
|
|
174
|
-
|
|
175
|
-
return new NextResponse('Not Found', { status: 404 });
|
|
176
|
-
}
|
|
177
|
-
|
|
178
|
-
export async function DELETE(req: NextRequest) {
|
|
179
|
-
const url = new URL(req.url);
|
|
180
|
-
const pathname = url.pathname;
|
|
181
|
-
|
|
182
|
-
// Threads routes
|
|
183
|
-
if (pathname.match(/\/threads\/[0-9a-fA-F-]{36}$/)) {
|
|
184
|
-
const match = pathname.match(/\/threads\/([0-9a-fA-F-]{36})$/);
|
|
185
|
-
if (match) {
|
|
186
|
-
const thread_id = match[1];
|
|
187
|
-
await client.threads.delete(thread_id);
|
|
188
|
-
return new NextResponse(null, { status: 204 });
|
|
189
|
-
}
|
|
190
|
-
}
|
|
191
|
-
|
|
192
|
-
return new NextResponse('Not Found', { status: 404 });
|
|
193
|
-
}
|
|
@@ -1,66 +0,0 @@
|
|
|
1
|
-
import z from "zod";
|
|
2
|
-
|
|
3
|
-
export const AssistantConfigurable = z
|
|
4
|
-
.object({
|
|
5
|
-
thread_id: z.string().optional(),
|
|
6
|
-
thread_ts: z.string().optional(),
|
|
7
|
-
})
|
|
8
|
-
.catchall(z.unknown());
|
|
9
|
-
|
|
10
|
-
export const AssistantConfig = z
|
|
11
|
-
.object({
|
|
12
|
-
tags: z.array(z.string()).optional(),
|
|
13
|
-
recursion_limit: z.number().int().optional(),
|
|
14
|
-
configurable: AssistantConfigurable.optional(),
|
|
15
|
-
})
|
|
16
|
-
.catchall(z.unknown())
|
|
17
|
-
.describe("The configuration of an assistant.");
|
|
18
|
-
|
|
19
|
-
export const Assistant = z.object({
|
|
20
|
-
assistant_id: z.string().uuid(),
|
|
21
|
-
graph_id: z.string(),
|
|
22
|
-
config: AssistantConfig,
|
|
23
|
-
created_at: z.string(),
|
|
24
|
-
updated_at: z.string(),
|
|
25
|
-
metadata: z.object({}).catchall(z.any()),
|
|
26
|
-
});
|
|
27
|
-
|
|
28
|
-
export const MetadataSchema = z
|
|
29
|
-
.object({
|
|
30
|
-
source: z
|
|
31
|
-
.union([
|
|
32
|
-
z.literal("input"),
|
|
33
|
-
z.literal("loop"),
|
|
34
|
-
z.literal("update"),
|
|
35
|
-
z.string(),
|
|
36
|
-
])
|
|
37
|
-
.optional(),
|
|
38
|
-
step: z.number().optional(),
|
|
39
|
-
writes: z.record(z.unknown()).nullable().optional(),
|
|
40
|
-
parents: z.record(z.string()).optional(),
|
|
41
|
-
})
|
|
42
|
-
.catchall(z.unknown());
|
|
43
|
-
|
|
44
|
-
export const SendSchema = z.object({
|
|
45
|
-
node: z.string(),
|
|
46
|
-
input: z.unknown().nullable(),
|
|
47
|
-
});
|
|
48
|
-
|
|
49
|
-
export const CommandSchema = z.object({
|
|
50
|
-
update: z
|
|
51
|
-
.union([
|
|
52
|
-
z.record(z.unknown()),
|
|
53
|
-
z.array(z.tuple([z.string(), z.unknown()])),
|
|
54
|
-
])
|
|
55
|
-
.nullable()
|
|
56
|
-
.optional(),
|
|
57
|
-
resume: z.unknown().optional(),
|
|
58
|
-
goto: z
|
|
59
|
-
.union([
|
|
60
|
-
SendSchema,
|
|
61
|
-
z.array(SendSchema),
|
|
62
|
-
z.string(),
|
|
63
|
-
z.array(z.string()),
|
|
64
|
-
])
|
|
65
|
-
.optional(),
|
|
66
|
-
});
|
package/src/adapter/zod.ts
DELETED
|
@@ -1,135 +0,0 @@
|
|
|
1
|
-
import z from 'zod';
|
|
2
|
-
|
|
3
|
-
export const AssistantConfigurable = z
|
|
4
|
-
.object({
|
|
5
|
-
thread_id: z.string().optional(),
|
|
6
|
-
thread_ts: z.string().optional(),
|
|
7
|
-
})
|
|
8
|
-
.catchall(z.unknown());
|
|
9
|
-
|
|
10
|
-
export const AssistantConfig = z
|
|
11
|
-
.object({
|
|
12
|
-
tags: z.array(z.string()).optional(),
|
|
13
|
-
recursion_limit: z.number().int().optional(),
|
|
14
|
-
configurable: AssistantConfigurable.optional(),
|
|
15
|
-
})
|
|
16
|
-
.catchall(z.unknown())
|
|
17
|
-
.describe('The configuration of an assistant.');
|
|
18
|
-
|
|
19
|
-
export const Assistant = z.object({
|
|
20
|
-
assistant_id: z.string().uuid(),
|
|
21
|
-
graph_id: z.string(),
|
|
22
|
-
config: AssistantConfig,
|
|
23
|
-
created_at: z.string(),
|
|
24
|
-
updated_at: z.string(),
|
|
25
|
-
metadata: z.object({}).catchall(z.any()),
|
|
26
|
-
});
|
|
27
|
-
|
|
28
|
-
export const MetadataSchema = z
|
|
29
|
-
.object({
|
|
30
|
-
source: z.union([z.literal('input'), z.literal('loop'), z.literal('update'), z.string()]).optional(),
|
|
31
|
-
step: z.number().optional(),
|
|
32
|
-
writes: z.record(z.unknown()).nullable().optional(),
|
|
33
|
-
parents: z.record(z.string()).optional(),
|
|
34
|
-
})
|
|
35
|
-
.catchall(z.unknown());
|
|
36
|
-
|
|
37
|
-
export const SendSchema = z.object({
|
|
38
|
-
node: z.string(),
|
|
39
|
-
input: z.unknown().nullable(),
|
|
40
|
-
});
|
|
41
|
-
|
|
42
|
-
export const CommandSchema = z.object({
|
|
43
|
-
update: z
|
|
44
|
-
.union([z.record(z.unknown()), z.array(z.tuple([z.string(), z.unknown()]))])
|
|
45
|
-
.nullable()
|
|
46
|
-
.optional(),
|
|
47
|
-
resume: z.unknown().optional(),
|
|
48
|
-
goto: z.union([SendSchema, z.array(SendSchema), z.string(), z.array(z.string())]).optional(),
|
|
49
|
-
});
|
|
50
|
-
|
|
51
|
-
// 公共的查询参数验证 schema
|
|
52
|
-
export const PaginationQuerySchema = z.object({
|
|
53
|
-
limit: z.number().int().optional(),
|
|
54
|
-
offset: z.number().int().optional(),
|
|
55
|
-
});
|
|
56
|
-
|
|
57
|
-
export const ThreadIdParamSchema = z.object({
|
|
58
|
-
thread_id: z.string().uuid(),
|
|
59
|
-
});
|
|
60
|
-
|
|
61
|
-
export const RunIdParamSchema = z.object({
|
|
62
|
-
thread_id: z.string().uuid(),
|
|
63
|
-
run_id: z.string().uuid(),
|
|
64
|
-
});
|
|
65
|
-
|
|
66
|
-
// Assistants 相关的 schema
|
|
67
|
-
export const AssistantsSearchSchema = z.object({
|
|
68
|
-
graph_id: z.string().optional(),
|
|
69
|
-
metadata: MetadataSchema.optional(),
|
|
70
|
-
limit: z.number().int().optional(),
|
|
71
|
-
offset: z.number().int().optional(),
|
|
72
|
-
});
|
|
73
|
-
|
|
74
|
-
export const AssistantGraphQuerySchema = z.object({
|
|
75
|
-
xray: z.string().optional(),
|
|
76
|
-
});
|
|
77
|
-
|
|
78
|
-
// Runs 相关的 schema
|
|
79
|
-
export const RunStreamPayloadSchema = z
|
|
80
|
-
.object({
|
|
81
|
-
assistant_id: z.union([z.string().uuid(), z.string()]),
|
|
82
|
-
checkpoint_id: z.string().optional(),
|
|
83
|
-
input: z.any().optional(),
|
|
84
|
-
command: CommandSchema.optional(),
|
|
85
|
-
metadata: MetadataSchema.optional(),
|
|
86
|
-
config: AssistantConfig.optional(),
|
|
87
|
-
webhook: z.string().optional(),
|
|
88
|
-
interrupt_before: z.union([z.literal('*'), z.array(z.string())]).optional(),
|
|
89
|
-
interrupt_after: z.union([z.literal('*'), z.array(z.string())]).optional(),
|
|
90
|
-
on_disconnect: z.enum(['cancel', 'continue']).optional().default('continue'),
|
|
91
|
-
multitask_strategy: z.enum(['reject', 'rollback', 'interrupt', 'enqueue']).optional(),
|
|
92
|
-
stream_mode: z
|
|
93
|
-
.array(z.enum(['values', 'messages', 'messages-tuple', 'updates', 'events', 'debug', 'custom']))
|
|
94
|
-
.optional(),
|
|
95
|
-
stream_subgraphs: z.boolean().optional(),
|
|
96
|
-
stream_resumable: z.boolean().optional(),
|
|
97
|
-
after_seconds: z.number().optional(),
|
|
98
|
-
if_not_exists: z.enum(['create', 'reject']).optional(),
|
|
99
|
-
on_completion: z.enum(['complete', 'continue']).optional(),
|
|
100
|
-
feedback_keys: z.array(z.string()).optional(),
|
|
101
|
-
langsmith_tracer: z.unknown().optional(),
|
|
102
|
-
})
|
|
103
|
-
.describe('Payload for creating a stateful run.');
|
|
104
|
-
|
|
105
|
-
export const RunListQuerySchema = z.object({
|
|
106
|
-
limit: z.coerce.number().int().optional(),
|
|
107
|
-
offset: z.coerce.number().int().optional(),
|
|
108
|
-
status: z.enum(['pending', 'running', 'error', 'success', 'timeout', 'interrupted']).optional(),
|
|
109
|
-
});
|
|
110
|
-
|
|
111
|
-
export const RunCancelQuerySchema = z.object({
|
|
112
|
-
wait: z.coerce.boolean().optional().default(false),
|
|
113
|
-
action: z.enum(['interrupt', 'rollback']).optional().default('interrupt'),
|
|
114
|
-
});
|
|
115
|
-
|
|
116
|
-
// Threads 相关的 schema
|
|
117
|
-
export const ThreadCreatePayloadSchema = z
|
|
118
|
-
.object({
|
|
119
|
-
thread_id: z.string().uuid().describe('The ID of the thread. If not provided, an ID is generated.').optional(),
|
|
120
|
-
metadata: MetadataSchema.optional(),
|
|
121
|
-
if_exists: z.union([z.literal('raise'), z.literal('do_nothing')]).optional(),
|
|
122
|
-
})
|
|
123
|
-
.describe('Payload for creating a thread.');
|
|
124
|
-
|
|
125
|
-
export const ThreadSearchPayloadSchema = z
|
|
126
|
-
.object({
|
|
127
|
-
metadata: z.record(z.unknown()).describe('Metadata to search for.').optional(),
|
|
128
|
-
status: z.enum(['idle', 'busy', 'interrupted', 'error']).describe('Filter by thread status.').optional(),
|
|
129
|
-
values: z.record(z.unknown()).describe('Filter by thread values.').optional(),
|
|
130
|
-
limit: z.number().int().gte(1).lte(1000).describe('Maximum number to return.').optional(),
|
|
131
|
-
offset: z.number().int().gte(0).describe('Offset to start from.').optional(),
|
|
132
|
-
sort_by: z.enum(['thread_id', 'status', 'created_at', 'updated_at']).describe('Sort by field.').optional(),
|
|
133
|
-
sort_order: z.enum(['asc', 'desc']).describe('Sort order.').optional(),
|
|
134
|
-
})
|
|
135
|
-
.describe('Payload for listing threads.');
|
package/src/createEndpoint.ts
DELETED
|
@@ -1,116 +0,0 @@
|
|
|
1
|
-
import { StreamEvent } from '@langchain/core/tracers/log_stream';
|
|
2
|
-
import { streamState } from './graph/stream.js';
|
|
3
|
-
import { Assistant, Run, StreamMode, Metadata, AssistantGraph } from '@langchain/langgraph-sdk';
|
|
4
|
-
import { getGraph, GRAPHS } from './utils/getGraph.js';
|
|
5
|
-
import { LangGraphGlobal } from './global.js';
|
|
6
|
-
import { AssistantSortBy, CancelAction, ILangGraphClient, RunStatus, SortOrder, StreamInputData } from './types.js';
|
|
7
|
-
export { registerGraph } from './utils/getGraph.js';
|
|
8
|
-
|
|
9
|
-
export const AssistantEndpoint: ILangGraphClient['assistants'] = {
|
|
10
|
-
async search(query?: {
|
|
11
|
-
graphId?: string;
|
|
12
|
-
metadata?: Metadata;
|
|
13
|
-
limit?: number;
|
|
14
|
-
offset?: number;
|
|
15
|
-
sortBy?: AssistantSortBy;
|
|
16
|
-
sortOrder?: SortOrder;
|
|
17
|
-
}): Promise<Assistant[]> {
|
|
18
|
-
if (query?.graphId) {
|
|
19
|
-
return [
|
|
20
|
-
{
|
|
21
|
-
assistant_id: query.graphId,
|
|
22
|
-
graph_id: query.graphId,
|
|
23
|
-
config: {},
|
|
24
|
-
created_at: new Date().toISOString(),
|
|
25
|
-
updated_at: new Date().toISOString(),
|
|
26
|
-
metadata: {},
|
|
27
|
-
version: 1,
|
|
28
|
-
name: query.graphId,
|
|
29
|
-
description: '',
|
|
30
|
-
} as Assistant,
|
|
31
|
-
];
|
|
32
|
-
}
|
|
33
|
-
return Object.entries(GRAPHS).map(
|
|
34
|
-
([graphId, _]) =>
|
|
35
|
-
({
|
|
36
|
-
assistant_id: graphId,
|
|
37
|
-
graph_id: graphId,
|
|
38
|
-
config: {},
|
|
39
|
-
metadata: {},
|
|
40
|
-
version: 1,
|
|
41
|
-
name: graphId,
|
|
42
|
-
description: '',
|
|
43
|
-
created_at: new Date().toISOString(),
|
|
44
|
-
updated_at: new Date().toISOString(),
|
|
45
|
-
} as Assistant),
|
|
46
|
-
);
|
|
47
|
-
},
|
|
48
|
-
async getGraph(assistantId: string, options?: { xray?: boolean | number }): Promise<AssistantGraph> {
|
|
49
|
-
const config = {};
|
|
50
|
-
const graph = await getGraph(assistantId, config);
|
|
51
|
-
const drawable = await graph.getGraphAsync({
|
|
52
|
-
...config,
|
|
53
|
-
xray: options?.xray ?? undefined,
|
|
54
|
-
});
|
|
55
|
-
return drawable.toJSON() as AssistantGraph;
|
|
56
|
-
},
|
|
57
|
-
};
|
|
58
|
-
|
|
59
|
-
export const createEndpoint = (): ILangGraphClient => {
|
|
60
|
-
const threads = LangGraphGlobal.globalThreadsManager;
|
|
61
|
-
return {
|
|
62
|
-
assistants: AssistantEndpoint,
|
|
63
|
-
threads,
|
|
64
|
-
runs: {
|
|
65
|
-
list(
|
|
66
|
-
threadId: string,
|
|
67
|
-
options?: {
|
|
68
|
-
limit?: number;
|
|
69
|
-
offset?: number;
|
|
70
|
-
status?: RunStatus;
|
|
71
|
-
},
|
|
72
|
-
): Promise<Run[]> {
|
|
73
|
-
return threads.listRuns(threadId, options);
|
|
74
|
-
},
|
|
75
|
-
async cancel(threadId: string, runId: string, wait?: boolean, action?: CancelAction): Promise<void> {
|
|
76
|
-
return LangGraphGlobal.globalMessageQueue.cancelQueue(runId);
|
|
77
|
-
},
|
|
78
|
-
async *stream(threadId: string, assistantId: string, payload: StreamInputData) {
|
|
79
|
-
if (!payload.config) {
|
|
80
|
-
payload.config = {
|
|
81
|
-
configurable: {
|
|
82
|
-
graph_id: assistantId,
|
|
83
|
-
thread_id: threadId,
|
|
84
|
-
},
|
|
85
|
-
};
|
|
86
|
-
}
|
|
87
|
-
|
|
88
|
-
for await (const data of streamState(
|
|
89
|
-
threads,
|
|
90
|
-
threads.createRun(threadId, assistantId, payload),
|
|
91
|
-
payload,
|
|
92
|
-
{
|
|
93
|
-
attempt: 0,
|
|
94
|
-
getGraph,
|
|
95
|
-
},
|
|
96
|
-
)) {
|
|
97
|
-
yield data;
|
|
98
|
-
}
|
|
99
|
-
},
|
|
100
|
-
joinStream(
|
|
101
|
-
threadId: string,
|
|
102
|
-
runId: string,
|
|
103
|
-
options?:
|
|
104
|
-
| {
|
|
105
|
-
signal?: AbortSignal;
|
|
106
|
-
cancelOnDisconnect?: boolean;
|
|
107
|
-
lastEventId?: string;
|
|
108
|
-
streamMode?: StreamMode | StreamMode[];
|
|
109
|
-
}
|
|
110
|
-
| AbortSignal,
|
|
111
|
-
): AsyncGenerator<{ id?: string; event: StreamEvent; data: any }> {
|
|
112
|
-
throw new Error('Function not implemented.');
|
|
113
|
-
},
|
|
114
|
-
},
|
|
115
|
-
};
|
|
116
|
-
};
|
package/src/e.d.ts
DELETED
package/src/global.ts
DELETED
|
@@ -1,11 +0,0 @@
|
|
|
1
|
-
import { createCheckPointer, createMessageQueue, createThreadManager } from './storage/index.js';
|
|
2
|
-
import type { SqliteSaver } from './storage/sqlite/checkpoint.js';
|
|
3
|
-
const [globalMessageQueue, globalCheckPointer] = await Promise.all([createMessageQueue(), createCheckPointer()]);
|
|
4
|
-
const globalThreadsManager = await createThreadManager({
|
|
5
|
-
checkpointer: globalCheckPointer as SqliteSaver,
|
|
6
|
-
});
|
|
7
|
-
export class LangGraphGlobal {
|
|
8
|
-
static globalMessageQueue = globalMessageQueue;
|
|
9
|
-
static globalCheckPointer = globalCheckPointer;
|
|
10
|
-
static globalThreadsManager = globalThreadsManager;
|
|
11
|
-
}
|