@filium/flite-js 0.1.0 → 0.2.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 (2) hide show
  1. package/package.json +9 -4
  2. package/src/mcp.js +62 -0
package/package.json CHANGED
@@ -1,18 +1,23 @@
1
1
  {
2
2
  "name": "@filium/flite-js",
3
- "version": "0.1.0",
4
- "description": "Byte-exact, token-saving source editor — a compiled wasm core (resilient sectioning + byte-exact splicing) plus fs. The standalone tool behind the filium-flite plugin. Runs in Node and Deno.",
3
+ "version": "0.2.0",
4
+ "description": "Byte-exact, token-saving source editor — a compiled wasm core (resilient sectioning + byte-exact splicing) plus fs. Ships as a library and as an MCP server (bin: filium-flite-mcp). Runs in Node and Deno.",
5
5
  "type": "module",
6
6
  "publishConfig": { "access": "public" },
7
7
  "main": "./src/index.js",
8
8
  "exports": {
9
9
  ".": "./src/index.js"
10
10
  },
11
+ "bin": { "filium-flite-mcp": "./src/mcp.js" },
11
12
  "files": ["src", "wasm"],
12
13
  "scripts": {
13
14
  "test": "node test/smoke.mjs"
14
15
  },
15
- "keywords": ["editor", "wasm", "tokens", "llm", "agent", "filium", "flite"],
16
+ "keywords": ["editor", "wasm", "tokens", "llm", "agent", "filium", "flite", "mcp"],
16
17
  "license": "BUSL-1.1",
17
- "engines": { "node": ">=18" }
18
+ "engines": { "node": ">=18" },
19
+ "dependencies": {
20
+ "@modelcontextprotocol/sdk": "^1.26.0",
21
+ "zod": "^3.23.0"
22
+ }
18
23
  }
package/src/mcp.js ADDED
@@ -0,0 +1,62 @@
1
+ #!/usr/bin/env node
2
+ // filium-flite MCP server — the package's second entry point (bin), alongside the
3
+ // library. Thin wiring over the Session in ./index.js: receive a tool call, forward
4
+ // it, return the result. The wasm core does the work (sectioning + byte-exact splices).
5
+ //
6
+ // The MCP SDK + zod are imported HERE only, never from index.js — so `import { Session }
7
+ // from "@filium/flite-js"` (library use) never loads them at runtime.
8
+ //
9
+ // stdio transport OWNS stdout — never console.log here; diagnostics go to stderr.
10
+ import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
11
+ import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
12
+ import { z } from "zod";
13
+ import { Session } from "./index.js";
14
+
15
+ const session = new Session();
16
+ const server = new McpServer({ name: "filium-flite", version: "0.2.0" });
17
+
18
+ const ok = (data) => ({ content: [{ type: "text", text: JSON.stringify(data ?? {}) }] });
19
+ const fail = (e) => ({
20
+ content: [{ type: "text", text: JSON.stringify({ error: e?.kind ?? "error", message: e?.message ?? String(e) }) }],
21
+ isError: true,
22
+ });
23
+
24
+ function tool(name, description, shape, handler) {
25
+ server.registerTool(name, { description, inputSchema: shape }, async (args) => {
26
+ try {
27
+ return ok(await handler(args));
28
+ } catch (e) {
29
+ return fail(e);
30
+ }
31
+ });
32
+ }
33
+
34
+ const P = { path: z.string().describe("file path") };
35
+ const SID = { section_id: z.string().describe("section id from the outline, e.g. s-3") };
36
+ const BODY = { content: z.string().describe("replacement/inserted text, verbatim") };
37
+
38
+ tool("filium_flite_open", "Section a file; returns its outline (id, heading, line range, balanced) without loading the whole file.",
39
+ { ...P }, async ({ path }) => ({ path, sections: await session.open(path) }));
40
+ tool("filium_flite_list", "List open buffers.", {}, () => ({ open: session.list() }));
41
+ tool("filium_flite_zoom", "Return the verbatim text of one section.",
42
+ { ...P, ...SID }, ({ path, section_id }) => ({ section_id, text: session.zoom(path, section_id) }));
43
+ tool("filium_flite_find", "Find sections whose text matches a query.",
44
+ { ...P, pattern: z.string() }, ({ path, pattern }) => ({ hits: session.find(path, pattern) }));
45
+ tool("filium_flite_edit", "Replace a section's bytes, byte-exact. Everything else is untouched.",
46
+ { ...P, ...SID, ...BODY }, ({ path, section_id, content }) => session.edit(path, section_id, content));
47
+ tool("filium_flite_replace", "Replace the first verbatim occurrence of an anchor.",
48
+ { ...P, anchor: z.string(), replacement: z.string() }, ({ path, anchor, replacement }) => session.replace(path, anchor, replacement));
49
+ tool("filium_flite_insert_before", "Insert text before a section.",
50
+ { ...P, ...SID, ...BODY }, ({ path, section_id, content }) => session.insertBefore(path, section_id, content));
51
+ tool("filium_flite_insert_after", "Insert text after a section.",
52
+ { ...P, ...SID, ...BODY }, ({ path, section_id, content }) => session.insertAfter(path, section_id, content));
53
+ tool("filium_flite_append", "Append text to the buffer.",
54
+ { ...P, ...BODY }, ({ path, content }) => session.append(path, content));
55
+ tool("filium_flite_save", "Write the buffer to disk (refuses if the file changed on disk since open).",
56
+ { ...P }, ({ path }) => session.save(path));
57
+ tool("filium_flite_close", "Close a buffer.",
58
+ { ...P }, ({ path }) => { session.close(path); return { path, closed: true }; });
59
+ tool("filium_flite_read_slice", "Return the verbatim text of a 0-based line range [start, end).",
60
+ { ...P, start: z.number().int(), end: z.number().int() }, ({ path, start, end }) => ({ path, start, end, text: session.readSlice(path, start, end) }));
61
+
62
+ await server.connect(new StdioServerTransport());