@reddb-io/ui-mcp 0.1.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/LICENSE ADDED
@@ -0,0 +1,17 @@
1
+ Apache License
2
+ Version 2.0, January 2004
3
+ http://www.apache.org/licenses/
4
+
5
+ Copyright 2026 reddb-io
6
+
7
+ Licensed under the Apache License, Version 2.0 (the "License");
8
+ you may not use this file except in compliance with the License.
9
+ You may obtain a copy of the License at
10
+
11
+ http://www.apache.org/licenses/LICENSE-2.0
12
+
13
+ Unless required by applicable law or agreed to in writing, software
14
+ distributed under the License is on an "AS IS" BASIS,
15
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16
+ See the License for the specific language governing permissions and
17
+ limitations under the License.
@@ -0,0 +1,20 @@
1
+ import { type TargetMode } from "./target-mode.js";
2
+ export interface ResolvedConnection {
3
+ /** http(s) base URL the RedClient fetches. Non-secret (ADR-0005). */
4
+ baseUrl: string;
5
+ /** Auth headers for the client. Never logged, never returned to the model. */
6
+ headers?: Record<string, string>;
7
+ mode: TargetMode;
8
+ }
9
+ export interface ResolveConnectionOptions {
10
+ /** Default target when the tool call omits `connectionUrl`. */
11
+ defaultUrl?: string;
12
+ /** Auth header value applied to remote requests (never logged/returned). */
13
+ authHeader?: string;
14
+ }
15
+ /**
16
+ * Resolve a tool-supplied (or configured) target into a reachable endpoint.
17
+ * Throws for a local-file target (#48 unimplemented) and for an absent target
18
+ * with no configured default — the data tools need a concrete server to read.
19
+ */
20
+ export declare function resolveConnection(target: string | undefined, opts?: ResolveConnectionOptions): ResolvedConnection;
@@ -0,0 +1,61 @@
1
+ // Connection resolution for the MCP data tools (#49, ADR-0006).
2
+ //
3
+ // A data tool receives an optional `connectionUrl`; combined with the configured
4
+ // default it resolves to a concrete reddb endpoint the server-side RedClient can
5
+ // reach. Two modes (ADR-0006, mirrors `open_red_ui`):
6
+ // - REMOTE: an http(s):// or red(s):// URL. red:// is an http(s) alias
7
+ // (ADR-0003); we normalise it to http(s) so `fetch` can reach it.
8
+ // - LOCAL: a filesystem path / file:// / *.rdb. Per ADR-0006 the MCP must spawn
9
+ // a local `red server` in front of the file and talk to it over
10
+ // http://localhost — but that spawn is issue #48 and not implemented yet, so
11
+ // resolving a local target throws a clear "not yet" error. This is the seam
12
+ // #48 plugs into: it will return the spawned server's baseUrl here.
13
+ //
14
+ // The resolved auth header (if any) is carried in `headers` and never surfaces in
15
+ // tool output or logs — secrets never ride the URL (ADR-0005).
16
+ import { classifyTarget } from "./target-mode.js";
17
+ /** Translate a `red(s)://` alias to its http(s) equivalent; pass other schemes
18
+ * through. red:// → http://, reds:// → https:// (ADR-0003). */
19
+ function normalizeRemoteUrl(target) {
20
+ const t = target.trim();
21
+ const lower = t.toLowerCase();
22
+ let url;
23
+ if (lower.startsWith("red://")) {
24
+ url = new URL("http://" + t.slice("red://".length));
25
+ }
26
+ else if (lower.startsWith("reds://")) {
27
+ url = new URL("https://" + t.slice("reds://".length));
28
+ }
29
+ else if (/^https?:\/\//i.test(t)) {
30
+ url = new URL(t);
31
+ }
32
+ else {
33
+ // Bare host:port / hostname — default to http (matches the UI's normalizer).
34
+ url = new URL("http://" + t);
35
+ }
36
+ if (url.protocol !== "http:" && url.protocol !== "https:") {
37
+ throw new Error(`Unsupported connection scheme: ${target}`);
38
+ }
39
+ url.hash = "";
40
+ return url.toString().replace(/\/$/, "");
41
+ }
42
+ /**
43
+ * Resolve a tool-supplied (or configured) target into a reachable endpoint.
44
+ * Throws for a local-file target (#48 unimplemented) and for an absent target
45
+ * with no configured default — the data tools need a concrete server to read.
46
+ */
47
+ export function resolveConnection(target, opts = {}) {
48
+ const raw = (target ?? "").trim() || (opts.defaultUrl ?? "").trim();
49
+ if (!raw) {
50
+ throw new Error("No reddb connection: pass a connectionUrl (http(s):// or red://), or set RED_UI_CONNECTION_URL on the MCP server.");
51
+ }
52
+ const mode = classifyTarget(raw);
53
+ if (mode === "local") {
54
+ throw new Error(`Cannot run data tools against the local file "${raw}" yet: local-file mode (a local red server in front of the file, ADR-0006 / #48) is not implemented. Point at an http(s):// or red:// server.`);
55
+ }
56
+ const headers = opts.authHeader
57
+ ? { Authorization: opts.authHeader }
58
+ : undefined;
59
+ return { baseUrl: normalizeRemoteUrl(raw), headers, mode };
60
+ }
61
+ //# sourceMappingURL=connection.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"connection.js","sourceRoot":"","sources":["../src/connection.ts"],"names":[],"mappings":"AAAA,gEAAgE;AAChE,EAAE;AACF,iFAAiF;AACjF,iFAAiF;AACjF,sDAAsD;AACtD,yEAAyE;AACzE,sEAAsE;AACtE,kFAAkF;AAClF,oEAAoE;AACpE,iFAAiF;AACjF,gFAAgF;AAChF,wEAAwE;AACxE,EAAE;AACF,kFAAkF;AAClF,+DAA+D;AAE/D,OAAO,EAAE,cAAc,EAAmB,MAAM,kBAAkB,CAAC;AAUnE;gEACgE;AAChE,SAAS,kBAAkB,CAAC,MAAc;IACxC,MAAM,CAAC,GAAG,MAAM,CAAC,IAAI,EAAE,CAAC;IACxB,MAAM,KAAK,GAAG,CAAC,CAAC,WAAW,EAAE,CAAC;IAC9B,IAAI,GAAQ,CAAC;IACb,IAAI,KAAK,CAAC,UAAU,CAAC,QAAQ,CAAC,EAAE,CAAC;QAC/B,GAAG,GAAG,IAAI,GAAG,CAAC,SAAS,GAAG,CAAC,CAAC,KAAK,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC,CAAC;IACtD,CAAC;SAAM,IAAI,KAAK,CAAC,UAAU,CAAC,SAAS,CAAC,EAAE,CAAC;QACvC,GAAG,GAAG,IAAI,GAAG,CAAC,UAAU,GAAG,CAAC,CAAC,KAAK,CAAC,SAAS,CAAC,MAAM,CAAC,CAAC,CAAC;IACxD,CAAC;SAAM,IAAI,eAAe,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC;QACnC,GAAG,GAAG,IAAI,GAAG,CAAC,CAAC,CAAC,CAAC;IACnB,CAAC;SAAM,CAAC;QACN,6EAA6E;QAC7E,GAAG,GAAG,IAAI,GAAG,CAAC,SAAS,GAAG,CAAC,CAAC,CAAC;IAC/B,CAAC;IACD,IAAI,GAAG,CAAC,QAAQ,KAAK,OAAO,IAAI,GAAG,CAAC,QAAQ,KAAK,QAAQ,EAAE,CAAC;QAC1D,MAAM,IAAI,KAAK,CAAC,kCAAkC,MAAM,EAAE,CAAC,CAAC;IAC9D,CAAC;IACD,GAAG,CAAC,IAAI,GAAG,EAAE,CAAC;IACd,OAAO,GAAG,CAAC,QAAQ,EAAE,CAAC,OAAO,CAAC,KAAK,EAAE,EAAE,CAAC,CAAC;AAC3C,CAAC;AASD;;;;GAIG;AACH,MAAM,UAAU,iBAAiB,CAC/B,MAA0B,EAC1B,OAAiC,EAAE;IAEnC,MAAM,GAAG,GAAG,CAAC,MAAM,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,IAAI,CAAC,IAAI,CAAC,UAAU,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,CAAC;IACpE,IAAI,CAAC,GAAG,EAAE,CAAC;QACT,MAAM,IAAI,KAAK,CACb,mHAAmH,CACpH,CAAC;IACJ,CAAC;IAED,MAAM,IAAI,GAAG,cAAc,CAAC,GAAG,CAAC,CAAC;IACjC,IAAI,IAAI,KAAK,OAAO,EAAE,CAAC;QACrB,MAAM,IAAI,KAAK,CACb,iDAAiD,GAAG,+IAA+I,CACpM,CAAC;IACJ,CAAC;IAED,MAAM,OAAO,GAAG,IAAI,CAAC,UAAU;QAC7B,CAAC,CAAC,EAAE,aAAa,EAAE,IAAI,CAAC,UAAU,EAAE;QACpC,CAAC,CAAC,SAAS,CAAC;IACd,OAAO,EAAE,OAAO,EAAE,kBAAkB,CAAC,GAAG,CAAC,EAAE,OAAO,EAAE,IAAI,EAAE,CAAC;AAC7D,CAAC"}
@@ -0,0 +1,51 @@
1
+ import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
2
+ import { type ReadClient } from "./red-client.js";
3
+ import { type ResolveConnectionOptions } from "./connection.js";
4
+ /** MCP tool result shape we build (subset of the SDK's CallToolResult). The
5
+ * index signature keeps it assignable to the SDK's `CallToolResult`. */
6
+ interface ToolResult {
7
+ content: Array<{
8
+ type: "text";
9
+ text: string;
10
+ }>;
11
+ structuredContent: Record<string, unknown>;
12
+ isError?: boolean;
13
+ [k: string]: unknown;
14
+ }
15
+ /** Strip leading line/block comments + whitespace, then return the first token
16
+ * lower-cased. Used to gate the `query` tool to read-shaped statements. */
17
+ export declare function leadingVerb(sql: string): string;
18
+ export declare function isReadOnlyQuery(sql: string): boolean;
19
+ export declare function runQueryTool(client: ReadClient, args: {
20
+ query: string;
21
+ maxRows?: number;
22
+ }, conn: {
23
+ baseUrl: string;
24
+ mode: string;
25
+ }): Promise<ToolResult>;
26
+ export declare function runListTool(client: ReadClient, args: {
27
+ collection?: string;
28
+ maxRows?: number;
29
+ }, conn: {
30
+ baseUrl: string;
31
+ mode: string;
32
+ }): Promise<ToolResult>;
33
+ export declare function runGetTool(client: ReadClient, args: {
34
+ collection: string;
35
+ id: string | number;
36
+ idColumn?: string;
37
+ }, conn: {
38
+ baseUrl: string;
39
+ mode: string;
40
+ }): Promise<ToolResult>;
41
+ export interface DataToolsConfig extends ResolveConnectionOptions {
42
+ /** Build a client for a resolved endpoint. Overridable in tests. */
43
+ createClient?: (baseUrl: string, headers?: Record<string, string>) => ReadClient;
44
+ }
45
+ /**
46
+ * Register the model-facing `query` / `list` / `get` data tools. They resolve a
47
+ * connection per call (tool arg `connectionUrl`, else the configured default),
48
+ * build a server-side RedClient, and return results as `structuredContent`.
49
+ */
50
+ export declare function registerDataTools(server: McpServer, config?: DataToolsConfig): void;
51
+ export {};
@@ -0,0 +1,285 @@
1
+ // Server-side data tools for the MCP App (#49, ADR-0006).
2
+ //
3
+ // `query` / `list` / `get` run a server-side RedClient against the resolved
4
+ // connection and return reddb results to the *model* as `structuredContent` —
5
+ // the model reads data directly without driving the visual iframe. Read-shaped
6
+ // only: `query` rejects any statement that is not a read (default-deny), and
7
+ // `list`/`get` build SELECTs. No secret/token is logged or returned.
8
+ import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
9
+ import { z } from "zod/v4";
10
+ import { RedClient, runQueryPreferStream, } from "./red-client.js";
11
+ import { resolveConnection, } from "./connection.js";
12
+ /** Leading verbs we accept as read-shaped. Everything else is denied — a
13
+ * default-deny allowlist keeps write/DDL statements out of read tools even as
14
+ * reddb's query surface grows. */
15
+ const READ_VERBS = new Set([
16
+ "select",
17
+ "with",
18
+ "show",
19
+ "explain",
20
+ "describe",
21
+ "desc",
22
+ "match", // graph traversal read
23
+ ]);
24
+ /** Strip leading line/block comments + whitespace, then return the first token
25
+ * lower-cased. Used to gate the `query` tool to read-shaped statements. */
26
+ export function leadingVerb(sql) {
27
+ let s = sql.trim();
28
+ // Drop leading -- line comments and /* */ block comments.
29
+ for (;;) {
30
+ if (s.startsWith("--")) {
31
+ const nl = s.indexOf("\n");
32
+ s = nl === -1 ? "" : s.slice(nl + 1).trim();
33
+ }
34
+ else if (s.startsWith("/*")) {
35
+ const end = s.indexOf("*/");
36
+ s = end === -1 ? "" : s.slice(end + 2).trim();
37
+ }
38
+ else {
39
+ break;
40
+ }
41
+ }
42
+ const m = /^[a-z]+/i.exec(s);
43
+ return m ? m[0].toLowerCase() : "";
44
+ }
45
+ export function isReadOnlyQuery(sql) {
46
+ return READ_VERBS.has(leadingVerb(sql));
47
+ }
48
+ const IDENT_RE = /^[A-Za-z_][A-Za-z0-9_]*$/;
49
+ /** Reject anything that is not a bare SQL identifier (collection / column). */
50
+ function assertIdentifier(value, label) {
51
+ if (!IDENT_RE.test(value)) {
52
+ throw new Error(`Invalid ${label} "${value}": expected a bare identifier (letters, digits, underscore).`);
53
+ }
54
+ return value;
55
+ }
56
+ /** Render an id literal for a WHERE clause: numbers inline, strings single-quoted
57
+ * with embedded quotes doubled. */
58
+ function idLiteral(id) {
59
+ if (typeof id === "number") {
60
+ if (!Number.isFinite(id))
61
+ throw new Error(`Invalid numeric id: ${id}`);
62
+ return String(id);
63
+ }
64
+ return `'${id.replaceAll("'", "''")}'`;
65
+ }
66
+ function ok(text, structured) {
67
+ return { content: [{ type: "text", text }], structuredContent: structured };
68
+ }
69
+ function fail(message) {
70
+ return {
71
+ content: [{ type: "text", text: message }],
72
+ structuredContent: { ok: false, error: message },
73
+ isError: true,
74
+ };
75
+ }
76
+ function shapeQueryResult(r, baseUrl, mode) {
77
+ const records = r.result?.records?.map((rec) => rec.values) ?? [];
78
+ return {
79
+ ok: r.ok !== false,
80
+ query: r.query,
81
+ columns: r.result?.columns ?? [],
82
+ records,
83
+ recordCount: r.record_count ?? records.length,
84
+ streamed: r.streamed ?? false,
85
+ truncated: r.truncated ?? false,
86
+ baseUrl,
87
+ mode,
88
+ };
89
+ }
90
+ // ---- Pure handlers (injectable client) — the unit-testable core. ----------
91
+ export async function runQueryTool(client, args, conn) {
92
+ if (!isReadOnlyQuery(args.query)) {
93
+ return fail(`Refused: "${leadingVerb(args.query) || "(empty)"}" is not a read statement. The query tool runs read-shaped statements only (SELECT/WITH/SHOW/EXPLAIN/DESCRIBE/MATCH).`);
94
+ }
95
+ try {
96
+ const r = await runQueryPreferStream(client, args.query, {
97
+ maxRows: args.maxRows,
98
+ });
99
+ const structured = shapeQueryResult(r, conn.baseUrl, conn.mode);
100
+ return ok(`${structured.recordCount} row(s) from ${conn.baseUrl}${structured.truncated ? " (truncated)" : ""}.`, structured);
101
+ }
102
+ catch (e) {
103
+ return fail(e instanceof Error ? e.message : String(e));
104
+ }
105
+ }
106
+ export async function runListTool(client, args, conn) {
107
+ try {
108
+ // No collection → list collection names. With one → list its rows (a read).
109
+ if (!args.collection) {
110
+ const collections = await client.collections();
111
+ return ok(`${collections.length} collection(s) on ${conn.baseUrl}.`, {
112
+ ok: true,
113
+ collections,
114
+ count: collections.length,
115
+ baseUrl: conn.baseUrl,
116
+ mode: conn.mode,
117
+ });
118
+ }
119
+ const name = assertIdentifier(args.collection, "collection");
120
+ const limit = args.maxRows ?? 100;
121
+ const r = await runQueryPreferStream(client, `SELECT * FROM ${name} LIMIT ${limit}`, { maxRows: limit });
122
+ const structured = shapeQueryResult(r, conn.baseUrl, conn.mode);
123
+ structured.collection = name;
124
+ return ok(`${structured.recordCount} row(s) from ${name} on ${conn.baseUrl}${structured.truncated ? " (truncated)" : ""}.`, structured);
125
+ }
126
+ catch (e) {
127
+ return fail(e instanceof Error ? e.message : String(e));
128
+ }
129
+ }
130
+ export async function runGetTool(client, args, conn) {
131
+ try {
132
+ const name = assertIdentifier(args.collection, "collection");
133
+ const idColumn = assertIdentifier(args.idColumn ?? "id", "idColumn");
134
+ const sql = `SELECT * FROM ${name} WHERE ${idColumn} = ${idLiteral(args.id)} LIMIT 1`;
135
+ const r = await runQueryPreferStream(client, sql, { maxRows: 1 });
136
+ const records = r.result?.records?.map((rec) => rec.values) ?? [];
137
+ const record = records[0] ?? null;
138
+ return ok(record
139
+ ? `Found ${name}/${args.id} on ${conn.baseUrl}.`
140
+ : `No ${name} where ${idColumn} = ${args.id} on ${conn.baseUrl}.`, {
141
+ ok: true,
142
+ found: record !== null,
143
+ collection: name,
144
+ id: args.id,
145
+ record,
146
+ baseUrl: conn.baseUrl,
147
+ mode: conn.mode,
148
+ });
149
+ }
150
+ catch (e) {
151
+ return fail(e instanceof Error ? e.message : String(e));
152
+ }
153
+ }
154
+ const MODEL_ONLY_META = { ui: { visibility: ["model"] } };
155
+ /**
156
+ * Register the model-facing `query` / `list` / `get` data tools. They resolve a
157
+ * connection per call (tool arg `connectionUrl`, else the configured default),
158
+ * build a server-side RedClient, and return results as `structuredContent`.
159
+ */
160
+ export function registerDataTools(server, config = {}) {
161
+ const createClient = config.createClient ??
162
+ ((baseUrl, headers) => new RedClient(baseUrl, { headers }));
163
+ const resolveOpts = {
164
+ defaultUrl: config.defaultUrl,
165
+ authHeader: config.authHeader,
166
+ };
167
+ function resolve(connectionUrl) {
168
+ const conn = resolveConnection(connectionUrl, resolveOpts);
169
+ return { conn, client: createClient(conn.baseUrl, conn.headers) };
170
+ }
171
+ const connectionUrlSchema = z
172
+ .string()
173
+ .optional()
174
+ .describe("reddb endpoint to read from (http(s):// or red://). Defaults to the MCP server's configured connection. Local file paths are not yet supported (#48).");
175
+ server.registerTool("query", {
176
+ title: "Query reddb",
177
+ description: "Run a read-only reddb query (SELECT/WITH/SHOW/EXPLAIN/DESCRIBE/MATCH) and return rows as structured data. Write/DDL statements are refused.",
178
+ inputSchema: {
179
+ query: z.string().describe("A read-only reddb SQL/graph statement."),
180
+ connectionUrl: connectionUrlSchema,
181
+ maxRows: z
182
+ .number()
183
+ .int()
184
+ .positive()
185
+ .optional()
186
+ .describe("Maximum rows to collect (default 10000)."),
187
+ },
188
+ outputSchema: {
189
+ ok: z.boolean(),
190
+ error: z.string().optional(),
191
+ query: z.string().optional(),
192
+ columns: z.array(z.string()).optional(),
193
+ records: z.array(z.record(z.string(), z.unknown())).optional(),
194
+ recordCount: z.number().optional(),
195
+ streamed: z.boolean().optional(),
196
+ truncated: z.boolean().optional(),
197
+ baseUrl: z.string().optional(),
198
+ mode: z.string().optional(),
199
+ },
200
+ _meta: MODEL_ONLY_META,
201
+ }, async ({ query, connectionUrl, maxRows }) => {
202
+ let resolved;
203
+ try {
204
+ resolved = resolve(connectionUrl);
205
+ }
206
+ catch (e) {
207
+ return fail(e instanceof Error ? e.message : String(e));
208
+ }
209
+ return runQueryTool(resolved.client, { query, maxRows }, resolved.conn);
210
+ });
211
+ server.registerTool("list", {
212
+ title: "List reddb collections or rows",
213
+ description: "List collection names, or — when a collection is given — the first rows of that collection. Read-only.",
214
+ inputSchema: {
215
+ collection: z
216
+ .string()
217
+ .optional()
218
+ .describe("Collection to list rows from. Omit to list collections."),
219
+ connectionUrl: connectionUrlSchema,
220
+ maxRows: z
221
+ .number()
222
+ .int()
223
+ .positive()
224
+ .optional()
225
+ .describe("Maximum rows when listing a collection (default 100)."),
226
+ },
227
+ outputSchema: {
228
+ ok: z.boolean(),
229
+ error: z.string().optional(),
230
+ collections: z.array(z.string()).optional(),
231
+ count: z.number().optional(),
232
+ collection: z.string().optional(),
233
+ columns: z.array(z.string()).optional(),
234
+ records: z.array(z.record(z.string(), z.unknown())).optional(),
235
+ recordCount: z.number().optional(),
236
+ truncated: z.boolean().optional(),
237
+ baseUrl: z.string().optional(),
238
+ mode: z.string().optional(),
239
+ },
240
+ _meta: MODEL_ONLY_META,
241
+ }, async ({ collection, connectionUrl, maxRows }) => {
242
+ let resolved;
243
+ try {
244
+ resolved = resolve(connectionUrl);
245
+ }
246
+ catch (e) {
247
+ return fail(e instanceof Error ? e.message : String(e));
248
+ }
249
+ return runListTool(resolved.client, { collection, maxRows }, resolved.conn);
250
+ });
251
+ server.registerTool("get", {
252
+ title: "Get a reddb record",
253
+ description: "Fetch a single record from a collection by id. Read-only; returns the record or null.",
254
+ inputSchema: {
255
+ collection: z.string().describe("Collection name."),
256
+ id: z.union([z.string(), z.number()]).describe("Record id to look up."),
257
+ idColumn: z
258
+ .string()
259
+ .optional()
260
+ .describe("Column to match the id against (default 'id')."),
261
+ connectionUrl: connectionUrlSchema,
262
+ },
263
+ outputSchema: {
264
+ ok: z.boolean(),
265
+ error: z.string().optional(),
266
+ found: z.boolean().optional(),
267
+ collection: z.string().optional(),
268
+ id: z.union([z.string(), z.number()]).optional(),
269
+ record: z.record(z.string(), z.unknown()).nullable().optional(),
270
+ baseUrl: z.string().optional(),
271
+ mode: z.string().optional(),
272
+ },
273
+ _meta: MODEL_ONLY_META,
274
+ }, async ({ collection, id, idColumn, connectionUrl }) => {
275
+ let resolved;
276
+ try {
277
+ resolved = resolve(connectionUrl);
278
+ }
279
+ catch (e) {
280
+ return fail(e instanceof Error ? e.message : String(e));
281
+ }
282
+ return runGetTool(resolved.client, { collection, id, idColumn }, resolved.conn);
283
+ });
284
+ }
285
+ //# sourceMappingURL=data-tools.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"data-tools.js","sourceRoot":"","sources":["../src/data-tools.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,40 @@
1
+ import type { Server } from "node:http";
2
+ export interface EmbedServerHandle {
3
+ baseUrl: string;
4
+ port: number;
5
+ /** Absolute path of the served embed bundle directory. */
6
+ embedDir: string;
7
+ server: Server;
8
+ /** Idempotent teardown; resolves once the HTTP server has closed. */
9
+ stop(): Promise<void>;
10
+ }
11
+ export interface StartEmbedServerOptions {
12
+ /** Override the embed bundle directory (tests, explicit config). */
13
+ embedDir?: string;
14
+ /** Override the ephemeral port (tests). */
15
+ port?: number;
16
+ }
17
+ /**
18
+ * Locate the built Embeddable Lib bundle directory (`@reddb-io/ui/dist/embed`),
19
+ * the one containing `index.js`. Resolution order: explicit `RED_UI_EMBED_DIR`
20
+ * → the published `@reddb-io/ui/embed` export → the monorepo sibling
21
+ * (`packages/ui/dist/embed`) → the published dependency layout (the MCP lives in
22
+ * `<ui>/node_modules/@reddb-io/ui-mcp`). Throws an actionable error when none of
23
+ * these holds the bundle.
24
+ */
25
+ export declare function resolveEmbedDir(override?: string): string;
26
+ /**
27
+ * The host page. It imports the embed bundle from the same origin, builds a
28
+ * single-connection InjectedClientProvider from the `?cs=` endpoint the MCP
29
+ * seeded (the spawned `red server`), and mounts red-ui into a full-document
30
+ * host element. `?to=` selects the initial route. No secret rides the URL
31
+ * (ADR-0005); the local server is loopback-only and unauthenticated.
32
+ */
33
+ export declare function renderHostHtml(): string;
34
+ /**
35
+ * Start one loopback HTTP server that serves the host page at `/` and the embed
36
+ * bundle under `/embed/`. The returned handle's `stop()` closes it.
37
+ */
38
+ export declare function startEmbedServer(options?: StartEmbedServerOptions): Promise<EmbedServerHandle>;
39
+ /** Stop every tracked embed server (MCP transport close / shutdown). */
40
+ export declare function stopAllEmbedServers(): Promise<void>;