@graphorin/server 0.5.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.
Files changed (204) hide show
  1. package/CHANGELOG.md +7 -0
  2. package/LICENSE +21 -0
  3. package/README.md +116 -0
  4. package/dist/app.d.ts +174 -0
  5. package/dist/app.d.ts.map +1 -0
  6. package/dist/app.js +684 -0
  7. package/dist/app.js.map +1 -0
  8. package/dist/commentary/audit-bridge.d.ts +57 -0
  9. package/dist/commentary/audit-bridge.d.ts.map +1 -0
  10. package/dist/commentary/audit-bridge.js +92 -0
  11. package/dist/commentary/audit-bridge.js.map +1 -0
  12. package/dist/commentary/built-in-patterns.d.ts +24 -0
  13. package/dist/commentary/built-in-patterns.d.ts.map +1 -0
  14. package/dist/commentary/built-in-patterns.js +62 -0
  15. package/dist/commentary/built-in-patterns.js.map +1 -0
  16. package/dist/commentary/index.d.ts +5 -0
  17. package/dist/commentary/index.js +5 -0
  18. package/dist/commentary/sanitizer.d.ts +37 -0
  19. package/dist/commentary/sanitizer.d.ts.map +1 -0
  20. package/dist/commentary/sanitizer.js +182 -0
  21. package/dist/commentary/sanitizer.js.map +1 -0
  22. package/dist/commentary/types.d.ts +120 -0
  23. package/dist/commentary/types.d.ts.map +1 -0
  24. package/dist/config.d.ts +760 -0
  25. package/dist/config.d.ts.map +1 -0
  26. package/dist/config.js +217 -0
  27. package/dist/config.js.map +1 -0
  28. package/dist/consolidator/daemon.d.ts +88 -0
  29. package/dist/consolidator/daemon.d.ts.map +1 -0
  30. package/dist/consolidator/daemon.js +54 -0
  31. package/dist/consolidator/daemon.js.map +1 -0
  32. package/dist/consolidator/index.d.ts +2 -0
  33. package/dist/consolidator/index.js +3 -0
  34. package/dist/errors/index.d.ts +104 -0
  35. package/dist/errors/index.d.ts.map +1 -0
  36. package/dist/errors/index.js +131 -0
  37. package/dist/errors/index.js.map +1 -0
  38. package/dist/health/checks.d.ts +120 -0
  39. package/dist/health/checks.d.ts.map +1 -0
  40. package/dist/health/checks.js +127 -0
  41. package/dist/health/checks.js.map +1 -0
  42. package/dist/health/index.d.ts +3 -0
  43. package/dist/health/index.js +4 -0
  44. package/dist/health/routes.d.ts +66 -0
  45. package/dist/health/routes.d.ts.map +1 -0
  46. package/dist/health/routes.js +96 -0
  47. package/dist/health/routes.js.map +1 -0
  48. package/dist/index.d.ts +88 -0
  49. package/dist/index.d.ts.map +1 -0
  50. package/dist/index.js +86 -0
  51. package/dist/index.js.map +1 -0
  52. package/dist/internal/context.d.ts +66 -0
  53. package/dist/internal/context.d.ts.map +1 -0
  54. package/dist/internal/ids.js +21 -0
  55. package/dist/internal/ids.js.map +1 -0
  56. package/dist/internal/json.js +46 -0
  57. package/dist/internal/json.js.map +1 -0
  58. package/dist/lifecycle/hooks.d.ts +57 -0
  59. package/dist/lifecycle/hooks.d.ts.map +1 -0
  60. package/dist/lifecycle/index.d.ts +2 -0
  61. package/dist/lifecycle/index.js +3 -0
  62. package/dist/lifecycle/pre-bind.d.ts +38 -0
  63. package/dist/lifecycle/pre-bind.d.ts.map +1 -0
  64. package/dist/lifecycle/pre-bind.js +62 -0
  65. package/dist/lifecycle/pre-bind.js.map +1 -0
  66. package/dist/metrics/catalog.d.ts +34 -0
  67. package/dist/metrics/catalog.d.ts.map +1 -0
  68. package/dist/metrics/catalog.js +61 -0
  69. package/dist/metrics/catalog.js.map +1 -0
  70. package/dist/metrics/index.d.ts +3 -0
  71. package/dist/metrics/index.js +4 -0
  72. package/dist/metrics/registry.d.ts +63 -0
  73. package/dist/metrics/registry.d.ts.map +1 -0
  74. package/dist/metrics/registry.js +222 -0
  75. package/dist/metrics/registry.js.map +1 -0
  76. package/dist/middleware/audit.d.ts +47 -0
  77. package/dist/middleware/audit.d.ts.map +1 -0
  78. package/dist/middleware/audit.js +71 -0
  79. package/dist/middleware/audit.js.map +1 -0
  80. package/dist/middleware/auth.d.ts +50 -0
  81. package/dist/middleware/auth.d.ts.map +1 -0
  82. package/dist/middleware/auth.js +164 -0
  83. package/dist/middleware/auth.js.map +1 -0
  84. package/dist/middleware/cors.d.ts +15 -0
  85. package/dist/middleware/cors.d.ts.map +1 -0
  86. package/dist/middleware/cors.js +45 -0
  87. package/dist/middleware/cors.js.map +1 -0
  88. package/dist/middleware/csrf.d.ts +15 -0
  89. package/dist/middleware/csrf.d.ts.map +1 -0
  90. package/dist/middleware/csrf.js +77 -0
  91. package/dist/middleware/csrf.js.map +1 -0
  92. package/dist/middleware/idempotency.d.ts +41 -0
  93. package/dist/middleware/idempotency.d.ts.map +1 -0
  94. package/dist/middleware/idempotency.js +198 -0
  95. package/dist/middleware/idempotency.js.map +1 -0
  96. package/dist/middleware/index.d.ts +9 -0
  97. package/dist/middleware/index.js +10 -0
  98. package/dist/middleware/rate-limit.d.ts +17 -0
  99. package/dist/middleware/rate-limit.d.ts.map +1 -0
  100. package/dist/middleware/rate-limit.js +47 -0
  101. package/dist/middleware/rate-limit.js.map +1 -0
  102. package/dist/middleware/request-state.d.ts +27 -0
  103. package/dist/middleware/request-state.d.ts.map +1 -0
  104. package/dist/middleware/request-state.js +42 -0
  105. package/dist/middleware/request-state.js.map +1 -0
  106. package/dist/middleware/scope.d.ts +24 -0
  107. package/dist/middleware/scope.d.ts.map +1 -0
  108. package/dist/middleware/scope.js +50 -0
  109. package/dist/middleware/scope.js.map +1 -0
  110. package/dist/registry/index.d.ts +135 -0
  111. package/dist/registry/index.d.ts.map +1 -0
  112. package/dist/registry/index.js +96 -0
  113. package/dist/registry/index.js.map +1 -0
  114. package/dist/replay/index.d.ts +2 -0
  115. package/dist/replay/index.js +3 -0
  116. package/dist/replay/routes.d.ts +46 -0
  117. package/dist/replay/routes.d.ts.map +1 -0
  118. package/dist/replay/routes.js +189 -0
  119. package/dist/replay/routes.js.map +1 -0
  120. package/dist/routes/agents.d.ts +41 -0
  121. package/dist/routes/agents.d.ts.map +1 -0
  122. package/dist/routes/agents.js +213 -0
  123. package/dist/routes/agents.js.map +1 -0
  124. package/dist/routes/audit.d.ts +57 -0
  125. package/dist/routes/audit.d.ts.map +1 -0
  126. package/dist/routes/audit.js +116 -0
  127. package/dist/routes/audit.js.map +1 -0
  128. package/dist/routes/auth.d.ts +26 -0
  129. package/dist/routes/auth.d.ts.map +1 -0
  130. package/dist/routes/auth.js +54 -0
  131. package/dist/routes/auth.js.map +1 -0
  132. package/dist/routes/health.d.ts +22 -0
  133. package/dist/routes/health.d.ts.map +1 -0
  134. package/dist/routes/health.js +33 -0
  135. package/dist/routes/health.js.map +1 -0
  136. package/dist/routes/index.d.ts +10 -0
  137. package/dist/routes/index.js +12 -0
  138. package/dist/routes/mcp.d.ts +32 -0
  139. package/dist/routes/mcp.d.ts.map +1 -0
  140. package/dist/routes/mcp.js +61 -0
  141. package/dist/routes/mcp.js.map +1 -0
  142. package/dist/routes/memory.d.ts +141 -0
  143. package/dist/routes/memory.d.ts.map +1 -0
  144. package/dist/routes/memory.js +102 -0
  145. package/dist/routes/memory.js.map +1 -0
  146. package/dist/routes/sessions.d.ts +54 -0
  147. package/dist/routes/sessions.d.ts.map +1 -0
  148. package/dist/routes/sessions.js +135 -0
  149. package/dist/routes/sessions.js.map +1 -0
  150. package/dist/routes/skills.d.ts +34 -0
  151. package/dist/routes/skills.d.ts.map +1 -0
  152. package/dist/routes/skills.js +54 -0
  153. package/dist/routes/skills.js.map +1 -0
  154. package/dist/routes/tokens.d.ts +25 -0
  155. package/dist/routes/tokens.d.ts.map +1 -0
  156. package/dist/routes/tokens.js +87 -0
  157. package/dist/routes/tokens.js.map +1 -0
  158. package/dist/routes/workflows.d.ts +27 -0
  159. package/dist/routes/workflows.d.ts.map +1 -0
  160. package/dist/routes/workflows.js +220 -0
  161. package/dist/routes/workflows.js.map +1 -0
  162. package/dist/runtime/run-state.d.ts +158 -0
  163. package/dist/runtime/run-state.d.ts.map +1 -0
  164. package/dist/runtime/run-state.js +182 -0
  165. package/dist/runtime/run-state.js.map +1 -0
  166. package/dist/sse/events.d.ts +44 -0
  167. package/dist/sse/events.d.ts.map +1 -0
  168. package/dist/sse/events.js +200 -0
  169. package/dist/sse/events.js.map +1 -0
  170. package/dist/sse/index.d.ts +2 -0
  171. package/dist/sse/index.js +3 -0
  172. package/dist/triggers/daemon.d.ts +74 -0
  173. package/dist/triggers/daemon.d.ts.map +1 -0
  174. package/dist/triggers/daemon.js +114 -0
  175. package/dist/triggers/daemon.js.map +1 -0
  176. package/dist/triggers/index.d.ts +3 -0
  177. package/dist/triggers/index.js +4 -0
  178. package/dist/triggers/routes.d.ts +21 -0
  179. package/dist/triggers/routes.d.ts.map +1 -0
  180. package/dist/triggers/routes.js +117 -0
  181. package/dist/triggers/routes.js.map +1 -0
  182. package/dist/ws/dispatcher.d.ts +169 -0
  183. package/dist/ws/dispatcher.d.ts.map +1 -0
  184. package/dist/ws/dispatcher.js +303 -0
  185. package/dist/ws/dispatcher.js.map +1 -0
  186. package/dist/ws/index.d.ts +6 -0
  187. package/dist/ws/index.js +7 -0
  188. package/dist/ws/replay-buffer.d.ts +47 -0
  189. package/dist/ws/replay-buffer.d.ts.map +1 -0
  190. package/dist/ws/replay-buffer.js +88 -0
  191. package/dist/ws/replay-buffer.js.map +1 -0
  192. package/dist/ws/subjects.d.ts +71 -0
  193. package/dist/ws/subjects.d.ts.map +1 -0
  194. package/dist/ws/subjects.js +112 -0
  195. package/dist/ws/subjects.js.map +1 -0
  196. package/dist/ws/ticket.d.ts +74 -0
  197. package/dist/ws/ticket.d.ts.map +1 -0
  198. package/dist/ws/ticket.js +112 -0
  199. package/dist/ws/ticket.js.map +1 -0
  200. package/dist/ws/upgrade.d.ts +63 -0
  201. package/dist/ws/upgrade.d.ts.map +1 -0
  202. package/dist/ws/upgrade.js +324 -0
  203. package/dist/ws/upgrade.js.map +1 -0
  204. package/package.json +156 -0
@@ -0,0 +1,32 @@
1
+ import { ServerVariables } from "../internal/context.js";
2
+ import { Hono } from "hono";
3
+
4
+ //#region src/routes/mcp.d.ts
5
+
6
+ /**
7
+ * @stable
8
+ */
9
+ interface McpApi {
10
+ list(): Promise<ReadonlyArray<unknown>>;
11
+ register(input: {
12
+ readonly id: string;
13
+ readonly transport: string;
14
+ readonly url?: string;
15
+ }): Promise<unknown>;
16
+ remove(id: string): Promise<boolean>;
17
+ }
18
+ /**
19
+ * @stable
20
+ */
21
+ interface McpRoutesDeps {
22
+ readonly mcp: McpApi;
23
+ }
24
+ /**
25
+ * @stable
26
+ */
27
+ declare function createMcpRoutes(deps: McpRoutesDeps): Hono<{
28
+ Variables: ServerVariables;
29
+ }>;
30
+ //#endregion
31
+ export { McpApi, McpRoutesDeps, createMcpRoutes };
32
+ //# sourceMappingURL=mcp.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"mcp.d.ts","names":[],"sources":["../../src/routes/mcp.ts"],"sourcesContent":[],"mappings":";;;;;AAgDA;;;AAAsD,UA5BrC,MAAA,CA4BqC;EAAI,IAAA,EAAA,EA3BhD,OA2BgD,CA3BxC,aA2BwC,CAAA,OAAA,CAAA,CAAA;;;;;MAtBpD;sBACgB;;;;;UAcL,aAAA;gBACD;;;;;iBAMA,eAAA,OAAsB,gBAAgB;aAAkB"}
@@ -0,0 +1,61 @@
1
+ import { createScopeMiddleware } from "../middleware/scope.js";
2
+ import { Hono } from "hono";
3
+ import { z } from "zod";
4
+
5
+ //#region src/routes/mcp.ts
6
+ const RegisterBodySchema = z.object({
7
+ id: z.string().min(1),
8
+ transport: z.enum([
9
+ "stdio",
10
+ "streamable-http",
11
+ "sse"
12
+ ]),
13
+ url: z.string().min(1).optional()
14
+ }).strict();
15
+ /**
16
+ * @stable
17
+ */
18
+ function createMcpRoutes(deps) {
19
+ const app = new Hono();
20
+ app.get("/servers", createScopeMiddleware("mcp:admin"), async (c) => {
21
+ return c.json({ servers: await deps.mcp.list() });
22
+ });
23
+ app.post("/servers", createScopeMiddleware("mcp:admin"), async (c) => {
24
+ const parsed = RegisterBodySchema.safeParse(await safelyParseJson(c));
25
+ if (!parsed.success) return c.json({
26
+ error: "config-invalid",
27
+ message: "Invalid MCP server body.",
28
+ issues: parsed.error.issues.map((i) => ({
29
+ path: i.path,
30
+ message: i.message
31
+ }))
32
+ }, 400);
33
+ const payload = {
34
+ id: parsed.data.id,
35
+ transport: parsed.data.transport
36
+ };
37
+ if (parsed.data.url !== void 0) payload.url = parsed.data.url;
38
+ const out = await deps.mcp.register(payload);
39
+ return c.json({ server: out }, 201);
40
+ });
41
+ app.delete("/servers/:id", createScopeMiddleware("mcp:admin"), async (c) => {
42
+ const id = c.req.param("id");
43
+ if (!await deps.mcp.remove(id)) return c.json({
44
+ error: "mcp-server-not-found",
45
+ message: `MCP server '${id}' not found.`
46
+ }, 404);
47
+ return c.body(null, 204);
48
+ });
49
+ return app;
50
+ }
51
+ async function safelyParseJson(c) {
52
+ try {
53
+ return await c.req.json();
54
+ } catch {
55
+ return {};
56
+ }
57
+ }
58
+
59
+ //#endregion
60
+ export { createMcpRoutes };
61
+ //# sourceMappingURL=mcp.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"mcp.js","names":["payload: { id: string; transport: string; url?: string }"],"sources":["../../src/routes/mcp.ts"],"sourcesContent":["/**\n * MCP server-management REST routes.\n *\n * GET /mcp/servers (scope `mcp:admin`)\n * POST /mcp/servers (idempotent; scope `mcp:admin`)\n * DELETE /mcp/servers/:id (scope `mcp:admin`)\n *\n * @packageDocumentation\n */\n\nimport type { Context } from 'hono';\nimport { Hono } from 'hono';\nimport { z } from 'zod';\n\nimport type { ServerVariables } from '../internal/context.js';\nimport { createScopeMiddleware } from '../middleware/scope.js';\n\n/**\n * @stable\n */\nexport interface McpApi {\n list(): Promise<ReadonlyArray<unknown>>;\n register(input: {\n readonly id: string;\n readonly transport: string;\n readonly url?: string;\n }): Promise<unknown>;\n remove(id: string): Promise<boolean>;\n}\n\nconst RegisterBodySchema = z\n .object({\n id: z.string().min(1),\n transport: z.enum(['stdio', 'streamable-http', 'sse']),\n url: z.string().min(1).optional(),\n })\n .strict();\n\n/**\n * @stable\n */\nexport interface McpRoutesDeps {\n readonly mcp: McpApi;\n}\n\n/**\n * @stable\n */\nexport function createMcpRoutes(deps: McpRoutesDeps): Hono<{ Variables: ServerVariables }> {\n const app = new Hono<{ Variables: ServerVariables }>();\n\n app.get('/servers', createScopeMiddleware('mcp:admin'), async (c) => {\n return c.json({ servers: await deps.mcp.list() });\n });\n\n app.post('/servers', createScopeMiddleware('mcp:admin'), async (c) => {\n const parsed = RegisterBodySchema.safeParse(await safelyParseJson(c));\n if (!parsed.success) {\n return c.json(\n {\n error: 'config-invalid',\n message: 'Invalid MCP server body.',\n issues: parsed.error.issues.map((i) => ({ path: i.path, message: i.message })),\n },\n 400,\n );\n }\n const payload: { id: string; transport: string; url?: string } = {\n id: parsed.data.id,\n transport: parsed.data.transport,\n };\n if (parsed.data.url !== undefined) payload.url = parsed.data.url;\n const out = await deps.mcp.register(payload);\n return c.json({ server: out }, 201);\n });\n\n app.delete('/servers/:id', createScopeMiddleware('mcp:admin'), async (c) => {\n const id = c.req.param('id');\n const removed = await deps.mcp.remove(id);\n if (!removed)\n return c.json(\n { error: 'mcp-server-not-found', message: `MCP server '${id}' not found.` },\n 404,\n );\n return c.body(null, 204);\n });\n\n return app;\n}\n\nasync function safelyParseJson(c: Context<{ Variables: ServerVariables }>): Promise<unknown> {\n try {\n return await c.req.json();\n } catch {\n return {};\n }\n}\n"],"mappings":";;;;;AA8BA,MAAM,qBAAqB,EACxB,OAAO;CACN,IAAI,EAAE,QAAQ,CAAC,IAAI,EAAE;CACrB,WAAW,EAAE,KAAK;EAAC;EAAS;EAAmB;EAAM,CAAC;CACtD,KAAK,EAAE,QAAQ,CAAC,IAAI,EAAE,CAAC,UAAU;CAClC,CAAC,CACD,QAAQ;;;;AAYX,SAAgB,gBAAgB,MAA2D;CACzF,MAAM,MAAM,IAAI,MAAsC;AAEtD,KAAI,IAAI,YAAY,sBAAsB,YAAY,EAAE,OAAO,MAAM;AACnE,SAAO,EAAE,KAAK,EAAE,SAAS,MAAM,KAAK,IAAI,MAAM,EAAE,CAAC;GACjD;AAEF,KAAI,KAAK,YAAY,sBAAsB,YAAY,EAAE,OAAO,MAAM;EACpE,MAAM,SAAS,mBAAmB,UAAU,MAAM,gBAAgB,EAAE,CAAC;AACrE,MAAI,CAAC,OAAO,QACV,QAAO,EAAE,KACP;GACE,OAAO;GACP,SAAS;GACT,QAAQ,OAAO,MAAM,OAAO,KAAK,OAAO;IAAE,MAAM,EAAE;IAAM,SAAS,EAAE;IAAS,EAAE;GAC/E,EACD,IACD;EAEH,MAAMA,UAA2D;GAC/D,IAAI,OAAO,KAAK;GAChB,WAAW,OAAO,KAAK;GACxB;AACD,MAAI,OAAO,KAAK,QAAQ,OAAW,SAAQ,MAAM,OAAO,KAAK;EAC7D,MAAM,MAAM,MAAM,KAAK,IAAI,SAAS,QAAQ;AAC5C,SAAO,EAAE,KAAK,EAAE,QAAQ,KAAK,EAAE,IAAI;GACnC;AAEF,KAAI,OAAO,gBAAgB,sBAAsB,YAAY,EAAE,OAAO,MAAM;EAC1E,MAAM,KAAK,EAAE,IAAI,MAAM,KAAK;AAE5B,MAAI,CADY,MAAM,KAAK,IAAI,OAAO,GAAG,CAEvC,QAAO,EAAE,KACP;GAAE,OAAO;GAAwB,SAAS,eAAe,GAAG;GAAe,EAC3E,IACD;AACH,SAAO,EAAE,KAAK,MAAM,IAAI;GACxB;AAEF,QAAO;;AAGT,eAAe,gBAAgB,GAA8D;AAC3F,KAAI;AACF,SAAO,MAAM,EAAE,IAAI,MAAM;SACnB;AACN,SAAO,EAAE"}
@@ -0,0 +1,141 @@
1
+ import { ServerVariables } from "../internal/context.js";
2
+ import { Hono } from "hono";
3
+ import { z } from "zod";
4
+
5
+ //#region src/routes/memory.d.ts
6
+
7
+ declare const SearchBodySchema: z.ZodObject<{
8
+ scope: z.ZodObject<{
9
+ userId: z.ZodString;
10
+ agentId: z.ZodOptional<z.ZodString>;
11
+ sessionId: z.ZodOptional<z.ZodString>;
12
+ }, "strict", z.ZodTypeAny, {
13
+ userId: string;
14
+ agentId?: string | undefined;
15
+ sessionId?: string | undefined;
16
+ }, {
17
+ userId: string;
18
+ agentId?: string | undefined;
19
+ sessionId?: string | undefined;
20
+ }>;
21
+ query: z.ZodString;
22
+ topK: z.ZodOptional<z.ZodNumber>;
23
+ }, "strict", z.ZodTypeAny, {
24
+ scope: {
25
+ userId: string;
26
+ agentId?: string | undefined;
27
+ sessionId?: string | undefined;
28
+ };
29
+ query: string;
30
+ topK?: number | undefined;
31
+ }, {
32
+ scope: {
33
+ userId: string;
34
+ agentId?: string | undefined;
35
+ sessionId?: string | undefined;
36
+ };
37
+ query: string;
38
+ topK?: number | undefined;
39
+ }>;
40
+ declare const RememberBodySchema: z.ZodObject<{
41
+ scope: z.ZodObject<{
42
+ userId: z.ZodString;
43
+ agentId: z.ZodOptional<z.ZodString>;
44
+ sessionId: z.ZodOptional<z.ZodString>;
45
+ }, "strict", z.ZodTypeAny, {
46
+ userId: string;
47
+ agentId?: string | undefined;
48
+ sessionId?: string | undefined;
49
+ }, {
50
+ userId: string;
51
+ agentId?: string | undefined;
52
+ sessionId?: string | undefined;
53
+ }>;
54
+ text: z.ZodString;
55
+ sensitivity: z.ZodOptional<z.ZodEnum<["public", "internal", "secret"]>>;
56
+ metadata: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnknown>>;
57
+ }, "strict", z.ZodTypeAny, {
58
+ scope: {
59
+ userId: string;
60
+ agentId?: string | undefined;
61
+ sessionId?: string | undefined;
62
+ };
63
+ text: string;
64
+ sensitivity?: "public" | "internal" | "secret" | undefined;
65
+ metadata?: Record<string, unknown> | undefined;
66
+ }, {
67
+ scope: {
68
+ userId: string;
69
+ agentId?: string | undefined;
70
+ sessionId?: string | undefined;
71
+ };
72
+ text: string;
73
+ sensitivity?: "public" | "internal" | "secret" | undefined;
74
+ metadata?: Record<string, unknown> | undefined;
75
+ }>;
76
+ declare const BlockBodySchema: z.ZodObject<{
77
+ scope: z.ZodObject<{
78
+ userId: z.ZodString;
79
+ agentId: z.ZodOptional<z.ZodString>;
80
+ sessionId: z.ZodOptional<z.ZodString>;
81
+ }, "strict", z.ZodTypeAny, {
82
+ userId: string;
83
+ agentId?: string | undefined;
84
+ sessionId?: string | undefined;
85
+ }, {
86
+ userId: string;
87
+ agentId?: string | undefined;
88
+ sessionId?: string | undefined;
89
+ }>;
90
+ label: z.ZodString;
91
+ body: z.ZodString;
92
+ }, "strict", z.ZodTypeAny, {
93
+ scope: {
94
+ userId: string;
95
+ agentId?: string | undefined;
96
+ sessionId?: string | undefined;
97
+ };
98
+ label: string;
99
+ body: string;
100
+ }, {
101
+ scope: {
102
+ userId: string;
103
+ agentId?: string | undefined;
104
+ sessionId?: string | undefined;
105
+ };
106
+ label: string;
107
+ body: string;
108
+ }>;
109
+ /**
110
+ * @stable
111
+ */
112
+ interface MemoryApi {
113
+ search(input: z.infer<typeof SearchBodySchema>): Promise<ReadonlyArray<unknown>>;
114
+ remember(input: z.infer<typeof RememberBodySchema>): Promise<{
115
+ readonly factId: string;
116
+ }>;
117
+ forget(scope: {
118
+ readonly userId: string;
119
+ }, factId: string): Promise<boolean>;
120
+ upsertBlock(input: z.infer<typeof BlockBodySchema>): Promise<{
121
+ readonly label: string;
122
+ }>;
123
+ deleteBlock(scope: {
124
+ readonly userId: string;
125
+ }, label: string): Promise<boolean>;
126
+ }
127
+ /**
128
+ * @stable
129
+ */
130
+ interface MemoryRoutesDeps {
131
+ readonly memory: MemoryApi;
132
+ }
133
+ /**
134
+ * @stable
135
+ */
136
+ declare function createMemoryRoutes(deps: MemoryRoutesDeps): Hono<{
137
+ Variables: ServerVariables;
138
+ }>;
139
+ //#endregion
140
+ export { MemoryApi, MemoryRoutesDeps, createMemoryRoutes };
141
+ //# sourceMappingURL=memory.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"memory.d.ts","names":[],"sources":["../../src/routes/memory.ts"],"sourcesContent":[],"mappings":";;;;;;cA6BM,kBAAgB,CAAA,CAAA;EAAA,KAAA,aAAA,CAAA;IAAA,MAAA,aAAA;IAQhB,OAAA,eAOK,YAAA,CAAA;;;;;;;;;;;;;;;;;;EAPa,CAAA;EAAA,KAAA,EAAA,MAAA;EASlB,IAAA,CAAA,EAAA,MAAA,GAAA,SAMK;;;;;;;;;;cAfL,oBAAkB,CAAA,CAAA;EASH,KAAA,aAAA,CAAA;IAAA,MAAA,aAAA;IAWJ,OAAA,eAAS,YAAA,CAAA;IACK,SAAA,eAAA,YAAA,CAAA;EAAb,CAAA,EAAA,QAAA,cAAA,EAAA;IAAyC,MAAA,EAAA,MAAA;IAAR,OAAA,CAAA,EAAA,MAAA,GAAA,SAAA;IAClB,SAAA,CAAA,EAAA,MAAA,GAAA,SAAA;EAAb,CAAA,EAAA;IAAmC,MAAA,EAAA,MAAA;IACO,OAAA,CAAA,EAAA,MAAA,GAAA,SAAA;IAC1B,SAAA,CAAA,EAAA,MAAA,GAAA,SAAA;EAAb,CAAA,CAAA;EAAgC,IAAA,aAAA;EACW,WAAA,eAAA,UAAA,CAAA,CAAA,QAAA,EAAA,UAAA,EAAA,QAAA,CAAA,CAAA,CAAA;EAAO,QAAA,eAAA,YAAA,YAAA,cAAA,CAAA,CAAA;AAMzE,CAAA,EAAA,QAAiB,cAAgB,EAAA;EAOjB,KAAA,EAAA;IAAyB,MAAA,EAAA,MAAA;IAAqC,OAAA,CAAA,EAAA,MAAA,GAAA,SAAA;IAAlB,SAAA,CAAA,EAAA,MAAA,GAAA,SAAA;EAAI,CAAA;;;;;;;;;;;;;;cA7B1D,iBAAe,CAAA,CAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;UAWJ,SAAA;gBACD,CAAA,CAAE,aAAa,oBAAoB,QAAQ;kBACzC,CAAA,CAAE,aAAa,sBAAsB;;;;;sBACO;qBACzC,CAAA,CAAE,aAAa,mBAAmB;;;;;qBACW;;;;;UAMjD,gBAAA;mBACE;;;;;iBAMH,kBAAA,OAAyB,mBAAmB;aAAkB"}
@@ -0,0 +1,102 @@
1
+ import { createScopeMiddleware } from "../middleware/scope.js";
2
+ import { Hono } from "hono";
3
+ import { z } from "zod";
4
+
5
+ //#region src/routes/memory.ts
6
+ const ScopeSchema = z.object({
7
+ userId: z.string().min(1),
8
+ agentId: z.string().min(1).optional(),
9
+ sessionId: z.string().min(1).optional()
10
+ }).strict();
11
+ const SearchBodySchema = z.object({
12
+ scope: ScopeSchema,
13
+ query: z.string().min(1),
14
+ topK: z.number().int().positive().max(200).optional()
15
+ }).strict();
16
+ const RememberBodySchema = z.object({
17
+ scope: ScopeSchema,
18
+ text: z.string().min(1),
19
+ sensitivity: z.enum([
20
+ "public",
21
+ "internal",
22
+ "secret"
23
+ ]).optional(),
24
+ metadata: z.record(z.string(), z.unknown()).optional()
25
+ }).strict();
26
+ const BlockBodySchema = z.object({
27
+ scope: ScopeSchema,
28
+ label: z.string().min(1),
29
+ body: z.string()
30
+ }).strict();
31
+ /**
32
+ * @stable
33
+ */
34
+ function createMemoryRoutes(deps) {
35
+ const app = new Hono();
36
+ app.post("/search", createScopeMiddleware("memory:read"), async (c) => {
37
+ const parsed = SearchBodySchema.safeParse(await safelyParseJson(c));
38
+ if (!parsed.success) return invalid(c, parsed.error.issues);
39
+ const hits = await deps.memory.search(parsed.data);
40
+ return c.json({ hits });
41
+ });
42
+ app.post("/facts", createScopeMiddleware("memory:write"), async (c) => {
43
+ const parsed = RememberBodySchema.safeParse(await safelyParseJson(c));
44
+ if (!parsed.success) return invalid(c, parsed.error.issues);
45
+ const out = await deps.memory.remember(parsed.data);
46
+ return c.json({ fact: out }, 201);
47
+ });
48
+ app.delete("/facts/:id", createScopeMiddleware("memory:write"), async (c) => {
49
+ const id = c.req.param("id");
50
+ const userId = c.req.query("userId");
51
+ if (userId === void 0 || userId.length === 0) return c.json({
52
+ error: "config-invalid",
53
+ message: "Query parameter `userId` is required."
54
+ }, 400);
55
+ if (!await deps.memory.forget({ userId }, id)) return c.json({
56
+ error: "fact-not-found",
57
+ message: `Fact '${id}' not found.`
58
+ }, 404);
59
+ return c.body(null, 204);
60
+ });
61
+ app.post("/blocks", createScopeMiddleware("memory:write"), async (c) => {
62
+ const parsed = BlockBodySchema.safeParse(await safelyParseJson(c));
63
+ if (!parsed.success) return invalid(c, parsed.error.issues);
64
+ const out = await deps.memory.upsertBlock(parsed.data);
65
+ return c.json({ block: out }, 201);
66
+ });
67
+ app.delete("/blocks/:label", createScopeMiddleware("memory:write"), async (c) => {
68
+ const label = c.req.param("label");
69
+ const userId = c.req.query("userId");
70
+ if (userId === void 0 || userId.length === 0) return c.json({
71
+ error: "config-invalid",
72
+ message: "Query parameter `userId` is required."
73
+ }, 400);
74
+ if (!await deps.memory.deleteBlock({ userId }, label)) return c.json({
75
+ error: "block-not-found",
76
+ message: `Block '${label}' not found.`
77
+ }, 404);
78
+ return c.body(null, 204);
79
+ });
80
+ return app;
81
+ }
82
+ function invalid(c, issues) {
83
+ return c.json({
84
+ error: "config-invalid",
85
+ message: "Invalid request body.",
86
+ issues: issues.map((i) => ({
87
+ path: i.path,
88
+ message: i.message
89
+ }))
90
+ }, 400);
91
+ }
92
+ async function safelyParseJson(c) {
93
+ try {
94
+ return await c.req.json();
95
+ } catch {
96
+ return {};
97
+ }
98
+ }
99
+
100
+ //#endregion
101
+ export { createMemoryRoutes };
102
+ //# sourceMappingURL=memory.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"memory.js","names":[],"sources":["../../src/routes/memory.ts"],"sourcesContent":["/**\n * Memory REST routes. The handlers delegate to a structurally-typed\n * `MemoryApi` provided by the operator (in practice, a thin shim\n * around `@graphorin/memory.createMemory({...})`).\n *\n * POST /memory/search (scope `memory:read`)\n * POST /memory/facts (idempotent; scope `memory:write`)\n * DELETE /memory/facts/:id (scope `memory:write`)\n * POST /memory/blocks (idempotent; scope `memory:write`)\n * DELETE /memory/blocks/:label (scope `memory:write`)\n *\n * @packageDocumentation\n */\n\nimport type { Context } from 'hono';\nimport { Hono } from 'hono';\nimport { z } from 'zod';\n\nimport type { ServerVariables } from '../internal/context.js';\nimport { createScopeMiddleware } from '../middleware/scope.js';\n\nconst ScopeSchema = z\n .object({\n userId: z.string().min(1),\n agentId: z.string().min(1).optional(),\n sessionId: z.string().min(1).optional(),\n })\n .strict();\n\nconst SearchBodySchema = z\n .object({\n scope: ScopeSchema,\n query: z.string().min(1),\n topK: z.number().int().positive().max(200).optional(),\n })\n .strict();\n\nconst RememberBodySchema = z\n .object({\n scope: ScopeSchema,\n text: z.string().min(1),\n sensitivity: z.enum(['public', 'internal', 'secret']).optional(),\n metadata: z.record(z.string(), z.unknown()).optional(),\n })\n .strict();\n\nconst BlockBodySchema = z\n .object({\n scope: ScopeSchema,\n label: z.string().min(1),\n body: z.string(),\n })\n .strict();\n\n/**\n * @stable\n */\nexport interface MemoryApi {\n search(input: z.infer<typeof SearchBodySchema>): Promise<ReadonlyArray<unknown>>;\n remember(input: z.infer<typeof RememberBodySchema>): Promise<{ readonly factId: string }>;\n forget(scope: { readonly userId: string }, factId: string): Promise<boolean>;\n upsertBlock(input: z.infer<typeof BlockBodySchema>): Promise<{ readonly label: string }>;\n deleteBlock(scope: { readonly userId: string }, label: string): Promise<boolean>;\n}\n\n/**\n * @stable\n */\nexport interface MemoryRoutesDeps {\n readonly memory: MemoryApi;\n}\n\n/**\n * @stable\n */\nexport function createMemoryRoutes(deps: MemoryRoutesDeps): Hono<{ Variables: ServerVariables }> {\n const app = new Hono<{ Variables: ServerVariables }>();\n\n app.post('/search', createScopeMiddleware('memory:read'), async (c) => {\n const parsed = SearchBodySchema.safeParse(await safelyParseJson(c));\n if (!parsed.success) {\n return invalid(c, parsed.error.issues);\n }\n const hits = await deps.memory.search(parsed.data);\n return c.json({ hits });\n });\n\n app.post('/facts', createScopeMiddleware('memory:write'), async (c) => {\n const parsed = RememberBodySchema.safeParse(await safelyParseJson(c));\n if (!parsed.success) return invalid(c, parsed.error.issues);\n const out = await deps.memory.remember(parsed.data);\n return c.json({ fact: out }, 201);\n });\n\n app.delete('/facts/:id', createScopeMiddleware('memory:write'), async (c) => {\n const id = c.req.param('id');\n const userId = c.req.query('userId');\n if (userId === undefined || userId.length === 0) {\n return c.json(\n { error: 'config-invalid', message: 'Query parameter `userId` is required.' },\n 400,\n );\n }\n const removed = await deps.memory.forget({ userId }, id);\n if (!removed)\n return c.json({ error: 'fact-not-found', message: `Fact '${id}' not found.` }, 404);\n return c.body(null, 204);\n });\n\n app.post('/blocks', createScopeMiddleware('memory:write'), async (c) => {\n const parsed = BlockBodySchema.safeParse(await safelyParseJson(c));\n if (!parsed.success) return invalid(c, parsed.error.issues);\n const out = await deps.memory.upsertBlock(parsed.data);\n return c.json({ block: out }, 201);\n });\n\n app.delete('/blocks/:label', createScopeMiddleware('memory:write'), async (c) => {\n const label = c.req.param('label');\n const userId = c.req.query('userId');\n if (userId === undefined || userId.length === 0) {\n return c.json(\n { error: 'config-invalid', message: 'Query parameter `userId` is required.' },\n 400,\n );\n }\n const removed = await deps.memory.deleteBlock({ userId }, label);\n if (!removed)\n return c.json({ error: 'block-not-found', message: `Block '${label}' not found.` }, 404);\n return c.body(null, 204);\n });\n\n return app;\n}\n\nfunction invalid(c: Context<{ Variables: ServerVariables }>, issues: ReadonlyArray<z.ZodIssue>) {\n return c.json(\n {\n error: 'config-invalid',\n message: 'Invalid request body.',\n issues: issues.map((i) => ({ path: i.path, message: i.message })),\n },\n 400,\n );\n}\n\nasync function safelyParseJson(c: Context<{ Variables: ServerVariables }>): Promise<unknown> {\n try {\n return await c.req.json();\n } catch {\n return {};\n }\n}\n"],"mappings":"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"}
@@ -0,0 +1,54 @@
1
+ import { ServerVariables } from "../internal/context.js";
2
+ import { Hono } from "hono";
3
+
4
+ //#region src/routes/sessions.d.ts
5
+
6
+ /**
7
+ * Minimal contract route handlers consume. Real deployments wire
8
+ * `@graphorin/sessions.SessionManager` in directly; tests pass a
9
+ * lighter stub.
10
+ *
11
+ * @stable
12
+ */
13
+ interface SessionApi {
14
+ list(opts: {
15
+ readonly userId?: string;
16
+ readonly agentId?: string;
17
+ }): Promise<ReadonlyArray<unknown>>;
18
+ get(sessionId: string): Promise<unknown | null>;
19
+ create(input: {
20
+ readonly userId: string;
21
+ readonly agentId: string;
22
+ readonly sessionId?: string;
23
+ readonly title?: string;
24
+ readonly tags?: ReadonlyArray<string>;
25
+ }): Promise<unknown>;
26
+ remove(sessionId: string): Promise<boolean>;
27
+ listMessages(sessionId: string, opts: {
28
+ readonly limit?: number;
29
+ }): Promise<ReadonlyArray<unknown>>;
30
+ listHandoffs(sessionId: string): Promise<ReadonlyArray<unknown>>;
31
+ exportSession?(sessionId: string, opts: {
32
+ readonly includeAuditEntries?: boolean;
33
+ readonly hash?: boolean;
34
+ }): Promise<unknown>;
35
+ replaySession?(sessionId: string, opts: {
36
+ readonly raw?: boolean;
37
+ readonly fromMessageId?: string;
38
+ }): AsyncIterable<unknown>;
39
+ }
40
+ /**
41
+ * @stable
42
+ */
43
+ interface SessionRoutesDeps {
44
+ readonly sessions: SessionApi;
45
+ }
46
+ /**
47
+ * @stable
48
+ */
49
+ declare function createSessionRoutes(deps: SessionRoutesDeps): Hono<{
50
+ Variables: ServerVariables;
51
+ }>;
52
+ //#endregion
53
+ export { SessionApi, SessionRoutesDeps, createSessionRoutes };
54
+ //# sourceMappingURL=sessions.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sessions.d.ts","names":[],"sources":["../../src/routes/sessions.ts"],"sourcesContent":[],"mappings":";;;;;AAkGA;AAOA;;;;;;UA1EiB,UAAA;;;;MAIX,QAAQ;0BACY;;;;;;oBAMN;MACd;6BACuB;;;MAIxB,QAAQ;mCACsB,QAAQ;;;;MAOtC;;;;MAIA;;;;;UAsCY,iBAAA;qBACI;;;;;iBAML,mBAAA,OAA0B,oBAAoB;aAAkB"}
@@ -0,0 +1,135 @@
1
+ import { createScopeMiddleware } from "../middleware/scope.js";
2
+ import { Hono } from "hono";
3
+ import { z } from "zod";
4
+
5
+ //#region src/routes/sessions.ts
6
+ const CreateBodySchema = z.object({
7
+ userId: z.string().min(1),
8
+ agentId: z.string().min(1),
9
+ sessionId: z.string().min(1).optional(),
10
+ title: z.string().min(1).optional(),
11
+ tags: z.array(z.string()).optional()
12
+ }).strict();
13
+ const MessagesQuerySchema = z.object({ limit: z.coerce.number().int().positive().max(1e3).optional() }).strict();
14
+ const ExportBodySchema = z.object({
15
+ includeAuditEntries: z.boolean().optional(),
16
+ hash: z.boolean().optional()
17
+ }).strict().default({});
18
+ z.object({
19
+ raw: z.boolean().optional(),
20
+ fromMessageId: z.string().min(1).optional()
21
+ }).strict().default({});
22
+ /**
23
+ * @stable
24
+ */
25
+ function createSessionRoutes(deps) {
26
+ const app = new Hono();
27
+ app.get("/", createScopeMiddleware("sessions:read"), async (c) => {
28
+ const userId = c.req.query("userId");
29
+ const agentId = c.req.query("agentId");
30
+ const filter = {};
31
+ if (userId !== void 0 && userId.length > 0) filter.userId = userId;
32
+ if (agentId !== void 0 && agentId.length > 0) filter.agentId = agentId;
33
+ const list = await deps.sessions.list(filter);
34
+ return c.json({ sessions: list });
35
+ });
36
+ app.post("/", createScopeMiddleware("sessions:write"), async (c) => {
37
+ const parsed = CreateBodySchema.safeParse(await safelyParseJson(c));
38
+ if (!parsed.success) return c.json({
39
+ error: "config-invalid",
40
+ message: "Invalid session body.",
41
+ issues: parsed.error.issues.map((i) => ({
42
+ path: i.path,
43
+ message: i.message
44
+ }))
45
+ }, 400);
46
+ const session = await deps.sessions.create({
47
+ userId: parsed.data.userId,
48
+ agentId: parsed.data.agentId,
49
+ ...parsed.data.sessionId !== void 0 ? { sessionId: parsed.data.sessionId } : {},
50
+ ...parsed.data.title !== void 0 ? { title: parsed.data.title } : {},
51
+ ...parsed.data.tags !== void 0 ? { tags: parsed.data.tags } : {}
52
+ });
53
+ return c.json({ session }, 201);
54
+ });
55
+ app.get("/:id", createScopeMiddleware("sessions:read"), async (c) => {
56
+ const id = c.req.param("id");
57
+ const session = await deps.sessions.get(id);
58
+ if (session === null) return c.json({
59
+ error: "session-not-found",
60
+ message: `Session '${id}' not found.`
61
+ }, 404);
62
+ return c.json({ session });
63
+ });
64
+ app.delete("/:id", createScopeMiddleware("sessions:write"), async (c) => {
65
+ const id = c.req.param("id");
66
+ if (!await deps.sessions.remove(id)) return c.json({
67
+ error: "session-not-found",
68
+ message: `Session '${id}' not found.`
69
+ }, 404);
70
+ return c.body(null, 204);
71
+ });
72
+ app.get("/:id/messages", createScopeMiddleware("sessions:read"), async (c) => {
73
+ const id = c.req.param("id");
74
+ const parsed = MessagesQuerySchema.safeParse({ limit: c.req.query("limit") });
75
+ if (!parsed.success) return c.json({
76
+ error: "config-invalid",
77
+ message: "Invalid messages query.",
78
+ issues: parsed.error.issues.map((i) => ({
79
+ path: i.path,
80
+ message: i.message
81
+ }))
82
+ }, 400);
83
+ const opts = {};
84
+ if (parsed.data.limit !== void 0) opts.limit = parsed.data.limit;
85
+ const messages = await deps.sessions.listMessages(id, opts);
86
+ return c.json({
87
+ sessionId: id,
88
+ messages
89
+ });
90
+ });
91
+ app.get("/:id/handoffs", createScopeMiddleware("sessions:read"), async (c) => {
92
+ const id = c.req.param("id");
93
+ const handoffs = await deps.sessions.listHandoffs(id);
94
+ return c.json({
95
+ sessionId: id,
96
+ handoffs
97
+ });
98
+ });
99
+ app.post("/:id/export", createScopeMiddleware("sessions:export"), async (c) => {
100
+ const id = c.req.param("id");
101
+ if (deps.sessions.exportSession === void 0) return c.json({
102
+ error: "session-export-unsupported",
103
+ message: "Export is not enabled."
104
+ }, 400);
105
+ const parsed = ExportBodySchema.safeParse(await safelyParseJson(c));
106
+ if (!parsed.success) return c.json({
107
+ error: "config-invalid",
108
+ message: "Invalid export body.",
109
+ issues: parsed.error.issues.map((i) => ({
110
+ path: i.path,
111
+ message: i.message
112
+ }))
113
+ }, 400);
114
+ const exportOpts = {};
115
+ if (parsed.data.includeAuditEntries !== void 0) exportOpts.includeAuditEntries = parsed.data.includeAuditEntries;
116
+ if (parsed.data.hash !== void 0) exportOpts.hash = parsed.data.hash;
117
+ const result = await deps.sessions.exportSession(id, exportOpts);
118
+ return c.json({
119
+ sessionId: id,
120
+ export: result
121
+ });
122
+ });
123
+ return app;
124
+ }
125
+ async function safelyParseJson(c) {
126
+ try {
127
+ return await c.req.json();
128
+ } catch {
129
+ return {};
130
+ }
131
+ }
132
+
133
+ //#endregion
134
+ export { createSessionRoutes };
135
+ //# sourceMappingURL=sessions.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sessions.js","names":["filter: { userId?: string; agentId?: string }","opts: { limit?: number }","exportOpts: { includeAuditEntries?: boolean; hash?: boolean }"],"sources":["../../src/routes/sessions.ts"],"sourcesContent":["/**\n * Session REST routes. Delegates to a structurally-typed `SessionApi`\n * supplied by the operator (in practice, the `@graphorin/sessions`\n * package's `SessionManager`); the contract is intentionally open so\n * tests can stub it without dragging the full sessions facade in.\n *\n * GET /sessions (scope `sessions:read`)\n * GET /sessions/:id (scope `sessions:read`)\n * POST /sessions (idempotent; scope `sessions:write`)\n * DELETE /sessions/:id (scope `sessions:write`)\n * GET /sessions/:id/messages (scope `sessions:read`)\n * GET /sessions/:id/handoffs (scope `sessions:read`)\n * POST /sessions/:id/export (scope `sessions:export`)\n *\n * @packageDocumentation\n */\n\nimport type { Context } from 'hono';\nimport { Hono } from 'hono';\nimport { z } from 'zod';\n\nimport type { ServerVariables } from '../internal/context.js';\nimport { createScopeMiddleware } from '../middleware/scope.js';\n\n/**\n * Minimal contract route handlers consume. Real deployments wire\n * `@graphorin/sessions.SessionManager` in directly; tests pass a\n * lighter stub.\n *\n * @stable\n */\nexport interface SessionApi {\n list(opts: {\n readonly userId?: string;\n readonly agentId?: string;\n }): Promise<ReadonlyArray<unknown>>;\n get(sessionId: string): Promise<unknown | null>;\n create(input: {\n readonly userId: string;\n readonly agentId: string;\n readonly sessionId?: string;\n readonly title?: string;\n readonly tags?: ReadonlyArray<string>;\n }): Promise<unknown>;\n remove(sessionId: string): Promise<boolean>;\n listMessages(\n sessionId: string,\n opts: { readonly limit?: number },\n ): Promise<ReadonlyArray<unknown>>;\n listHandoffs(sessionId: string): Promise<ReadonlyArray<unknown>>;\n exportSession?(\n sessionId: string,\n opts: {\n readonly includeAuditEntries?: boolean;\n readonly hash?: boolean;\n },\n ): Promise<unknown>;\n replaySession?(\n sessionId: string,\n opts: { readonly raw?: boolean; readonly fromMessageId?: string },\n ): AsyncIterable<unknown>;\n}\n\nconst CreateBodySchema = z\n .object({\n userId: z.string().min(1),\n agentId: z.string().min(1),\n sessionId: z.string().min(1).optional(),\n title: z.string().min(1).optional(),\n tags: z.array(z.string()).optional(),\n })\n .strict();\n\nconst MessagesQuerySchema = z\n .object({\n limit: z.coerce.number().int().positive().max(1000).optional(),\n })\n .strict();\n\nconst ExportBodySchema = z\n .object({\n includeAuditEntries: z.boolean().optional(),\n hash: z.boolean().optional(),\n })\n .strict()\n .default({});\n\nconst _ReplayBodySchema = z\n .object({\n raw: z.boolean().optional(),\n fromMessageId: z.string().min(1).optional(),\n })\n .strict()\n .default({});\n\n/**\n * @stable\n */\nexport interface SessionRoutesDeps {\n readonly sessions: SessionApi;\n}\n\n/**\n * @stable\n */\nexport function createSessionRoutes(deps: SessionRoutesDeps): Hono<{ Variables: ServerVariables }> {\n const app = new Hono<{ Variables: ServerVariables }>();\n\n app.get('/', createScopeMiddleware('sessions:read'), async (c) => {\n const userId = c.req.query('userId');\n const agentId = c.req.query('agentId');\n const filter: { userId?: string; agentId?: string } = {};\n if (userId !== undefined && userId.length > 0) filter.userId = userId;\n if (agentId !== undefined && agentId.length > 0) filter.agentId = agentId;\n const list = await deps.sessions.list(filter);\n return c.json({ sessions: list });\n });\n\n app.post('/', createScopeMiddleware('sessions:write'), async (c) => {\n const parsed = CreateBodySchema.safeParse(await safelyParseJson(c));\n if (!parsed.success) {\n return c.json(\n {\n error: 'config-invalid',\n message: 'Invalid session body.',\n issues: parsed.error.issues.map((i) => ({ path: i.path, message: i.message })),\n },\n 400,\n );\n }\n const session = await deps.sessions.create({\n userId: parsed.data.userId,\n agentId: parsed.data.agentId,\n ...(parsed.data.sessionId !== undefined ? { sessionId: parsed.data.sessionId } : {}),\n ...(parsed.data.title !== undefined ? { title: parsed.data.title } : {}),\n ...(parsed.data.tags !== undefined ? { tags: parsed.data.tags } : {}),\n });\n return c.json({ session }, 201);\n });\n\n app.get('/:id', createScopeMiddleware('sessions:read'), async (c) => {\n const id = c.req.param('id');\n const session = await deps.sessions.get(id);\n if (session === null) {\n return c.json({ error: 'session-not-found', message: `Session '${id}' not found.` }, 404);\n }\n return c.json({ session });\n });\n\n app.delete('/:id', createScopeMiddleware('sessions:write'), async (c) => {\n const id = c.req.param('id');\n const removed = await deps.sessions.remove(id);\n if (!removed) {\n return c.json({ error: 'session-not-found', message: `Session '${id}' not found.` }, 404);\n }\n return c.body(null, 204);\n });\n\n app.get('/:id/messages', createScopeMiddleware('sessions:read'), async (c) => {\n const id = c.req.param('id');\n const parsed = MessagesQuerySchema.safeParse({ limit: c.req.query('limit') });\n if (!parsed.success) {\n return c.json(\n {\n error: 'config-invalid',\n message: 'Invalid messages query.',\n issues: parsed.error.issues.map((i) => ({ path: i.path, message: i.message })),\n },\n 400,\n );\n }\n const opts: { limit?: number } = {};\n if (parsed.data.limit !== undefined) opts.limit = parsed.data.limit;\n const messages = await deps.sessions.listMessages(id, opts);\n return c.json({ sessionId: id, messages });\n });\n\n app.get('/:id/handoffs', createScopeMiddleware('sessions:read'), async (c) => {\n const id = c.req.param('id');\n const handoffs = await deps.sessions.listHandoffs(id);\n return c.json({ sessionId: id, handoffs });\n });\n\n app.post('/:id/export', createScopeMiddleware('sessions:export'), async (c) => {\n const id = c.req.param('id');\n if (deps.sessions.exportSession === undefined) {\n return c.json(\n { error: 'session-export-unsupported', message: 'Export is not enabled.' },\n 400,\n );\n }\n const parsed = ExportBodySchema.safeParse(await safelyParseJson(c));\n if (!parsed.success) {\n return c.json(\n {\n error: 'config-invalid',\n message: 'Invalid export body.',\n issues: parsed.error.issues.map((i) => ({ path: i.path, message: i.message })),\n },\n 400,\n );\n }\n const exportOpts: { includeAuditEntries?: boolean; hash?: boolean } = {};\n if (parsed.data.includeAuditEntries !== undefined) {\n exportOpts.includeAuditEntries = parsed.data.includeAuditEntries;\n }\n if (parsed.data.hash !== undefined) exportOpts.hash = parsed.data.hash;\n const result = await deps.sessions.exportSession(id, exportOpts);\n return c.json({ sessionId: id, export: result });\n });\n\n // IP-14: the session-replay route lives in `replay/routes.ts` (the\n // scope-laddered, audit-backed implementation). The Phase-14a stub\n // that lived here SHADOWED it (mounted earlier on the same path)\n // while advertising a `session:<id>/replay` subject the WS grammar\n // cannot parse — deleted.\n\n return app;\n}\n\nasync function safelyParseJson(c: Context<{ Variables: ServerVariables }>): Promise<unknown> {\n try {\n return await c.req.json();\n } catch {\n return {};\n }\n}\n"],"mappings":"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"}
@@ -0,0 +1,34 @@
1
+ import { ServerVariables } from "../internal/context.js";
2
+ import { Hono } from "hono";
3
+
4
+ //#region src/routes/skills.d.ts
5
+
6
+ /**
7
+ * @stable
8
+ */
9
+ interface SkillsApi {
10
+ list(): Promise<ReadonlyArray<{
11
+ readonly name: string;
12
+ readonly version?: string;
13
+ }>>;
14
+ get(name: string): Promise<unknown | null>;
15
+ install(input: {
16
+ readonly source: string;
17
+ readonly trust?: 'verified' | 'unverified';
18
+ }): Promise<unknown>;
19
+ }
20
+ /**
21
+ * @stable
22
+ */
23
+ interface SkillsRoutesDeps {
24
+ readonly skills: SkillsApi;
25
+ }
26
+ /**
27
+ * @stable
28
+ */
29
+ declare function createSkillsRoutes(deps: SkillsRoutesDeps): Hono<{
30
+ Variables: ServerVariables;
31
+ }>;
32
+ //#endregion
33
+ export { SkillsApi, SkillsRoutesDeps, createSkillsRoutes };
34
+ //# sourceMappingURL=skills.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"skills.d.ts","names":[],"sources":["../../src/routes/skills.ts"],"sourcesContent":[],"mappings":";;;;;AA8CA;;;AAA4D,UA1B3C,SAAA,CA0B2C;EAAI,IAAA,EAAA,EAzBtD,OAyBsD,CAzB9C,aAyB8C,CAAA;;;;qBAxB3C;;;;MAIf;;;;;UAaW,gBAAA;mBACE;;;;;iBAMH,kBAAA,OAAyB,mBAAmB;aAAkB"}