langgraph-api 0.2.130__py3-none-any.whl → 0.2.132__py3-none-any.whl
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.
Potentially problematic release.
This version of langgraph-api might be problematic. Click here for more details.
- langgraph_api/__init__.py +1 -1
- langgraph_api/api/assistants.py +6 -5
- langgraph_api/api/meta.py +3 -1
- langgraph_api/api/openapi.py +1 -1
- langgraph_api/api/runs.py +13 -10
- langgraph_api/api/ui.py +2 -0
- langgraph_api/asgi_transport.py +2 -2
- langgraph_api/asyncio.py +10 -8
- langgraph_api/auth/custom.py +9 -4
- langgraph_api/auth/langsmith/client.py +1 -1
- langgraph_api/cli.py +5 -4
- langgraph_api/config.py +1 -1
- langgraph_api/executor_entrypoint.py +23 -0
- langgraph_api/graph.py +25 -9
- langgraph_api/http.py +10 -7
- langgraph_api/http_metrics.py +4 -1
- langgraph_api/js/build.mts +11 -2
- langgraph_api/js/client.http.mts +2 -0
- langgraph_api/js/client.mts +13 -3
- langgraph_api/js/remote.py +17 -12
- langgraph_api/js/src/preload.mjs +9 -1
- langgraph_api/js/src/utils/files.mts +5 -2
- langgraph_api/js/sse.py +1 -1
- langgraph_api/logging.py +3 -3
- langgraph_api/middleware/http_logger.py +2 -1
- langgraph_api/models/run.py +19 -14
- langgraph_api/patch.py +2 -2
- langgraph_api/queue_entrypoint.py +33 -18
- langgraph_api/schema.py +20 -1
- langgraph_api/serde.py +32 -5
- langgraph_api/server.py +5 -3
- langgraph_api/state.py +8 -8
- langgraph_api/store.py +1 -1
- langgraph_api/stream.py +33 -20
- langgraph_api/traceblock.py +1 -1
- langgraph_api/utils/__init__.py +21 -5
- langgraph_api/utils/config.py +13 -4
- langgraph_api/utils/future.py +1 -1
- langgraph_api/utils/uuids.py +87 -0
- langgraph_api/webhook.py +20 -20
- langgraph_api/worker.py +8 -5
- {langgraph_api-0.2.130.dist-info → langgraph_api-0.2.132.dist-info}/METADATA +1 -1
- {langgraph_api-0.2.130.dist-info → langgraph_api-0.2.132.dist-info}/RECORD +46 -44
- {langgraph_api-0.2.130.dist-info → langgraph_api-0.2.132.dist-info}/WHEEL +0 -0
- {langgraph_api-0.2.130.dist-info → langgraph_api-0.2.132.dist-info}/entry_points.txt +0 -0
- {langgraph_api-0.2.130.dist-info → langgraph_api-0.2.132.dist-info}/licenses/LICENSE +0 -0
langgraph_api/stream.py
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import uuid
|
|
1
2
|
from collections.abc import AsyncIterator, Callable
|
|
2
3
|
from contextlib import AsyncExitStack, aclosing, asynccontextmanager
|
|
3
4
|
from functools import lru_cache
|
|
@@ -93,21 +94,23 @@ def _preproces_debug_checkpoint_task(task: dict[str, Any]) -> dict[str, Any]:
|
|
|
93
94
|
return task
|
|
94
95
|
|
|
95
96
|
|
|
96
|
-
def _preprocess_debug_checkpoint(
|
|
97
|
+
def _preprocess_debug_checkpoint(
|
|
98
|
+
payload: CheckpointPayload | None,
|
|
99
|
+
) -> dict[str, Any] | None:
|
|
97
100
|
from langgraph_api.state import runnable_config_to_checkpoint
|
|
98
101
|
|
|
99
102
|
if not payload:
|
|
100
103
|
return None
|
|
101
104
|
|
|
102
|
-
payload["checkpoint"] = runnable_config_to_checkpoint(payload["config"])
|
|
103
|
-
payload["parent_checkpoint"] = runnable_config_to_checkpoint(
|
|
104
|
-
payload["parent_config"] if "parent_config" in payload else None
|
|
105
|
-
)
|
|
106
|
-
|
|
107
|
-
payload["tasks"] = [_preproces_debug_checkpoint_task(t) for t in payload["tasks"]]
|
|
108
|
-
|
|
109
105
|
# TODO: deprecate the `config`` and `parent_config`` fields
|
|
110
|
-
return
|
|
106
|
+
return {
|
|
107
|
+
**payload,
|
|
108
|
+
"checkpoint": runnable_config_to_checkpoint(payload["config"]),
|
|
109
|
+
"parent_checkpoint": runnable_config_to_checkpoint(
|
|
110
|
+
payload["parent_config"] if "parent_config" in payload else None
|
|
111
|
+
),
|
|
112
|
+
"tasks": [_preproces_debug_checkpoint_task(t) for t in payload["tasks"]],
|
|
113
|
+
}
|
|
111
114
|
|
|
112
115
|
|
|
113
116
|
@asynccontextmanager
|
|
@@ -216,7 +219,7 @@ async def astream_state(
|
|
|
216
219
|
if use_astream_events:
|
|
217
220
|
async with (
|
|
218
221
|
stack,
|
|
219
|
-
aclosing(
|
|
222
|
+
aclosing( # type: ignore[invalid-argument-type]
|
|
220
223
|
graph.astream_events(
|
|
221
224
|
input,
|
|
222
225
|
config,
|
|
@@ -231,6 +234,7 @@ async def astream_state(
|
|
|
231
234
|
event = await wait_if_not_done(anext(stream, sentinel), done)
|
|
232
235
|
if event is sentinel:
|
|
233
236
|
break
|
|
237
|
+
event = cast(dict, event)
|
|
234
238
|
if event.get("tags") and "langsmith:hidden" in event["tags"]:
|
|
235
239
|
continue
|
|
236
240
|
if "messages" in stream_mode and isinstance(graph, BaseRemotePregel):
|
|
@@ -251,6 +255,7 @@ async def astream_state(
|
|
|
251
255
|
if mode == "debug":
|
|
252
256
|
if chunk["type"] == "checkpoint":
|
|
253
257
|
checkpoint = _preprocess_debug_checkpoint(chunk["payload"])
|
|
258
|
+
chunk["payload"] = checkpoint
|
|
254
259
|
on_checkpoint(checkpoint)
|
|
255
260
|
elif chunk["type"] == "task_result":
|
|
256
261
|
on_task_result(chunk["payload"])
|
|
@@ -261,11 +266,14 @@ async def astream_state(
|
|
|
261
266
|
else:
|
|
262
267
|
yield "messages", chunk
|
|
263
268
|
else:
|
|
264
|
-
|
|
269
|
+
msg_, meta = cast(
|
|
265
270
|
tuple[BaseMessage | dict, dict[str, Any]], chunk
|
|
266
271
|
)
|
|
267
|
-
|
|
268
|
-
|
|
272
|
+
msg = (
|
|
273
|
+
convert_to_messages([msg_])[0]
|
|
274
|
+
if isinstance(msg_, dict)
|
|
275
|
+
else cast(BaseMessage, msg_)
|
|
276
|
+
)
|
|
269
277
|
if msg.id in messages:
|
|
270
278
|
messages[msg.id] += msg
|
|
271
279
|
else:
|
|
@@ -323,14 +331,15 @@ async def astream_state(
|
|
|
323
331
|
if event is sentinel:
|
|
324
332
|
break
|
|
325
333
|
if subgraphs:
|
|
326
|
-
ns, mode, chunk = event
|
|
334
|
+
ns, mode, chunk = cast(tuple[str, str, dict[str, Any]], event)
|
|
327
335
|
else:
|
|
328
|
-
mode, chunk = event
|
|
336
|
+
mode, chunk = cast(tuple[str, dict[str, Any]], event)
|
|
329
337
|
ns = None
|
|
330
338
|
# --- begin shared logic with astream_events ---
|
|
331
339
|
if mode == "debug":
|
|
332
340
|
if chunk["type"] == "checkpoint":
|
|
333
341
|
checkpoint = _preprocess_debug_checkpoint(chunk["payload"])
|
|
342
|
+
chunk["payload"] = checkpoint
|
|
334
343
|
on_checkpoint(checkpoint)
|
|
335
344
|
elif chunk["type"] == "task_result":
|
|
336
345
|
on_task_result(chunk["payload"])
|
|
@@ -341,11 +350,15 @@ async def astream_state(
|
|
|
341
350
|
else:
|
|
342
351
|
yield "messages", chunk
|
|
343
352
|
else:
|
|
344
|
-
|
|
353
|
+
msg_, meta = cast(
|
|
345
354
|
tuple[BaseMessage | dict, dict[str, Any]], chunk
|
|
346
355
|
)
|
|
347
|
-
|
|
348
|
-
|
|
356
|
+
msg = (
|
|
357
|
+
convert_to_messages([msg_])[0]
|
|
358
|
+
if isinstance(msg_, dict)
|
|
359
|
+
else cast(BaseMessage, msg_)
|
|
360
|
+
)
|
|
361
|
+
|
|
349
362
|
if msg.id in messages:
|
|
350
363
|
messages[msg.id] += msg
|
|
351
364
|
else:
|
|
@@ -399,7 +412,7 @@ async def astream_state(
|
|
|
399
412
|
|
|
400
413
|
async def consume(
|
|
401
414
|
stream: AnyStream,
|
|
402
|
-
run_id: str,
|
|
415
|
+
run_id: str | uuid.UUID,
|
|
403
416
|
resumable: bool = False,
|
|
404
417
|
stream_modes: set[StreamMode] | None = None,
|
|
405
418
|
) -> None:
|
|
@@ -408,7 +421,7 @@ async def consume(
|
|
|
408
421
|
stream_modes.add("messages")
|
|
409
422
|
stream_modes.add("metadata")
|
|
410
423
|
|
|
411
|
-
async with aclosing(stream):
|
|
424
|
+
async with aclosing(stream): # type: ignore[invalid-argument-type]
|
|
412
425
|
try:
|
|
413
426
|
async for mode, payload in stream:
|
|
414
427
|
await Runs.Stream.publish(
|
langgraph_api/traceblock.py
CHANGED
langgraph_api/utils/__init__.py
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import contextvars
|
|
2
2
|
import uuid
|
|
3
|
-
from collections.abc import
|
|
3
|
+
from collections.abc import AsyncIterator
|
|
4
4
|
from contextlib import asynccontextmanager
|
|
5
5
|
from datetime import datetime
|
|
6
|
-
from typing import Any, Protocol, TypeAlias, TypeVar
|
|
6
|
+
from typing import Any, Protocol, TypeAlias, TypeVar, cast
|
|
7
7
|
|
|
8
8
|
import structlog
|
|
9
9
|
from langgraph_sdk import Auth
|
|
@@ -12,6 +12,7 @@ from starlette.exceptions import HTTPException
|
|
|
12
12
|
from starlette.schemas import BaseSchemaGenerator
|
|
13
13
|
|
|
14
14
|
from langgraph_api.auth.custom import SimpleUser
|
|
15
|
+
from langgraph_api.utils.uuids import uuid7
|
|
15
16
|
|
|
16
17
|
logger = structlog.stdlib.get_logger(__name__)
|
|
17
18
|
|
|
@@ -32,7 +33,9 @@ async def with_user(
|
|
|
32
33
|
yield
|
|
33
34
|
if current is None:
|
|
34
35
|
return
|
|
35
|
-
set_auth_ctx(
|
|
36
|
+
set_auth_ctx(
|
|
37
|
+
cast(BaseUser, current.user), AuthCredentials(scopes=current.permissions)
|
|
38
|
+
)
|
|
36
39
|
|
|
37
40
|
|
|
38
41
|
def set_auth_ctx(
|
|
@@ -99,7 +102,7 @@ def validate_uuid(uuid_str: str, invalid_uuid_detail: str | None) -> uuid.UUID:
|
|
|
99
102
|
|
|
100
103
|
|
|
101
104
|
def next_cron_date(schedule: str, base_time: datetime) -> datetime:
|
|
102
|
-
import croniter
|
|
105
|
+
import croniter # type: ignore[unresolved-import]
|
|
103
106
|
|
|
104
107
|
cron_iter = croniter.croniter(schedule, base_time)
|
|
105
108
|
return cron_iter.get_next(datetime)
|
|
@@ -130,7 +133,7 @@ class SchemaGenerator(BaseSchemaGenerator):
|
|
|
130
133
|
|
|
131
134
|
|
|
132
135
|
async def get_pagination_headers(
|
|
133
|
-
resource:
|
|
136
|
+
resource: AsyncIterator[T],
|
|
134
137
|
next_offset: int | None,
|
|
135
138
|
offset: int,
|
|
136
139
|
) -> tuple[list[T], dict[str, str]]:
|
|
@@ -143,3 +146,16 @@ async def get_pagination_headers(
|
|
|
143
146
|
"X-Pagination-Next": str(next_offset),
|
|
144
147
|
}
|
|
145
148
|
return resources, response_headers
|
|
149
|
+
|
|
150
|
+
|
|
151
|
+
__all__ = [
|
|
152
|
+
"AsyncCursorProto",
|
|
153
|
+
"AsyncPipelineProto",
|
|
154
|
+
"AsyncConnectionProto",
|
|
155
|
+
"fetchone",
|
|
156
|
+
"validate_uuid",
|
|
157
|
+
"next_cron_date",
|
|
158
|
+
"SchemaGenerator",
|
|
159
|
+
"get_pagination_headers",
|
|
160
|
+
"uuid7",
|
|
161
|
+
]
|
langgraph_api/utils/config.py
CHANGED
|
@@ -7,9 +7,10 @@ from collections import ChainMap
|
|
|
7
7
|
from concurrent.futures import Executor
|
|
8
8
|
from contextvars import copy_context
|
|
9
9
|
from os import getenv
|
|
10
|
-
from typing import Any, ParamSpec, TypeVar
|
|
10
|
+
from typing import Any, ParamSpec, TypeVar
|
|
11
11
|
|
|
12
12
|
from langgraph.constants import CONF
|
|
13
|
+
from typing_extensions import TypedDict
|
|
13
14
|
|
|
14
15
|
if typing.TYPE_CHECKING:
|
|
15
16
|
from langchain_core.runnables import RunnableConfig
|
|
@@ -19,7 +20,7 @@ try:
|
|
|
19
20
|
var_child_runnable_config,
|
|
20
21
|
)
|
|
21
22
|
except ImportError:
|
|
22
|
-
var_child_runnable_config = None
|
|
23
|
+
var_child_runnable_config = None # type: ignore[invalid-assignment]
|
|
23
24
|
|
|
24
25
|
CONFIG_KEYS = [
|
|
25
26
|
"tags",
|
|
@@ -52,6 +53,14 @@ def _is_not_empty(value: Any) -> bool:
|
|
|
52
53
|
return value is not None
|
|
53
54
|
|
|
54
55
|
|
|
56
|
+
class _Config(TypedDict):
|
|
57
|
+
tags: list[str]
|
|
58
|
+
metadata: ChainMap
|
|
59
|
+
callbacks: None
|
|
60
|
+
recursion_limit: int
|
|
61
|
+
configurable: dict[str, Any]
|
|
62
|
+
|
|
63
|
+
|
|
55
64
|
def ensure_config(*configs: RunnableConfig | None) -> RunnableConfig:
|
|
56
65
|
"""Return a config with all keys, merging any provided configs.
|
|
57
66
|
|
|
@@ -61,7 +70,7 @@ def ensure_config(*configs: RunnableConfig | None) -> RunnableConfig:
|
|
|
61
70
|
Returns:
|
|
62
71
|
RunnableConfig: The merged and ensured config.
|
|
63
72
|
"""
|
|
64
|
-
empty =
|
|
73
|
+
empty = _Config(
|
|
65
74
|
tags=[],
|
|
66
75
|
metadata=ChainMap(),
|
|
67
76
|
callbacks=None,
|
|
@@ -84,7 +93,7 @@ def ensure_config(*configs: RunnableConfig | None) -> RunnableConfig:
|
|
|
84
93
|
for k, v in config.items():
|
|
85
94
|
if _is_not_empty(v) and k in CONFIG_KEYS:
|
|
86
95
|
if k == CONF:
|
|
87
|
-
empty[k] =
|
|
96
|
+
empty[k] = v.copy() # type: ignore
|
|
88
97
|
else:
|
|
89
98
|
empty[k] = v # type: ignore[literal-required]
|
|
90
99
|
for k, v in config.items():
|
langgraph_api/utils/future.py
CHANGED
|
@@ -167,7 +167,7 @@ def _ensure_future(
|
|
|
167
167
|
elif EAGER_NOT_SUPPORTED or lazy:
|
|
168
168
|
return loop.create_task(coro_or_future, name=name, context=context)
|
|
169
169
|
else:
|
|
170
|
-
return asyncio.eager_task_factory(
|
|
170
|
+
return asyncio.eager_task_factory( # type: ignore[unresolved-attribute]
|
|
171
171
|
loop, coro_or_future, name=name, context=context
|
|
172
172
|
)
|
|
173
173
|
except RuntimeError:
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
import os
|
|
2
|
+
import time
|
|
3
|
+
from uuid import UUID, SafeUUID
|
|
4
|
+
|
|
5
|
+
_last_timestamp_v7 = None
|
|
6
|
+
_last_counter_v7 = 0 # 42-bit counter
|
|
7
|
+
_RFC_4122_VERSION_7_FLAGS = (7 << 76) | (0x8000 << 48)
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
def _uuid7_get_counter_and_tail():
|
|
11
|
+
rand = int.from_bytes(os.urandom(10))
|
|
12
|
+
# 42-bit counter with MSB set to 0
|
|
13
|
+
counter = (rand >> 32) & 0x1FF_FFFF_FFFF
|
|
14
|
+
# 32-bit random data
|
|
15
|
+
tail = rand & 0xFFFF_FFFF
|
|
16
|
+
return counter, tail
|
|
17
|
+
|
|
18
|
+
|
|
19
|
+
def _from_int(value: int) -> UUID:
|
|
20
|
+
uid = object.__new__(UUID)
|
|
21
|
+
object.__setattr__(uid, "int", value)
|
|
22
|
+
object.__setattr__(uid, "is_safe", SafeUUID.unknown)
|
|
23
|
+
return uid
|
|
24
|
+
|
|
25
|
+
|
|
26
|
+
def uuid7():
|
|
27
|
+
"""Generate a UUID from a Unix timestamp in milliseconds and random bits.
|
|
28
|
+
|
|
29
|
+
UUIDv7 objects feature monotonicity within a millisecond.
|
|
30
|
+
"""
|
|
31
|
+
# --- 48 --- -- 4 -- --- 12 --- -- 2 -- --- 30 --- - 32 -
|
|
32
|
+
# unix_ts_ms | version | counter_hi | variant | counter_lo | random
|
|
33
|
+
#
|
|
34
|
+
# 'counter = counter_hi | counter_lo' is a 42-bit counter constructed
|
|
35
|
+
# with Method 1 of RFC 9562, §6.2, and its MSB is set to 0.
|
|
36
|
+
#
|
|
37
|
+
# 'random' is a 32-bit random value regenerated for every new UUID.
|
|
38
|
+
#
|
|
39
|
+
# If multiple UUIDs are generated within the same millisecond, the LSB
|
|
40
|
+
# of 'counter' is incremented by 1. When overflowing, the timestamp is
|
|
41
|
+
# advanced and the counter is reset to a random 42-bit integer with MSB
|
|
42
|
+
# set to 0.
|
|
43
|
+
|
|
44
|
+
global _last_timestamp_v7
|
|
45
|
+
global _last_counter_v7
|
|
46
|
+
|
|
47
|
+
nanoseconds = time.time_ns()
|
|
48
|
+
timestamp_ms = nanoseconds // 1_000_000
|
|
49
|
+
|
|
50
|
+
if _last_timestamp_v7 is None or timestamp_ms > _last_timestamp_v7:
|
|
51
|
+
counter, tail = _uuid7_get_counter_and_tail()
|
|
52
|
+
else:
|
|
53
|
+
if timestamp_ms < _last_timestamp_v7:
|
|
54
|
+
timestamp_ms = _last_timestamp_v7 + 1
|
|
55
|
+
# advance the 42-bit counter
|
|
56
|
+
counter = _last_counter_v7 + 1
|
|
57
|
+
if counter > 0x3FF_FFFF_FFFF:
|
|
58
|
+
# advance the 48-bit timestamp
|
|
59
|
+
timestamp_ms += 1
|
|
60
|
+
counter, tail = _uuid7_get_counter_and_tail()
|
|
61
|
+
else:
|
|
62
|
+
# 32-bit random data
|
|
63
|
+
tail = int.from_bytes(os.urandom(4))
|
|
64
|
+
|
|
65
|
+
unix_ts_ms = timestamp_ms & 0xFFFF_FFFF_FFFF
|
|
66
|
+
counter_msbs = counter >> 30
|
|
67
|
+
# keep 12 counter's MSBs and clear variant bits
|
|
68
|
+
counter_hi = counter_msbs & 0x0FFF
|
|
69
|
+
# keep 30 counter's LSBs and clear version bits
|
|
70
|
+
counter_lo = counter & 0x3FFF_FFFF
|
|
71
|
+
# ensure that the tail is always a 32-bit integer (by construction,
|
|
72
|
+
# it is already the case, but future interfaces may allow the user
|
|
73
|
+
# to specify the random tail)
|
|
74
|
+
tail &= 0xFFFF_FFFF
|
|
75
|
+
|
|
76
|
+
int_uuid_7 = unix_ts_ms << 80
|
|
77
|
+
int_uuid_7 |= counter_hi << 64
|
|
78
|
+
int_uuid_7 |= counter_lo << 32
|
|
79
|
+
int_uuid_7 |= tail
|
|
80
|
+
# by construction, the variant and version bits are already cleared
|
|
81
|
+
int_uuid_7 |= _RFC_4122_VERSION_7_FLAGS
|
|
82
|
+
res = _from_int(int_uuid_7)
|
|
83
|
+
|
|
84
|
+
# defer global update until all computations are done
|
|
85
|
+
_last_timestamp_v7 = timestamp_ms
|
|
86
|
+
_last_counter_v7 = counter
|
|
87
|
+
return res
|
langgraph_api/webhook.py
CHANGED
|
@@ -27,23 +27,23 @@ async def call_webhook(result: "WorkerResult") -> None:
|
|
|
27
27
|
}
|
|
28
28
|
if exception := result["exception"]:
|
|
29
29
|
payload["error"] = str(exception)
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
30
|
+
webhook = result.get("webhook")
|
|
31
|
+
if webhook:
|
|
32
|
+
try:
|
|
33
|
+
if webhook.startswith("/"):
|
|
34
|
+
# Call into this own app
|
|
35
|
+
webhook_client = get_loopback_client()
|
|
36
|
+
else:
|
|
37
|
+
webhook_client = get_http_client()
|
|
38
|
+
await http_request("POST", webhook, json=payload, client=webhook_client)
|
|
39
|
+
await logger.ainfo(
|
|
40
|
+
"Background worker called webhook",
|
|
41
|
+
webhook=result["webhook"],
|
|
42
|
+
run_id=result["run"]["run_id"],
|
|
43
|
+
)
|
|
44
|
+
except Exception as exc:
|
|
45
|
+
logger.exception(
|
|
46
|
+
f"Background worker failed to call webhook {result['webhook']}",
|
|
47
|
+
exc_info=exc,
|
|
48
|
+
webhook=result["webhook"],
|
|
49
|
+
)
|
langgraph_api/worker.py
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import asyncio
|
|
2
2
|
import time
|
|
3
|
+
import uuid
|
|
3
4
|
from collections.abc import AsyncGenerator
|
|
4
5
|
from contextlib import asynccontextmanager
|
|
5
6
|
from datetime import UTC, datetime
|
|
6
|
-
from typing import cast
|
|
7
7
|
|
|
8
8
|
import structlog
|
|
9
9
|
from langgraph.pregel.debug import CheckpointPayload, TaskResultPayload
|
|
@@ -73,7 +73,7 @@ async def worker(
|
|
|
73
73
|
if attempt == 1:
|
|
74
74
|
incr_runs()
|
|
75
75
|
checkpoint: CheckpointPayload | None = None
|
|
76
|
-
exception: Exception | None = None
|
|
76
|
+
exception: Exception | asyncio.CancelledError | None = None
|
|
77
77
|
status: str | None = None
|
|
78
78
|
webhook = run["kwargs"].get("webhook", None)
|
|
79
79
|
request_created_at: int | None = run["kwargs"]["config"]["configurable"].get(
|
|
@@ -131,7 +131,10 @@ async def worker(
|
|
|
131
131
|
|
|
132
132
|
# Wrap the graph execution to separate user errors from server errors
|
|
133
133
|
async def wrap_user_errors(
|
|
134
|
-
stream: AnyStream,
|
|
134
|
+
stream: AnyStream,
|
|
135
|
+
run_id: str | uuid.UUID,
|
|
136
|
+
resumable: bool,
|
|
137
|
+
stream_modes: set[StreamMode],
|
|
135
138
|
):
|
|
136
139
|
try:
|
|
137
140
|
await consume(stream, run_id, resumable, stream_modes)
|
|
@@ -177,10 +180,10 @@ async def worker(
|
|
|
177
180
|
raise RuntimeError(error_message)
|
|
178
181
|
async with set_auth_ctx_for_run(run["kwargs"]):
|
|
179
182
|
if temporary:
|
|
180
|
-
stream = astream_state(
|
|
183
|
+
stream = astream_state(run, attempt, done)
|
|
181
184
|
else:
|
|
182
185
|
stream = astream_state(
|
|
183
|
-
|
|
186
|
+
run,
|
|
184
187
|
attempt,
|
|
185
188
|
done,
|
|
186
189
|
on_checkpoint=on_checkpoint,
|
|
@@ -1,86 +1,88 @@
|
|
|
1
|
-
langgraph_api/__init__.py,sha256=
|
|
2
|
-
langgraph_api/asgi_transport.py,sha256=
|
|
3
|
-
langgraph_api/asyncio.py,sha256=
|
|
4
|
-
langgraph_api/cli.py,sha256
|
|
1
|
+
langgraph_api/__init__.py,sha256=ZpmpXVo5ei1oY1HLuUDNlmF0Bhvc8snVh01NPuU1B0M,24
|
|
2
|
+
langgraph_api/asgi_transport.py,sha256=XtiLOu4WWsd-xizagBLzT5xUkxc9ZG9YqwvETBPjBFE,5161
|
|
3
|
+
langgraph_api/asyncio.py,sha256=l4fVoYIcczMqC2Wrj4LTk50nKV29AXwweiehOwaeC4Y,9754
|
|
4
|
+
langgraph_api/cli.py,sha256=-ruIeKi1imvS6GriOfRDZY-waV4SbWiJ0BEFAciPVYI,16330
|
|
5
5
|
langgraph_api/command.py,sha256=3O9v3i0OPa96ARyJ_oJbLXkfO8rPgDhLCswgO9koTFA,768
|
|
6
|
-
langgraph_api/config.py,sha256=
|
|
6
|
+
langgraph_api/config.py,sha256=LxWOteBq-RNyr0Dc3Tm7HwoXrn1aDdvgnKlDsXCDFMg,12111
|
|
7
7
|
langgraph_api/cron_scheduler.py,sha256=CiwZ-U4gDOdG9zl9dlr7mH50USUgNB2Fvb8YTKVRBN4,2625
|
|
8
8
|
langgraph_api/errors.py,sha256=zlnl3xXIwVG0oGNKKpXf1an9Rn_SBDHSyhe53hU6aLw,1858
|
|
9
|
+
langgraph_api/executor_entrypoint.py,sha256=ClMyM9TB9oPisQzHqixA77Lnj_QGUg55MtQx-xku4o8,671
|
|
9
10
|
langgraph_api/feature_flags.py,sha256=GjwmNjfg0Jhs3OzR2VbK2WgrRy3o5l8ibIYiUtQkDPA,363
|
|
10
|
-
langgraph_api/graph.py,sha256=
|
|
11
|
-
langgraph_api/http.py,sha256=
|
|
12
|
-
langgraph_api/http_metrics.py,sha256=
|
|
13
|
-
langgraph_api/logging.py,sha256=
|
|
11
|
+
langgraph_api/graph.py,sha256=HTjJNQadrdi1tzJYNJ_iPIR6-zqC4-hj6YTD6zGQHYA,25072
|
|
12
|
+
langgraph_api/http.py,sha256=xCeyqm9Vafx_8OaUfwlIMPZTspJQzivgcJqTc4wweaE,5704
|
|
13
|
+
langgraph_api/http_metrics.py,sha256=MU9ccXt7aBb0AJ2SWEjwtbtbJEWmeqSdx7-CI51e32o,5594
|
|
14
|
+
langgraph_api/logging.py,sha256=v7TOQt_YuZ_lTQ4rp_9hE6pLtSKxObkuFxyAdHW0y5c,4862
|
|
14
15
|
langgraph_api/metadata.py,sha256=fVsbwxVitAj4LGVYpCcadYeIFANEaNtcx6LBxQLcTqg,6949
|
|
15
|
-
langgraph_api/patch.py,sha256=
|
|
16
|
-
langgraph_api/queue_entrypoint.py,sha256=
|
|
16
|
+
langgraph_api/patch.py,sha256=iLwSd9ZWoVj6MxozMyGyMvWWbE9RIP5eZX1dpCBSlSU,1480
|
|
17
|
+
langgraph_api/queue_entrypoint.py,sha256=KDLpQtBu3amZTbNHS-RGFLR0DphuVQN6kUZm3ZGLe9g,5991
|
|
17
18
|
langgraph_api/route.py,sha256=PEM5sZk-wtoH6dA9jI5M4z9lL0ZFybWllDQGOapMG8k,5026
|
|
18
|
-
langgraph_api/schema.py,sha256=
|
|
19
|
-
langgraph_api/serde.py,sha256=
|
|
20
|
-
langgraph_api/server.py,sha256=
|
|
19
|
+
langgraph_api/schema.py,sha256=v2pP9WD2Y2EEhLDmn2Lq8CQieSyrqF1nv7lc0MtEDtA,6907
|
|
20
|
+
langgraph_api/serde.py,sha256=5F4xMTRY3kNwpdkAzM48KzxFEUmVD1I3CaVWzp_syT8,6067
|
|
21
|
+
langgraph_api/server.py,sha256=uCAqPgCLJ6ckslLs0i_dacSR8mzuR0Y6PkkJYk0O3bE,7196
|
|
21
22
|
langgraph_api/sse.py,sha256=SLdtZmTdh5D8fbWrQjuY9HYLd2dg8Rmi6ZMmFMVc2iE,4204
|
|
22
|
-
langgraph_api/state.py,sha256=
|
|
23
|
-
langgraph_api/store.py,sha256=
|
|
24
|
-
langgraph_api/stream.py,sha256=
|
|
23
|
+
langgraph_api/state.py,sha256=5RTOShiFVnkx-o6t99_x63CGwXw_8Eb-dSTpYirP8ro,4683
|
|
24
|
+
langgraph_api/store.py,sha256=_UwEzGXKMFvpnyz1DUeOmfpy2w3WhPAtAJzIh7VTRBY,4679
|
|
25
|
+
langgraph_api/stream.py,sha256=P82M1yVbn1N20ZRSLb6_F1wbkfQLVU1OGEHF2ES-Nvg,18199
|
|
25
26
|
langgraph_api/thread_ttl.py,sha256=7H3gFlWcUiODPoaEzcwB0LR61uvcuyjD0ew_4BztB7k,1902
|
|
26
|
-
langgraph_api/traceblock.py,sha256=
|
|
27
|
+
langgraph_api/traceblock.py,sha256=Qq5CUdefnMDaRDnyvBSWGBClEj-f3oO7NbH6fedxOSE,630
|
|
27
28
|
langgraph_api/utils.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
28
29
|
langgraph_api/validation.py,sha256=zMuKmwUEBjBgFMwAaeLZmatwGVijKv2sOYtYg7gfRtc,4950
|
|
29
|
-
langgraph_api/webhook.py,sha256=
|
|
30
|
-
langgraph_api/worker.py,sha256=
|
|
30
|
+
langgraph_api/webhook.py,sha256=SvSM1rdnNtiH4q3JQYmAqJUk2Sable5xAcwOLuRhtlo,1723
|
|
31
|
+
langgraph_api/worker.py,sha256=0ztx8AbggDdEjnW40Fai85S2jVGtFcNLU1kGWdN_w24,15198
|
|
31
32
|
langgraph_api/api/__init__.py,sha256=WHy6oNLWtH1K7AxmmsU9RD-Vm6WP-Ov16xS8Ey9YCmQ,6090
|
|
32
|
-
langgraph_api/api/assistants.py,sha256=
|
|
33
|
+
langgraph_api/api/assistants.py,sha256=7EvFK77_X0oh5pHpGunfrSOtZvmPQVFzxSieTwVXoYs,16150
|
|
33
34
|
langgraph_api/api/mcp.py,sha256=qe10ZRMN3f-Hli-9TI8nbQyWvMeBb72YB1PZVbyqBQw,14418
|
|
34
|
-
langgraph_api/api/meta.py,sha256=
|
|
35
|
-
langgraph_api/api/openapi.py,sha256=
|
|
36
|
-
langgraph_api/api/runs.py,sha256=
|
|
35
|
+
langgraph_api/api/meta.py,sha256=w88TK1Wu4xOhgCfs04LBfL4pZkWhUW6QRwwAWdFby5A,4245
|
|
36
|
+
langgraph_api/api/openapi.py,sha256=If-z1ckXt-Yu5bwQytK1LWyX_T7G46UtLfixgEP8hwc,11959
|
|
37
|
+
langgraph_api/api/runs.py,sha256=Kzqe2Ucq7O-Ibnr8EWpicoEx7w__3Yce78zXIv59mIw,20640
|
|
37
38
|
langgraph_api/api/store.py,sha256=TSeMiuMfrifmEnEbL0aObC2DPeseLlmZvAMaMzPgG3Y,5535
|
|
38
39
|
langgraph_api/api/threads.py,sha256=Cpw1LIWRAF3YBq65OMVXNu9K86WCITaJ5fGWZlzmnUE,9724
|
|
39
|
-
langgraph_api/api/ui.py,sha256=
|
|
40
|
+
langgraph_api/api/ui.py,sha256=_genglTUy5BMHlL0lkQypX524yFv6Z5fraIvnrxp7yE,2639
|
|
40
41
|
langgraph_api/auth/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
41
|
-
langgraph_api/auth/custom.py,sha256=
|
|
42
|
+
langgraph_api/auth/custom.py,sha256=b2NOPqBFUQiFkwlfFg4agZo3YfskTZMJyolv52suCeI,22433
|
|
42
43
|
langgraph_api/auth/middleware.py,sha256=jDA4t41DUoAArEY_PNoXesIUBJ0nGhh85QzRdn5EPD0,1916
|
|
43
44
|
langgraph_api/auth/noop.py,sha256=Bk6Nf3p8D_iMVy_OyfPlyiJp_aEwzL-sHrbxoXpCbac,586
|
|
44
45
|
langgraph_api/auth/studio_user.py,sha256=fojJpexdIZYI1w3awiqOLSwMUiK_M_3p4mlfQI0o-BE,454
|
|
45
46
|
langgraph_api/auth/langsmith/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
46
47
|
langgraph_api/auth/langsmith/backend.py,sha256=36nQnVb9VtNvSnLiNYWAI9o9H74I-mSN2X-FrWoj0QA,3646
|
|
47
|
-
langgraph_api/auth/langsmith/client.py,sha256
|
|
48
|
+
langgraph_api/auth/langsmith/client.py,sha256=-KyZSTyeiMhupkPfr--nlm_ELR1ZkjM-h61eGcMG5E0,4002
|
|
48
49
|
langgraph_api/js/.gitignore,sha256=l5yI6G_V6F1600I1IjiUKn87f4uYIrBAYU1MOyBBhg4,59
|
|
49
50
|
langgraph_api/js/.prettierrc,sha256=0es3ovvyNIqIw81rPQsdt1zCQcOdBqyR_DMbFE4Ifms,19
|
|
50
51
|
langgraph_api/js/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
51
52
|
langgraph_api/js/base.py,sha256=CJihwc51MwOVkis80f8zudRa1fQz_5jrom4rY8trww8,1133
|
|
52
|
-
langgraph_api/js/build.mts,sha256=
|
|
53
|
-
langgraph_api/js/client.http.mts,sha256=
|
|
54
|
-
langgraph_api/js/client.mts,sha256=
|
|
53
|
+
langgraph_api/js/build.mts,sha256=wguMiExRjJYpnxol_IxNHuC65CnJFsasQhZiIVSZZq8,3377
|
|
54
|
+
langgraph_api/js/client.http.mts,sha256=cvn8JV9go4pUMWkcug8FfSYWsp1wTaT8SgJaskqEzkQ,4747
|
|
55
|
+
langgraph_api/js/client.mts,sha256=gDvYiW7Qfl4re2YhZ5oNqtuvffnW_Sf7DK5aUbKB3vw,32330
|
|
55
56
|
langgraph_api/js/errors.py,sha256=Cm1TKWlUCwZReDC5AQ6SgNIVGD27Qov2xcgHyf8-GXo,361
|
|
56
57
|
langgraph_api/js/global.d.ts,sha256=j4GhgtQSZ5_cHzjSPcHgMJ8tfBThxrH-pUOrrJGteOU,196
|
|
57
58
|
langgraph_api/js/package.json,sha256=93_RZHDEggtEUJ-DburVd5D9Y9ceD_5mSc23go1BfPw,1335
|
|
58
|
-
langgraph_api/js/remote.py,sha256=
|
|
59
|
+
langgraph_api/js/remote.py,sha256=x2gO12HBriCb4bFXf4lt6uqDgoOKFihy95kHFSBz7bA,38374
|
|
59
60
|
langgraph_api/js/schema.py,sha256=M4fLtr50O1jck8H1hm_0W4cZOGYGdkrB7riLyCes4oY,438
|
|
60
|
-
langgraph_api/js/sse.py,sha256=
|
|
61
|
+
langgraph_api/js/sse.py,sha256=tVcAGVz5jOKWsESxoqm0Nk1B9yP2A7cRcVDNnR1bUv4,4144
|
|
61
62
|
langgraph_api/js/traceblock.mts,sha256=QtGSN5VpzmGqDfbArrGXkMiONY94pMQ5CgzetT_bKYg,761
|
|
62
63
|
langgraph_api/js/tsconfig.json,sha256=imCYqVnqFpaBoZPx8k1nO4slHIWBFsSlmCYhO73cpBs,341
|
|
63
64
|
langgraph_api/js/ui.py,sha256=XNT8iBcyT8XmbIqSQUWd-j_00HsaWB2vRTVabwFBkik,2439
|
|
64
65
|
langgraph_api/js/yarn.lock,sha256=6OAHOACcieOA-r_nSh26qpGLuJaWvqXiZBcRkvkUtsU,84904
|
|
65
66
|
langgraph_api/js/src/graph.mts,sha256=9zTQNdtanI_CFnOwNRoamoCVHHQHGbNlbm91aRxDeOc,2675
|
|
66
67
|
langgraph_api/js/src/load.hooks.mjs,sha256=xNVHq75W0Lk6MUKl1pQYrx-wtQ8_neiUyI6SO-k0ecM,2235
|
|
67
|
-
langgraph_api/js/src/preload.mjs,sha256=
|
|
68
|
-
langgraph_api/js/src/utils/files.mts,sha256=
|
|
68
|
+
langgraph_api/js/src/preload.mjs,sha256=8m3bYkf9iZLCQzKAYAdU8snxUwAG3dVLwGvAjfGfgIc,959
|
|
69
|
+
langgraph_api/js/src/utils/files.mts,sha256=nU09Y8lN8SYsg0x2ffmbIW8LEDBl-SWkmxsoXunFU0M,219
|
|
69
70
|
langgraph_api/js/src/utils/importMap.mts,sha256=pX4TGOyUpuuWF82kXcxcv3-8mgusRezOGe6Uklm2O5A,1644
|
|
70
71
|
langgraph_api/js/src/utils/pythonSchemas.mts,sha256=98IW7Z_VP7L_CHNRMb3_MsiV3BgLE2JsWQY_PQcRR3o,685
|
|
71
72
|
langgraph_api/js/src/utils/serde.mts,sha256=D9o6MwTgwPezC_DEmsWS5NnLPnjPMVWIb1I1D4QPEPo,743
|
|
72
73
|
langgraph_api/middleware/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
73
|
-
langgraph_api/middleware/http_logger.py,sha256=
|
|
74
|
+
langgraph_api/middleware/http_logger.py,sha256=2LABfhzTAUtqT8nf1ACy8cYXteatkwraBUEeWeNnP68,3942
|
|
74
75
|
langgraph_api/middleware/private_network.py,sha256=eYgdyU8AzU2XJu362i1L8aSFoQRiV7_aLBPw7_EgeqI,2111
|
|
75
76
|
langgraph_api/middleware/request_id.py,sha256=SDj3Yi3WvTbFQ2ewrPQBjAV8sYReOJGeIiuoHeZpR9g,1242
|
|
76
77
|
langgraph_api/models/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
77
|
-
langgraph_api/models/run.py,sha256=
|
|
78
|
+
langgraph_api/models/run.py,sha256=p5F7npi9TFcMUyyn81_InljCg8LE8jKoFSWVl4XtbZ4,15434
|
|
78
79
|
langgraph_api/tunneling/cloudflare.py,sha256=iKb6tj-VWPlDchHFjuQyep2Dpb-w2NGfJKt-WJG9LH0,3650
|
|
79
|
-
langgraph_api/utils/__init__.py,sha256=
|
|
80
|
+
langgraph_api/utils/__init__.py,sha256=_J8hvOubgC4V6x25oPjFdvuzqBIzyh6xNfEXIZO8lJQ,4478
|
|
80
81
|
langgraph_api/utils/cache.py,sha256=SrtIWYibbrNeZzLXLUGBFhJPkMVNQnVxR5giiYGHEfI,1810
|
|
81
|
-
langgraph_api/utils/config.py,sha256=
|
|
82
|
-
langgraph_api/utils/future.py,sha256=
|
|
82
|
+
langgraph_api/utils/config.py,sha256=Tbp4tKDSLKXQJ44EKr885wAQupY-9VWNJ6rgUU2oLOY,4162
|
|
83
|
+
langgraph_api/utils/future.py,sha256=lXsRQPhJwY7JUbFFZrK-94JjgsToLu-EWU896hvbUxE,7289
|
|
83
84
|
langgraph_api/utils/headers.py,sha256=Mfh8NEbb0leaTDQPZNUwQBlBmG8snKFftvPzJ5qSgC4,2777
|
|
85
|
+
langgraph_api/utils/uuids.py,sha256=AW_9-1iFqK2K5hljmi-jtaNzUIoBshk5QPt8LbpbD2g,2975
|
|
84
86
|
langgraph_license/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
85
87
|
langgraph_license/validation.py,sha256=CU38RUZ5xhP1S8F_y8TNeV6OmtO-tIGjCXbXTwJjJO4,612
|
|
86
88
|
langgraph_runtime/__init__.py,sha256=O4GgSmu33c-Pr8Xzxj_brcK5vkm70iNTcyxEjICFZxA,1075
|
|
@@ -95,8 +97,8 @@ langgraph_runtime/store.py,sha256=7mowndlsIroGHv3NpTSOZDJR0lCuaYMBoTnTrewjslw,11
|
|
|
95
97
|
LICENSE,sha256=ZPwVR73Biwm3sK6vR54djCrhaRiM4cAD2zvOQZV8Xis,3859
|
|
96
98
|
logging.json,sha256=3RNjSADZmDq38eHePMm1CbP6qZ71AmpBtLwCmKU9Zgo,379
|
|
97
99
|
openapi.json,sha256=vPWB-A1eCJZL5i7VjwAMuIn0E2oEF2hD0UeYnftK_LM,150727
|
|
98
|
-
langgraph_api-0.2.
|
|
99
|
-
langgraph_api-0.2.
|
|
100
|
-
langgraph_api-0.2.
|
|
101
|
-
langgraph_api-0.2.
|
|
102
|
-
langgraph_api-0.2.
|
|
100
|
+
langgraph_api-0.2.132.dist-info/METADATA,sha256=nPQ-UunjQUdqdx3Q5Sh_MIIchvFqpUx4EWzpy5Zj_HE,3891
|
|
101
|
+
langgraph_api-0.2.132.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
|
|
102
|
+
langgraph_api-0.2.132.dist-info/entry_points.txt,sha256=hGedv8n7cgi41PypMfinwS_HfCwA7xJIfS0jAp8htV8,78
|
|
103
|
+
langgraph_api-0.2.132.dist-info/licenses/LICENSE,sha256=ZPwVR73Biwm3sK6vR54djCrhaRiM4cAD2zvOQZV8Xis,3859
|
|
104
|
+
langgraph_api-0.2.132.dist-info/RECORD,,
|
|
File without changes
|
|
File without changes
|
|
File without changes
|