@keak/webmcp-core 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (111) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +165 -0
  3. package/dist/config.d.ts +103 -0
  4. package/dist/config.d.ts.map +1 -0
  5. package/dist/config.js +54 -0
  6. package/dist/config.js.map +1 -0
  7. package/dist/exporter/manifest.d.ts +6 -0
  8. package/dist/exporter/manifest.d.ts.map +1 -0
  9. package/dist/exporter/manifest.js +36 -0
  10. package/dist/exporter/manifest.js.map +1 -0
  11. package/dist/exporter/snippet.d.ts +7 -0
  12. package/dist/exporter/snippet.d.ts.map +1 -0
  13. package/dist/exporter/snippet.js +197 -0
  14. package/dist/exporter/snippet.js.map +1 -0
  15. package/dist/exporter/userscript.d.ts +6 -0
  16. package/dist/exporter/userscript.d.ts.map +1 -0
  17. package/dist/exporter/userscript.js +53 -0
  18. package/dist/exporter/userscript.js.map +1 -0
  19. package/dist/exporter/yaml.d.ts +6 -0
  20. package/dist/exporter/yaml.d.ts.map +1 -0
  21. package/dist/exporter/yaml.js +90 -0
  22. package/dist/exporter/yaml.js.map +1 -0
  23. package/dist/extractor/api-extractor.d.ts +3 -0
  24. package/dist/extractor/api-extractor.d.ts.map +1 -0
  25. package/dist/extractor/api-extractor.js +274 -0
  26. package/dist/extractor/api-extractor.js.map +1 -0
  27. package/dist/extractor/click-extractor.d.ts +3 -0
  28. package/dist/extractor/click-extractor.d.ts.map +1 -0
  29. package/dist/extractor/click-extractor.js +52 -0
  30. package/dist/extractor/click-extractor.js.map +1 -0
  31. package/dist/extractor/form-extractor.d.ts +3 -0
  32. package/dist/extractor/form-extractor.d.ts.map +1 -0
  33. package/dist/extractor/form-extractor.js +27 -0
  34. package/dist/extractor/form-extractor.js.map +1 -0
  35. package/dist/extractor/route-extractor.d.ts +3 -0
  36. package/dist/extractor/route-extractor.d.ts.map +1 -0
  37. package/dist/extractor/route-extractor.js +84 -0
  38. package/dist/extractor/route-extractor.js.map +1 -0
  39. package/dist/extractor/schema-inferrer.d.ts +4 -0
  40. package/dist/extractor/schema-inferrer.d.ts.map +1 -0
  41. package/dist/extractor/schema-inferrer.js +128 -0
  42. package/dist/extractor/schema-inferrer.js.map +1 -0
  43. package/dist/index.d.ts +88 -0
  44. package/dist/index.d.ts.map +1 -0
  45. package/dist/index.js +170 -0
  46. package/dist/index.js.map +1 -0
  47. package/dist/linter/linter.d.ts +10 -0
  48. package/dist/linter/linter.d.ts.map +1 -0
  49. package/dist/linter/linter.js +39 -0
  50. package/dist/linter/linter.js.map +1 -0
  51. package/dist/linter/rules.d.ts +4 -0
  52. package/dist/linter/rules.d.ts.map +1 -0
  53. package/dist/linter/rules.js +111 -0
  54. package/dist/linter/rules.js.map +1 -0
  55. package/dist/scanner/browser.d.ts +14 -0
  56. package/dist/scanner/browser.d.ts.map +1 -0
  57. package/dist/scanner/browser.js +42 -0
  58. package/dist/scanner/browser.js.map +1 -0
  59. package/dist/scanner/crawler.d.ts +12 -0
  60. package/dist/scanner/crawler.d.ts.map +1 -0
  61. package/dist/scanner/crawler.js +80 -0
  62. package/dist/scanner/crawler.js.map +1 -0
  63. package/dist/scanner/dom-capture.d.ts +4 -0
  64. package/dist/scanner/dom-capture.d.ts.map +1 -0
  65. package/dist/scanner/dom-capture.js +148 -0
  66. package/dist/scanner/dom-capture.js.map +1 -0
  67. package/dist/scanner/network-capture.d.ts +8 -0
  68. package/dist/scanner/network-capture.d.ts.map +1 -0
  69. package/dist/scanner/network-capture.js +112 -0
  70. package/dist/scanner/network-capture.js.map +1 -0
  71. package/dist/scanner/screenshot.d.ts +3 -0
  72. package/dist/scanner/screenshot.d.ts.map +1 -0
  73. package/dist/scanner/screenshot.js +10 -0
  74. package/dist/scanner/screenshot.js.map +1 -0
  75. package/dist/synthesizer/clusterer.d.ts +7 -0
  76. package/dist/synthesizer/clusterer.d.ts.map +1 -0
  77. package/dist/synthesizer/clusterer.js +310 -0
  78. package/dist/synthesizer/clusterer.js.map +1 -0
  79. package/dist/synthesizer/describer.d.ts +3 -0
  80. package/dist/synthesizer/describer.d.ts.map +1 -0
  81. package/dist/synthesizer/describer.js +92 -0
  82. package/dist/synthesizer/describer.js.map +1 -0
  83. package/dist/synthesizer/llm-client.d.ts +7 -0
  84. package/dist/synthesizer/llm-client.d.ts.map +1 -0
  85. package/dist/synthesizer/llm-client.js +7 -0
  86. package/dist/synthesizer/llm-client.js.map +1 -0
  87. package/dist/synthesizer/namer.d.ts +3 -0
  88. package/dist/synthesizer/namer.d.ts.map +1 -0
  89. package/dist/synthesizer/namer.js +154 -0
  90. package/dist/synthesizer/namer.js.map +1 -0
  91. package/dist/synthesizer/safety-classifier.d.ts +3 -0
  92. package/dist/synthesizer/safety-classifier.d.ts.map +1 -0
  93. package/dist/synthesizer/safety-classifier.js +68 -0
  94. package/dist/synthesizer/safety-classifier.js.map +1 -0
  95. package/dist/synthesizer/schema-builder.d.ts +3 -0
  96. package/dist/synthesizer/schema-builder.d.ts.map +1 -0
  97. package/dist/synthesizer/schema-builder.js +99 -0
  98. package/dist/synthesizer/schema-builder.js.map +1 -0
  99. package/dist/types.d.ts +271 -0
  100. package/dist/types.d.ts.map +1 -0
  101. package/dist/types.js +3 -0
  102. package/dist/types.js.map +1 -0
  103. package/dist/utils/redact.d.ts +3 -0
  104. package/dist/utils/redact.d.ts.map +1 -0
  105. package/dist/utils/redact.js +42 -0
  106. package/dist/utils/redact.js.map +1 -0
  107. package/dist/utils/validation.d.ts +876 -0
  108. package/dist/utils/validation.d.ts.map +1 -0
  109. package/dist/utils/validation.js +108 -0
  110. package/dist/utils/validation.js.map +1 -0
  111. package/package.json +69 -0
@@ -0,0 +1,42 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.launchBrowser = launchBrowser;
4
+ const playwright_1 = require("playwright");
5
+ async function launchBrowser(config = {}) {
6
+ const launchOptions = {
7
+ headless: config.headless ?? false,
8
+ };
9
+ if (config.executablePath) {
10
+ launchOptions.executablePath = config.executablePath;
11
+ }
12
+ const browser = await playwright_1.chromium.launch(launchOptions);
13
+ const contextOptions = {
14
+ viewport: { width: 1440, height: 900 },
15
+ userAgent: "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/146.0.0.0 Safari/537.36",
16
+ };
17
+ const context = await browser.newContext(contextOptions);
18
+ if (config.cookie) {
19
+ const cookies = parseCookieString(config.cookie);
20
+ if (cookies.length > 0) {
21
+ await context.addCookies(cookies);
22
+ }
23
+ }
24
+ const page = await context.newPage();
25
+ return { browser, context, page };
26
+ }
27
+ function parseCookieString(cookieString) {
28
+ return cookieString
29
+ .split(";")
30
+ .map((pair) => pair.trim())
31
+ .filter(Boolean)
32
+ .map((pair) => {
33
+ const [name, ...rest] = pair.split("=");
34
+ return {
35
+ name: name.trim(),
36
+ value: rest.join("=").trim(),
37
+ domain: "", // Will be set from the page URL
38
+ path: "/",
39
+ };
40
+ });
41
+ }
42
+ //# sourceMappingURL=browser.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"browser.js","sourceRoot":"","sources":["../../src/scanner/browser.ts"],"names":[],"mappings":";;AAeA,sCA+BC;AA9CD,2CAAoF;AAe7E,KAAK,UAAU,aAAa,CACjC,SAAwB,EAAE;IAE1B,MAAM,aAAa,GAA4B;QAC7C,QAAQ,EAAE,MAAM,CAAC,QAAQ,IAAI,KAAK;KACnC,CAAC;IAEF,IAAI,MAAM,CAAC,cAAc,EAAE,CAAC;QAC1B,aAAa,CAAC,cAAc,GAAG,MAAM,CAAC,cAAc,CAAC;IACvD,CAAC;IAED,MAAM,OAAO,GAAG,MAAM,qBAAQ,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC;IAErD,MAAM,cAAc,GAA4B;QAC9C,QAAQ,EAAE,EAAE,KAAK,EAAE,IAAI,EAAE,MAAM,EAAE,GAAG,EAAE;QACtC,SAAS,EACP,uHAAuH;KAC1H,CAAC;IAEF,MAAM,OAAO,GAAG,MAAM,OAAO,CAAC,UAAU,CAAC,cAAc,CAAC,CAAC;IAEzD,IAAI,MAAM,CAAC,MAAM,EAAE,CAAC;QAClB,MAAM,OAAO,GAAG,iBAAiB,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC;QACjD,IAAI,OAAO,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;YACvB,MAAM,OAAO,CAAC,UAAU,CAAC,OAAO,CAAC,CAAC;QACpC,CAAC;IACH,CAAC;IAED,MAAM,IAAI,GAAG,MAAM,OAAO,CAAC,OAAO,EAAE,CAAC;IAErC,OAAO,EAAE,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,CAAC;AACpC,CAAC;AAED,SAAS,iBAAiB,CACxB,YAAoB;IAEpB,OAAO,YAAY;SAChB,KAAK,CAAC,GAAG,CAAC;SACV,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,IAAI,EAAE,CAAC;SAC1B,MAAM,CAAC,OAAO,CAAC;SACf,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE;QACZ,MAAM,CAAC,IAAI,EAAE,GAAG,IAAI,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;QACxC,OAAO;YACL,IAAI,EAAE,IAAI,CAAC,IAAI,EAAE;YACjB,KAAK,EAAE,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE;YAC5B,MAAM,EAAE,EAAE,EAAE,gCAAgC;YAC5C,IAAI,EAAE,GAAG;SACV,CAAC;IACJ,CAAC,CAAC,CAAC;AACP,CAAC"}
@@ -0,0 +1,12 @@
1
+ import type { Page } from "playwright";
2
+ export interface CrawlOptions {
3
+ depth: number;
4
+ timeout: number;
5
+ ignoreSelectors: string[];
6
+ }
7
+ export interface PageVisit {
8
+ url: string;
9
+ depth: number;
10
+ }
11
+ export declare function crawlSite(page: Page, startUrl: string, options: CrawlOptions): AsyncGenerator<PageVisit>;
12
+ //# sourceMappingURL=crawler.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"crawler.d.ts","sourceRoot":"","sources":["../../src/scanner/crawler.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,YAAY,CAAC;AAEvC,MAAM,WAAW,YAAY;IAC3B,KAAK,EAAE,MAAM,CAAC;IACd,OAAO,EAAE,MAAM,CAAC;IAChB,eAAe,EAAE,MAAM,EAAE,CAAC;CAC3B;AAED,MAAM,WAAW,SAAS;IACxB,GAAG,EAAE,MAAM,CAAC;IACZ,KAAK,EAAE,MAAM,CAAC;CACf;AAED,wBAAuB,SAAS,CAC9B,IAAI,EAAE,IAAI,EACV,QAAQ,EAAE,MAAM,EAChB,OAAO,EAAE,YAAY,GACpB,cAAc,CAAC,SAAS,CAAC,CAyC3B"}
@@ -0,0 +1,80 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.crawlSite = crawlSite;
4
+ async function* crawlSite(page, startUrl, options) {
5
+ const visited = new Set();
6
+ const queue = [
7
+ { url: normalizeUrl(startUrl), depth: 0 },
8
+ ];
9
+ while (queue.length > 0) {
10
+ const current = queue.shift();
11
+ const normalized = normalizeUrl(current.url);
12
+ if (visited.has(normalized))
13
+ continue;
14
+ if (current.depth > options.depth)
15
+ continue;
16
+ visited.add(normalized);
17
+ try {
18
+ await page.goto(current.url, {
19
+ waitUntil: "domcontentloaded",
20
+ timeout: options.timeout,
21
+ });
22
+ await page.waitForLoadState("load").catch(() => { });
23
+ await page.waitForTimeout(2000);
24
+ yield { url: current.url, depth: current.depth };
25
+ if (current.depth < options.depth) {
26
+ const links = await discoverInternalLinks(page, startUrl, options.ignoreSelectors);
27
+ for (const link of links) {
28
+ const normalizedLink = normalizeUrl(link);
29
+ if (!visited.has(normalizedLink)) {
30
+ queue.push({ url: link, depth: current.depth + 1 });
31
+ }
32
+ }
33
+ }
34
+ }
35
+ catch (error) {
36
+ const message = error instanceof Error ? error.message : String(error);
37
+ console.warn(` Warning: Failed to load ${current.url}: ${message}`);
38
+ }
39
+ }
40
+ }
41
+ async function discoverInternalLinks(page, baseUrl, ignoreSelectors) {
42
+ const baseOrigin = new URL(baseUrl).origin;
43
+ const ignoreSelectorsStr = JSON.stringify(ignoreSelectors);
44
+ return page.evaluate(({ origin, ignoreArr }) => {
45
+ const links = [];
46
+ const anchors = document.querySelectorAll("a[href]");
47
+ for (const anchor of anchors) {
48
+ const shouldIgnore = ignoreArr.some((sel) => anchor.matches(sel));
49
+ if (shouldIgnore)
50
+ continue;
51
+ const href = anchor.href;
52
+ try {
53
+ const url = new URL(href);
54
+ if (url.origin === origin && !url.hash) {
55
+ links.push(url.href);
56
+ }
57
+ }
58
+ catch {
59
+ // Invalid URL, skip
60
+ }
61
+ }
62
+ return [...new Set(links)];
63
+ }, { origin: baseOrigin, ignoreArr: JSON.parse(ignoreSelectorsStr) });
64
+ }
65
+ function normalizeUrl(url) {
66
+ try {
67
+ const parsed = new URL(url);
68
+ parsed.hash = "";
69
+ let path = parsed.pathname;
70
+ if (path.endsWith("/") && path !== "/") {
71
+ path = path.slice(0, -1);
72
+ }
73
+ parsed.pathname = path;
74
+ return parsed.toString();
75
+ }
76
+ catch {
77
+ return url;
78
+ }
79
+ }
80
+ //# sourceMappingURL=crawler.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"crawler.js","sourceRoot":"","sources":["../../src/scanner/crawler.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,4 @@
1
+ import type { Page } from "playwright";
2
+ import type { DomSnapshot } from "../types.js";
3
+ export declare function captureDom(page: Page): Promise<DomSnapshot>;
4
+ //# sourceMappingURL=dom-capture.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"dom-capture.d.ts","sourceRoot":"","sources":["../../src/scanner/dom-capture.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,YAAY,CAAC;AACvC,OAAO,KAAK,EAAE,WAAW,EAA0C,MAAM,aAAa,CAAC;AAEvF,wBAAsB,UAAU,CAAC,IAAI,EAAE,IAAI,GAAG,OAAO,CAAC,WAAW,CAAC,CAqJjE"}
@@ -0,0 +1,148 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.captureDom = captureDom;
4
+ async function captureDom(page) {
5
+ const result = await page.evaluate(() => {
6
+ const forms = [];
7
+ document.querySelectorAll("form").forEach((form, formIndex) => {
8
+ const fields = [];
9
+ const formSelector = form.id
10
+ ? `#${form.id}`
11
+ : `form:nth-of-type(${formIndex + 1})`;
12
+ form.querySelectorAll("input, select, textarea").forEach((el) => {
13
+ const input = el;
14
+ const name = input.name || input.id || "";
15
+ if (!name)
16
+ return;
17
+ let label;
18
+ const labelEl = form.querySelector(`label[for="${input.id}"]`);
19
+ if (labelEl) {
20
+ label = labelEl.textContent?.trim();
21
+ }
22
+ else {
23
+ const parentLabel = input.closest("label");
24
+ if (parentLabel) {
25
+ label = parentLabel.textContent?.trim()?.replace(input.value, "").trim();
26
+ }
27
+ }
28
+ let type = "string";
29
+ if (el.tagName === "SELECT")
30
+ type = "enum";
31
+ else if (input.type === "number" || input.type === "range")
32
+ type = "number";
33
+ else if (input.type === "checkbox")
34
+ type = "boolean";
35
+ else if (input.type === "email")
36
+ type = "email";
37
+ else if (input.type === "tel")
38
+ type = "tel";
39
+ else if (input.type === "url")
40
+ type = "url";
41
+ else if (input.type === "date" || input.type === "datetime-local")
42
+ type = "date";
43
+ let options;
44
+ if (el.tagName === "SELECT") {
45
+ options = Array.from(el.options)
46
+ .filter((opt) => opt.value)
47
+ .map((opt) => opt.value);
48
+ }
49
+ fields.push({
50
+ name,
51
+ type,
52
+ required: input.required || input.hasAttribute("required"),
53
+ label,
54
+ placeholder: input.placeholder || undefined,
55
+ options,
56
+ pattern: input.pattern || undefined,
57
+ min: input.min ? Number(input.min) : undefined,
58
+ max: input.max ? Number(input.max) : undefined,
59
+ defaultValue: input.defaultValue || undefined,
60
+ });
61
+ });
62
+ const submitBtn = form.querySelector('button[type="submit"]') ||
63
+ form.querySelector('input[type="submit"]') ||
64
+ form.querySelector("button:not([type])");
65
+ const submitSelector = submitBtn
66
+ ? submitBtn.id
67
+ ? `#${submitBtn.id}`
68
+ : `${formSelector} button[type="submit"]`
69
+ : `${formSelector} button`;
70
+ const labels = [];
71
+ const ariaLabel = form.getAttribute("aria-label");
72
+ if (ariaLabel)
73
+ labels.push(ariaLabel);
74
+ const legend = form.querySelector("legend");
75
+ if (legend)
76
+ labels.push(legend.textContent?.trim() || "");
77
+ const prev = form.previousElementSibling;
78
+ if (prev && /^h[1-6]$/i.test(prev.tagName)) {
79
+ labels.push(prev.textContent?.trim() || "");
80
+ }
81
+ forms.push({
82
+ selector: formSelector,
83
+ id: form.id || undefined,
84
+ action: form.action || undefined,
85
+ method: (form.method || "GET").toUpperCase(),
86
+ fields,
87
+ submitSelector,
88
+ labels: labels.filter(Boolean),
89
+ });
90
+ });
91
+ const buttons = [];
92
+ document
93
+ .querySelectorAll("button, [role='button'], a.btn, a.button")
94
+ .forEach((el, idx) => {
95
+ const isInsideForm = !!el.closest("form");
96
+ const text = el.textContent?.trim() || "";
97
+ const ariaLabel = el.getAttribute("aria-label") || undefined;
98
+ if (!text && !ariaLabel)
99
+ return;
100
+ const selector = el.id
101
+ ? `#${el.id}`
102
+ : `[data-webmcp-idx="${idx}"]`;
103
+ buttons.push({
104
+ selector,
105
+ text,
106
+ ariaLabel,
107
+ type: el.type || undefined,
108
+ isInsideForm,
109
+ });
110
+ });
111
+ const links = [];
112
+ document.querySelectorAll("a[href]").forEach((el) => {
113
+ const anchor = el;
114
+ const text = anchor.textContent?.trim() || "";
115
+ const href = anchor.href;
116
+ const ariaLabel = anchor.getAttribute("aria-label") || undefined;
117
+ if (!text && !ariaLabel)
118
+ return;
119
+ let isInternal = false;
120
+ try {
121
+ isInternal = new URL(href).origin === window.location.origin;
122
+ }
123
+ catch {
124
+ isInternal = true;
125
+ }
126
+ const selector = anchor.id
127
+ ? `#${anchor.id}`
128
+ : `a[href="${anchor.getAttribute("href")}"]`;
129
+ links.push({
130
+ selector,
131
+ text,
132
+ href,
133
+ ariaLabel,
134
+ isInternal,
135
+ });
136
+ });
137
+ return {
138
+ url: window.location.href,
139
+ title: document.title,
140
+ forms,
141
+ buttons,
142
+ links,
143
+ timestamp: new Date().toISOString(),
144
+ };
145
+ });
146
+ return result;
147
+ }
148
+ //# sourceMappingURL=dom-capture.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"dom-capture.js","sourceRoot":"","sources":["../../src/scanner/dom-capture.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,8 @@
1
+ import type { Page } from "playwright";
2
+ import type { NetworkCall } from "../types.js";
3
+ export interface NetworkRecorder {
4
+ getCalls(): NetworkCall[];
5
+ stop(): void;
6
+ }
7
+ export declare function createNetworkRecorder(page: Page, baseUrl: string): NetworkRecorder;
8
+ //# sourceMappingURL=network-capture.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"network-capture.d.ts","sourceRoot":"","sources":["../../src/scanner/network-capture.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,IAAI,EAAqB,MAAM,YAAY,CAAC;AAC1D,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,aAAa,CAAC;AAE/C,MAAM,WAAW,eAAe;IAC9B,QAAQ,IAAI,WAAW,EAAE,CAAC;IAC1B,IAAI,IAAI,IAAI,CAAC;CACd;AAED,wBAAgB,qBAAqB,CAAC,IAAI,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,GAAG,eAAe,CAoFlF"}
@@ -0,0 +1,112 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.createNetworkRecorder = createNetworkRecorder;
4
+ function createNetworkRecorder(page, baseUrl) {
5
+ const calls = [];
6
+ let active = true;
7
+ const baseHost = getBaseDomain(baseUrl);
8
+ const onResponse = async (response) => {
9
+ if (!active)
10
+ return;
11
+ const request = response.request();
12
+ const resourceType = request.resourceType();
13
+ if (resourceType !== "fetch" &&
14
+ resourceType !== "xhr" &&
15
+ resourceType !== "document") {
16
+ return;
17
+ }
18
+ const url = request.url();
19
+ if (!isSameSite(url, baseHost))
20
+ return;
21
+ if (isStaticResource(url))
22
+ return;
23
+ const method = request.method();
24
+ const status = response.status();
25
+ let requestBodySample = undefined;
26
+ let responseBodySample = undefined;
27
+ let operationName;
28
+ let operationType = undefined;
29
+ try {
30
+ const postData = request.postData();
31
+ if (postData) {
32
+ try {
33
+ const parsed = JSON.parse(postData);
34
+ requestBodySample = parsed;
35
+ if (parsed.query && (parsed.operationName || parsed.variables !== undefined)) {
36
+ operationName = parsed.operationName;
37
+ operationType = parsed.query.trim().startsWith("mutation")
38
+ ? "mutation"
39
+ : "query";
40
+ }
41
+ }
42
+ catch {
43
+ requestBodySample = postData;
44
+ }
45
+ }
46
+ }
47
+ catch {
48
+ // Request body not available
49
+ }
50
+ try {
51
+ const contentType = response.headers()["content-type"] || "";
52
+ if (contentType.includes("json")) {
53
+ const body = await response.json();
54
+ responseBodySample = body;
55
+ }
56
+ }
57
+ catch {
58
+ // Response body not available
59
+ }
60
+ calls.push({
61
+ method,
62
+ url,
63
+ status,
64
+ requestBodySample,
65
+ responseBodySample,
66
+ operationName,
67
+ operationType,
68
+ });
69
+ };
70
+ page.on("response", onResponse);
71
+ return {
72
+ getCalls: () => [...calls],
73
+ stop: () => {
74
+ active = false;
75
+ page.off("response", onResponse);
76
+ },
77
+ };
78
+ }
79
+ function getBaseDomain(url) {
80
+ try {
81
+ return new URL(url).hostname;
82
+ }
83
+ catch {
84
+ return url;
85
+ }
86
+ }
87
+ // Matches exact hostname or any subdomain relationship
88
+ function isSameSite(requestUrl, baseHost) {
89
+ try {
90
+ const callHost = new URL(requestUrl).hostname;
91
+ return (callHost === baseHost ||
92
+ callHost.endsWith("." + baseHost) ||
93
+ baseHost.endsWith("." + callHost));
94
+ }
95
+ catch {
96
+ return false;
97
+ }
98
+ }
99
+ function isStaticResource(url) {
100
+ const staticExtensions = [
101
+ ".js", ".css", ".png", ".jpg", ".jpeg", ".gif", ".svg", ".ico",
102
+ ".woff", ".woff2", ".ttf", ".eot", ".map",
103
+ ];
104
+ try {
105
+ const path = new URL(url).pathname.toLowerCase();
106
+ return staticExtensions.some((ext) => path.endsWith(ext));
107
+ }
108
+ catch {
109
+ return false;
110
+ }
111
+ }
112
+ //# sourceMappingURL=network-capture.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"network-capture.js","sourceRoot":"","sources":["../../src/scanner/network-capture.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,3 @@
1
+ import type { Page } from "playwright";
2
+ export declare function captureScreenshot(page: Page, outputPath: string): Promise<void>;
3
+ //# sourceMappingURL=screenshot.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"screenshot.d.ts","sourceRoot":"","sources":["../../src/scanner/screenshot.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,YAAY,CAAC;AAEvC,wBAAsB,iBAAiB,CACrC,IAAI,EAAE,IAAI,EACV,UAAU,EAAE,MAAM,GACjB,OAAO,CAAC,IAAI,CAAC,CAKf"}
@@ -0,0 +1,10 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.captureScreenshot = captureScreenshot;
4
+ async function captureScreenshot(page, outputPath) {
5
+ await page.screenshot({
6
+ path: outputPath,
7
+ fullPage: true,
8
+ });
9
+ }
10
+ //# sourceMappingURL=screenshot.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"screenshot.js","sourceRoot":"","sources":["../../src/scanner/screenshot.ts"],"names":[],"mappings":";;AAEA,8CAQC;AARM,KAAK,UAAU,iBAAiB,CACrC,IAAU,EACV,UAAkB;IAElB,MAAM,IAAI,CAAC,UAAU,CAAC;QACpB,IAAI,EAAE,UAAU;QAChB,QAAQ,EAAE,IAAI;KACf,CAAC,CAAC;AACL,CAAC"}
@@ -0,0 +1,7 @@
1
+ import type { Action, ToolSpec } from "../types.js";
2
+ export interface ClusterOptions {
3
+ minConfidence?: number;
4
+ domain?: string;
5
+ }
6
+ export declare function clusterActions(actions: Action[], options?: ClusterOptions): ToolSpec[];
7
+ //# sourceMappingURL=clusterer.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"clusterer.d.ts","sourceRoot":"","sources":["../../src/synthesizer/clusterer.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EACV,MAAM,EACN,QAAQ,EAKT,MAAM,aAAa,CAAC;AAMrB,MAAM,WAAW,cAAc;IAC7B,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB;AAED,wBAAgB,cAAc,CAC5B,OAAO,EAAE,MAAM,EAAE,EACjB,OAAO,GAAE,cAAmB,GAC3B,QAAQ,EAAE,CAiBZ"}