@skein-js/server-kit 0.9.1 → 0.11.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.ts +37 -4
- package/dist/index.js +34 -3
- package/package.json +7 -6
package/dist/index.d.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { ProtocolRuntime, ProtocolDeps, Logger, RunWorkerOptions, GraphResolver, ProtocolResponse } from '@skein-js/agent-protocol';
|
|
2
|
-
export { CompiledGraphFactory, DEFAULT_RUN_CONCURRENCY, GraphResolver, ProtocolDeps, ResolvedGraph, RunWorkerOptions } from '@skein-js/agent-protocol';
|
|
3
|
-
import { ModuleImporter, GraphSchemas } from '@skein-js/config';
|
|
2
|
+
export { CompiledGraphFactory, DEFAULT_RUN_CONCURRENCY, DEFAULT_SHUTDOWN_GRACE_MS, GraphResolver, ProtocolDeps, ResolvedGraph, RunWorkerOptions } from '@skein-js/agent-protocol';
|
|
3
|
+
import { ModuleImporter, LanggraphJson, GraphSchemas } from '@skein-js/config';
|
|
4
4
|
import { CorsOptions } from 'cors';
|
|
5
5
|
export { CorsOptions } from 'cors';
|
|
6
6
|
import { MemoryStoreSnapshot } from '@skein-js/storage-memory';
|
|
@@ -33,6 +33,11 @@ interface SkeinRuntimeCommonOptions {
|
|
|
33
33
|
* engine's execution lock — but see the head-of-line note in docs/runs-and-redis.md if your workload
|
|
34
34
|
* leans on `multitask_strategy: "enqueue"`. Ignored by the invoke-only surface, which starts no
|
|
35
35
|
* worker.
|
|
36
|
+
*
|
|
37
|
+
* `shutdownGraceMs` is how long `worker.stop()` lets in-flight runs finish before aborting them
|
|
38
|
+
* (default `DEFAULT_SHUTDOWN_GRACE_MS`); omit it and skein reads `SKEIN_SHUTDOWN_GRACE_MS`, with
|
|
39
|
+
* the same explicit-wins-but-still-validated rule. Whatever forces the process to exit must wait
|
|
40
|
+
* longer than this, or the abort step never runs — see docs/deploy.md.
|
|
36
41
|
*/
|
|
37
42
|
worker?: RunWorkerOptions;
|
|
38
43
|
}
|
|
@@ -90,6 +95,20 @@ declare function resolveProtocolRuntime(options: SkeinRuntimeOptions): Promise<R
|
|
|
90
95
|
*/
|
|
91
96
|
declare function resolveRunConcurrency(explicit?: number, env?: NodeJS.ProcessEnv): number;
|
|
92
97
|
|
|
98
|
+
/**
|
|
99
|
+
* The one precedence chain for the shutdown drain window: an explicit `worker.shutdownGraceMs` wins,
|
|
100
|
+
* else `SKEIN_SHUTDOWN_GRACE_MS`, else {@link DEFAULT_SHUTDOWN_GRACE_MS}. The environment is read and
|
|
101
|
+
* validated even when `explicit` is given, so a bad value can't sit unnoticed in a deployment that
|
|
102
|
+
* also passes the option.
|
|
103
|
+
*
|
|
104
|
+
* Zero is allowed and means "abort in-flight runs immediately" — a legitimate choice for a fleet that
|
|
105
|
+
* relies on queue redelivery instead of draining.
|
|
106
|
+
*
|
|
107
|
+
* `env` is injected (defaulting to `process.env`) so callers — and tests — can resolve against an
|
|
108
|
+
* environment they control.
|
|
109
|
+
*/
|
|
110
|
+
declare function resolveShutdownGraceMs(explicit?: number, env?: NodeJS.ProcessEnv): number;
|
|
111
|
+
|
|
93
112
|
/** The checkpoint tuple `[checkpoint, metadata, parentId?]` with the blobs base64-encoded. */
|
|
94
113
|
type SerializedCheckpointTuple = [string, string, string | undefined];
|
|
95
114
|
/** `MemorySaver.storage` (thread → namespace → checkpointId → tuple) with blobs base64-encoded. */
|
|
@@ -116,6 +135,13 @@ interface InMemoryRuntimeConfig {
|
|
|
116
135
|
/** Load `langgraph.json`, wiring fresh in-memory drivers and reading its `http.cors` for the adapter. */
|
|
117
136
|
declare function loadInMemoryRuntime(configPath: string, importModule?: ModuleImporter, staticSchemas?: Record<string, GraphSchemas>): Promise<InMemoryRuntimeConfig>;
|
|
118
137
|
interface ReloadableInMemoryRuntime extends InMemoryRuntimeConfig {
|
|
138
|
+
/**
|
|
139
|
+
* The parsed `langgraph.json`, so a caller that needs a block this runtime doesn't act on itself
|
|
140
|
+
* (`telemetry`, say) can read it without a second `loadConfig` — which would re-import every graph.
|
|
141
|
+
*/
|
|
142
|
+
config: LanggraphJson;
|
|
143
|
+
/** Directory holding `langgraph.json`, for resolving paths declared relative to it. */
|
|
144
|
+
configDir: string;
|
|
119
145
|
/**
|
|
120
146
|
* Re-read the config and swap in freshly imported graphs, keeping the same drivers. Because the
|
|
121
147
|
* run engine calls `graphs.load()` per run (it never caches the compiled graph itself), the next
|
|
@@ -134,7 +160,14 @@ interface ReloadableInMemoryRuntime extends InMemoryRuntimeConfig {
|
|
|
134
160
|
* dev` pairs this with vite's watcher (clear vite's cache, then `reloadGraphs()` — no server
|
|
135
161
|
* restart, no lost state) and with on-disk JSON persistence across restarts.
|
|
136
162
|
*/
|
|
137
|
-
declare function loadReloadableInMemoryRuntime(configPath: string, importModule?: ModuleImporter, staticSchemas?: Record<string, GraphSchemas
|
|
163
|
+
declare function loadReloadableInMemoryRuntime(configPath: string, importModule?: ModuleImporter, staticSchemas?: Record<string, GraphSchemas>,
|
|
164
|
+
/**
|
|
165
|
+
* Extra deps to build in, for a caller that acts on a config block this runtime doesn't itself
|
|
166
|
+
* read (`telemetry`). Merged **into** the constructed `deps`, so every consumer sees the same
|
|
167
|
+
* object — patching the returned `deps` afterwards would miss anything that already snapshotted it
|
|
168
|
+
* (`resolveDeps` spreads, it doesn't alias).
|
|
169
|
+
*/
|
|
170
|
+
extraDeps?: Partial<Omit<ProtocolDeps, "graphs">>): Promise<ReloadableInMemoryRuntime>;
|
|
138
171
|
|
|
139
172
|
type AnyCompiledGraph = CompiledGraph<any>;
|
|
140
173
|
/**
|
|
@@ -259,4 +292,4 @@ declare function sendNodeError(error: unknown, res: ServerResponse, logger?: Log
|
|
|
259
292
|
*/
|
|
260
293
|
declare function stripBasePath(pathname: string, basePath: string): string | null;
|
|
261
294
|
|
|
262
|
-
export { type CorsSetting, type DevStateCounts, type DevStateSnapshot, type EmbeddableGraph, type InMemoryRuntimeConfig, type LanggraphCorsConfig, type ReloadableInMemoryRuntime, type ResolvedProtocolRuntime, type ResolvedRuntimeDeps, type SkeinRuntimeCommonOptions, type SkeinRuntimeOptions, allowedOrigin, applyNodeCors, corsFromHttpConfig, corsPreflightHeaders, corsResponseHeaders, createInMemoryDeps, describeSnapshot, embedInMemoryGraphs, graphMapToResolver, joinList, loadInMemoryRuntime, loadReloadableInMemoryRuntime, loadSnapshotIntoStore, normalizeEmbeddableGraphs, readLanggraphDevState, resolveProtocolRuntime, resolveRunConcurrency, resolveRuntimeDeps, sendNodeError, sendNodePreflight, sendNodeResponse, stripBasePath, toCorsOptions };
|
|
295
|
+
export { type CorsSetting, type DevStateCounts, type DevStateSnapshot, type EmbeddableGraph, type InMemoryRuntimeConfig, type LanggraphCorsConfig, type ReloadableInMemoryRuntime, type ResolvedProtocolRuntime, type ResolvedRuntimeDeps, type SkeinRuntimeCommonOptions, type SkeinRuntimeOptions, allowedOrigin, applyNodeCors, corsFromHttpConfig, corsPreflightHeaders, corsResponseHeaders, createInMemoryDeps, describeSnapshot, embedInMemoryGraphs, graphMapToResolver, joinList, loadInMemoryRuntime, loadReloadableInMemoryRuntime, loadSnapshotIntoStore, normalizeEmbeddableGraphs, readLanggraphDevState, resolveProtocolRuntime, resolveRunConcurrency, resolveRuntimeDeps, resolveShutdownGraceMs, sendNodeError, sendNodePreflight, sendNodeResponse, stripBasePath, toCorsOptions };
|
package/dist/index.js
CHANGED
|
@@ -153,7 +153,7 @@ async function loadInMemoryRuntime(configPath, importModule, staticSchemas) {
|
|
|
153
153
|
cors: corsFromHttpConfig(config.http)
|
|
154
154
|
};
|
|
155
155
|
}
|
|
156
|
-
async function loadReloadableInMemoryRuntime(configPath, importModule, staticSchemas) {
|
|
156
|
+
async function loadReloadableInMemoryRuntime(configPath, importModule, staticSchemas, extraDeps) {
|
|
157
157
|
const first = await loadConfig({ configPath, importModule, staticSchemas });
|
|
158
158
|
let current = first.graphs;
|
|
159
159
|
const graphs = {
|
|
@@ -169,11 +169,14 @@ async function loadReloadableInMemoryRuntime(configPath, importModule, staticSch
|
|
|
169
169
|
queue: new MemoryRunQueue2(),
|
|
170
170
|
bus: new MemoryRunEventBus2(),
|
|
171
171
|
checkpointer,
|
|
172
|
-
auth: await loadAuthEngine(first.config.auth, { configDir: first.configDir, importModule })
|
|
172
|
+
auth: await loadAuthEngine(first.config.auth, { configDir: first.configDir, importModule }),
|
|
173
|
+
...extraDeps
|
|
173
174
|
};
|
|
174
175
|
return {
|
|
175
176
|
deps,
|
|
176
177
|
cors: corsFromHttpConfig(first.config.http),
|
|
178
|
+
config: first.config,
|
|
179
|
+
configDir: first.configDir,
|
|
177
180
|
reloadGraphs: async () => {
|
|
178
181
|
current = (await loadConfig({ configPath, importModule, staticSchemas })).graphs;
|
|
179
182
|
},
|
|
@@ -214,6 +217,30 @@ function resolveRunConcurrency(explicit, env = process.env) {
|
|
|
214
217
|
return requirePositiveInteger("worker.maxConcurrency", explicit);
|
|
215
218
|
}
|
|
216
219
|
|
|
220
|
+
// src/shutdown-grace.ts
|
|
221
|
+
import { DEFAULT_SHUTDOWN_GRACE_MS } from "@skein-js/agent-protocol";
|
|
222
|
+
import { SkeinConfigError as SkeinConfigError2 } from "@skein-js/config";
|
|
223
|
+
var SHUTDOWN_GRACE_ENV_VAR = "SKEIN_SHUTDOWN_GRACE_MS";
|
|
224
|
+
function requireNonNegativeInteger(source, raw) {
|
|
225
|
+
const parsed = Number(raw);
|
|
226
|
+
if (!Number.isInteger(parsed) || parsed < 0) {
|
|
227
|
+
throw new SkeinConfigError2(
|
|
228
|
+
`${source} must be a non-negative integer in milliseconds (got "${String(raw)}").`
|
|
229
|
+
);
|
|
230
|
+
}
|
|
231
|
+
return parsed;
|
|
232
|
+
}
|
|
233
|
+
function shutdownGraceFromEnv(env) {
|
|
234
|
+
const raw = env[SHUTDOWN_GRACE_ENV_VAR];
|
|
235
|
+
if (raw === void 0 || raw.trim() === "") return void 0;
|
|
236
|
+
return requireNonNegativeInteger(SHUTDOWN_GRACE_ENV_VAR, raw);
|
|
237
|
+
}
|
|
238
|
+
function resolveShutdownGraceMs(explicit, env = process.env) {
|
|
239
|
+
const fromEnv = shutdownGraceFromEnv(env);
|
|
240
|
+
if (explicit === void 0) return fromEnv ?? DEFAULT_SHUTDOWN_GRACE_MS;
|
|
241
|
+
return requireNonNegativeInteger("worker.shutdownGraceMs", explicit);
|
|
242
|
+
}
|
|
243
|
+
|
|
217
244
|
// src/resolve-runtime.ts
|
|
218
245
|
async function resolveRuntimeDeps(options) {
|
|
219
246
|
if (options.deps) return { deps: options.deps };
|
|
@@ -225,7 +252,8 @@ async function resolveProtocolRuntime(options) {
|
|
|
225
252
|
const runtime = createProtocolRuntime(deps, {
|
|
226
253
|
worker: {
|
|
227
254
|
...options.worker,
|
|
228
|
-
maxConcurrency: resolveRunConcurrency(options.worker?.maxConcurrency)
|
|
255
|
+
maxConcurrency: resolveRunConcurrency(options.worker?.maxConcurrency),
|
|
256
|
+
shutdownGraceMs: resolveShutdownGraceMs(options.worker?.shutdownGraceMs)
|
|
229
257
|
}
|
|
230
258
|
});
|
|
231
259
|
await runtime.service.assistants.registerGraphAssistants();
|
|
@@ -244,6 +272,7 @@ async function resolveProtocolRuntime(options) {
|
|
|
244
272
|
|
|
245
273
|
// src/index.ts
|
|
246
274
|
import { DEFAULT_RUN_CONCURRENCY as DEFAULT_RUN_CONCURRENCY2 } from "@skein-js/agent-protocol";
|
|
275
|
+
import { DEFAULT_SHUTDOWN_GRACE_MS as DEFAULT_SHUTDOWN_GRACE_MS2 } from "@skein-js/agent-protocol";
|
|
247
276
|
|
|
248
277
|
// src/langgraph-import.ts
|
|
249
278
|
import { readFile } from "fs/promises";
|
|
@@ -685,6 +714,7 @@ function stripBasePath(pathname, basePath) {
|
|
|
685
714
|
}
|
|
686
715
|
export {
|
|
687
716
|
DEFAULT_RUN_CONCURRENCY2 as DEFAULT_RUN_CONCURRENCY,
|
|
717
|
+
DEFAULT_SHUTDOWN_GRACE_MS2 as DEFAULT_SHUTDOWN_GRACE_MS,
|
|
688
718
|
allowedOrigin,
|
|
689
719
|
applyNodeCors,
|
|
690
720
|
corsFromHttpConfig,
|
|
@@ -703,6 +733,7 @@ export {
|
|
|
703
733
|
resolveProtocolRuntime,
|
|
704
734
|
resolveRunConcurrency,
|
|
705
735
|
resolveRuntimeDeps,
|
|
736
|
+
resolveShutdownGraceMs,
|
|
706
737
|
sendNodeError,
|
|
707
738
|
sendNodePreflight,
|
|
708
739
|
sendNodeResponse,
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@skein-js/server-kit",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.11.1",
|
|
4
4
|
"description": "Shared, framework-agnostic building blocks for skein-js HTTP adapters — in-memory dev runtime, LangGraph dev-state import, and langgraph.json CORS mapping.",
|
|
5
5
|
"license": "Apache-2.0",
|
|
6
6
|
"author": "Maina Wycliffe <wmmaina7@gmail.com>",
|
|
@@ -27,7 +27,8 @@
|
|
|
27
27
|
"exports": {
|
|
28
28
|
".": {
|
|
29
29
|
"types": "./dist/index.d.ts",
|
|
30
|
-
"import": "./dist/index.js"
|
|
30
|
+
"import": "./dist/index.js",
|
|
31
|
+
"default": "./dist/index.js"
|
|
31
32
|
}
|
|
32
33
|
},
|
|
33
34
|
"files": [
|
|
@@ -43,10 +44,10 @@
|
|
|
43
44
|
"cors": "^2.8.5",
|
|
44
45
|
"superjson": "^2.2.6",
|
|
45
46
|
"zod": "^3.25.76",
|
|
46
|
-
"@skein-js/agent-protocol": "0.
|
|
47
|
-
"@skein-js/
|
|
48
|
-
"@skein-js/
|
|
49
|
-
"@skein-js/
|
|
47
|
+
"@skein-js/agent-protocol": "0.11.1",
|
|
48
|
+
"@skein-js/config": "0.11.1",
|
|
49
|
+
"@skein-js/core": "0.11.1",
|
|
50
|
+
"@skein-js/storage-memory": "0.11.1"
|
|
50
51
|
},
|
|
51
52
|
"peerDependencies": {
|
|
52
53
|
"@langchain/langgraph": "^1.4.0"
|