@sightmap/mcp 0.5.2 → 0.6.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/dist/index.js CHANGED
@@ -1,5 +1,9 @@
1
1
  // src/server.ts
2
- import { match as sightmapMatch4 } from "@sightmap/sightmap";
2
+ import {
3
+ match as sightmapMatch2,
4
+ resolveSightmapAct,
5
+ buildInPageEvalFunction
6
+ } from "@sightmap/sightmap";
3
7
 
4
8
  // src/tools/match.ts
5
9
  import { match as sightmapMatch } from "@sightmap/sightmap";
@@ -32,72 +36,20 @@ function handleSightmapMatch(sightmap, input) {
32
36
  }
33
37
 
34
38
  // src/tools/snapshot.ts
35
- import { match as sightmapMatch2 } from "@sightmap/sightmap";
39
+ import {
40
+ enrichSnapshot
41
+ } from "@sightmap/sightmap";
36
42
  function buildSightmapSnapshotResponse(opts) {
37
- const { sightmap, currentUrl, ariaSnapshotText, inPageMatches } = opts;
38
- const result = sightmapMatch2(sightmap, { url: currentUrl });
39
- const inPageByName = /* @__PURE__ */ new Map();
40
- for (const m of inPageMatches) inPageByName.set(m.name, m);
41
- const components = result.components.map((c) => {
42
- const inPage = inPageByName.get(c.name);
43
- return {
44
- name: c.name,
45
- selector: c.selector,
46
- memory: c.memory ?? [],
47
- scope: c.scope,
48
- matchCount: inPage?.matchCount ?? 0,
49
- ...inPage?.samplePosition !== void 0 ? { samplePosition: inPage.samplePosition } : {}
50
- };
43
+ const enriched = enrichSnapshot({
44
+ sightmap: opts.sightmap,
45
+ currentUrl: opts.currentUrl,
46
+ inPageMatches: opts.inPageMatches
51
47
  });
52
- return {
53
- view: result.view ? {
54
- name: result.view.name,
55
- route: result.view.route,
56
- memory: result.view.memory ?? []
57
- } : null,
58
- components,
59
- memory: result.memory ?? [],
60
- ariaSnapshot: ariaSnapshotText
61
- };
62
- }
63
-
64
- // src/tools/act.ts
65
- function resolveSightmapAct(sightmap, input) {
66
- const found = findComponentByName(sightmap, input.componentName);
67
- if (found === null) {
68
- return {
69
- kind: "error",
70
- message: `Component "${input.componentName}" not found in the loaded sightmap.`
71
- };
72
- }
73
- const selectors = Array.isArray(found.selector) ? found.selector : [];
74
- if (selectors.length === 0) {
75
- return {
76
- kind: "error",
77
- message: `Component "${input.componentName}" has no selector \u2014 cannot dispatch an action.`
78
- };
79
- }
80
- return {
81
- kind: "ok",
82
- componentName: input.componentName,
83
- selector: selectors[0],
84
- allSelectors: selectors
85
- };
86
- }
87
- function findComponentByName(sightmap, name) {
88
- for (const c of sightmap.globalComponents) {
89
- if (c.name === name) return c;
90
- }
91
- for (const v of sightmap.views) {
92
- for (const c of v.components ?? []) {
93
- if (c.name === name) return c;
94
- }
95
- }
96
- return null;
48
+ return { ...enriched, ariaSnapshot: opts.ariaSnapshotText };
97
49
  }
98
50
 
99
51
  // src/tools/network.ts
100
- import { match as sightmapMatch3 } from "@sightmap/sightmap";
52
+ import { annotateNetworkRequests } from "@sightmap/sightmap";
101
53
  function parseNetworkRequestsText(text) {
102
54
  const lines = text.split(/\r?\n/);
103
55
  const requests = [];
@@ -114,18 +66,6 @@ function parseNetworkRequestsText(text) {
114
66
  }
115
67
  return requests;
116
68
  }
117
- function annotateNetworkRequests(sightmap, requests) {
118
- return requests.map((req) => {
119
- const result = sightmapMatch3(sightmap, { url: req.url, method: req.method });
120
- const first = result.requests[0];
121
- if (first === void 0) return req;
122
- const annotated = { ...req, sightmapName: first.name };
123
- if (first.memory && first.memory.length > 0) {
124
- annotated.sightmapMemory = first.memory;
125
- }
126
- return annotated;
127
- });
128
- }
129
69
 
130
70
  // src/tools/curate/list.ts
131
71
  function handleListViews(sightmap, input) {
@@ -911,7 +851,7 @@ var SightmapMcpServer = class {
911
851
  }
912
852
  const ariaSnapshotText = snapResult.content.map((b) => b.text).join("\n");
913
853
  const currentUrl = parsePageUrl(ariaSnapshotText) ?? "";
914
- const matchResult = sightmapMatch4(this.sightmap, { url: currentUrl });
854
+ const matchResult = sightmapMatch2(this.sightmap, { url: currentUrl });
915
855
  const componentSelectors = matchResult.components.map((c) => ({
916
856
  name: c.name,
917
857
  selector: c.selector
@@ -1055,43 +995,6 @@ function parsePageUrl(text) {
1055
995
  const m = /Page URL:\s*(\S+)/.exec(text);
1056
996
  return m?.[1] ?? null;
1057
997
  }
1058
- function buildInPageEvalFunction(components) {
1059
- const componentsJson = JSON.stringify(components);
1060
- return `() => {
1061
- const components = ${componentsJson};
1062
- const matches = components.map((c) => {
1063
- const selectors = c.selector || [];
1064
- const seen = new Set();
1065
- const elements = [];
1066
- for (const sel of selectors) {
1067
- try {
1068
- const found = document.querySelectorAll(sel);
1069
- for (const el of Array.from(found)) {
1070
- if (!seen.has(el)) {
1071
- seen.add(el);
1072
- elements.push(el);
1073
- }
1074
- }
1075
- } catch {
1076
- // Invalid selector \u2014 skip silently.
1077
- }
1078
- }
1079
- const first = elements[0];
1080
- let samplePosition;
1081
- if (first && typeof first.getBoundingClientRect === "function") {
1082
- const r = first.getBoundingClientRect();
1083
- samplePosition = { x: r.x, y: r.y, width: r.width, height: r.height };
1084
- }
1085
- return {
1086
- name: c.name,
1087
- selector: selectors,
1088
- matchCount: elements.length,
1089
- samplePosition,
1090
- };
1091
- });
1092
- return { url: window.location.href, matches };
1093
- }`;
1094
- }
1095
998
  function parseInPageEvalResult(text) {
1096
999
  const afterResult = text.split(/^###\s*Result/im)[1] ?? text;
1097
1000
  const start = afterResult.indexOf("{");
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/server.ts","../src/tools/match.ts","../src/tools/snapshot.ts","../src/tools/act.ts","../src/tools/network.ts","../src/tools/curate/list.ts","../src/tools/curate/get.ts","../src/curate/locator.ts","../src/tools/curate/check.ts","../src/tools/curate/update.ts","../src/tools/curate/init.ts","../src/curate/scaffolder.ts","../src/prompts/sepTrack.ts","../src/prompts/index.ts","../src/upstream.ts","../src/mcpServer.ts"],"sourcesContent":["import { match as sightmapMatch, type Sightmap } from \"@sightmap/sightmap\";\nimport { handleSightmapMatch } from \"./tools/match.js\";\nimport {\n buildSightmapSnapshotResponse,\n type InPageSightmapMatch,\n} from \"./tools/snapshot.js\";\nimport { resolveSightmapAct } from \"./tools/act.js\";\nimport {\n parseNetworkRequestsText,\n annotateNetworkRequests,\n} from \"./tools/network.js\";\nimport {\n handleListViews,\n type ListViewsInput,\n} from \"./tools/curate/list.js\";\nimport { handleGetView } from \"./tools/curate/get.js\";\nimport { handleCheck, type CheckInput } from \"./tools/curate/check.js\";\nimport {\n handleUpdateView,\n type ViewPatch,\n} from \"./tools/curate/update.js\";\nimport {\n handleInitProject,\n type InitProjectInput,\n} from \"./tools/curate/init.js\";\nimport type { PromptDefinition, PromptEntry, PromptResult } from \"./prompts/index.js\";\nimport { PROMPT_REGISTRY } from \"./prompts/index.js\";\n\nexport interface ToolDefinition {\n name: string;\n description: string;\n inputSchema: {\n type: \"object\";\n properties?: Record<string, unknown>;\n required?: string[];\n additionalProperties?: boolean;\n };\n}\n\nexport interface ToolResult {\n content: Array<{ type: \"text\"; text: string }>;\n isError?: boolean;\n}\n\n/**\n * Abstraction over the upstream MCP server (typically `@playwright/mcp`).\n *\n * Implementations: a real MCP-SDK Client connected via stdio in production,\n * a fake in unit tests.\n */\nexport interface UpstreamClient {\n listTools(): Promise<ToolDefinition[]>;\n callTool(name: string, args: Record<string, unknown>): Promise<ToolResult>;\n}\n\nexport interface SightmapMcpServerOptions {\n sightmap: Sightmap;\n /** Optional upstream MCP server to proxy non-sightmap_* tool calls through. */\n upstream?: UpstreamClient;\n /**\n * Writable `.sightmap/` directory for curation tools that read/write files\n * (e.g. `sightmap_get_view`, `sightmap_update_view`). The CLI populates this\n * from `--curate-root` (or, by default, the first `--sightmap-dir`).\n */\n curateRoot?: string;\n}\n\nconst SIGHTMAP_MATCH: ToolDefinition = {\n name: \"sightmap_match\",\n description:\n \"Pure-query lookup against the loaded sightmap. Returns the matched view, applicable components, applicable requests, and aggregated memory for a given URL. Useful for agent planning before navigation. Does not touch the browser.\",\n inputSchema: {\n type: \"object\",\n properties: {\n url: {\n type: \"string\",\n description: \"The URL to resolve against the sightmap's view routes.\",\n },\n method: {\n type: \"string\",\n description: \"Optional HTTP method to filter matched requests (e.g., 'GET', 'POST').\",\n },\n },\n required: [\"url\"],\n additionalProperties: false,\n },\n};\n\nconst SIGHTMAP_SNAPSHOT: ToolDefinition = {\n name: \"sightmap_snapshot\",\n description:\n \"Returns the upstream ARIA snapshot enriched with sightmap awareness: matched view name, applicable component names with their selectors and live matchCount on the page, view-level memory, and page-aggregated memory. Use this instead of browser_snapshot when you want sightmap-aware semantics in one round-trip.\",\n inputSchema: {\n type: \"object\",\n properties: {},\n additionalProperties: false,\n },\n};\n\nconst SIGHTMAP_NETWORK_REQUESTS: ToolDefinition = {\n name: \"sightmap_network_requests\",\n description:\n \"Returns recent network requests captured by the upstream, annotated with sightmap names and memory where the request URL+method matches a sightmap `requests:` entry. Use this in place of browser_network_requests when you want sightmap-aware semantics for network calls.\",\n inputSchema: {\n type: \"object\",\n properties: {\n static: {\n type: \"boolean\",\n description:\n \"Include successful static resources (images, fonts, scripts). Default false.\",\n },\n filter: {\n type: \"string\",\n description: \"Only return requests whose URL matches this regexp.\",\n },\n },\n additionalProperties: false,\n },\n};\n\nconst SIGHTMAP_INIT_PROJECT: ToolDefinition = {\n name: \"sightmap_init_project\",\n description:\n \"Scaffold an empty .sightmap/ directory in the target project. Pass `dir` to override the location (default: server cwd). Refuses to overwrite an existing .sightmap/ unless `force=true`.\",\n inputSchema: {\n type: \"object\",\n properties: {\n dir: { type: \"string\", description: \"Project root. Default: server cwd.\" },\n force: { type: \"boolean\", description: \"Default false.\" },\n },\n additionalProperties: false,\n },\n};\n\nconst SIGHTMAP_UPDATE_VIEW: ToolDefinition = {\n name: \"sightmap_update_view\",\n description:\n \"Apply a partial patch to a view's agent-authored fields (description, intent, memory). Memory edits use either `memory_append` (default operation) or `memory_replace` — pass exactly one. Component / route / selector edits are NOT supported here — those are codegen-owned; edit source and re-run sightmap-react gen instead.\",\n inputSchema: {\n type: \"object\",\n properties: {\n name: { type: \"string\" },\n patch: {\n type: \"object\",\n properties: {\n description: { type: \"string\" },\n intent: { type: \"string\" },\n memory_append: { type: \"array\", items: { type: \"string\" } },\n memory_replace: { type: \"array\", items: { type: \"string\" } },\n },\n additionalProperties: false,\n },\n },\n required: [\"name\", \"patch\"],\n additionalProperties: false,\n },\n};\n\nconst SIGHTMAP_CHECK: ToolDefinition = {\n name: \"sightmap_check\",\n description:\n \"Validate the loaded sightmap. level='schema' returns only schema-level diagnostics (parse errors, schema failures, merge collisions). level='quality' (default) also runs lint rules: duplicate routes, route shadowing, selector syntax, unknown source attributions. Returns an array of diagnostics; an empty array means clean.\",\n inputSchema: {\n type: \"object\",\n properties: {\n level: {\n type: \"string\",\n enum: [\"schema\", \"quality\"],\n description: \"Default 'quality'.\",\n },\n },\n additionalProperties: false,\n },\n};\n\nconst SIGHTMAP_GET_VIEW: ToolDefinition = {\n name: \"sightmap_get_view\",\n description:\n \"Fetch a single view by name, including all memory, components, and requests. Returns the file path the view was read from for subsequent edits. Use sightmap_list_views first to discover view names.\",\n inputSchema: {\n type: \"object\",\n properties: {\n name: { type: \"string\", description: \"View name (case-sensitive).\" },\n },\n required: [\"name\"],\n additionalProperties: false,\n },\n};\n\nconst SIGHTMAP_LIST_VIEWS: ToolDefinition = {\n name: \"sightmap_list_views\",\n description:\n \"List all views in the loaded sightmap. Returns compact summaries (name, route, description) by default; pass detail='full' for the complete view objects including memory and components. Token-efficient: prefer the default for any agent that hasn't yet narrowed to a specific view.\",\n inputSchema: {\n type: \"object\",\n properties: {\n detail: {\n type: \"string\",\n enum: [\"summary\", \"full\"],\n description: \"Default 'summary'.\",\n },\n },\n additionalProperties: false,\n },\n};\n\nconst SIGHTMAP_ACT: ToolDefinition = {\n name: \"sightmap_act\",\n description:\n \"Performs an action on a UI element. Prefer `componentName` so the agent operates in sightmap semantics; fall back to a raw `selector` for one-off targets the sightmap doesn't define (e.g., a stray link or a third-party widget). Supported actions: 'click' (browser_click), 'type' (browser_type, requires `text`), 'hover' (browser_hover). Pass exactly one of `componentName` or `selector`.\",\n inputSchema: {\n type: \"object\",\n properties: {\n componentName: {\n type: \"string\",\n description: \"Sightmap component name to act on (case-sensitive). Mutually exclusive with `selector`.\",\n },\n selector: {\n type: \"string\",\n description:\n \"Escape hatch: a raw CSS selector for a target the sightmap doesn't name. Same tagging + dispatch path as componentName. Use this only when no sightmap component fits — most actions should use `componentName` so the agent's reasoning stays in sightmap semantics. Mutually exclusive with `componentName`.\",\n },\n action: {\n type: \"string\",\n enum: [\"click\", \"type\", \"hover\"],\n description: \"The action to perform on the component.\",\n },\n text: {\n type: \"string\",\n description: \"Required for action='type'. Text to enter into the matched element.\",\n },\n submit: {\n type: \"boolean\",\n description: \"For action='type' only. Press Enter after typing.\",\n },\n instance: {\n type: \"integer\",\n minimum: 0,\n description:\n \"Zero-based index of the matching element when the component selector resolves to multiple elements (default 0). Use sightmap_snapshot.matchCount to discover how many instances exist. Mutually exclusive with `containingText`.\",\n },\n containingText: {\n type: \"string\",\n description:\n \"Disambiguator for multi-match components: pick the first element whose visible text contains this substring (case-insensitive). Use this instead of `instance` when you can identify the element by its visible label rather than position. Mutually exclusive with `instance`.\",\n },\n },\n required: [\"componentName\", \"action\"],\n additionalProperties: false,\n },\n};\n\n/**\n * Upstream tools whose sightmap-aware equivalents should appear instead in\n * the listed-tools surface. The agent only sees one of each pair, biasing\n * its tool choices toward sightmap semantics. Direct invocation by name\n * still works for callers that need the raw passthrough.\n */\nconst SHADOWED_UPSTREAM_TOOLS: ReadonlySet<string> = new Set([\n \"browser_snapshot\",\n \"browser_click\",\n \"browser_type\",\n \"browser_hover\",\n \"browser_network_requests\",\n]);\n\n/**\n * Core dispatcher for the sightmap-mcp wrapper.\n *\n * Holds the loaded sightmap, exposes the surface of sightmap-aware tools, and\n * dispatches `callTool` requests. Transport-agnostic — wired up to stdio in\n * the CLI entry, and unit-testable directly without spinning up MCP plumbing.\n *\n * Phase 1 surface: `sightmap_match` only. Subsequent phases add\n * `sightmap_snapshot` and `sightmap_act`, plus a passthrough proxy for the\n * upstream @playwright/mcp tools.\n */\nexport class SightmapMcpServer {\n private readonly sightmap: Sightmap;\n private readonly upstream: UpstreamClient | undefined;\n private readonly curateRoot: string | undefined;\n\n constructor(opts: SightmapMcpServerOptions) {\n this.sightmap = opts.sightmap;\n this.upstream = opts.upstream;\n this.curateRoot = opts.curateRoot;\n }\n\n /** Synchronous list of sightmap-aware tools that don't need an upstream. */\n listTools(): ToolDefinition[] {\n return [\n SIGHTMAP_MATCH,\n SIGHTMAP_LIST_VIEWS,\n SIGHTMAP_GET_VIEW,\n SIGHTMAP_CHECK,\n SIGHTMAP_UPDATE_VIEW,\n SIGHTMAP_INIT_PROJECT,\n ];\n }\n\n /** Full async list including upstream-proxied tools, if configured. */\n async listToolsAsync(): Promise<ToolDefinition[]> {\n const own: ToolDefinition[] = [\n SIGHTMAP_MATCH,\n SIGHTMAP_LIST_VIEWS,\n SIGHTMAP_GET_VIEW,\n SIGHTMAP_CHECK,\n SIGHTMAP_UPDATE_VIEW,\n SIGHTMAP_INIT_PROJECT,\n ];\n if (this.upstream !== undefined) {\n own.push(SIGHTMAP_SNAPSHOT, SIGHTMAP_ACT, SIGHTMAP_NETWORK_REQUESTS);\n }\n if (this.upstream === undefined) return own;\n const upstreamTools = await this.upstream.listTools();\n // Hide upstream tools that have a sightmap_* equivalent. Goal: nudge the\n // agent toward the sightmap-aware surface instead of letting it fall\n // back to the generic browser_* duplicates by habit. Calls to these\n // hidden tools still pass through if the agent invokes them by name —\n // hiding only affects the discovery surface.\n const shadowed = SHADOWED_UPSTREAM_TOOLS;\n const filtered = upstreamTools.filter((t) => !shadowed.has(t.name));\n return [...own, ...filtered];\n }\n\n /** All prompts the server advertises. Static; no upstream involvement. */\n listPrompts(): PromptDefinition[] {\n return PROMPT_REGISTRY.map((p) => p.definition);\n }\n\n /**\n * Resolve a prompt by name, validate args, and produce the prompt result\n * (the messages the agent will inject). Throws on unknown names or on a\n * handler that itself throws (e.g., bad phase value).\n */\n getPrompt(name: string, args: Record<string, string>): PromptResult {\n const entry: PromptEntry | undefined = PROMPT_REGISTRY.find(\n (p) => p.definition.name === name,\n );\n if (entry === undefined) throw new Error(`unknown prompt: ${name}`);\n return entry.handler(args);\n }\n\n async callTool(name: string, args: Record<string, unknown>): Promise<ToolResult> {\n if (isSightmapTool(name)) {\n switch (name) {\n case \"sightmap_match\":\n return this.callSightmapMatch(args);\n case \"sightmap_list_views\":\n return this.callSightmapListViews(args);\n case \"sightmap_get_view\":\n return this.callSightmapGetView(args);\n case \"sightmap_check\":\n return this.callSightmapCheck(args);\n case \"sightmap_update_view\":\n return this.callSightmapUpdateView(args);\n case \"sightmap_init_project\":\n return this.callSightmapInitProject(args);\n case \"sightmap_snapshot\":\n return this.callSightmapSnapshot();\n case \"sightmap_act\":\n return this.callSightmapAct(args);\n case \"sightmap_network_requests\":\n return this.callSightmapNetworkRequests(args);\n default:\n return errorResult(`Unknown sightmap tool: ${name}`);\n }\n }\n if (this.upstream !== undefined) {\n return this.upstream.callTool(name, args);\n }\n return errorResult(`Unknown tool: ${name}`);\n }\n\n /**\n * Tag a single element matching `selector` with a unique\n * `data-sm-act-target` attribute and return a CSS selector that resolves\n * to exactly that element. The selection mode picks WHICH match to tag:\n * - `{ kind: \"index\", index }` — pick the Nth match (default).\n * - `{ kind: \"containingText\", text }` — pick the first match whose\n * `textContent` contains `text` (case-insensitive).\n *\n * Returns null if no candidate is selected (index out of range, or no\n * element's text contains the needle).\n */\n private async tagSingleMatch(\n selector: string,\n selection:\n | { kind: \"index\"; index: number }\n | { kind: \"containingText\"; text: string },\n ): Promise<string | null> {\n if (this.upstream === undefined) return null;\n const marker = `sm-${Math.random().toString(36).slice(2, 10)}-${Date.now().toString(36)}`;\n const pickExpr =\n selection.kind === \"index\"\n ? `els[${selection.index}]`\n : `els.find((el) => (el.textContent || \"\").toLowerCase().includes(${JSON.stringify(selection.text.toLowerCase())}))`;\n const fnBody = `() => {\n const els = Array.from(document.querySelectorAll(${JSON.stringify(selector)}));\n const target = ${pickExpr};\n if (!target) return null;\n target.setAttribute(\"data-sm-act-target\", ${JSON.stringify(marker)});\n return \"[data-sm-act-target=\\\\\"\" + ${JSON.stringify(marker)} + \"\\\\\"]\";\n }`;\n const r = await this.upstream.callTool(\"browser_evaluate\", { function: fnBody });\n if (r.isError === true) return null;\n const text = r.content.map((b) => b.text).join(\"\\n\");\n const decoded = decodeMcpEvalResult(text);\n if (typeof decoded !== \"string\") return null;\n if (!decoded.includes(`data-sm-act-target=\"${marker}\"`)) return null;\n return decoded;\n }\n\n private async callSightmapNetworkRequests(\n args: Record<string, unknown>,\n ): Promise<ToolResult> {\n if (this.upstream === undefined) {\n return errorResult(\n \"sightmap_network_requests: requires an upstream (e.g., @playwright/mcp).\",\n );\n }\n const upstreamArgs: Record<string, unknown> = {};\n if (typeof args[\"static\"] === \"boolean\") upstreamArgs[\"static\"] = args[\"static\"];\n if (typeof args[\"filter\"] === \"string\") upstreamArgs[\"filter\"] = args[\"filter\"];\n\n const r = await this.upstream.callTool(\"browser_network_requests\", upstreamArgs);\n if (r.isError === true) {\n return r;\n }\n const text = r.content.map((b) => b.text).join(\"\\n\");\n const parsed = parseNetworkRequestsText(text);\n const annotated = annotateNetworkRequests(this.sightmap, parsed);\n return {\n content: [{ type: \"text\", text: JSON.stringify({ requests: annotated }, null, 2) }],\n };\n }\n\n private async callSightmapAct(args: Record<string, unknown>): Promise<ToolResult> {\n if (this.upstream === undefined) {\n return errorResult(\n \"sightmap_act: requires an upstream (e.g., @playwright/mcp) to be configured.\",\n );\n }\n const hasComponent =\n typeof args[\"componentName\"] === \"string\" && args[\"componentName\"].length > 0;\n const hasSelector =\n typeof args[\"selector\"] === \"string\" && args[\"selector\"].length > 0;\n if (hasComponent && hasSelector) {\n return errorResult(\n \"sightmap_act: `componentName` and `selector` are mutually exclusive — pass one, not both.\",\n );\n }\n if (!hasComponent && !hasSelector) {\n return errorResult(\n \"sightmap_act: pass either `componentName` (preferred) or `selector` (escape hatch for off-sightmap targets).\",\n );\n }\n if (typeof args[\"action\"] !== \"string\") {\n return errorResult(\"sightmap_act: required argument `action` (string) is missing.\");\n }\n\n const action = args[\"action\"];\n const validActions = new Set([\"click\", \"type\", \"hover\"]);\n if (!validActions.has(action)) {\n return errorResult(\n `sightmap_act: unsupported action \"${action}\". Supported: click, type, hover.`,\n );\n }\n if (action === \"type\" && typeof args[\"text\"] !== \"string\") {\n return errorResult(\"sightmap_act: action='type' requires `text` (string).\");\n }\n\n const hasInstance = typeof args[\"instance\"] === \"number\";\n const hasContainingText =\n typeof args[\"containingText\"] === \"string\" && args[\"containingText\"].length > 0;\n if (hasInstance && hasContainingText) {\n return errorResult(\n \"sightmap_act: `instance` and `containingText` are mutually exclusive — pass one, not both.\",\n );\n }\n\n // Resolve the target: either via sightmap lookup or directly from `selector`.\n let targetSelector: string;\n let targetLabel: string;\n if (hasComponent) {\n const resolved = resolveSightmapAct(this.sightmap, {\n componentName: args[\"componentName\"] as string,\n });\n if (resolved.kind === \"error\") {\n return errorResult(\"sightmap_act: \" + resolved.message);\n }\n targetSelector = resolved.selector;\n targetLabel = resolved.componentName;\n } else {\n targetSelector = args[\"selector\"] as string;\n targetLabel = `selector:${targetSelector}`;\n }\n const resolved = { kind: \"ok\" as const, componentName: targetLabel, selector: targetSelector };\n\n // Tag a single matching element with a unique data-sm-act-target marker\n // via browser_evaluate, then act on that uniquely-tagged element. This\n // sidesteps Playwright's strict-mode multi-match violation regardless of\n // whether the sightmap selector resolves to one element or many. Costs\n // one extra round-trip per action; buys universal correctness.\n const selection: { kind: \"index\"; index: number } | { kind: \"containingText\"; text: string } =\n hasContainingText\n ? { kind: \"containingText\", text: args[\"containingText\"] as string }\n : { kind: \"index\", index: hasInstance ? Math.floor(args[\"instance\"] as number) : 0 };\n const taggedSelector = await this.tagSingleMatch(resolved.selector, selection);\n if (taggedSelector === null) {\n const reason =\n selection.kind === \"containingText\"\n ? `no instance of \"${resolved.componentName}\" contains text ${JSON.stringify(selection.text)}`\n : `could not tag the element at instance=${selection.index} for component \"${resolved.componentName}\"`;\n return errorResult(\n `sightmap_act: ${reason}. The selector ${JSON.stringify(resolved.selector)} ` +\n `may not resolve any matching elements on the current page.`,\n );\n }\n\n const baseArgs: Record<string, unknown> = {\n target: taggedSelector,\n element: resolved.componentName,\n };\n\n let upstreamName: string;\n let upstreamArgs: Record<string, unknown>;\n switch (action) {\n case \"click\":\n upstreamName = \"browser_click\";\n upstreamArgs = baseArgs;\n break;\n case \"hover\":\n upstreamName = \"browser_hover\";\n upstreamArgs = baseArgs;\n break;\n case \"type\":\n upstreamName = \"browser_type\";\n upstreamArgs = {\n ...baseArgs,\n text: args[\"text\"],\n ...(args[\"submit\"] === true ? { submit: true } : {}),\n };\n break;\n default:\n return errorResult(`sightmap_act: unsupported action \"${action}\".`);\n }\n\n return this.upstream.callTool(upstreamName, upstreamArgs);\n }\n\n private async callSightmapSnapshot(): Promise<ToolResult> {\n if (this.upstream === undefined) {\n return errorResult(\n \"sightmap_snapshot: requires an upstream (e.g., @playwright/mcp) to be configured.\",\n );\n }\n\n // 1. Pull the ARIA snapshot from upstream.\n const snapResult = await this.upstream.callTool(\"browser_snapshot\", {});\n if (snapResult.isError === true) {\n return errorResult(\n \"sightmap_snapshot: upstream browser_snapshot failed: \" +\n (snapResult.content[0]?.text ?? \"unknown error\"),\n );\n }\n const ariaSnapshotText = snapResult.content.map((b) => b.text).join(\"\\n\");\n\n // 2. Determine the URL and find sightmap-applicable components for it.\n // We do this server-side via match(), so the in-page eval only needs\n // to look up `document.querySelectorAll(selector)` for each.\n const currentUrl = parsePageUrl(ariaSnapshotText) ?? \"\";\n const matchResult = sightmapMatch(this.sightmap, { url: currentUrl });\n const componentSelectors = matchResult.components.map((c) => ({\n name: c.name,\n selector: c.selector,\n }));\n\n // 3. In-page evaluate: query each component's selectors, return matchCount\n // and first match's bounding rect.\n const evalResult = await this.upstream.callTool(\"browser_evaluate\", {\n function: buildInPageEvalFunction(componentSelectors),\n });\n if (evalResult.isError === true) {\n return errorResult(\n \"sightmap_snapshot: upstream browser_evaluate failed: \" +\n (evalResult.content[0]?.text ?? \"unknown error\"),\n );\n }\n const inPageMatches = parseInPageEvalResult(\n evalResult.content.map((b) => b.text).join(\"\\n\"),\n );\n\n // 4. Synthesize the response.\n const response = buildSightmapSnapshotResponse({\n sightmap: this.sightmap,\n currentUrl,\n ariaSnapshotText,\n inPageMatches,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(response, null, 2) }],\n };\n }\n\n private callSightmapMatch(args: Record<string, unknown>): ToolResult {\n if (typeof args[\"url\"] !== \"string\" || args[\"url\"].length === 0) {\n return errorResult(\"sightmap_match: required argument `url` (string) is missing or empty.\");\n }\n const input: { url: string; method?: string } = { url: args[\"url\"] };\n if (typeof args[\"method\"] === \"string\") {\n input.method = args[\"method\"];\n }\n const output = handleSightmapMatch(this.sightmap, input);\n return {\n content: [{ type: \"text\", text: JSON.stringify(output, null, 2) }],\n };\n }\n\n private async callSightmapGetView(args: Record<string, unknown>): Promise<ToolResult> {\n if (this.curateRoot === undefined) {\n return errorResult(\n \"sightmap_get_view: no writable sightmap dir configured (pass --curate-root or --sightmap-dir).\",\n );\n }\n if (typeof args[\"name\"] !== \"string\" || args[\"name\"].length === 0) {\n return errorResult(\"sightmap_get_view: required argument `name` (string) is missing or empty.\");\n }\n try {\n const result = await handleGetView({\n sightmapDir: this.curateRoot,\n name: args[\"name\"],\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n } catch (err) {\n return errorResult(err instanceof Error ? err.message : String(err));\n }\n }\n\n private async callSightmapInitProject(args: Record<string, unknown>): Promise<ToolResult> {\n const input: InitProjectInput = {};\n if (typeof args[\"dir\"] === \"string\") input.dir = args[\"dir\"];\n if (args[\"force\"] === true) input.force = true;\n try {\n const result = await handleInitProject(input);\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n } catch (err) {\n return errorResult(err instanceof Error ? err.message : String(err));\n }\n }\n\n private async callSightmapUpdateView(args: Record<string, unknown>): Promise<ToolResult> {\n if (this.curateRoot === undefined) {\n return errorResult(\n \"sightmap_update_view: no writable sightmap dir configured (pass --curate-root or --sightmap-dir).\",\n );\n }\n if (typeof args[\"name\"] !== \"string\" || args[\"name\"].length === 0) {\n return errorResult(\n \"sightmap_update_view: required argument `name` (string) is missing or empty.\",\n );\n }\n if (\n args[\"patch\"] === null ||\n typeof args[\"patch\"] !== \"object\" ||\n Array.isArray(args[\"patch\"])\n ) {\n return errorResult(\n \"sightmap_update_view: required argument `patch` (object) is missing.\",\n );\n }\n try {\n const result = await handleUpdateView({\n sightmapDir: this.curateRoot,\n name: args[\"name\"],\n patch: args[\"patch\"] as ViewPatch,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n } catch (err) {\n return errorResult(err instanceof Error ? err.message : String(err));\n }\n }\n\n private async callSightmapCheck(args: Record<string, unknown>): Promise<ToolResult> {\n const input: CheckInput = {};\n if (args[\"level\"] === \"schema\" || args[\"level\"] === \"quality\") {\n input.level = args[\"level\"];\n } else if (args[\"level\"] !== undefined) {\n return errorResult(\n `sightmap_check: level must be \"schema\" or \"quality\".`,\n );\n }\n const result = await handleCheck(this.sightmap, input);\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n }\n\n private callSightmapListViews(args: Record<string, unknown>): ToolResult {\n const input: ListViewsInput = {};\n if (args[\"detail\"] === \"summary\" || args[\"detail\"] === \"full\") {\n input.detail = args[\"detail\"];\n } else if (args[\"detail\"] !== undefined) {\n return errorResult(\n `sightmap_list_views: detail must be \"summary\" or \"full\".`,\n );\n }\n const output = handleListViews(this.sightmap, input);\n return {\n content: [{ type: \"text\", text: JSON.stringify(output, null, 2) }],\n };\n }\n}\n\nfunction errorResult(text: string): ToolResult {\n return {\n content: [{ type: \"text\", text }],\n isError: true,\n };\n}\n\nfunction isSightmapTool(name: string): boolean {\n return name.startsWith(\"sightmap_\");\n}\n\n/** Extract the \"Page URL: ...\" line from an upstream browser_snapshot response. */\nfunction parsePageUrl(text: string): string | null {\n const m = /Page URL:\\s*(\\S+)/.exec(text);\n return m?.[1] ?? null;\n}\n\n/**\n * Build the in-page evaluate function body. Embeds the component selectors\n * inline; the page only needs to query the DOM. No sightmap-js dependency\n * in the page context.\n */\nfunction buildInPageEvalFunction(\n components: Array<{ name: string; selector: string[] }>,\n): string {\n const componentsJson = JSON.stringify(components);\n return `() => {\n const components = ${componentsJson};\n const matches = components.map((c) => {\n const selectors = c.selector || [];\n const seen = new Set();\n const elements = [];\n for (const sel of selectors) {\n try {\n const found = document.querySelectorAll(sel);\n for (const el of Array.from(found)) {\n if (!seen.has(el)) {\n seen.add(el);\n elements.push(el);\n }\n }\n } catch {\n // Invalid selector — skip silently.\n }\n }\n const first = elements[0];\n let samplePosition;\n if (first && typeof first.getBoundingClientRect === \"function\") {\n const r = first.getBoundingClientRect();\n samplePosition = { x: r.x, y: r.y, width: r.width, height: r.height };\n }\n return {\n name: c.name,\n selector: selectors,\n matchCount: elements.length,\n samplePosition,\n };\n });\n return { url: window.location.href, matches };\n }`;\n}\n\n/**\n * Parse the upstream `browser_evaluate` response text into a JSON payload.\n *\n * @playwright/mcp wraps the result like:\n * ### Result\n * {\"url\": \"...\", \"matches\": [...]}\n * ### Ran Playwright code\n * ...\n *\n * We extract the first JSON object after `### Result`. If the format changes,\n * fall back to a generic { from first '{' } scan.\n */\nfunction parseInPageEvalResult(text: string): InPageSightmapMatch[] {\n const afterResult = text.split(/^###\\s*Result/im)[1] ?? text;\n const start = afterResult.indexOf(\"{\");\n if (start < 0) return [];\n for (let end = afterResult.length; end > start; end--) {\n try {\n const parsed = JSON.parse(afterResult.slice(start, end)) as {\n url?: string;\n matches?: unknown[];\n };\n if (Array.isArray(parsed.matches)) {\n return parsed.matches.filter(isInPageMatch);\n }\n } catch {\n // try shorter window\n }\n }\n return [];\n}\n\n/**\n * Decode the value an upstream `browser_evaluate` returned to us.\n * Format is text after `### Result`, JSON-encoded: a number is `42`, a\n * string is `\"foo\"`, an object/array is the JSON literal.\n */\nfunction decodeMcpEvalResult(text: string): unknown {\n const afterResult = text.split(/^###\\s*Result/im)[1] ?? \"\";\n const trimmed = afterResult.trim();\n if (trimmed.length === 0) return undefined;\n // Find the first JSON-y token at the start of trimmed.\n for (let end = trimmed.length; end > 0; end--) {\n try {\n return JSON.parse(trimmed.slice(0, end));\n } catch {\n // try shorter\n }\n }\n return undefined;\n}\n\nfunction isInPageMatch(value: unknown): value is InPageSightmapMatch {\n if (typeof value !== \"object\" || value === null) return false;\n const v = value as Record<string, unknown>;\n return typeof v[\"name\"] === \"string\" && typeof v[\"matchCount\"] === \"number\";\n}\n","import { match as sightmapMatch, type Sightmap, type MatchResult } from \"@sightmap/sightmap\";\n\nexport interface SightmapMatchInput {\n url: string;\n method?: string;\n}\n\nexport interface SightmapMatchOutput {\n view: { name: string; route: string; description?: string } | null;\n components: Array<{\n name: string;\n selector: string[];\n memory: string[];\n scope: \"global\" | \"view-scoped\";\n }>;\n requests: Array<{\n name: string;\n route: string;\n method?: string;\n memory: string[];\n }>;\n /** Page-level aggregated memory from sightmap-js. */\n memory: string[];\n /** Memory attached to the matched view itself, if any. */\n viewMemory: string[];\n}\n\n/**\n * Pure handler for the `sightmap_match` MCP tool.\n *\n * Wraps sightmap-js's `match()` and shapes the response for agent consumption.\n * No browser involvement — this is the planning-side query: \"what should I\n * expect at this URL?\"\n */\nexport function handleSightmapMatch(\n sightmap: Sightmap,\n input: SightmapMatchInput,\n): SightmapMatchOutput {\n const result: MatchResult = sightmapMatch(sightmap, {\n url: input.url,\n ...(input.method !== undefined ? { method: input.method } : {}),\n });\n\n return {\n view: result.view\n ? {\n name: result.view.name,\n route: result.view.route,\n ...(result.view.description !== undefined\n ? { description: result.view.description }\n : {}),\n }\n : null,\n components: result.components.map((c) => ({\n name: c.name,\n selector: c.selector,\n memory: c.memory ?? [],\n scope: c.scope,\n })),\n requests: result.requests.map((r) => ({\n name: r.name,\n route: r.route,\n ...(r.method !== undefined ? { method: r.method } : {}),\n memory: r.memory ?? [],\n })),\n memory: result.memory ?? [],\n viewMemory: result.view?.memory ?? [],\n };\n}\n","import { match as sightmapMatch, type Sightmap } from \"@sightmap/sightmap\";\n\nexport interface BoundingRect {\n x: number;\n y: number;\n width: number;\n height: number;\n}\n\n/**\n * What the in-page evaluate script returns for each sightmap component.\n *\n * `matchCount` is the number of DOM elements matching any of the selectors\n * (after dedup); `samplePosition` is the bounding rect of the first match,\n * which the agent can use to disambiguate when there are multiple instances.\n */\nexport interface InPageSightmapMatch {\n name: string;\n selector: string[];\n matchCount: number;\n samplePosition?: BoundingRect | undefined;\n}\n\nexport interface BuildSnapshotOptions {\n sightmap: Sightmap;\n currentUrl: string;\n ariaSnapshotText: string;\n inPageMatches: InPageSightmapMatch[];\n}\n\nexport interface SightmapSnapshotComponent {\n name: string;\n selector: string[];\n memory: string[];\n scope: \"global\" | \"view-scoped\";\n matchCount: number;\n samplePosition?: BoundingRect | undefined;\n}\n\nexport interface SightmapSnapshotResponse {\n view: { name: string; route: string; memory: string[] } | null;\n components: SightmapSnapshotComponent[];\n /** Page-level memory aggregate (sightmap-js MatchResult.memory). */\n memory: string[];\n /** Raw ARIA tree text passthrough from `browser_snapshot`. */\n ariaSnapshot: string;\n}\n\n/**\n * Pure function that combines a parsed sightmap, the agent's current URL,\n * the upstream ARIA snapshot text, and the in-page sightmap match results\n * into a single response shape suitable for the `sightmap_snapshot` tool.\n *\n * Side-effect-free; all I/O happens at the dispatcher boundary.\n */\nexport function buildSightmapSnapshotResponse(\n opts: BuildSnapshotOptions,\n): SightmapSnapshotResponse {\n const { sightmap, currentUrl, ariaSnapshotText, inPageMatches } = opts;\n const result = sightmapMatch(sightmap, { url: currentUrl });\n\n const inPageByName = new Map<string, InPageSightmapMatch>();\n for (const m of inPageMatches) inPageByName.set(m.name, m);\n\n const components: SightmapSnapshotComponent[] = result.components.map((c) => {\n const inPage = inPageByName.get(c.name);\n return {\n name: c.name,\n selector: c.selector,\n memory: c.memory ?? [],\n scope: c.scope,\n matchCount: inPage?.matchCount ?? 0,\n ...(inPage?.samplePosition !== undefined\n ? { samplePosition: inPage.samplePosition }\n : {}),\n };\n });\n\n return {\n view: result.view\n ? {\n name: result.view.name,\n route: result.view.route,\n memory: result.view.memory ?? [],\n }\n : null,\n components,\n memory: result.memory ?? [],\n ariaSnapshot: ariaSnapshotText,\n };\n}\n","import type { Sightmap } from \"@sightmap/sightmap\";\nimport type { Component } from \"@sightmap/sightmap\";\n\nexport interface ResolveSightmapActInput {\n componentName: string;\n}\n\nexport type ResolveSightmapActResult =\n | {\n kind: \"ok\";\n componentName: string;\n selector: string;\n /** All selectors for this component, in declared order. */\n allSelectors: string[];\n }\n | { kind: \"error\"; message: string };\n\n/**\n * Resolve a sightmap component by name to a CSS selector that the upstream\n * MCP's action tools (browser_click, browser_type, browser_hover, ...) can\n * use as the `target` parameter.\n *\n * Lookup order:\n * 1. Global components (sightmap.globalComponents)\n * 2. View-scoped components, walking each view's `components` list\n *\n * The first selector in the matching component's selector array is returned;\n * additional selectors are exposed in `allSelectors` so callers can fall\n * back if PW-MCP's first-selector resolution fails.\n */\nexport function resolveSightmapAct(\n sightmap: Sightmap,\n input: ResolveSightmapActInput,\n): ResolveSightmapActResult {\n const found = findComponentByName(sightmap, input.componentName);\n if (found === null) {\n return {\n kind: \"error\",\n message: `Component \"${input.componentName}\" not found in the loaded sightmap.`,\n };\n }\n\n const selectors = Array.isArray(found.selector) ? found.selector : [];\n if (selectors.length === 0) {\n return {\n kind: \"error\",\n message: `Component \"${input.componentName}\" has no selector — cannot dispatch an action.`,\n };\n }\n\n return {\n kind: \"ok\",\n componentName: input.componentName,\n selector: selectors[0]!,\n allSelectors: selectors,\n };\n}\n\nfunction findComponentByName(sightmap: Sightmap, name: string): Component | null {\n for (const c of sightmap.globalComponents) {\n if (c.name === name) return c;\n }\n for (const v of sightmap.views) {\n for (const c of v.components ?? []) {\n if (c.name === name) return c;\n }\n }\n return null;\n}\n","import { match as sightmapMatch, type Sightmap } from \"@sightmap/sightmap\";\n\nexport interface ParsedNetworkRequest {\n method: string;\n url: string;\n status: number;\n statusText: string;\n}\n\nexport interface AnnotatedNetworkRequest extends ParsedNetworkRequest {\n sightmapName?: string;\n sightmapMemory?: string[];\n}\n\n/**\n * Parse the text output of `@playwright/mcp` `browser_network_requests`.\n *\n * Expected line format (one request per line, in the body after `### Result`):\n *\n * N. [METHOD] URL => [STATUS] STATUS_TEXT\n *\n * Lines that don't match are silently dropped — `browser_network_requests`\n * also emits notes about static resources, page-level metadata, etc.\n */\nexport function parseNetworkRequestsText(text: string): ParsedNetworkRequest[] {\n const lines = text.split(/\\r?\\n/);\n const requests: ParsedNetworkRequest[] = [];\n // Match: \"1. [GET] http://x.test/api/x => [200] OK\"\n // The URL portion can contain anything but \" =>\". We anchor on the brackets.\n const re = /^\\s*\\d+\\.\\s*\\[([A-Z]+)\\]\\s+(\\S+)\\s+=>\\s+\\[(\\d+)\\]\\s+(.*?)\\s*$/;\n for (const line of lines) {\n const m = re.exec(line);\n if (m === null) continue;\n requests.push({\n method: m[1] ?? \"\",\n url: m[2] ?? \"\",\n status: Number.parseInt(m[3] ?? \"0\", 10),\n statusText: m[4] ?? \"\",\n });\n }\n return requests;\n}\n\n/**\n * Cross-reference each captured network request with sightmap's `requests:`\n * declarations. When a match is found, attaches the sightmap name + memory\n * to the response. Unmatched requests are returned unchanged.\n */\nexport function annotateNetworkRequests(\n sightmap: Sightmap,\n requests: ParsedNetworkRequest[],\n): AnnotatedNetworkRequest[] {\n return requests.map((req) => {\n // Use sightmap-js's match() per request — it does the same glob\n // routeMatch + method filter that we'd need to replicate.\n const result = sightmapMatch(sightmap, { url: req.url, method: req.method });\n const first = result.requests[0];\n if (first === undefined) return req;\n const annotated: AnnotatedNetworkRequest = { ...req, sightmapName: first.name };\n if (first.memory && first.memory.length > 0) {\n annotated.sightmapMemory = first.memory;\n }\n return annotated;\n });\n}\n","// `sightmap_list_views` handler.\n//\n// Read-only; defaults to compact summaries (name + route + optional\n// description) so a single-call discovery in an agent's first turn fits in a\n// small token budget. `detail: \"full\"` returns the entire View object\n// including memory, components, and requests.\n\nimport type { Sightmap, View } from \"@sightmap/sightmap\";\n\nexport interface ListViewsInput {\n detail?: \"summary\" | \"full\";\n}\n\nexport interface ViewSummary {\n name: string;\n route: string;\n description?: string;\n}\n\nexport interface ListViewsOutput {\n views: Array<ViewSummary | View>;\n}\n\nexport function handleListViews(\n sightmap: Sightmap,\n input: ListViewsInput,\n): ListViewsOutput {\n const detail = input.detail ?? \"summary\";\n const sorted = [...sightmap.views].sort((a, b) =>\n a.name.localeCompare(b.name),\n );\n\n if (detail === \"full\") {\n return { views: sorted };\n }\n\n return {\n views: sorted.map((v) => {\n const summary: ViewSummary = { name: v.name, route: v.route };\n if (v.description !== undefined) summary.description = v.description;\n return summary;\n }),\n };\n}\n","// `sightmap_get_view` handler.\n//\n// Read-only single-view fetch. Returns the parsed view object plus the file\n// path it was read from, so callers can chain `update_view` against the same\n// file without an extra lookup.\n\nimport { readFile } from \"node:fs/promises\";\nimport { parse, type View } from \"@sightmap/sightmap\";\nimport { findFileForView } from \"../../curate/locator.js\";\n\nexport interface GetViewInput {\n sightmapDir: string;\n name: string;\n}\n\nexport interface GetViewOutput {\n view: View;\n file: string;\n}\n\nexport async function handleGetView(input: GetViewInput): Promise<GetViewOutput> {\n const file = await findFileForView(input.sightmapDir, input.name);\n if (file === null) {\n throw new Error(\n `View \"${input.name}\" not found in ${input.sightmapDir}`,\n );\n }\n const text = await readFile(file, \"utf8\");\n const parsed = parse(text, { sourceFile: file });\n const view = parsed.views?.find((v) => v.name === input.name);\n if (view === undefined) {\n throw new Error(\n `View \"${input.name}\" not found in ${file} (locator drift?)`,\n );\n }\n return { view, file };\n}\n","// Locate the YAML file in a `.sightmap/` directory that contains a given view.\n//\n// Used by curation tools (`get_view`, `update_view`) so callers can pass a view\n// name without also tracking which file declared it.\n\nimport { readdir, readFile } from \"node:fs/promises\";\nimport { join } from \"node:path\";\nimport { parse } from \"@sightmap/sightmap\";\n\nexport type FindViewOptions = {\n onWarning?: (msg: string) => void;\n};\n\nexport async function findFileForView(\n sightmapDir: string,\n viewName: string,\n options: FindViewOptions = {},\n): Promise<string | null> {\n const entries = await readdir(sightmapDir);\n const yamlFiles = entries\n .filter((e) => e.endsWith(\".yaml\") || e.endsWith(\".yml\"))\n .sort();\n\n let firstMatch: string | null = null;\n let matchCount = 0;\n\n for (const file of yamlFiles) {\n const path = join(sightmapDir, file);\n let parsed;\n try {\n const text = await readFile(path, \"utf8\");\n parsed = parse(text, { sourceFile: path });\n } catch {\n // Skip unparseable files; `sightmap_check` is the right tool for those.\n continue;\n }\n if (parsed.views?.some((v) => v.name === viewName)) {\n matchCount++;\n if (firstMatch === null) firstMatch = path;\n }\n }\n\n if (matchCount > 1 && options.onWarning) {\n options.onWarning(\n `duplicate view name \"${viewName}\" found in ${matchCount} files; using ${firstMatch}`,\n );\n }\n\n return firstMatch;\n}\n","// `sightmap_check` handler.\n//\n// Wraps `@sightmap/sightmap`'s `lint` plus the merge/load diagnostics already\n// attached to the loaded `Sightmap` (parse errors, schema failures, merge\n// collisions). Two levels:\n//\n// schema - return only the schema-level diagnostics already on the sightmap.\n// quality - schema diagnostics plus lint output (duplicate routes, route\n// shadowing, selector syntax, etc.).\n\nimport { lint, type Sightmap, type Diagnostic } from \"@sightmap/sightmap\";\n\nexport interface CheckInput {\n level?: \"schema\" | \"quality\";\n}\n\nexport interface CheckOutput {\n diagnostics: Diagnostic[];\n}\n\nexport async function handleCheck(\n sightmap: Sightmap,\n input: CheckInput,\n): Promise<CheckOutput> {\n const level = input.level ?? \"quality\";\n const schemaDiag = [...sightmap.diagnostics];\n if (level === \"schema\") return { diagnostics: schemaDiag };\n const lintDiag = await lint(sightmap);\n return { diagnostics: [...schemaDiag, ...lintDiag] };\n}\n","// `sightmap_update_view` handler.\n//\n// Reads the YAML file containing the named view, applies a narrow patch to\n// the agent-authored fields (description, intent, memory), then re-writes the\n// file via the canonical writer. The emitted bytes are piped through\n// `canonicalize()` so the result passes `sightmap fmt --check` (per sightmap\n// spec adapter-behavior guidance).\n//\n// Component / route / selector edits are intentionally NOT supported here\n// (those are codegen-owned in `@sightmap/react`). Memory edits use either\n// `memory_append` (the default operation) or `memory_replace` — never both\n// in the same patch.\n\nimport { readFile, writeFile } from \"node:fs/promises\";\nimport {\n parse,\n format,\n canonicalize,\n type FormatInput,\n type View,\n} from \"@sightmap/sightmap\";\nimport { findFileForView } from \"../../curate/locator.js\";\n\nexport interface ViewPatch {\n description?: string;\n intent?: string;\n memory_append?: string[];\n memory_replace?: string[];\n}\n\nexport interface UpdateViewInput {\n sightmapDir: string;\n name: string;\n patch: ViewPatch;\n}\n\nexport interface UpdateViewOutput {\n ok: true;\n file: string;\n written: View;\n}\n\nexport async function handleUpdateView(\n input: UpdateViewInput,\n): Promise<UpdateViewOutput> {\n if (input.patch.memory_append && input.patch.memory_replace) {\n throw new Error(\n \"cannot use both memory_append and memory_replace in the same patch\",\n );\n }\n\n const file = await findFileForView(input.sightmapDir, input.name);\n if (file === null) {\n throw new Error(\n `View \"${input.name}\" not found in ${input.sightmapDir}`,\n );\n }\n\n const text = await readFile(file, \"utf8\");\n const parsed = parse(text, { sourceFile: file });\n const views = parsed.views ?? [];\n const idx = views.findIndex((v) => v.name === input.name);\n if (idx < 0) {\n throw new Error(\n `View \"${input.name}\" not found in ${file} (locator drift?)`,\n );\n }\n\n const before = views[idx]!;\n const after: View & { intent?: string } = { ...before };\n if (input.patch.description !== undefined) {\n after.description = input.patch.description;\n }\n if (input.patch.intent !== undefined) {\n after.intent = input.patch.intent;\n }\n if (input.patch.memory_append) {\n after.memory = [...(before.memory ?? []), ...input.patch.memory_append];\n }\n if (input.patch.memory_replace) {\n after.memory = [...input.patch.memory_replace];\n }\n\n const nextViews: View[] = [...views];\n nextViews[idx] = after;\n const nextDoc = stripFragmentBrand(parsed as unknown as Record<string, unknown>);\n nextDoc.views = nextViews;\n const out = format(nextDoc);\n // Pipe through `canonicalize()` so the rewritten file matches what\n // `sightmap fmt --check` expects (per-entry-type key order, top-level seq\n // sort, blank-line separators, etc.). The value object came from the parsed\n // file plus a narrow patch, so canonicalize won't return schema-invalid in\n // practice; fall back to the format() bytes if it does.\n const c = canonicalize(out, { file });\n const finalText = c.kind === \"canonical\" ? c.text : out;\n await writeFile(file, finalText, \"utf8\");\n\n return { ok: true, file, written: after };\n}\n\nfunction stripFragmentBrand(input: Record<string, unknown>): FormatInput {\n const out: Record<string, unknown> = {};\n for (const k of Object.keys(input)) {\n if (k === \"__brand\" || k === \"__sourceFile\") continue;\n out[k] = input[k];\n }\n return out as FormatInput;\n}\n","// `sightmap_init_project` handler.\n//\n// Scaffolds an empty `.sightmap/app.yaml` in a target project directory.\n// Refuses to overwrite an existing `.sightmap/` unless `force: true`.\n\nimport { mkdir, writeFile, access } from \"node:fs/promises\";\nimport { join } from \"node:path\";\nimport { makeStarterSightmap } from \"../../curate/scaffolder.js\";\n\nexport interface InitProjectInput {\n dir?: string;\n force?: boolean;\n}\n\nexport interface InitProjectOutput {\n ok: true;\n files: string[];\n}\n\nexport async function handleInitProject(\n input: InitProjectInput,\n): Promise<InitProjectOutput> {\n const root = input.dir ?? process.cwd();\n const sightmapDir = join(root, \".sightmap\");\n const appFile = join(sightmapDir, \"app.yaml\");\n\n if (input.force !== true) {\n let exists = false;\n try {\n await access(sightmapDir);\n exists = true;\n } catch {\n /* dir does not exist; continue */\n }\n if (exists) {\n throw new Error(\n `.sightmap/ already exists at ${sightmapDir} — pass force=true to overwrite`,\n );\n }\n }\n\n await mkdir(sightmapDir, { recursive: true });\n await writeFile(appFile, makeStarterSightmap(), \"utf8\");\n\n return { ok: true, files: [appFile] };\n}\n","// Starter `.sightmap/` scaffolding.\n//\n// `makeStarterSightmap` returns a minimal canonical YAML document — just a\n// `version: 1` line with no views/components/requests. Real content lands when\n// the user (or `sightmap-react gen`) adds files to the directory.\n//\n// Output is piped through `canonicalize()` so the emitted bytes match what\n// `sightmap fmt --check` expects. See sightmap/spec\n// docs/authoring-conventions.md#adapter-behavior.\n\nimport { format, canonicalize } from \"@sightmap/sightmap\";\n\nexport function makeStarterSightmap(): string {\n const text = format({ version: 1 });\n const c = canonicalize(text, { file: \"app.yaml\" });\n return c.kind === \"canonical\" ? c.text : text;\n}\n","import type { PromptEntry, PromptResult } from \"./index.js\";\n\n/**\n * sightmap_sep_track — multi-phase prompt that walks an author through\n * writing a Sightmap Enhancement Proposal, the matching spec/ change,\n * and the matching conformance/ fixture.\n *\n * Phase model:\n * draft → write seps/NNNN-{slug}.md, then STOP for user confirmation\n * spec → propose a diff against spec/, then STOP for user confirmation\n * fixture → create conformance/NNN-{slug}/, then STOP for user confirmation\n * verify → terminal summary message, no further phases\n *\n * Confirmation gates are encoded as text directives in each non-final phase\n * because MCP prompts have no native \"wait for user\" primitive. The agent\n * is expected to honor them.\n *\n * Inspired by Archcore's architecture_track (Archcore audit §1.6).\n */\n\nconst VALID_PHASES = [\"draft\", \"spec\", \"fixture\", \"verify\"] as const;\ntype Phase = (typeof VALID_PHASES)[number];\n\nfunction buildDraftPhase(args: { slug?: string }): string {\n const slug = args.slug ?? \"{slug}\";\n return [\n `# SEP track — phase 1 of 4: Draft the SEP`,\n ``,\n `You are helping the user author a Sightmap Enhancement Proposal (SEP).`,\n `An SEP is required for any change to the spec's schema, semantics, or`,\n `discovery rules. See \\`seps/README.md\\` for the full list.`,\n ``,\n `## Steps for this phase`,\n ``,\n `1. **Pick a number.** Look at \\`seps/\\` and find the lowest unused 4-digit`,\n ` integer (skip \\`0000-template.md\\`). Call this NNNN.`,\n `2. **Copy the template.** \\`cp seps/0000-template.md seps/NNNN-${slug}.md\\`.`,\n `3. **Fill in the front-matter.** Title, author, today's date, status: Draft.`,\n `4. **Write the body.** Sections from the template:`,\n ` - Summary (one paragraph; treat as the abstract)`,\n ` - Motivation (concrete user-facing problem; name a real app or pattern)`,\n ` - Proposal (Shape, Semantics, Conformance — show YAML, show JSON Schema diff)`,\n ` - Alternatives considered (at least two, including \"do nothing\")`,\n ` - Migration (what changes for existing users)`,\n ` - Open questions`,\n `5. **Read it back.** Does it pass the acceptance checklist in \\`seps/README.md\\`?`,\n ``,\n `## STOP HERE`,\n ``,\n `Show the draft to the user. Ask for explicit \"go\" before continuing.`,\n `Do **not** open the spec edit until the user confirms the SEP draft.`,\n ``,\n `When the user is ready, call this prompt again with`,\n `\\`phase: \"spec\"\\` and pass \\`sep_number: \"NNNN\"\\` and \\`slug: \"${slug}\"\\`.`,\n ].join(\"\\n\");\n}\n\nfunction buildSpecPhase(args: { slug?: string; sep_number?: string }): string {\n const slug = args.slug ?? \"{slug}\";\n const sep = args.sep_number ?? \"NNNN\";\n return [\n `# SEP track — phase 2 of 4: Propose the spec change`,\n ``,\n `Building on \\`seps/${sep}-${slug}.md\\`.`,\n ``,\n `## Steps for this phase`,\n ``,\n `1. **Identify the spec files affected.** Most changes touch:`,\n ` - \\`spec/v1/sightmap.schema.json\\` (the JSON Schema)`,\n ` - \\`spec/v1/sightmap.spec.md\\` (the prose spec)`,\n ` - Possibly \\`spec/v1/examples/\\` if the change adds a shape worth showing`,\n `2. **Make the edits.** Keep the diff small. The SEP is the design doc;`,\n ` the spec edit is the precise textual change.`,\n `3. **Run \\`pnpm -F @sightmap/sightmap test\\`.** Existing examples must still`,\n ` parse and validate, unless the SEP is explicitly breaking — in which`,\n ` case the SEP's Migration section must say so.`,\n `4. **Cross-reference.** Add a \"Spec changes:\" line near the top of the SEP`,\n ` listing the touched files. Add a comment in the schema file pointing`,\n ` back to \\`seps/${sep}-${slug}.md\\` if the rationale isn't obvious from`,\n ` the diff alone.`,\n ``,\n `## STOP HERE`,\n ``,\n `Show the spec diff to the user. Ask for explicit \"go\" before continuing.`,\n `Do **not** start the conformance fixture until the user confirms the spec edit.`,\n ``,\n `When the user is ready, call this prompt again with`,\n `\\`phase: \"fixture\"\\`, \\`sep_number: \"${sep}\"\\`, \\`slug: \"${slug}\"\\`.`,\n ].join(\"\\n\");\n}\n\nfunction buildFixturePhase(args: { slug?: string; sep_number?: string }): string {\n const slug = args.slug ?? \"{slug}\";\n const sep = args.sep_number ?? \"NNNN\";\n // Conformance fixture numbers in this repo are 3-digit; SEP numbers are 4-digit.\n // Drop the leading zero of the SEP number to suggest a fixture number, but\n // tell the agent to verify against existing fixtures.\n const fixtureGuess = sep.startsWith(\"0\") ? sep.slice(1) : sep;\n return [\n `# SEP track — phase 3 of 4: Write the conformance fixture`,\n ``,\n `Building on \\`seps/${sep}-${slug}.md\\` and the spec edit from phase 2.`,\n ``,\n `## Steps for this phase`,\n ``,\n `1. **Pick a fixture number.** Conformance fixtures use 3-digit numbers`,\n ` (\\`001-minimal\\`, \\`002-multi-file-merge\\`, …). Pick the lowest unused`,\n ` number — likely \\`${fixtureGuess}\\` if the SEP and fixture numberings`,\n ` line up, but verify against \\`conformance/\\`.`,\n `2. **Create the directory.** \\`mkdir conformance/${fixtureGuess}-${slug}\\`.`,\n `3. **Write the input.** \\`conformance/${fixtureGuess}-${slug}/sightmap/\\``,\n ` contains one or more \\`.yaml\\` files demonstrating the new behavior.`,\n ` Keep it minimal — one fixture, one behavior under test.`,\n `4. **Write the expected output.** \\`conformance/${fixtureGuess}-${slug}/expected.json\\``,\n ` is the canonical merged + resolved sightmap that any spec-conformant`,\n ` parser must produce. Use the existing \\`@sightmap/sightmap\\` parser`,\n ` to generate the baseline, then hand-audit it against the SEP.`,\n `5. **Run the conformance suite.** \\`pnpm -F @sightmap/sightmap test\\` should`,\n ` pick up the new fixture and validate it.`,\n ``,\n `## STOP HERE`,\n ``,\n `Show the fixture (input + expected.json) to the user. Ask for explicit`,\n `\"go\" before continuing. Do **not** declare the SEP ready for review until`,\n `the user confirms all three artefacts.`,\n ``,\n `When the user is ready, call this prompt again with`,\n `\\`phase: \"verify\"\\`, \\`sep_number: \"${sep}\"\\`, \\`slug: \"${slug}\"\\`.`,\n ].join(\"\\n\");\n}\n\nfunction buildVerifyPhase(args: { slug?: string; sep_number?: string }): string {\n const slug = args.slug ?? \"{slug}\";\n const sep = args.sep_number ?? \"NNNN\";\n return [\n `# SEP track — phase 4 of 4: Verify and hand off`,\n ``,\n `## Summary`,\n ``,\n `SEP ${sep} ← spec edit ← conformance fixture, ready for review.`,\n ``,\n `Three artefacts should now exist on this branch:`,\n ``,\n `- \\`seps/${sep}-${slug}.md\\` (Draft → flip to Review when filing the PR)`,\n `- spec/ edits (listed in the SEP's \"Spec changes:\" line)`,\n `- \\`conformance/<fixture-number>-${slug}/\\` with \\`sightmap/\\` input and`,\n ` \\`expected.json\\` output`,\n ``,\n `## Next steps for the user`,\n ``,\n `1. Open a draft PR titled \"SEP ${sep}: <short title>\".`,\n `2. PR description: link the SEP, the spec diff, and the fixture; link any`,\n ` prior Discussion or Issue.`,\n `3. Flip the SEP front-matter \\`status\\` from \\`Draft\\` to \\`Review\\` when`,\n ` ready for substantive feedback.`,\n `4. Per \\`seps/README.md\\`: minimum review window is 7 days for minor`,\n ` changes, 14 days for anything affecting the JSON Schema.`,\n ``,\n `Track is complete. No further phases.`,\n ].join(\"\\n\");\n}\n\nfunction buildPhase(args: Record<string, string>): string {\n if (typeof args[\"phase\"] !== \"string\" || args[\"phase\"].length === 0) {\n throw new Error(`sightmap_sep_track: argument \"phase\" is required`);\n }\n if (!(VALID_PHASES as readonly string[]).includes(args[\"phase\"])) {\n throw new Error(\n `sightmap_sep_track: unknown phase \"${args[\"phase\"]}\" — expected one of ${VALID_PHASES.join(\", \")}`,\n );\n }\n const phase = args[\"phase\"] as Phase;\n // Build the per-phase argument bag conditionally so undefined values are\n // omitted (required by `exactOptionalPropertyTypes: true`).\n const phaseArgs: { slug?: string; sep_number?: string } = {};\n if (typeof args[\"slug\"] === \"string\") phaseArgs.slug = args[\"slug\"];\n if (typeof args[\"sep_number\"] === \"string\") phaseArgs.sep_number = args[\"sep_number\"];\n switch (phase) {\n case \"draft\":\n return buildDraftPhase(phaseArgs);\n case \"spec\":\n return buildSpecPhase(phaseArgs);\n case \"fixture\":\n return buildFixturePhase(phaseArgs);\n case \"verify\":\n return buildVerifyPhase(phaseArgs);\n }\n}\n\nexport const sepTrackPrompt: PromptEntry = {\n definition: {\n name: \"sightmap_sep_track\",\n description:\n \"Walks an author through writing a Sightmap Enhancement Proposal (SEP), the matching spec/ change, and the matching conformance/ fixture in four phases (draft → spec → fixture → verify). Each non-final phase ends with a confirmation gate — call this prompt again with the next phase only after the user confirms. Inspired by Archcore's architecture_track pattern.\",\n arguments: [\n {\n name: \"phase\",\n description: 'One of \"draft\", \"spec\", \"fixture\", \"verify\". Required.',\n required: true,\n },\n {\n name: \"slug\",\n description: \"Short kebab-case slug for the SEP (e.g. 'extend-memory').\",\n required: false,\n },\n {\n name: \"sep_number\",\n description: 'Four-digit SEP number assigned in phase \"draft\" (e.g. \"0001\").',\n required: false,\n },\n ],\n },\n handler: (args): PromptResult => {\n const text = buildPhase(args);\n return {\n messages: [\n {\n role: \"user\",\n content: { type: \"text\", text },\n },\n ],\n };\n },\n};\n","import type { GetPromptResult } from \"@modelcontextprotocol/sdk/types.js\";\nimport { sepTrackPrompt } from \"./sepTrack.js\";\n\n/** MCP prompt argument descriptor (mirrors the SDK's PromptArgumentSchema). */\nexport interface PromptArgumentDef {\n name: string;\n description?: string;\n required?: boolean;\n}\n\n/** A prompt the server advertises in `prompts/list`. */\nexport interface PromptDefinition {\n name: string;\n description: string;\n arguments?: PromptArgumentDef[];\n}\n\n/** Result of `prompts/get` — what the agent gets. */\nexport type PromptResult = GetPromptResult;\n\n/** Handler signature: takes user-supplied string args, returns the result. */\nexport type PromptHandler = (args: Record<string, string>) => PromptResult;\n\n/**\n * Promise-tolerant variant for handlers that need IO. None today; reserved.\n */\nexport type AsyncPromptHandler = (args: Record<string, string>) => Promise<PromptResult>;\n\n/** Registry entry pairing a definition with its handler. */\nexport interface PromptEntry {\n definition: PromptDefinition;\n handler: PromptHandler;\n}\n\n/** All prompts the server exposes via `prompts/list` and `prompts/get`. */\nexport const PROMPT_REGISTRY: PromptEntry[] = [sepTrackPrompt];\n","import type { Client } from \"@modelcontextprotocol/sdk/client/index.js\";\nimport type { ToolDefinition, ToolResult, UpstreamClient } from \"./server.js\";\n\ninterface SdkTool {\n name: string;\n description?: string;\n inputSchema: ToolDefinition[\"inputSchema\"];\n}\n\ninterface SdkToolsResponse {\n tools: SdkTool[];\n}\n\ninterface SdkContentBlock {\n type: string;\n text?: string;\n data?: string;\n mimeType?: string;\n}\n\ninterface SdkCallResponse {\n content?: SdkContentBlock[];\n isError?: boolean;\n}\n\n/**\n * Wraps a connected `@modelcontextprotocol/sdk` Client and exposes it as\n * the `UpstreamClient` interface that `SightmapMcpServer` consumes.\n *\n * The constructor takes an *already-connected* Client so testing can\n * substitute any duck-typed implementation. The CLI builds the real one.\n */\nexport class McpClientUpstream implements UpstreamClient {\n constructor(private readonly client: Client) {}\n\n async listTools(): Promise<ToolDefinition[]> {\n const r = (await this.client.listTools()) as unknown as SdkToolsResponse;\n return r.tools.map((t) => ({\n name: t.name,\n description: t.description ?? \"\",\n inputSchema: t.inputSchema,\n }));\n }\n\n async callTool(name: string, args: Record<string, unknown>): Promise<ToolResult> {\n const raw = (await this.client.callTool({\n name,\n arguments: args,\n })) as unknown as SdkCallResponse;\n\n const content = (raw.content ?? []).map((block) => {\n if (block.type === \"text\" && typeof block.text === \"string\") {\n return { type: \"text\" as const, text: block.text };\n }\n // Non-text content (image, audio, embedded resource): serialize to text\n // so nothing is silently dropped. Agent can decide what to do with the\n // string description.\n return {\n type: \"text\" as const,\n text: stringifyNonTextBlock(block),\n };\n });\n\n return {\n content: content.length > 0 ? content : [{ type: \"text\", text: \"\" }],\n ...(raw.isError === true ? { isError: true } : {}),\n };\n }\n}\n\nfunction stringifyNonTextBlock(block: SdkContentBlock): string {\n const parts: string[] = [`[${block.type}]`];\n if (block.mimeType) parts.push(`mimeType=${block.mimeType}`);\n if (typeof block.data === \"string\") {\n const preview = block.data.length > 64 ? block.data.slice(0, 64) + \"…\" : block.data;\n parts.push(`data=${preview}`);\n }\n return parts.join(\" \");\n}\n","import { Server } from \"@modelcontextprotocol/sdk/server/index.js\";\nimport {\n CallToolRequestSchema,\n ListToolsRequestSchema,\n ListPromptsRequestSchema,\n GetPromptRequestSchema,\n} from \"@modelcontextprotocol/sdk/types.js\";\nimport type { SightmapMcpServer } from \"./server.js\";\n\n/**\n * Wraps a `SightmapMcpServer` (the dispatcher) in an MCP SDK `Server`,\n * registering tools/list, tools/call, prompts/list, and prompts/get handlers\n * that delegate to it.\n *\n * Returns the Server unconnected — caller chooses transport (stdio,\n * InMemoryTransport for tests, etc.) and calls `.connect(transport)`.\n */\nexport function buildMcpServer(dispatcher: SightmapMcpServer): Server {\n const server = new Server(\n { name: \"sightmap-mcp\", version: \"0.0.0\" },\n { capabilities: { tools: {}, prompts: {} } },\n );\n\n server.setRequestHandler(ListToolsRequestSchema, async () => {\n const tools = await dispatcher.listToolsAsync();\n return { tools };\n });\n\n server.setRequestHandler(CallToolRequestSchema, async (req) => {\n const name = req.params.name;\n const args = (req.params.arguments ?? {}) as Record<string, unknown>;\n const result = await dispatcher.callTool(name, args);\n // The SDK's CallToolResult is a discriminated union (regular result vs.\n // long-running task indicator). We always return a regular result.\n return result as unknown as { content: Array<{ type: \"text\"; text: string }>; isError?: boolean };\n });\n\n server.setRequestHandler(ListPromptsRequestSchema, async () => {\n return { prompts: dispatcher.listPrompts() };\n });\n\n server.setRequestHandler(GetPromptRequestSchema, async (req) => {\n const name = req.params.name;\n const args = (req.params.arguments ?? {}) as Record<string, string>;\n return dispatcher.getPrompt(name, args);\n });\n\n return server;\n}\n"],"mappings":"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","names":["sightmapMatch","sightmapMatch","sightmapMatch","readFile","parse","readFile","parse","readFile","parse","readFile","parse","writeFile","join","format","canonicalize","join","writeFile","resolved","sightmapMatch"]}
1
+ {"version":3,"sources":["../src/server.ts","../src/tools/match.ts","../src/tools/snapshot.ts","../src/tools/network.ts","../src/tools/curate/list.ts","../src/tools/curate/get.ts","../src/curate/locator.ts","../src/tools/curate/check.ts","../src/tools/curate/update.ts","../src/tools/curate/init.ts","../src/curate/scaffolder.ts","../src/prompts/sepTrack.ts","../src/prompts/index.ts","../src/upstream.ts","../src/mcpServer.ts"],"sourcesContent":["import {\n match as sightmapMatch,\n resolveSightmapAct,\n buildInPageEvalFunction,\n type Sightmap,\n} from \"@sightmap/sightmap\";\nimport { handleSightmapMatch } from \"./tools/match.js\";\nimport {\n buildSightmapSnapshotResponse,\n type InPageSightmapMatch,\n} from \"./tools/snapshot.js\";\nimport {\n parseNetworkRequestsText,\n annotateNetworkRequests,\n} from \"./tools/network.js\";\nimport {\n handleListViews,\n type ListViewsInput,\n} from \"./tools/curate/list.js\";\nimport { handleGetView } from \"./tools/curate/get.js\";\nimport { handleCheck, type CheckInput } from \"./tools/curate/check.js\";\nimport {\n handleUpdateView,\n type ViewPatch,\n} from \"./tools/curate/update.js\";\nimport {\n handleInitProject,\n type InitProjectInput,\n} from \"./tools/curate/init.js\";\nimport type { PromptDefinition, PromptEntry, PromptResult } from \"./prompts/index.js\";\nimport { PROMPT_REGISTRY } from \"./prompts/index.js\";\n\nexport interface ToolDefinition {\n name: string;\n description: string;\n inputSchema: {\n type: \"object\";\n properties?: Record<string, unknown>;\n required?: string[];\n additionalProperties?: boolean;\n };\n}\n\nexport interface ToolResult {\n content: Array<{ type: \"text\"; text: string }>;\n isError?: boolean;\n}\n\n/**\n * Abstraction over the upstream MCP server (typically `@playwright/mcp`).\n *\n * Implementations: a real MCP-SDK Client connected via stdio in production,\n * a fake in unit tests.\n */\nexport interface UpstreamClient {\n listTools(): Promise<ToolDefinition[]>;\n callTool(name: string, args: Record<string, unknown>): Promise<ToolResult>;\n}\n\nexport interface SightmapMcpServerOptions {\n sightmap: Sightmap;\n /** Optional upstream MCP server to proxy non-sightmap_* tool calls through. */\n upstream?: UpstreamClient;\n /**\n * Writable `.sightmap/` directory for curation tools that read/write files\n * (e.g. `sightmap_get_view`, `sightmap_update_view`). The CLI populates this\n * from `--curate-root` (or, by default, the first `--sightmap-dir`).\n */\n curateRoot?: string;\n}\n\nconst SIGHTMAP_MATCH: ToolDefinition = {\n name: \"sightmap_match\",\n description:\n \"Pure-query lookup against the loaded sightmap. Returns the matched view, applicable components, applicable requests, and aggregated memory for a given URL. Useful for agent planning before navigation. Does not touch the browser.\",\n inputSchema: {\n type: \"object\",\n properties: {\n url: {\n type: \"string\",\n description: \"The URL to resolve against the sightmap's view routes.\",\n },\n method: {\n type: \"string\",\n description: \"Optional HTTP method to filter matched requests (e.g., 'GET', 'POST').\",\n },\n },\n required: [\"url\"],\n additionalProperties: false,\n },\n};\n\nconst SIGHTMAP_SNAPSHOT: ToolDefinition = {\n name: \"sightmap_snapshot\",\n description:\n \"Returns the upstream ARIA snapshot enriched with sightmap awareness: matched view name, applicable component names with their selectors and live matchCount on the page, view-level memory, and page-aggregated memory. Use this instead of browser_snapshot when you want sightmap-aware semantics in one round-trip.\",\n inputSchema: {\n type: \"object\",\n properties: {},\n additionalProperties: false,\n },\n};\n\nconst SIGHTMAP_NETWORK_REQUESTS: ToolDefinition = {\n name: \"sightmap_network_requests\",\n description:\n \"Returns recent network requests captured by the upstream, annotated with sightmap names and memory where the request URL+method matches a sightmap `requests:` entry. Use this in place of browser_network_requests when you want sightmap-aware semantics for network calls.\",\n inputSchema: {\n type: \"object\",\n properties: {\n static: {\n type: \"boolean\",\n description:\n \"Include successful static resources (images, fonts, scripts). Default false.\",\n },\n filter: {\n type: \"string\",\n description: \"Only return requests whose URL matches this regexp.\",\n },\n },\n additionalProperties: false,\n },\n};\n\nconst SIGHTMAP_INIT_PROJECT: ToolDefinition = {\n name: \"sightmap_init_project\",\n description:\n \"Scaffold an empty .sightmap/ directory in the target project. Pass `dir` to override the location (default: server cwd). Refuses to overwrite an existing .sightmap/ unless `force=true`.\",\n inputSchema: {\n type: \"object\",\n properties: {\n dir: { type: \"string\", description: \"Project root. Default: server cwd.\" },\n force: { type: \"boolean\", description: \"Default false.\" },\n },\n additionalProperties: false,\n },\n};\n\nconst SIGHTMAP_UPDATE_VIEW: ToolDefinition = {\n name: \"sightmap_update_view\",\n description:\n \"Apply a partial patch to a view's agent-authored fields (description, intent, memory). Memory edits use either `memory_append` (default operation) or `memory_replace` — pass exactly one. Component / route / selector edits are NOT supported here — those are codegen-owned; edit source and re-run sightmap-react gen instead.\",\n inputSchema: {\n type: \"object\",\n properties: {\n name: { type: \"string\" },\n patch: {\n type: \"object\",\n properties: {\n description: { type: \"string\" },\n intent: { type: \"string\" },\n memory_append: { type: \"array\", items: { type: \"string\" } },\n memory_replace: { type: \"array\", items: { type: \"string\" } },\n },\n additionalProperties: false,\n },\n },\n required: [\"name\", \"patch\"],\n additionalProperties: false,\n },\n};\n\nconst SIGHTMAP_CHECK: ToolDefinition = {\n name: \"sightmap_check\",\n description:\n \"Validate the loaded sightmap. level='schema' returns only schema-level diagnostics (parse errors, schema failures, merge collisions). level='quality' (default) also runs lint rules: duplicate routes, route shadowing, selector syntax, unknown source attributions. Returns an array of diagnostics; an empty array means clean.\",\n inputSchema: {\n type: \"object\",\n properties: {\n level: {\n type: \"string\",\n enum: [\"schema\", \"quality\"],\n description: \"Default 'quality'.\",\n },\n },\n additionalProperties: false,\n },\n};\n\nconst SIGHTMAP_GET_VIEW: ToolDefinition = {\n name: \"sightmap_get_view\",\n description:\n \"Fetch a single view by name, including all memory, components, and requests. Returns the file path the view was read from for subsequent edits. Use sightmap_list_views first to discover view names.\",\n inputSchema: {\n type: \"object\",\n properties: {\n name: { type: \"string\", description: \"View name (case-sensitive).\" },\n },\n required: [\"name\"],\n additionalProperties: false,\n },\n};\n\nconst SIGHTMAP_LIST_VIEWS: ToolDefinition = {\n name: \"sightmap_list_views\",\n description:\n \"List all views in the loaded sightmap. Returns compact summaries (name, route, description) by default; pass detail='full' for the complete view objects including memory and components. Token-efficient: prefer the default for any agent that hasn't yet narrowed to a specific view.\",\n inputSchema: {\n type: \"object\",\n properties: {\n detail: {\n type: \"string\",\n enum: [\"summary\", \"full\"],\n description: \"Default 'summary'.\",\n },\n },\n additionalProperties: false,\n },\n};\n\nconst SIGHTMAP_ACT: ToolDefinition = {\n name: \"sightmap_act\",\n description:\n \"Performs an action on a UI element. Prefer `componentName` so the agent operates in sightmap semantics; fall back to a raw `selector` for one-off targets the sightmap doesn't define (e.g., a stray link or a third-party widget). Supported actions: 'click' (browser_click), 'type' (browser_type, requires `text`), 'hover' (browser_hover). Pass exactly one of `componentName` or `selector`.\",\n inputSchema: {\n type: \"object\",\n properties: {\n componentName: {\n type: \"string\",\n description: \"Sightmap component name to act on (case-sensitive). Mutually exclusive with `selector`.\",\n },\n selector: {\n type: \"string\",\n description:\n \"Escape hatch: a raw CSS selector for a target the sightmap doesn't name. Same tagging + dispatch path as componentName. Use this only when no sightmap component fits — most actions should use `componentName` so the agent's reasoning stays in sightmap semantics. Mutually exclusive with `componentName`.\",\n },\n action: {\n type: \"string\",\n enum: [\"click\", \"type\", \"hover\"],\n description: \"The action to perform on the component.\",\n },\n text: {\n type: \"string\",\n description: \"Required for action='type'. Text to enter into the matched element.\",\n },\n submit: {\n type: \"boolean\",\n description: \"For action='type' only. Press Enter after typing.\",\n },\n instance: {\n type: \"integer\",\n minimum: 0,\n description:\n \"Zero-based index of the matching element when the component selector resolves to multiple elements (default 0). Use sightmap_snapshot.matchCount to discover how many instances exist. Mutually exclusive with `containingText`.\",\n },\n containingText: {\n type: \"string\",\n description:\n \"Disambiguator for multi-match components: pick the first element whose visible text contains this substring (case-insensitive). Use this instead of `instance` when you can identify the element by its visible label rather than position. Mutually exclusive with `instance`.\",\n },\n },\n required: [\"componentName\", \"action\"],\n additionalProperties: false,\n },\n};\n\n/**\n * Upstream tools whose sightmap-aware equivalents should appear instead in\n * the listed-tools surface. The agent only sees one of each pair, biasing\n * its tool choices toward sightmap semantics. Direct invocation by name\n * still works for callers that need the raw passthrough.\n */\nconst SHADOWED_UPSTREAM_TOOLS: ReadonlySet<string> = new Set([\n \"browser_snapshot\",\n \"browser_click\",\n \"browser_type\",\n \"browser_hover\",\n \"browser_network_requests\",\n]);\n\n/**\n * Core dispatcher for the sightmap-mcp wrapper.\n *\n * Holds the loaded sightmap, exposes the surface of sightmap-aware tools, and\n * dispatches `callTool` requests. Transport-agnostic — wired up to stdio in\n * the CLI entry, and unit-testable directly without spinning up MCP plumbing.\n *\n * Phase 1 surface: `sightmap_match` only. Subsequent phases add\n * `sightmap_snapshot` and `sightmap_act`, plus a passthrough proxy for the\n * upstream @playwright/mcp tools.\n */\nexport class SightmapMcpServer {\n private readonly sightmap: Sightmap;\n private readonly upstream: UpstreamClient | undefined;\n private readonly curateRoot: string | undefined;\n\n constructor(opts: SightmapMcpServerOptions) {\n this.sightmap = opts.sightmap;\n this.upstream = opts.upstream;\n this.curateRoot = opts.curateRoot;\n }\n\n /** Synchronous list of sightmap-aware tools that don't need an upstream. */\n listTools(): ToolDefinition[] {\n return [\n SIGHTMAP_MATCH,\n SIGHTMAP_LIST_VIEWS,\n SIGHTMAP_GET_VIEW,\n SIGHTMAP_CHECK,\n SIGHTMAP_UPDATE_VIEW,\n SIGHTMAP_INIT_PROJECT,\n ];\n }\n\n /** Full async list including upstream-proxied tools, if configured. */\n async listToolsAsync(): Promise<ToolDefinition[]> {\n const own: ToolDefinition[] = [\n SIGHTMAP_MATCH,\n SIGHTMAP_LIST_VIEWS,\n SIGHTMAP_GET_VIEW,\n SIGHTMAP_CHECK,\n SIGHTMAP_UPDATE_VIEW,\n SIGHTMAP_INIT_PROJECT,\n ];\n if (this.upstream !== undefined) {\n own.push(SIGHTMAP_SNAPSHOT, SIGHTMAP_ACT, SIGHTMAP_NETWORK_REQUESTS);\n }\n if (this.upstream === undefined) return own;\n const upstreamTools = await this.upstream.listTools();\n // Hide upstream tools that have a sightmap_* equivalent. Goal: nudge the\n // agent toward the sightmap-aware surface instead of letting it fall\n // back to the generic browser_* duplicates by habit. Calls to these\n // hidden tools still pass through if the agent invokes them by name —\n // hiding only affects the discovery surface.\n const shadowed = SHADOWED_UPSTREAM_TOOLS;\n const filtered = upstreamTools.filter((t) => !shadowed.has(t.name));\n return [...own, ...filtered];\n }\n\n /** All prompts the server advertises. Static; no upstream involvement. */\n listPrompts(): PromptDefinition[] {\n return PROMPT_REGISTRY.map((p) => p.definition);\n }\n\n /**\n * Resolve a prompt by name, validate args, and produce the prompt result\n * (the messages the agent will inject). Throws on unknown names or on a\n * handler that itself throws (e.g., bad phase value).\n */\n getPrompt(name: string, args: Record<string, string>): PromptResult {\n const entry: PromptEntry | undefined = PROMPT_REGISTRY.find(\n (p) => p.definition.name === name,\n );\n if (entry === undefined) throw new Error(`unknown prompt: ${name}`);\n return entry.handler(args);\n }\n\n async callTool(name: string, args: Record<string, unknown>): Promise<ToolResult> {\n if (isSightmapTool(name)) {\n switch (name) {\n case \"sightmap_match\":\n return this.callSightmapMatch(args);\n case \"sightmap_list_views\":\n return this.callSightmapListViews(args);\n case \"sightmap_get_view\":\n return this.callSightmapGetView(args);\n case \"sightmap_check\":\n return this.callSightmapCheck(args);\n case \"sightmap_update_view\":\n return this.callSightmapUpdateView(args);\n case \"sightmap_init_project\":\n return this.callSightmapInitProject(args);\n case \"sightmap_snapshot\":\n return this.callSightmapSnapshot();\n case \"sightmap_act\":\n return this.callSightmapAct(args);\n case \"sightmap_network_requests\":\n return this.callSightmapNetworkRequests(args);\n default:\n return errorResult(`Unknown sightmap tool: ${name}`);\n }\n }\n if (this.upstream !== undefined) {\n return this.upstream.callTool(name, args);\n }\n return errorResult(`Unknown tool: ${name}`);\n }\n\n /**\n * Tag a single element matching `selector` with a unique\n * `data-sm-act-target` attribute and return a CSS selector that resolves\n * to exactly that element. The selection mode picks WHICH match to tag:\n * - `{ kind: \"index\", index }` — pick the Nth match (default).\n * - `{ kind: \"containingText\", text }` — pick the first match whose\n * `textContent` contains `text` (case-insensitive).\n *\n * Returns null if no candidate is selected (index out of range, or no\n * element's text contains the needle).\n */\n private async tagSingleMatch(\n selector: string,\n selection:\n | { kind: \"index\"; index: number }\n | { kind: \"containingText\"; text: string },\n ): Promise<string | null> {\n if (this.upstream === undefined) return null;\n const marker = `sm-${Math.random().toString(36).slice(2, 10)}-${Date.now().toString(36)}`;\n const pickExpr =\n selection.kind === \"index\"\n ? `els[${selection.index}]`\n : `els.find((el) => (el.textContent || \"\").toLowerCase().includes(${JSON.stringify(selection.text.toLowerCase())}))`;\n const fnBody = `() => {\n const els = Array.from(document.querySelectorAll(${JSON.stringify(selector)}));\n const target = ${pickExpr};\n if (!target) return null;\n target.setAttribute(\"data-sm-act-target\", ${JSON.stringify(marker)});\n return \"[data-sm-act-target=\\\\\"\" + ${JSON.stringify(marker)} + \"\\\\\"]\";\n }`;\n const r = await this.upstream.callTool(\"browser_evaluate\", { function: fnBody });\n if (r.isError === true) return null;\n const text = r.content.map((b) => b.text).join(\"\\n\");\n const decoded = decodeMcpEvalResult(text);\n if (typeof decoded !== \"string\") return null;\n if (!decoded.includes(`data-sm-act-target=\"${marker}\"`)) return null;\n return decoded;\n }\n\n private async callSightmapNetworkRequests(\n args: Record<string, unknown>,\n ): Promise<ToolResult> {\n if (this.upstream === undefined) {\n return errorResult(\n \"sightmap_network_requests: requires an upstream (e.g., @playwright/mcp).\",\n );\n }\n const upstreamArgs: Record<string, unknown> = {};\n if (typeof args[\"static\"] === \"boolean\") upstreamArgs[\"static\"] = args[\"static\"];\n if (typeof args[\"filter\"] === \"string\") upstreamArgs[\"filter\"] = args[\"filter\"];\n\n const r = await this.upstream.callTool(\"browser_network_requests\", upstreamArgs);\n if (r.isError === true) {\n return r;\n }\n const text = r.content.map((b) => b.text).join(\"\\n\");\n const parsed = parseNetworkRequestsText(text);\n const annotated = annotateNetworkRequests(this.sightmap, parsed);\n return {\n content: [{ type: \"text\", text: JSON.stringify({ requests: annotated }, null, 2) }],\n };\n }\n\n private async callSightmapAct(args: Record<string, unknown>): Promise<ToolResult> {\n if (this.upstream === undefined) {\n return errorResult(\n \"sightmap_act: requires an upstream (e.g., @playwright/mcp) to be configured.\",\n );\n }\n const hasComponent =\n typeof args[\"componentName\"] === \"string\" && args[\"componentName\"].length > 0;\n const hasSelector =\n typeof args[\"selector\"] === \"string\" && args[\"selector\"].length > 0;\n if (hasComponent && hasSelector) {\n return errorResult(\n \"sightmap_act: `componentName` and `selector` are mutually exclusive — pass one, not both.\",\n );\n }\n if (!hasComponent && !hasSelector) {\n return errorResult(\n \"sightmap_act: pass either `componentName` (preferred) or `selector` (escape hatch for off-sightmap targets).\",\n );\n }\n if (typeof args[\"action\"] !== \"string\") {\n return errorResult(\"sightmap_act: required argument `action` (string) is missing.\");\n }\n\n const action = args[\"action\"];\n const validActions = new Set([\"click\", \"type\", \"hover\"]);\n if (!validActions.has(action)) {\n return errorResult(\n `sightmap_act: unsupported action \"${action}\". Supported: click, type, hover.`,\n );\n }\n if (action === \"type\" && typeof args[\"text\"] !== \"string\") {\n return errorResult(\"sightmap_act: action='type' requires `text` (string).\");\n }\n\n const hasInstance = typeof args[\"instance\"] === \"number\";\n const hasContainingText =\n typeof args[\"containingText\"] === \"string\" && args[\"containingText\"].length > 0;\n if (hasInstance && hasContainingText) {\n return errorResult(\n \"sightmap_act: `instance` and `containingText` are mutually exclusive — pass one, not both.\",\n );\n }\n\n // Resolve the target: either via sightmap lookup or directly from `selector`.\n let targetSelector: string;\n let targetLabel: string;\n if (hasComponent) {\n const resolved = resolveSightmapAct(this.sightmap, {\n componentName: args[\"componentName\"] as string,\n });\n if (resolved.kind === \"error\") {\n return errorResult(\"sightmap_act: \" + resolved.message);\n }\n targetSelector = resolved.selector;\n targetLabel = resolved.componentName;\n } else {\n targetSelector = args[\"selector\"] as string;\n targetLabel = `selector:${targetSelector}`;\n }\n const resolved = { kind: \"ok\" as const, componentName: targetLabel, selector: targetSelector };\n\n // Tag a single matching element with a unique data-sm-act-target marker\n // via browser_evaluate, then act on that uniquely-tagged element. This\n // sidesteps Playwright's strict-mode multi-match violation regardless of\n // whether the sightmap selector resolves to one element or many. Costs\n // one extra round-trip per action; buys universal correctness.\n const selection: { kind: \"index\"; index: number } | { kind: \"containingText\"; text: string } =\n hasContainingText\n ? { kind: \"containingText\", text: args[\"containingText\"] as string }\n : { kind: \"index\", index: hasInstance ? Math.floor(args[\"instance\"] as number) : 0 };\n const taggedSelector = await this.tagSingleMatch(resolved.selector, selection);\n if (taggedSelector === null) {\n const reason =\n selection.kind === \"containingText\"\n ? `no instance of \"${resolved.componentName}\" contains text ${JSON.stringify(selection.text)}`\n : `could not tag the element at instance=${selection.index} for component \"${resolved.componentName}\"`;\n return errorResult(\n `sightmap_act: ${reason}. The selector ${JSON.stringify(resolved.selector)} ` +\n `may not resolve any matching elements on the current page.`,\n );\n }\n\n const baseArgs: Record<string, unknown> = {\n target: taggedSelector,\n element: resolved.componentName,\n };\n\n let upstreamName: string;\n let upstreamArgs: Record<string, unknown>;\n switch (action) {\n case \"click\":\n upstreamName = \"browser_click\";\n upstreamArgs = baseArgs;\n break;\n case \"hover\":\n upstreamName = \"browser_hover\";\n upstreamArgs = baseArgs;\n break;\n case \"type\":\n upstreamName = \"browser_type\";\n upstreamArgs = {\n ...baseArgs,\n text: args[\"text\"],\n ...(args[\"submit\"] === true ? { submit: true } : {}),\n };\n break;\n default:\n return errorResult(`sightmap_act: unsupported action \"${action}\".`);\n }\n\n return this.upstream.callTool(upstreamName, upstreamArgs);\n }\n\n private async callSightmapSnapshot(): Promise<ToolResult> {\n if (this.upstream === undefined) {\n return errorResult(\n \"sightmap_snapshot: requires an upstream (e.g., @playwright/mcp) to be configured.\",\n );\n }\n\n // 1. Pull the ARIA snapshot from upstream.\n const snapResult = await this.upstream.callTool(\"browser_snapshot\", {});\n if (snapResult.isError === true) {\n return errorResult(\n \"sightmap_snapshot: upstream browser_snapshot failed: \" +\n (snapResult.content[0]?.text ?? \"unknown error\"),\n );\n }\n const ariaSnapshotText = snapResult.content.map((b) => b.text).join(\"\\n\");\n\n // 2. Determine the URL and find sightmap-applicable components for it.\n // We do this server-side via match(), so the in-page eval only needs\n // to look up `document.querySelectorAll(selector)` for each.\n const currentUrl = parsePageUrl(ariaSnapshotText) ?? \"\";\n const matchResult = sightmapMatch(this.sightmap, { url: currentUrl });\n const componentSelectors = matchResult.components.map((c) => ({\n name: c.name,\n selector: c.selector,\n }));\n\n // 3. In-page evaluate: query each component's selectors, return matchCount\n // and first match's bounding rect.\n const evalResult = await this.upstream.callTool(\"browser_evaluate\", {\n function: buildInPageEvalFunction(componentSelectors),\n });\n if (evalResult.isError === true) {\n return errorResult(\n \"sightmap_snapshot: upstream browser_evaluate failed: \" +\n (evalResult.content[0]?.text ?? \"unknown error\"),\n );\n }\n const inPageMatches = parseInPageEvalResult(\n evalResult.content.map((b) => b.text).join(\"\\n\"),\n );\n\n // 4. Synthesize the response.\n const response = buildSightmapSnapshotResponse({\n sightmap: this.sightmap,\n currentUrl,\n ariaSnapshotText,\n inPageMatches,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(response, null, 2) }],\n };\n }\n\n private callSightmapMatch(args: Record<string, unknown>): ToolResult {\n if (typeof args[\"url\"] !== \"string\" || args[\"url\"].length === 0) {\n return errorResult(\"sightmap_match: required argument `url` (string) is missing or empty.\");\n }\n const input: { url: string; method?: string } = { url: args[\"url\"] };\n if (typeof args[\"method\"] === \"string\") {\n input.method = args[\"method\"];\n }\n const output = handleSightmapMatch(this.sightmap, input);\n return {\n content: [{ type: \"text\", text: JSON.stringify(output, null, 2) }],\n };\n }\n\n private async callSightmapGetView(args: Record<string, unknown>): Promise<ToolResult> {\n if (this.curateRoot === undefined) {\n return errorResult(\n \"sightmap_get_view: no writable sightmap dir configured (pass --curate-root or --sightmap-dir).\",\n );\n }\n if (typeof args[\"name\"] !== \"string\" || args[\"name\"].length === 0) {\n return errorResult(\"sightmap_get_view: required argument `name` (string) is missing or empty.\");\n }\n try {\n const result = await handleGetView({\n sightmapDir: this.curateRoot,\n name: args[\"name\"],\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n } catch (err) {\n return errorResult(err instanceof Error ? err.message : String(err));\n }\n }\n\n private async callSightmapInitProject(args: Record<string, unknown>): Promise<ToolResult> {\n const input: InitProjectInput = {};\n if (typeof args[\"dir\"] === \"string\") input.dir = args[\"dir\"];\n if (args[\"force\"] === true) input.force = true;\n try {\n const result = await handleInitProject(input);\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n } catch (err) {\n return errorResult(err instanceof Error ? err.message : String(err));\n }\n }\n\n private async callSightmapUpdateView(args: Record<string, unknown>): Promise<ToolResult> {\n if (this.curateRoot === undefined) {\n return errorResult(\n \"sightmap_update_view: no writable sightmap dir configured (pass --curate-root or --sightmap-dir).\",\n );\n }\n if (typeof args[\"name\"] !== \"string\" || args[\"name\"].length === 0) {\n return errorResult(\n \"sightmap_update_view: required argument `name` (string) is missing or empty.\",\n );\n }\n if (\n args[\"patch\"] === null ||\n typeof args[\"patch\"] !== \"object\" ||\n Array.isArray(args[\"patch\"])\n ) {\n return errorResult(\n \"sightmap_update_view: required argument `patch` (object) is missing.\",\n );\n }\n try {\n const result = await handleUpdateView({\n sightmapDir: this.curateRoot,\n name: args[\"name\"],\n patch: args[\"patch\"] as ViewPatch,\n });\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n } catch (err) {\n return errorResult(err instanceof Error ? err.message : String(err));\n }\n }\n\n private async callSightmapCheck(args: Record<string, unknown>): Promise<ToolResult> {\n const input: CheckInput = {};\n if (args[\"level\"] === \"schema\" || args[\"level\"] === \"quality\") {\n input.level = args[\"level\"];\n } else if (args[\"level\"] !== undefined) {\n return errorResult(\n `sightmap_check: level must be \"schema\" or \"quality\".`,\n );\n }\n const result = await handleCheck(this.sightmap, input);\n return {\n content: [{ type: \"text\", text: JSON.stringify(result, null, 2) }],\n };\n }\n\n private callSightmapListViews(args: Record<string, unknown>): ToolResult {\n const input: ListViewsInput = {};\n if (args[\"detail\"] === \"summary\" || args[\"detail\"] === \"full\") {\n input.detail = args[\"detail\"];\n } else if (args[\"detail\"] !== undefined) {\n return errorResult(\n `sightmap_list_views: detail must be \"summary\" or \"full\".`,\n );\n }\n const output = handleListViews(this.sightmap, input);\n return {\n content: [{ type: \"text\", text: JSON.stringify(output, null, 2) }],\n };\n }\n}\n\nfunction errorResult(text: string): ToolResult {\n return {\n content: [{ type: \"text\", text }],\n isError: true,\n };\n}\n\nfunction isSightmapTool(name: string): boolean {\n return name.startsWith(\"sightmap_\");\n}\n\n/** Extract the \"Page URL: ...\" line from an upstream browser_snapshot response. */\nfunction parsePageUrl(text: string): string | null {\n const m = /Page URL:\\s*(\\S+)/.exec(text);\n return m?.[1] ?? null;\n}\n\n/**\n * Parse the upstream `browser_evaluate` response text into a JSON payload.\n *\n * @playwright/mcp wraps the result like:\n * ### Result\n * {\"url\": \"...\", \"matches\": [...]}\n * ### Ran Playwright code\n * ...\n *\n * We extract the first JSON object after `### Result`. If the format changes,\n * fall back to a generic { from first '{' } scan.\n */\nfunction parseInPageEvalResult(text: string): InPageSightmapMatch[] {\n const afterResult = text.split(/^###\\s*Result/im)[1] ?? text;\n const start = afterResult.indexOf(\"{\");\n if (start < 0) return [];\n for (let end = afterResult.length; end > start; end--) {\n try {\n const parsed = JSON.parse(afterResult.slice(start, end)) as {\n url?: string;\n matches?: unknown[];\n };\n if (Array.isArray(parsed.matches)) {\n return parsed.matches.filter(isInPageMatch);\n }\n } catch {\n // try shorter window\n }\n }\n return [];\n}\n\n/**\n * Decode the value an upstream `browser_evaluate` returned to us.\n * Format is text after `### Result`, JSON-encoded: a number is `42`, a\n * string is `\"foo\"`, an object/array is the JSON literal.\n */\nfunction decodeMcpEvalResult(text: string): unknown {\n const afterResult = text.split(/^###\\s*Result/im)[1] ?? \"\";\n const trimmed = afterResult.trim();\n if (trimmed.length === 0) return undefined;\n // Find the first JSON-y token at the start of trimmed.\n for (let end = trimmed.length; end > 0; end--) {\n try {\n return JSON.parse(trimmed.slice(0, end));\n } catch {\n // try shorter\n }\n }\n return undefined;\n}\n\nfunction isInPageMatch(value: unknown): value is InPageSightmapMatch {\n if (typeof value !== \"object\" || value === null) return false;\n const v = value as Record<string, unknown>;\n return typeof v[\"name\"] === \"string\" && typeof v[\"matchCount\"] === \"number\";\n}\n","import { match as sightmapMatch, type Sightmap, type MatchResult } from \"@sightmap/sightmap\";\n\nexport interface SightmapMatchInput {\n url: string;\n method?: string;\n}\n\nexport interface SightmapMatchOutput {\n view: { name: string; route: string; description?: string } | null;\n components: Array<{\n name: string;\n selector: string[];\n memory: string[];\n scope: \"global\" | \"view-scoped\";\n }>;\n requests: Array<{\n name: string;\n route: string;\n method?: string;\n memory: string[];\n }>;\n /** Page-level aggregated memory from sightmap-js. */\n memory: string[];\n /** Memory attached to the matched view itself, if any. */\n viewMemory: string[];\n}\n\n/**\n * Pure handler for the `sightmap_match` MCP tool.\n *\n * Wraps sightmap-js's `match()` and shapes the response for agent consumption.\n * No browser involvement — this is the planning-side query: \"what should I\n * expect at this URL?\"\n */\nexport function handleSightmapMatch(\n sightmap: Sightmap,\n input: SightmapMatchInput,\n): SightmapMatchOutput {\n const result: MatchResult = sightmapMatch(sightmap, {\n url: input.url,\n ...(input.method !== undefined ? { method: input.method } : {}),\n });\n\n return {\n view: result.view\n ? {\n name: result.view.name,\n route: result.view.route,\n ...(result.view.description !== undefined\n ? { description: result.view.description }\n : {}),\n }\n : null,\n components: result.components.map((c) => ({\n name: c.name,\n selector: c.selector,\n memory: c.memory ?? [],\n scope: c.scope,\n })),\n requests: result.requests.map((r) => ({\n name: r.name,\n route: r.route,\n ...(r.method !== undefined ? { method: r.method } : {}),\n memory: r.memory ?? [],\n })),\n memory: result.memory ?? [],\n viewMemory: result.view?.memory ?? [],\n };\n}\n","import {\n enrichSnapshot,\n type EnrichedSnapshot,\n type InPageSightmapMatch,\n type BoundingRect,\n type SightmapSnapshotComponent,\n type Sightmap,\n} from \"@sightmap/sightmap\";\n\n// Re-export kernel types so existing MCP callers keep working unchanged.\nexport type { InPageSightmapMatch, BoundingRect, SightmapSnapshotComponent };\n\nexport interface BuildSnapshotOptions {\n sightmap: Sightmap;\n currentUrl: string;\n ariaSnapshotText: string;\n inPageMatches: InPageSightmapMatch[];\n}\n\nexport type SightmapSnapshotResponse = EnrichedSnapshot & {\n /** Raw ARIA tree text passthrough from browser_snapshot. */\n ariaSnapshot: string;\n};\n\n/**\n * Wraps the kernel's enrichSnapshot with the Playwright-MCP-specific\n * ariaSnapshot passthrough. The agent gets both the structured enrichment\n * (view, components, memory) and the raw a11y text for context.\n */\nexport function buildSightmapSnapshotResponse(\n opts: BuildSnapshotOptions,\n): SightmapSnapshotResponse {\n const enriched = enrichSnapshot({\n sightmap: opts.sightmap,\n currentUrl: opts.currentUrl,\n inPageMatches: opts.inPageMatches,\n });\n return { ...enriched, ariaSnapshot: opts.ariaSnapshotText };\n}\n","import type { ParsedNetworkRequest } from \"@sightmap/sightmap\";\n\n// Re-export so existing MCP callers continue to work.\nexport type {\n ParsedNetworkRequest,\n AnnotatedNetworkRequest,\n} from \"@sightmap/sightmap\";\nexport { annotateNetworkRequests } from \"@sightmap/sightmap\";\n\n/**\n * Parse the text output of `@playwright/mcp` `browser_network_requests`.\n *\n * Expected line format (one request per line, in the body after `### Result`):\n *\n * N. [METHOD] URL => [STATUS] STATUS_TEXT\n *\n * Lines that don't match are silently dropped — `browser_network_requests`\n * also emits notes about static resources, page-level metadata, etc.\n *\n * This parser is Playwright-MCP-specific and stays here; other engine\n * adapters write their own parser against their own engine's output.\n */\nexport function parseNetworkRequestsText(text: string): ParsedNetworkRequest[] {\n const lines = text.split(/\\r?\\n/);\n const requests: ParsedNetworkRequest[] = [];\n const re = /^\\s*\\d+\\.\\s*\\[([A-Z]+)\\]\\s+(\\S+)\\s+=>\\s+\\[(\\d+)\\]\\s+(.*?)\\s*$/;\n for (const line of lines) {\n const m = re.exec(line);\n if (m === null) continue;\n requests.push({\n method: m[1] ?? \"\",\n url: m[2] ?? \"\",\n status: Number.parseInt(m[3] ?? \"0\", 10),\n statusText: m[4] ?? \"\",\n });\n }\n return requests;\n}\n","// `sightmap_list_views` handler.\n//\n// Read-only; defaults to compact summaries (name + route + optional\n// description) so a single-call discovery in an agent's first turn fits in a\n// small token budget. `detail: \"full\"` returns the entire View object\n// including memory, components, and requests.\n\nimport type { Sightmap, View } from \"@sightmap/sightmap\";\n\nexport interface ListViewsInput {\n detail?: \"summary\" | \"full\";\n}\n\nexport interface ViewSummary {\n name: string;\n route: string;\n description?: string;\n}\n\nexport interface ListViewsOutput {\n views: Array<ViewSummary | View>;\n}\n\nexport function handleListViews(\n sightmap: Sightmap,\n input: ListViewsInput,\n): ListViewsOutput {\n const detail = input.detail ?? \"summary\";\n const sorted = [...sightmap.views].sort((a, b) =>\n a.name.localeCompare(b.name),\n );\n\n if (detail === \"full\") {\n return { views: sorted };\n }\n\n return {\n views: sorted.map((v) => {\n const summary: ViewSummary = { name: v.name, route: v.route };\n if (v.description !== undefined) summary.description = v.description;\n return summary;\n }),\n };\n}\n","// `sightmap_get_view` handler.\n//\n// Read-only single-view fetch. Returns the parsed view object plus the file\n// path it was read from, so callers can chain `update_view` against the same\n// file without an extra lookup.\n\nimport { readFile } from \"node:fs/promises\";\nimport { parse, type View } from \"@sightmap/sightmap\";\nimport { findFileForView } from \"../../curate/locator.js\";\n\nexport interface GetViewInput {\n sightmapDir: string;\n name: string;\n}\n\nexport interface GetViewOutput {\n view: View;\n file: string;\n}\n\nexport async function handleGetView(input: GetViewInput): Promise<GetViewOutput> {\n const file = await findFileForView(input.sightmapDir, input.name);\n if (file === null) {\n throw new Error(\n `View \"${input.name}\" not found in ${input.sightmapDir}`,\n );\n }\n const text = await readFile(file, \"utf8\");\n const parsed = parse(text, { sourceFile: file });\n const view = parsed.views?.find((v) => v.name === input.name);\n if (view === undefined) {\n throw new Error(\n `View \"${input.name}\" not found in ${file} (locator drift?)`,\n );\n }\n return { view, file };\n}\n","// Locate the YAML file in a `.sightmap/` directory that contains a given view.\n//\n// Used by curation tools (`get_view`, `update_view`) so callers can pass a view\n// name without also tracking which file declared it.\n\nimport { readdir, readFile } from \"node:fs/promises\";\nimport { join } from \"node:path\";\nimport { parse } from \"@sightmap/sightmap\";\n\nexport type FindViewOptions = {\n onWarning?: (msg: string) => void;\n};\n\nexport async function findFileForView(\n sightmapDir: string,\n viewName: string,\n options: FindViewOptions = {},\n): Promise<string | null> {\n const entries = await readdir(sightmapDir);\n const yamlFiles = entries\n .filter((e) => e.endsWith(\".yaml\") || e.endsWith(\".yml\"))\n .sort();\n\n let firstMatch: string | null = null;\n let matchCount = 0;\n\n for (const file of yamlFiles) {\n const path = join(sightmapDir, file);\n let parsed;\n try {\n const text = await readFile(path, \"utf8\");\n parsed = parse(text, { sourceFile: path });\n } catch {\n // Skip unparseable files; `sightmap_check` is the right tool for those.\n continue;\n }\n if (parsed.views?.some((v) => v.name === viewName)) {\n matchCount++;\n if (firstMatch === null) firstMatch = path;\n }\n }\n\n if (matchCount > 1 && options.onWarning) {\n options.onWarning(\n `duplicate view name \"${viewName}\" found in ${matchCount} files; using ${firstMatch}`,\n );\n }\n\n return firstMatch;\n}\n","// `sightmap_check` handler.\n//\n// Wraps `@sightmap/sightmap`'s `lint` plus the merge/load diagnostics already\n// attached to the loaded `Sightmap` (parse errors, schema failures, merge\n// collisions). Two levels:\n//\n// schema - return only the schema-level diagnostics already on the sightmap.\n// quality - schema diagnostics plus lint output (duplicate routes, route\n// shadowing, selector syntax, etc.).\n\nimport { lint, type Sightmap, type Diagnostic } from \"@sightmap/sightmap\";\n\nexport interface CheckInput {\n level?: \"schema\" | \"quality\";\n}\n\nexport interface CheckOutput {\n diagnostics: Diagnostic[];\n}\n\nexport async function handleCheck(\n sightmap: Sightmap,\n input: CheckInput,\n): Promise<CheckOutput> {\n const level = input.level ?? \"quality\";\n const schemaDiag = [...sightmap.diagnostics];\n if (level === \"schema\") return { diagnostics: schemaDiag };\n const lintDiag = await lint(sightmap);\n return { diagnostics: [...schemaDiag, ...lintDiag] };\n}\n","// `sightmap_update_view` handler.\n//\n// Reads the YAML file containing the named view, applies a narrow patch to\n// the agent-authored fields (description, intent, memory), then re-writes the\n// file via the canonical writer. The emitted bytes are piped through\n// `canonicalize()` so the result passes `sightmap fmt --check` (per sightmap\n// spec adapter-behavior guidance).\n//\n// Component / route / selector edits are intentionally NOT supported here\n// (those are codegen-owned in `@sightmap/react`). Memory edits use either\n// `memory_append` (the default operation) or `memory_replace` — never both\n// in the same patch.\n\nimport { readFile, writeFile } from \"node:fs/promises\";\nimport {\n parse,\n format,\n canonicalize,\n type FormatInput,\n type View,\n} from \"@sightmap/sightmap\";\nimport { findFileForView } from \"../../curate/locator.js\";\n\nexport interface ViewPatch {\n description?: string;\n intent?: string;\n memory_append?: string[];\n memory_replace?: string[];\n}\n\nexport interface UpdateViewInput {\n sightmapDir: string;\n name: string;\n patch: ViewPatch;\n}\n\nexport interface UpdateViewOutput {\n ok: true;\n file: string;\n written: View;\n}\n\nexport async function handleUpdateView(\n input: UpdateViewInput,\n): Promise<UpdateViewOutput> {\n if (input.patch.memory_append && input.patch.memory_replace) {\n throw new Error(\n \"cannot use both memory_append and memory_replace in the same patch\",\n );\n }\n\n const file = await findFileForView(input.sightmapDir, input.name);\n if (file === null) {\n throw new Error(\n `View \"${input.name}\" not found in ${input.sightmapDir}`,\n );\n }\n\n const text = await readFile(file, \"utf8\");\n const parsed = parse(text, { sourceFile: file });\n const views = parsed.views ?? [];\n const idx = views.findIndex((v) => v.name === input.name);\n if (idx < 0) {\n throw new Error(\n `View \"${input.name}\" not found in ${file} (locator drift?)`,\n );\n }\n\n const before = views[idx]!;\n const after: View & { intent?: string } = { ...before };\n if (input.patch.description !== undefined) {\n after.description = input.patch.description;\n }\n if (input.patch.intent !== undefined) {\n after.intent = input.patch.intent;\n }\n if (input.patch.memory_append) {\n after.memory = [...(before.memory ?? []), ...input.patch.memory_append];\n }\n if (input.patch.memory_replace) {\n after.memory = [...input.patch.memory_replace];\n }\n\n const nextViews: View[] = [...views];\n nextViews[idx] = after;\n const nextDoc = stripFragmentBrand(parsed as unknown as Record<string, unknown>);\n nextDoc.views = nextViews;\n const out = format(nextDoc);\n // Pipe through `canonicalize()` so the rewritten file matches what\n // `sightmap fmt --check` expects (per-entry-type key order, top-level seq\n // sort, blank-line separators, etc.). The value object came from the parsed\n // file plus a narrow patch, so canonicalize won't return schema-invalid in\n // practice; fall back to the format() bytes if it does.\n const c = canonicalize(out, { file });\n const finalText = c.kind === \"canonical\" ? c.text : out;\n await writeFile(file, finalText, \"utf8\");\n\n return { ok: true, file, written: after };\n}\n\nfunction stripFragmentBrand(input: Record<string, unknown>): FormatInput {\n const out: Record<string, unknown> = {};\n for (const k of Object.keys(input)) {\n if (k === \"__brand\" || k === \"__sourceFile\") continue;\n out[k] = input[k];\n }\n return out as FormatInput;\n}\n","// `sightmap_init_project` handler.\n//\n// Scaffolds an empty `.sightmap/app.yaml` in a target project directory.\n// Refuses to overwrite an existing `.sightmap/` unless `force: true`.\n\nimport { mkdir, writeFile, access } from \"node:fs/promises\";\nimport { join } from \"node:path\";\nimport { makeStarterSightmap } from \"../../curate/scaffolder.js\";\n\nexport interface InitProjectInput {\n dir?: string;\n force?: boolean;\n}\n\nexport interface InitProjectOutput {\n ok: true;\n files: string[];\n}\n\nexport async function handleInitProject(\n input: InitProjectInput,\n): Promise<InitProjectOutput> {\n const root = input.dir ?? process.cwd();\n const sightmapDir = join(root, \".sightmap\");\n const appFile = join(sightmapDir, \"app.yaml\");\n\n if (input.force !== true) {\n let exists = false;\n try {\n await access(sightmapDir);\n exists = true;\n } catch {\n /* dir does not exist; continue */\n }\n if (exists) {\n throw new Error(\n `.sightmap/ already exists at ${sightmapDir} — pass force=true to overwrite`,\n );\n }\n }\n\n await mkdir(sightmapDir, { recursive: true });\n await writeFile(appFile, makeStarterSightmap(), \"utf8\");\n\n return { ok: true, files: [appFile] };\n}\n","// Starter `.sightmap/` scaffolding.\n//\n// `makeStarterSightmap` returns a minimal canonical YAML document — just a\n// `version: 1` line with no views/components/requests. Real content lands when\n// the user (or `sightmap-react gen`) adds files to the directory.\n//\n// Output is piped through `canonicalize()` so the emitted bytes match what\n// `sightmap fmt --check` expects. See sightmap/spec\n// docs/authoring-conventions.md#adapter-behavior.\n\nimport { format, canonicalize } from \"@sightmap/sightmap\";\n\nexport function makeStarterSightmap(): string {\n const text = format({ version: 1 });\n const c = canonicalize(text, { file: \"app.yaml\" });\n return c.kind === \"canonical\" ? c.text : text;\n}\n","import type { PromptEntry, PromptResult } from \"./index.js\";\n\n/**\n * sightmap_sep_track — multi-phase prompt that walks an author through\n * writing a Sightmap Enhancement Proposal, the matching spec/ change,\n * and the matching conformance/ fixture.\n *\n * Phase model:\n * draft → write seps/NNNN-{slug}.md, then STOP for user confirmation\n * spec → propose a diff against spec/, then STOP for user confirmation\n * fixture → create conformance/NNN-{slug}/, then STOP for user confirmation\n * verify → terminal summary message, no further phases\n *\n * Confirmation gates are encoded as text directives in each non-final phase\n * because MCP prompts have no native \"wait for user\" primitive. The agent\n * is expected to honor them.\n *\n * Inspired by Archcore's architecture_track (Archcore audit §1.6).\n */\n\nconst VALID_PHASES = [\"draft\", \"spec\", \"fixture\", \"verify\"] as const;\ntype Phase = (typeof VALID_PHASES)[number];\n\nfunction buildDraftPhase(args: { slug?: string }): string {\n const slug = args.slug ?? \"{slug}\";\n return [\n `# SEP track — phase 1 of 4: Draft the SEP`,\n ``,\n `You are helping the user author a Sightmap Enhancement Proposal (SEP).`,\n `An SEP is required for any change to the spec's schema, semantics, or`,\n `discovery rules. See \\`seps/README.md\\` for the full list.`,\n ``,\n `## Steps for this phase`,\n ``,\n `1. **Pick a number.** Look at \\`seps/\\` and find the lowest unused 4-digit`,\n ` integer (skip \\`0000-template.md\\`). Call this NNNN.`,\n `2. **Copy the template.** \\`cp seps/0000-template.md seps/NNNN-${slug}.md\\`.`,\n `3. **Fill in the front-matter.** Title, author, today's date, status: Draft.`,\n `4. **Write the body.** Sections from the template:`,\n ` - Summary (one paragraph; treat as the abstract)`,\n ` - Motivation (concrete user-facing problem; name a real app or pattern)`,\n ` - Proposal (Shape, Semantics, Conformance — show YAML, show JSON Schema diff)`,\n ` - Alternatives considered (at least two, including \"do nothing\")`,\n ` - Migration (what changes for existing users)`,\n ` - Open questions`,\n `5. **Read it back.** Does it pass the acceptance checklist in \\`seps/README.md\\`?`,\n ``,\n `## STOP HERE`,\n ``,\n `Show the draft to the user. Ask for explicit \"go\" before continuing.`,\n `Do **not** open the spec edit until the user confirms the SEP draft.`,\n ``,\n `When the user is ready, call this prompt again with`,\n `\\`phase: \"spec\"\\` and pass \\`sep_number: \"NNNN\"\\` and \\`slug: \"${slug}\"\\`.`,\n ].join(\"\\n\");\n}\n\nfunction buildSpecPhase(args: { slug?: string; sep_number?: string }): string {\n const slug = args.slug ?? \"{slug}\";\n const sep = args.sep_number ?? \"NNNN\";\n return [\n `# SEP track — phase 2 of 4: Propose the spec change`,\n ``,\n `Building on \\`seps/${sep}-${slug}.md\\`.`,\n ``,\n `## Steps for this phase`,\n ``,\n `1. **Identify the spec files affected.** Most changes touch:`,\n ` - \\`spec/v1/sightmap.schema.json\\` (the JSON Schema)`,\n ` - \\`spec/v1/sightmap.spec.md\\` (the prose spec)`,\n ` - Possibly \\`spec/v1/examples/\\` if the change adds a shape worth showing`,\n `2. **Make the edits.** Keep the diff small. The SEP is the design doc;`,\n ` the spec edit is the precise textual change.`,\n `3. **Run \\`pnpm -F @sightmap/sightmap test\\`.** Existing examples must still`,\n ` parse and validate, unless the SEP is explicitly breaking — in which`,\n ` case the SEP's Migration section must say so.`,\n `4. **Cross-reference.** Add a \"Spec changes:\" line near the top of the SEP`,\n ` listing the touched files. Add a comment in the schema file pointing`,\n ` back to \\`seps/${sep}-${slug}.md\\` if the rationale isn't obvious from`,\n ` the diff alone.`,\n ``,\n `## STOP HERE`,\n ``,\n `Show the spec diff to the user. Ask for explicit \"go\" before continuing.`,\n `Do **not** start the conformance fixture until the user confirms the spec edit.`,\n ``,\n `When the user is ready, call this prompt again with`,\n `\\`phase: \"fixture\"\\`, \\`sep_number: \"${sep}\"\\`, \\`slug: \"${slug}\"\\`.`,\n ].join(\"\\n\");\n}\n\nfunction buildFixturePhase(args: { slug?: string; sep_number?: string }): string {\n const slug = args.slug ?? \"{slug}\";\n const sep = args.sep_number ?? \"NNNN\";\n // Conformance fixture numbers in this repo are 3-digit; SEP numbers are 4-digit.\n // Drop the leading zero of the SEP number to suggest a fixture number, but\n // tell the agent to verify against existing fixtures.\n const fixtureGuess = sep.startsWith(\"0\") ? sep.slice(1) : sep;\n return [\n `# SEP track — phase 3 of 4: Write the conformance fixture`,\n ``,\n `Building on \\`seps/${sep}-${slug}.md\\` and the spec edit from phase 2.`,\n ``,\n `## Steps for this phase`,\n ``,\n `1. **Pick a fixture number.** Conformance fixtures use 3-digit numbers`,\n ` (\\`001-minimal\\`, \\`002-multi-file-merge\\`, …). Pick the lowest unused`,\n ` number — likely \\`${fixtureGuess}\\` if the SEP and fixture numberings`,\n ` line up, but verify against \\`conformance/\\`.`,\n `2. **Create the directory.** \\`mkdir conformance/${fixtureGuess}-${slug}\\`.`,\n `3. **Write the input.** \\`conformance/${fixtureGuess}-${slug}/sightmap/\\``,\n ` contains one or more \\`.yaml\\` files demonstrating the new behavior.`,\n ` Keep it minimal — one fixture, one behavior under test.`,\n `4. **Write the expected output.** \\`conformance/${fixtureGuess}-${slug}/expected.json\\``,\n ` is the canonical merged + resolved sightmap that any spec-conformant`,\n ` parser must produce. Use the existing \\`@sightmap/sightmap\\` parser`,\n ` to generate the baseline, then hand-audit it against the SEP.`,\n `5. **Run the conformance suite.** \\`pnpm -F @sightmap/sightmap test\\` should`,\n ` pick up the new fixture and validate it.`,\n ``,\n `## STOP HERE`,\n ``,\n `Show the fixture (input + expected.json) to the user. Ask for explicit`,\n `\"go\" before continuing. Do **not** declare the SEP ready for review until`,\n `the user confirms all three artefacts.`,\n ``,\n `When the user is ready, call this prompt again with`,\n `\\`phase: \"verify\"\\`, \\`sep_number: \"${sep}\"\\`, \\`slug: \"${slug}\"\\`.`,\n ].join(\"\\n\");\n}\n\nfunction buildVerifyPhase(args: { slug?: string; sep_number?: string }): string {\n const slug = args.slug ?? \"{slug}\";\n const sep = args.sep_number ?? \"NNNN\";\n return [\n `# SEP track — phase 4 of 4: Verify and hand off`,\n ``,\n `## Summary`,\n ``,\n `SEP ${sep} ← spec edit ← conformance fixture, ready for review.`,\n ``,\n `Three artefacts should now exist on this branch:`,\n ``,\n `- \\`seps/${sep}-${slug}.md\\` (Draft → flip to Review when filing the PR)`,\n `- spec/ edits (listed in the SEP's \"Spec changes:\" line)`,\n `- \\`conformance/<fixture-number>-${slug}/\\` with \\`sightmap/\\` input and`,\n ` \\`expected.json\\` output`,\n ``,\n `## Next steps for the user`,\n ``,\n `1. Open a draft PR titled \"SEP ${sep}: <short title>\".`,\n `2. PR description: link the SEP, the spec diff, and the fixture; link any`,\n ` prior Discussion or Issue.`,\n `3. Flip the SEP front-matter \\`status\\` from \\`Draft\\` to \\`Review\\` when`,\n ` ready for substantive feedback.`,\n `4. Per \\`seps/README.md\\`: minimum review window is 7 days for minor`,\n ` changes, 14 days for anything affecting the JSON Schema.`,\n ``,\n `Track is complete. No further phases.`,\n ].join(\"\\n\");\n}\n\nfunction buildPhase(args: Record<string, string>): string {\n if (typeof args[\"phase\"] !== \"string\" || args[\"phase\"].length === 0) {\n throw new Error(`sightmap_sep_track: argument \"phase\" is required`);\n }\n if (!(VALID_PHASES as readonly string[]).includes(args[\"phase\"])) {\n throw new Error(\n `sightmap_sep_track: unknown phase \"${args[\"phase\"]}\" — expected one of ${VALID_PHASES.join(\", \")}`,\n );\n }\n const phase = args[\"phase\"] as Phase;\n // Build the per-phase argument bag conditionally so undefined values are\n // omitted (required by `exactOptionalPropertyTypes: true`).\n const phaseArgs: { slug?: string; sep_number?: string } = {};\n if (typeof args[\"slug\"] === \"string\") phaseArgs.slug = args[\"slug\"];\n if (typeof args[\"sep_number\"] === \"string\") phaseArgs.sep_number = args[\"sep_number\"];\n switch (phase) {\n case \"draft\":\n return buildDraftPhase(phaseArgs);\n case \"spec\":\n return buildSpecPhase(phaseArgs);\n case \"fixture\":\n return buildFixturePhase(phaseArgs);\n case \"verify\":\n return buildVerifyPhase(phaseArgs);\n }\n}\n\nexport const sepTrackPrompt: PromptEntry = {\n definition: {\n name: \"sightmap_sep_track\",\n description:\n \"Walks an author through writing a Sightmap Enhancement Proposal (SEP), the matching spec/ change, and the matching conformance/ fixture in four phases (draft → spec → fixture → verify). Each non-final phase ends with a confirmation gate — call this prompt again with the next phase only after the user confirms. Inspired by Archcore's architecture_track pattern.\",\n arguments: [\n {\n name: \"phase\",\n description: 'One of \"draft\", \"spec\", \"fixture\", \"verify\". Required.',\n required: true,\n },\n {\n name: \"slug\",\n description: \"Short kebab-case slug for the SEP (e.g. 'extend-memory').\",\n required: false,\n },\n {\n name: \"sep_number\",\n description: 'Four-digit SEP number assigned in phase \"draft\" (e.g. \"0001\").',\n required: false,\n },\n ],\n },\n handler: (args): PromptResult => {\n const text = buildPhase(args);\n return {\n messages: [\n {\n role: \"user\",\n content: { type: \"text\", text },\n },\n ],\n };\n },\n};\n","import type { GetPromptResult } from \"@modelcontextprotocol/sdk/types.js\";\nimport { sepTrackPrompt } from \"./sepTrack.js\";\n\n/** MCP prompt argument descriptor (mirrors the SDK's PromptArgumentSchema). */\nexport interface PromptArgumentDef {\n name: string;\n description?: string;\n required?: boolean;\n}\n\n/** A prompt the server advertises in `prompts/list`. */\nexport interface PromptDefinition {\n name: string;\n description: string;\n arguments?: PromptArgumentDef[];\n}\n\n/** Result of `prompts/get` — what the agent gets. */\nexport type PromptResult = GetPromptResult;\n\n/** Handler signature: takes user-supplied string args, returns the result. */\nexport type PromptHandler = (args: Record<string, string>) => PromptResult;\n\n/**\n * Promise-tolerant variant for handlers that need IO. None today; reserved.\n */\nexport type AsyncPromptHandler = (args: Record<string, string>) => Promise<PromptResult>;\n\n/** Registry entry pairing a definition with its handler. */\nexport interface PromptEntry {\n definition: PromptDefinition;\n handler: PromptHandler;\n}\n\n/** All prompts the server exposes via `prompts/list` and `prompts/get`. */\nexport const PROMPT_REGISTRY: PromptEntry[] = [sepTrackPrompt];\n","import type { Client } from \"@modelcontextprotocol/sdk/client/index.js\";\nimport type { ToolDefinition, ToolResult, UpstreamClient } from \"./server.js\";\n\ninterface SdkTool {\n name: string;\n description?: string;\n inputSchema: ToolDefinition[\"inputSchema\"];\n}\n\ninterface SdkToolsResponse {\n tools: SdkTool[];\n}\n\ninterface SdkContentBlock {\n type: string;\n text?: string;\n data?: string;\n mimeType?: string;\n}\n\ninterface SdkCallResponse {\n content?: SdkContentBlock[];\n isError?: boolean;\n}\n\n/**\n * Wraps a connected `@modelcontextprotocol/sdk` Client and exposes it as\n * the `UpstreamClient` interface that `SightmapMcpServer` consumes.\n *\n * The constructor takes an *already-connected* Client so testing can\n * substitute any duck-typed implementation. The CLI builds the real one.\n */\nexport class McpClientUpstream implements UpstreamClient {\n constructor(private readonly client: Client) {}\n\n async listTools(): Promise<ToolDefinition[]> {\n const r = (await this.client.listTools()) as unknown as SdkToolsResponse;\n return r.tools.map((t) => ({\n name: t.name,\n description: t.description ?? \"\",\n inputSchema: t.inputSchema,\n }));\n }\n\n async callTool(name: string, args: Record<string, unknown>): Promise<ToolResult> {\n const raw = (await this.client.callTool({\n name,\n arguments: args,\n })) as unknown as SdkCallResponse;\n\n const content = (raw.content ?? []).map((block) => {\n if (block.type === \"text\" && typeof block.text === \"string\") {\n return { type: \"text\" as const, text: block.text };\n }\n // Non-text content (image, audio, embedded resource): serialize to text\n // so nothing is silently dropped. Agent can decide what to do with the\n // string description.\n return {\n type: \"text\" as const,\n text: stringifyNonTextBlock(block),\n };\n });\n\n return {\n content: content.length > 0 ? content : [{ type: \"text\", text: \"\" }],\n ...(raw.isError === true ? { isError: true } : {}),\n };\n }\n}\n\nfunction stringifyNonTextBlock(block: SdkContentBlock): string {\n const parts: string[] = [`[${block.type}]`];\n if (block.mimeType) parts.push(`mimeType=${block.mimeType}`);\n if (typeof block.data === \"string\") {\n const preview = block.data.length > 64 ? block.data.slice(0, 64) + \"…\" : block.data;\n parts.push(`data=${preview}`);\n }\n return parts.join(\" \");\n}\n","import { Server } from \"@modelcontextprotocol/sdk/server/index.js\";\nimport {\n CallToolRequestSchema,\n ListToolsRequestSchema,\n ListPromptsRequestSchema,\n GetPromptRequestSchema,\n} from \"@modelcontextprotocol/sdk/types.js\";\nimport type { SightmapMcpServer } from \"./server.js\";\n\n/**\n * Wraps a `SightmapMcpServer` (the dispatcher) in an MCP SDK `Server`,\n * registering tools/list, tools/call, prompts/list, and prompts/get handlers\n * that delegate to it.\n *\n * Returns the Server unconnected — caller chooses transport (stdio,\n * InMemoryTransport for tests, etc.) and calls `.connect(transport)`.\n */\nexport function buildMcpServer(dispatcher: SightmapMcpServer): Server {\n const server = new Server(\n { name: \"sightmap-mcp\", version: \"0.0.0\" },\n { capabilities: { tools: {}, prompts: {} } },\n );\n\n server.setRequestHandler(ListToolsRequestSchema, async () => {\n const tools = await dispatcher.listToolsAsync();\n return { tools };\n });\n\n server.setRequestHandler(CallToolRequestSchema, async (req) => {\n const name = req.params.name;\n const args = (req.params.arguments ?? {}) as Record<string, unknown>;\n const result = await dispatcher.callTool(name, args);\n // The SDK's CallToolResult is a discriminated union (regular result vs.\n // long-running task indicator). We always return a regular result.\n return result as unknown as { content: Array<{ type: \"text\"; text: string }>; isError?: boolean };\n });\n\n server.setRequestHandler(ListPromptsRequestSchema, async () => {\n return { prompts: dispatcher.listPrompts() };\n });\n\n server.setRequestHandler(GetPromptRequestSchema, async (req) => {\n const name = req.params.name;\n const args = (req.params.arguments ?? {}) as Record<string, string>;\n return dispatcher.getPrompt(name, args);\n });\n\n return server;\n}\n"],"mappings":"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","names":["sightmapMatch","readFile","parse","readFile","parse","readFile","parse","readFile","parse","writeFile","join","format","canonicalize","join","writeFile","resolved","sightmapMatch"]}