@cuylabs/agent-server 0.10.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/LICENSE +201 -0
- package/README.md +262 -0
- package/dist/index.d.ts +893 -0
- package/dist/index.js +2288 -0
- package/docs/README.md +22 -0
- package/docs/architecture.md +61 -0
- package/docs/clients-and-transports.md +92 -0
- package/docs/plugins-and-boundaries.md +41 -0
- package/docs/protocol.md +111 -0
- package/docs/runtime-and-dapr.md +41 -0
- package/package.json +57 -0
package/docs/README.md
ADDED
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
# Agent Server Docs
|
|
2
|
+
|
|
3
|
+
- [Architecture](./architecture.md)
|
|
4
|
+
- [Protocol](./protocol.md)
|
|
5
|
+
- [Clients And Transports](./clients-and-transports.md)
|
|
6
|
+
- [Plugins And Boundaries](./plugins-and-boundaries.md)
|
|
7
|
+
- [Runtime And Dapr](./runtime-and-dapr.md)
|
|
8
|
+
|
|
9
|
+
## Source map
|
|
10
|
+
|
|
11
|
+
- `src/protocol/contracts.ts`
|
|
12
|
+
- capability contract, shared types, adapter surface
|
|
13
|
+
- `src/protocol/wire.ts`
|
|
14
|
+
- request / response / notification wire schema (29 methods)
|
|
15
|
+
- `src/runtime/in-process-server.ts`
|
|
16
|
+
- session and turn authority
|
|
17
|
+
- `src/runtime/interactive-handlers.ts`
|
|
18
|
+
- `InteractiveRequestBridge` and approval/human-input server handlers
|
|
19
|
+
- `src/client/`
|
|
20
|
+
- in-process and remote client facades, `streamTurn` helper
|
|
21
|
+
- `src/transport/`
|
|
22
|
+
- stdio, websocket, and RPC connection plumbing
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
# Architecture
|
|
2
|
+
|
|
3
|
+
`@cuylabs/agent-server` is the host layer above the agent framework.
|
|
4
|
+
|
|
5
|
+
It does not replace the lower packages:
|
|
6
|
+
|
|
7
|
+
- `@cuylabs/agent-core`
|
|
8
|
+
- agent execution, sessions, tools, middleware, plugins
|
|
9
|
+
- `@cuylabs/agent-runtime`
|
|
10
|
+
- scheduling and orchestration abstractions
|
|
11
|
+
- `@cuylabs/agent-runtime-dapr`
|
|
12
|
+
- Dapr-backed durability and hosted workflows
|
|
13
|
+
- `@cuylabs/agent-server`
|
|
14
|
+
- live session and turn ownership for clients
|
|
15
|
+
|
|
16
|
+
## Role
|
|
17
|
+
|
|
18
|
+
The server owns:
|
|
19
|
+
|
|
20
|
+
- session listing, creation, reading, deletion, and branching
|
|
21
|
+
- turn start, wait, interrupt, steering, and follow-up queuing
|
|
22
|
+
- follow-up management (list, get, resolve/discard)
|
|
23
|
+
- live notification fanout
|
|
24
|
+
- approval request routing
|
|
25
|
+
- human input request routing
|
|
26
|
+
- startup and workspace summary snapshots
|
|
27
|
+
- capability-gated agent affordances such as model inspection, model switching, and runtime status
|
|
28
|
+
|
|
29
|
+
Clients own:
|
|
30
|
+
|
|
31
|
+
- user input
|
|
32
|
+
- rendering
|
|
33
|
+
- command routing in the host app
|
|
34
|
+
- reconnect behavior and transport choice
|
|
35
|
+
|
|
36
|
+
## Public surface
|
|
37
|
+
|
|
38
|
+
The package is intentionally split by role:
|
|
39
|
+
|
|
40
|
+
- `src/types.ts`
|
|
41
|
+
- protocol contracts and wire types
|
|
42
|
+
- `src/server.ts`
|
|
43
|
+
- server-side runtime, transport helpers, and interactive request handlers
|
|
44
|
+
- `src/client.ts`
|
|
45
|
+
- client-side facades and `streamTurn` helper
|
|
46
|
+
|
|
47
|
+
That matches the package entrypoints exported from `src/index.ts`.
|
|
48
|
+
|
|
49
|
+
## Current implementation
|
|
50
|
+
|
|
51
|
+
The current runtime authority is `InProcessAgentServer` in `src/runtime/in-process-server.ts`.
|
|
52
|
+
|
|
53
|
+
It tracks:
|
|
54
|
+
|
|
55
|
+
- active turns
|
|
56
|
+
- session runtime state
|
|
57
|
+
- pending approval/input requests
|
|
58
|
+
- queued follow-up records
|
|
59
|
+
- subscribers for live notifications
|
|
60
|
+
|
|
61
|
+
Transports do not own the agent loop. They only expose the same server surface over different connections.
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
# Clients And Transports
|
|
2
|
+
|
|
3
|
+
The client surface is split into two layers:
|
|
4
|
+
|
|
5
|
+
- `src/client/`
|
|
6
|
+
- client facades
|
|
7
|
+
- `src/transport/`
|
|
8
|
+
- connection implementations
|
|
9
|
+
|
|
10
|
+
## Clients
|
|
11
|
+
|
|
12
|
+
`InProcessAgentServerClient`
|
|
13
|
+
|
|
14
|
+
- talks directly to an in-memory `AgentServer`
|
|
15
|
+
- used by the CLI in embedded mode
|
|
16
|
+
- good for local execution and tests
|
|
17
|
+
|
|
18
|
+
`RemoteAgentServerClient`
|
|
19
|
+
|
|
20
|
+
- speaks the wire protocol over a transport
|
|
21
|
+
- caches turn notifications for inspection
|
|
22
|
+
- handles request timeouts and reconnect-sensitive state
|
|
23
|
+
|
|
24
|
+
### Helpers
|
|
25
|
+
|
|
26
|
+
`streamTurn(client, sessionId, message, options?)`
|
|
27
|
+
|
|
28
|
+
- async generator that starts a turn, subscribes to events, and yields `AgentEvent`s
|
|
29
|
+
- the primary streaming utility for consuming agent output
|
|
30
|
+
|
|
31
|
+
`createInProcessAgentServer(agent)` / `createInProcessAgentServerClient(agent)`
|
|
32
|
+
|
|
33
|
+
- convenience factories that wire `createAgentServerAdapter` + server/client construction in one call
|
|
34
|
+
|
|
35
|
+
## Transports
|
|
36
|
+
|
|
37
|
+
### Stdio
|
|
38
|
+
|
|
39
|
+
Defined in `src/transport/stdio.ts`.
|
|
40
|
+
|
|
41
|
+
Use it when:
|
|
42
|
+
|
|
43
|
+
- a parent process wants to spawn `cuylabs server`
|
|
44
|
+
- exactly one child client needs the connection
|
|
45
|
+
- pipes are simpler than sockets
|
|
46
|
+
|
|
47
|
+
Characteristics:
|
|
48
|
+
|
|
49
|
+
- `protocol.transport = "stdio"`
|
|
50
|
+
- `reconnectable = false`
|
|
51
|
+
- `multiClient = false`
|
|
52
|
+
- stdout is reserved for the wire protocol
|
|
53
|
+
|
|
54
|
+
API:
|
|
55
|
+
|
|
56
|
+
- `attachAgentServerStdio(server, options?)` — server side
|
|
57
|
+
- `connectStdioAgentServerClient(options)` — spawns a child process and returns a connected `RemoteAgentServerClient`
|
|
58
|
+
|
|
59
|
+
### WebSocket
|
|
60
|
+
|
|
61
|
+
Defined in `src/transport/websocket.ts`.
|
|
62
|
+
|
|
63
|
+
Use it when:
|
|
64
|
+
|
|
65
|
+
- external clients need reconnectable access
|
|
66
|
+
- more than one client may connect over time
|
|
67
|
+
- a local service should stay up independently of a single shell
|
|
68
|
+
|
|
69
|
+
Characteristics:
|
|
70
|
+
|
|
71
|
+
- `protocol.transport = "websocket"`
|
|
72
|
+
- `reconnectable = true`
|
|
73
|
+
- `multiClient = true`
|
|
74
|
+
|
|
75
|
+
API:
|
|
76
|
+
|
|
77
|
+
- `startAgentServerWebSocketServer(server, options)` — server side. Options: `{ port?, host?, httpServer? }`. The `httpServer` option lets you share a port with another HTTP surface (e.g. `agent-runtime-dapr`'s REST/SSE handler).
|
|
78
|
+
- `connectWebSocketAgentServerClient(options)` — client side. Options: `{ url, headers?, requestTimeoutMs? }`.
|
|
79
|
+
|
|
80
|
+
## RPC connection
|
|
81
|
+
|
|
82
|
+
`AgentServerRpcConnection` in `src/transport/rpc-connection.ts` adapts an `AgentServer` to any envelope-based transport.
|
|
83
|
+
|
|
84
|
+
It is responsible for:
|
|
85
|
+
|
|
86
|
+
- per-connection capability overrides
|
|
87
|
+
- dispatching wire requests to the server
|
|
88
|
+
- forwarding notifications to subscribers
|
|
89
|
+
|
|
90
|
+
Also exports `matchesNotificationSubscription(notification, options?)` — a utility for filtering notifications by turn/session/type.
|
|
91
|
+
|
|
92
|
+
That keeps transport code thin and keeps request routing in one place.
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
# Plugins And Boundaries
|
|
2
|
+
|
|
3
|
+
`@cuylabs/agent-server` does not introduce a second plugin model.
|
|
4
|
+
|
|
5
|
+
## What stays server-side
|
|
6
|
+
|
|
7
|
+
`agent-core` plugins still own:
|
|
8
|
+
|
|
9
|
+
- tools
|
|
10
|
+
- middleware
|
|
11
|
+
- prompt sections
|
|
12
|
+
- lifecycle hooks
|
|
13
|
+
- plugin commands
|
|
14
|
+
|
|
15
|
+
That logic runs where the agent runs.
|
|
16
|
+
|
|
17
|
+
## What clients should not do
|
|
18
|
+
|
|
19
|
+
Clients should not expect plugins to:
|
|
20
|
+
|
|
21
|
+
- render custom TUI widgets
|
|
22
|
+
- render custom web components
|
|
23
|
+
- import host UI internals
|
|
24
|
+
- manipulate renderer state directly
|
|
25
|
+
|
|
26
|
+
`agent-server` keeps the plugin contract headless.
|
|
27
|
+
|
|
28
|
+
## Plugin commands
|
|
29
|
+
|
|
30
|
+
The server does expose plugin commands through the contract:
|
|
31
|
+
|
|
32
|
+
- `listPluginCommands()`
|
|
33
|
+
- `executePluginCommand(name, args)`
|
|
34
|
+
|
|
35
|
+
That lets a host discover and route plugin-defined commands without duplicating plugin logic in every client.
|
|
36
|
+
|
|
37
|
+
## Future UI extensions
|
|
38
|
+
|
|
39
|
+
If the project later needs renderer-specific extensions, they should be introduced as a separate client-layer API.
|
|
40
|
+
|
|
41
|
+
Do not expand `agent-core` plugins into a mixed server-plus-UI contract.
|
package/docs/protocol.md
ADDED
|
@@ -0,0 +1,111 @@
|
|
|
1
|
+
# Protocol
|
|
2
|
+
|
|
3
|
+
The shared contract lives in `src/protocol/contracts.ts`.
|
|
4
|
+
|
|
5
|
+
## Core concepts
|
|
6
|
+
|
|
7
|
+
- `session`
|
|
8
|
+
- persisted conversation state backed by `agent-core` storage
|
|
9
|
+
- `turn`
|
|
10
|
+
- one user message plus the streamed agent work that follows
|
|
11
|
+
- `notification`
|
|
12
|
+
- a server-emitted update such as `turn/event`, `turn/completed`, or `input/request`
|
|
13
|
+
|
|
14
|
+
## Capabilities
|
|
15
|
+
|
|
16
|
+
Clients inspect `getCapabilities()` first instead of assuming a feature exists.
|
|
17
|
+
|
|
18
|
+
The capability sections are:
|
|
19
|
+
|
|
20
|
+
- `protocol`
|
|
21
|
+
- protocol version, transport kind, reconnectability, multi-client support
|
|
22
|
+
- `sessions`
|
|
23
|
+
- persistent storage, list, create, read, delete, branch
|
|
24
|
+
- `turns`
|
|
25
|
+
- start, wait, interrupt, steer, follow-up, follow-up management, event streaming, concurrent turns per session
|
|
26
|
+
- `interactive`
|
|
27
|
+
- approval requests, human input requests
|
|
28
|
+
- `runtime`
|
|
29
|
+
- execution mode, orchestration backend, durability mode, Dapr availability
|
|
30
|
+
- `agent`
|
|
31
|
+
- workspace summary, runtime status, model inspection, model switching, tool/skill/sub-agent inventory, compact, undo, diff
|
|
32
|
+
- `plugins`
|
|
33
|
+
- headless plugin behavior and plugin command support
|
|
34
|
+
|
|
35
|
+
## Workspace summary
|
|
36
|
+
|
|
37
|
+
`getWorkspaceSummary()` gives clients a startup snapshot without forcing them to stitch together:
|
|
38
|
+
|
|
39
|
+
- model label and switchable flag
|
|
40
|
+
- tool count
|
|
41
|
+
- skill count
|
|
42
|
+
- sub-agent count
|
|
43
|
+
- session count
|
|
44
|
+
- workspace cwd
|
|
45
|
+
|
|
46
|
+
That is what the CLI welcome state now uses by default.
|
|
47
|
+
|
|
48
|
+
## Wire contract
|
|
49
|
+
|
|
50
|
+
The transport-level request and response types live in `src/protocol/wire.ts`.
|
|
51
|
+
|
|
52
|
+
Important methods include:
|
|
53
|
+
|
|
54
|
+
### Session & workspace
|
|
55
|
+
|
|
56
|
+
- `initialize`
|
|
57
|
+
- `capabilities/get`
|
|
58
|
+
- `workspace/summary`
|
|
59
|
+
- `session/list`
|
|
60
|
+
- `session/create`
|
|
61
|
+
- `session/read`
|
|
62
|
+
- `session/delete`
|
|
63
|
+
- `session/branch`
|
|
64
|
+
- `session/status`
|
|
65
|
+
- `session/compact`
|
|
66
|
+
- `session/undo`
|
|
67
|
+
- `session/diff`
|
|
68
|
+
|
|
69
|
+
### Agent inspection
|
|
70
|
+
|
|
71
|
+
- `agent/model/get`
|
|
72
|
+
- `agent/model/switch`
|
|
73
|
+
- `agent/tools`
|
|
74
|
+
- `agent/skills`
|
|
75
|
+
- `agent/sub-agents`
|
|
76
|
+
|
|
77
|
+
### Turn lifecycle
|
|
78
|
+
|
|
79
|
+
- `turn/start`
|
|
80
|
+
- `turn/get`
|
|
81
|
+
- `turn/wait`
|
|
82
|
+
- `turn/interrupt`
|
|
83
|
+
- `turn/steer`
|
|
84
|
+
- `turn/follow-up`
|
|
85
|
+
|
|
86
|
+
### Follow-up management
|
|
87
|
+
|
|
88
|
+
- `follow-up/list`
|
|
89
|
+
- `follow-up/get`
|
|
90
|
+
- `follow-up/resolve`
|
|
91
|
+
|
|
92
|
+
### Interactive
|
|
93
|
+
|
|
94
|
+
- `input/respond`
|
|
95
|
+
|
|
96
|
+
For human-input routing in direct mode, the server adapter exposes
|
|
97
|
+
`interactive.humanRequests = true` only when the hosted agent has:
|
|
98
|
+
|
|
99
|
+
- a configured human-input controller
|
|
100
|
+
- at least one human-input-capable tool
|
|
101
|
+
|
|
102
|
+
That keeps protocol capability reporting aligned with the actual request
|
|
103
|
+
surface instead of assuming every direct agent can answer human-input
|
|
104
|
+
requests.
|
|
105
|
+
|
|
106
|
+
### Plugins
|
|
107
|
+
|
|
108
|
+
- `plugin-command/list`
|
|
109
|
+
- `plugin-command/execute`
|
|
110
|
+
|
|
111
|
+
Notifications are streamed independently of request responses.
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
# Runtime And Dapr
|
|
2
|
+
|
|
3
|
+
`agent-server` is the client-facing host layer.
|
|
4
|
+
|
|
5
|
+
It is not the same thing as `agent-runtime` or `agent-runtime-dapr`.
|
|
6
|
+
|
|
7
|
+
## Responsibilities
|
|
8
|
+
|
|
9
|
+
`agent-server`
|
|
10
|
+
|
|
11
|
+
- owns session and turn APIs
|
|
12
|
+
- owns subscriptions and live notifications
|
|
13
|
+
- owns reconnect semantics for clients
|
|
14
|
+
|
|
15
|
+
`agent-runtime`
|
|
16
|
+
|
|
17
|
+
- defines orchestration abstractions
|
|
18
|
+
- schedules and dispatches work
|
|
19
|
+
|
|
20
|
+
`agent-runtime-dapr`
|
|
21
|
+
|
|
22
|
+
- provides Dapr-backed durability
|
|
23
|
+
- provides workflow hosting and checkpoints
|
|
24
|
+
- can back some turns or workloads behind the same server-facing contract
|
|
25
|
+
|
|
26
|
+
## Why the separation matters
|
|
27
|
+
|
|
28
|
+
Clients should not need to know whether a turn is:
|
|
29
|
+
|
|
30
|
+
- direct and local
|
|
31
|
+
- orchestrated through `agent-runtime`
|
|
32
|
+
- delegated to `agent-runtime-dapr`
|
|
33
|
+
|
|
34
|
+
They only need to inspect the exposed capabilities and interact with the same session and turn surface.
|
|
35
|
+
|
|
36
|
+
That is why the capability contract includes:
|
|
37
|
+
|
|
38
|
+
- execution mode
|
|
39
|
+
- orchestration backend
|
|
40
|
+
- durability mode
|
|
41
|
+
- Dapr availability flags
|
package/package.json
ADDED
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@cuylabs/agent-server",
|
|
3
|
+
"version": "0.10.0",
|
|
4
|
+
"description": "Transport-neutral local server for @cuylabs/agent-core sessions, turns, and streamed events",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"main": "./dist/index.js",
|
|
7
|
+
"types": "./dist/index.d.ts",
|
|
8
|
+
"exports": {
|
|
9
|
+
".": {
|
|
10
|
+
"types": "./dist/index.d.ts",
|
|
11
|
+
"import": "./dist/index.js",
|
|
12
|
+
"default": "./dist/index.js"
|
|
13
|
+
}
|
|
14
|
+
},
|
|
15
|
+
"files": [
|
|
16
|
+
"dist",
|
|
17
|
+
"docs",
|
|
18
|
+
"README.md"
|
|
19
|
+
],
|
|
20
|
+
"dependencies": {
|
|
21
|
+
"ws": "^8.19.0",
|
|
22
|
+
"@cuylabs/agent-core": "^0.10.0"
|
|
23
|
+
},
|
|
24
|
+
"devDependencies": {
|
|
25
|
+
"@types/node": "^22.0.0",
|
|
26
|
+
"tsup": "^8.0.0",
|
|
27
|
+
"typescript": "^5.7.0",
|
|
28
|
+
"vitest": "^4.0.18"
|
|
29
|
+
},
|
|
30
|
+
"keywords": [
|
|
31
|
+
"agent",
|
|
32
|
+
"app-server",
|
|
33
|
+
"sessions",
|
|
34
|
+
"turns",
|
|
35
|
+
"streaming"
|
|
36
|
+
],
|
|
37
|
+
"author": "cuylabs",
|
|
38
|
+
"license": "Apache-2.0",
|
|
39
|
+
"repository": {
|
|
40
|
+
"type": "git",
|
|
41
|
+
"url": "https://github.com/cuylabs-ai/agents-ts.git",
|
|
42
|
+
"directory": "packages/agent-server"
|
|
43
|
+
},
|
|
44
|
+
"engines": {
|
|
45
|
+
"node": ">=20"
|
|
46
|
+
},
|
|
47
|
+
"publishConfig": {
|
|
48
|
+
"access": "public"
|
|
49
|
+
},
|
|
50
|
+
"scripts": {
|
|
51
|
+
"build": "tsup src/index.ts --format esm --dts --clean",
|
|
52
|
+
"dev": "tsup src/index.ts --format esm --dts --watch",
|
|
53
|
+
"test": "vitest run",
|
|
54
|
+
"typecheck": "tsc --noEmit",
|
|
55
|
+
"clean": "rm -rf dist"
|
|
56
|
+
}
|
|
57
|
+
}
|