chrome-e2e-sdk 0.0.0-stage → 1.0.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 (67) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +739 -2
  3. package/dist/assertion/Assertion.d.ts +87 -0
  4. package/dist/assertion/Assertion.d.ts.map +1 -0
  5. package/dist/assertion/Assertion.js +459 -0
  6. package/dist/assertion/Assertion.js.map +1 -0
  7. package/dist/assertion/recorder.d.ts +41 -0
  8. package/dist/assertion/recorder.d.ts.map +1 -0
  9. package/dist/assertion/recorder.js +37 -0
  10. package/dist/assertion/recorder.js.map +1 -0
  11. package/dist/browser/Browser.d.ts +44 -0
  12. package/dist/browser/Browser.d.ts.map +1 -0
  13. package/dist/browser/Browser.js +167 -0
  14. package/dist/browser/Browser.js.map +1 -0
  15. package/dist/browser/Locator.d.ts +94 -0
  16. package/dist/browser/Locator.d.ts.map +1 -0
  17. package/dist/browser/Locator.js +533 -0
  18. package/dist/browser/Locator.js.map +1 -0
  19. package/dist/browser/Page.d.ts +272 -0
  20. package/dist/browser/Page.d.ts.map +1 -0
  21. package/dist/browser/Page.js +979 -0
  22. package/dist/browser/Page.js.map +1 -0
  23. package/dist/client/MCPClient.d.ts +72 -0
  24. package/dist/client/MCPClient.d.ts.map +1 -0
  25. package/dist/client/MCPClient.js +302 -0
  26. package/dist/client/MCPClient.js.map +1 -0
  27. package/dist/client/MCPCommand.d.ts +51 -0
  28. package/dist/client/MCPCommand.d.ts.map +1 -0
  29. package/dist/client/MCPCommand.js +74 -0
  30. package/dist/client/MCPCommand.js.map +1 -0
  31. package/dist/env/loadEnv.d.ts +8 -0
  32. package/dist/env/loadEnv.d.ts.map +1 -0
  33. package/dist/env/loadEnv.js +19 -0
  34. package/dist/env/loadEnv.js.map +1 -0
  35. package/dist/errors/E2EError.d.ts +50 -0
  36. package/dist/errors/E2EError.d.ts.map +1 -0
  37. package/dist/errors/E2EError.js +90 -0
  38. package/dist/errors/E2EError.js.map +1 -0
  39. package/dist/index.d.ts +32 -0
  40. package/dist/index.d.ts.map +1 -0
  41. package/dist/index.js +37 -0
  42. package/dist/index.js.map +1 -0
  43. package/dist/logger.d.ts +12 -0
  44. package/dist/logger.d.ts.map +1 -0
  45. package/dist/logger.js +57 -0
  46. package/dist/logger.js.map +1 -0
  47. package/dist/network/Network.d.ts +72 -0
  48. package/dist/network/Network.d.ts.map +1 -0
  49. package/dist/network/Network.js +236 -0
  50. package/dist/network/Network.js.map +1 -0
  51. package/dist/test/HtmlReport.d.ts +26 -0
  52. package/dist/test/HtmlReport.d.ts.map +1 -0
  53. package/dist/test/HtmlReport.js +653 -0
  54. package/dist/test/HtmlReport.js.map +1 -0
  55. package/dist/test/Runner.d.ts +146 -0
  56. package/dist/test/Runner.d.ts.map +1 -0
  57. package/dist/test/Runner.js +390 -0
  58. package/dist/test/Runner.js.map +1 -0
  59. package/dist/test/index.d.ts +4 -0
  60. package/dist/test/index.d.ts.map +1 -0
  61. package/dist/test/index.js +3 -0
  62. package/dist/test/index.js.map +1 -0
  63. package/dist/version.d.ts +2 -0
  64. package/dist/version.d.ts.map +1 -0
  65. package/dist/version.js +4 -0
  66. package/dist/version.js.map +1 -0
  67. package/package.json +63 -4
@@ -0,0 +1,50 @@
1
+ export declare enum E2EErrorCode {
2
+ CONNECTION_ERROR = "CONNECTION_ERROR",
3
+ PAGE_NOT_FOUND = "PAGE_NOT_FOUND",
4
+ ELEMENT_NOT_FOUND = "ELEMENT_NOT_FOUND",
5
+ ELEMENT_NOT_INTERACTABLE = "ELEMENT_NOT_INTERACTABLE",
6
+ TIMEOUT = "TIMEOUT",
7
+ NETWORK_TIMEOUT = "NETWORK_TIMEOUT",
8
+ MCP_ERROR = "MCP_ERROR",
9
+ ASSERTION_ERROR = "ASSERTION_ERROR",
10
+ INVALID_ARGUMENT = "INVALID_ARGUMENT",
11
+ BROWSER_CLOSED = "BROWSER_CLOSED",
12
+ NAVIGATION_ERROR = "NAVIGATION_ERROR",
13
+ SCRIPT_ERROR = "SCRIPT_ERROR",
14
+ /** The MCP server rejected the call because its category flag is off. */
15
+ TOOL_DISABLED = "TOOL_DISABLED"
16
+ }
17
+ export declare class E2EError extends Error {
18
+ readonly code: E2EErrorCode;
19
+ readonly details?: Record<string, unknown>;
20
+ readonly cause?: Error;
21
+ constructor(code: E2EErrorCode, message: string, options?: {
22
+ details?: Record<string, unknown>;
23
+ cause?: Error;
24
+ });
25
+ static connectionError(message: string, cause?: Error): E2EError;
26
+ static pageNotFound(url?: string): E2EError;
27
+ static elementNotFound(selector: Selector, url?: string): E2EError;
28
+ static elementNotInteractable(selector: Selector, reason: string, url?: string): E2EError;
29
+ static timeout(operation: string, timeoutMs: number, details?: Record<string, unknown>): E2EError;
30
+ static networkTimeout(url: string, timeoutMs: number): E2EError;
31
+ static mcpError(message: string, cause?: Error, details?: Record<string, unknown>): E2EError;
32
+ static assertionError(message: string, details?: Record<string, unknown>): E2EError;
33
+ static invalidArgument(param: string, expected: string, received: unknown): E2EError;
34
+ static browserClosed(): E2EError;
35
+ static navigationError(url: string, cause?: Error): E2EError;
36
+ static scriptError(message: string, cause?: Error): E2EError;
37
+ static toolDisabled(toolName: string, reason: string, cause?: Error): E2EError;
38
+ toJSON(): Record<string, unknown>;
39
+ }
40
+ export interface Selector {
41
+ role?: string;
42
+ name?: string;
43
+ text?: string;
44
+ label?: string;
45
+ css?: string;
46
+ xpath?: string;
47
+ index?: number;
48
+ exact?: boolean;
49
+ }
50
+ //# sourceMappingURL=E2EError.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"E2EError.d.ts","sourceRoot":"","sources":["../../src/errors/E2EError.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,90 @@
1
+ export var E2EErrorCode;
2
+ (function (E2EErrorCode) {
3
+ E2EErrorCode["CONNECTION_ERROR"] = "CONNECTION_ERROR";
4
+ E2EErrorCode["PAGE_NOT_FOUND"] = "PAGE_NOT_FOUND";
5
+ E2EErrorCode["ELEMENT_NOT_FOUND"] = "ELEMENT_NOT_FOUND";
6
+ E2EErrorCode["ELEMENT_NOT_INTERACTABLE"] = "ELEMENT_NOT_INTERACTABLE";
7
+ E2EErrorCode["TIMEOUT"] = "TIMEOUT";
8
+ E2EErrorCode["NETWORK_TIMEOUT"] = "NETWORK_TIMEOUT";
9
+ E2EErrorCode["MCP_ERROR"] = "MCP_ERROR";
10
+ E2EErrorCode["ASSERTION_ERROR"] = "ASSERTION_ERROR";
11
+ E2EErrorCode["INVALID_ARGUMENT"] = "INVALID_ARGUMENT";
12
+ E2EErrorCode["BROWSER_CLOSED"] = "BROWSER_CLOSED";
13
+ E2EErrorCode["NAVIGATION_ERROR"] = "NAVIGATION_ERROR";
14
+ E2EErrorCode["SCRIPT_ERROR"] = "SCRIPT_ERROR";
15
+ /** The MCP server rejected the call because its category flag is off. */
16
+ E2EErrorCode["TOOL_DISABLED"] = "TOOL_DISABLED";
17
+ })(E2EErrorCode || (E2EErrorCode = {}));
18
+ export class E2EError extends Error {
19
+ code;
20
+ details;
21
+ cause;
22
+ constructor(code, message, options) {
23
+ super(message);
24
+ this.name = 'E2EError';
25
+ this.code = code;
26
+ this.details = options?.details;
27
+ this.cause = options?.cause;
28
+ if (Error.captureStackTrace) {
29
+ Error.captureStackTrace(this, E2EError);
30
+ }
31
+ }
32
+ static connectionError(message, cause) {
33
+ return new E2EError(E2EErrorCode.CONNECTION_ERROR, message, { cause });
34
+ }
35
+ static pageNotFound(url) {
36
+ return new E2EError(E2EErrorCode.PAGE_NOT_FOUND, url ? `Page not found: ${url}` : 'Page not found', { details: { url } });
37
+ }
38
+ static elementNotFound(selector, url) {
39
+ const strategy = selector.role
40
+ ? `role=${selector.role}`
41
+ : selector.text
42
+ ? `text="${selector.text}"`
43
+ : selector.label
44
+ ? `label="${selector.label}"`
45
+ : selector.css
46
+ ? `css="${selector.css}"`
47
+ : 'unknown';
48
+ return new E2EError(E2EErrorCode.ELEMENT_NOT_FOUND, `Unable to find element. Strategy: ${strategy}`, { details: { selector, url, strategy } });
49
+ }
50
+ static elementNotInteractable(selector, reason, url) {
51
+ return new E2EError(E2EErrorCode.ELEMENT_NOT_INTERACTABLE, `Element not interactable: ${reason}`, { details: { selector, reason, url } });
52
+ }
53
+ static timeout(operation, timeoutMs, details) {
54
+ return new E2EError(E2EErrorCode.TIMEOUT, `${operation} timed out after ${timeoutMs}ms`, { details: { operation, timeoutMs, ...details } });
55
+ }
56
+ static networkTimeout(url, timeoutMs) {
57
+ return new E2EError(E2EErrorCode.NETWORK_TIMEOUT, `Network request to ${url} timed out after ${timeoutMs}ms`, { details: { url, timeoutMs } });
58
+ }
59
+ static mcpError(message, cause, details) {
60
+ return new E2EError(E2EErrorCode.MCP_ERROR, message, { cause, details });
61
+ }
62
+ static assertionError(message, details) {
63
+ return new E2EError(E2EErrorCode.ASSERTION_ERROR, message, { details });
64
+ }
65
+ static invalidArgument(param, expected, received) {
66
+ return new E2EError(E2EErrorCode.INVALID_ARGUMENT, `Invalid argument: ${param}. Expected ${expected}, received ${JSON.stringify(received)}`, { details: { param, expected, received } });
67
+ }
68
+ static browserClosed() {
69
+ return new E2EError(E2EErrorCode.BROWSER_CLOSED, 'Browser has been closed');
70
+ }
71
+ static navigationError(url, cause) {
72
+ return new E2EError(E2EErrorCode.NAVIGATION_ERROR, `Navigation to ${url} failed`, { details: { url }, cause });
73
+ }
74
+ static scriptError(message, cause) {
75
+ return new E2EError(E2EErrorCode.SCRIPT_ERROR, message, { cause });
76
+ }
77
+ static toolDisabled(toolName, reason, cause) {
78
+ return new E2EError(E2EErrorCode.TOOL_DISABLED, `Tool ${toolName} is disabled in the MCP server: ${reason}`, { details: { tool: toolName, reason }, cause });
79
+ }
80
+ toJSON() {
81
+ return {
82
+ name: this.name,
83
+ code: this.code,
84
+ message: this.message,
85
+ details: this.details,
86
+ stack: this.stack
87
+ };
88
+ }
89
+ }
90
+ //# sourceMappingURL=E2EError.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"E2EError.js","sourceRoot":"","sources":["../../src/errors/E2EError.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,32 @@
1
+ import { E2EError, E2EErrorCode, type Selector } from './errors/E2EError.js';
2
+ import { MCPClient, type MCPClientOptions, type ToolResult, createMCPClient } from './client/MCPClient.js';
3
+ import { type MCPCommandOptions, type ConnectionMode, buildMCPArgs } from './client/MCPCommand.js';
4
+ import { Browser, type BrowserOptions, type PageInfo, connect } from './browser/Browser.js';
5
+ import { Page, PageLocalStorage, type SnapshotResult, type ScreenshotOptions, type ResizeOptions, type StorageOperationOptions, type WaitOptions, type LoadState, type ConsoleMessage, type ConsoleMessageDetail, type EmulateOptions } from './browser/Page.js';
6
+ import { Locator, type LocatorOptions } from './browser/Locator.js';
7
+ import { Network, type NetworkRequest, type NetworkResponse, type WaitForResponseOptions, type ListNetworkOptions, type ResourceType } from './network/Network.js';
8
+ import { expect, Expect, AssertionError, SoftAssertions, type ExpectOptions } from './assertion/Assertion.js';
9
+ import { logger, getLogger, setDebugMode, isDebugMode, type Logger } from './logger.js';
10
+ import { loadEnv, type LoadEnvOptions, type LoadEnvResult } from './env/loadEnv.js';
11
+ export { E2EError, E2EErrorCode, type Selector, MCPClient, type MCPClientOptions, type ToolResult, createMCPClient, type MCPCommandOptions, type ConnectionMode, buildMCPArgs, Browser, type BrowserOptions, type PageInfo, connect, Page, PageLocalStorage, type SnapshotResult, type ScreenshotOptions, type ResizeOptions, type StorageOperationOptions, type WaitOptions, type LoadState, type ConsoleMessage, type ConsoleMessageDetail, type EmulateOptions, Locator, type LocatorOptions, Network, type NetworkRequest, type NetworkResponse, type WaitForResponseOptions, type ListNetworkOptions, type ResourceType, expect, Expect, AssertionError, SoftAssertions, type ExpectOptions, logger, getLogger, setDebugMode, isDebugMode, loadEnv, type LoadEnvOptions, type LoadEnvResult, type Logger };
12
+ export { VERSION } from './version.js';
13
+ declare const _default: {
14
+ Browser: typeof Browser;
15
+ Page: typeof Page;
16
+ Locator: typeof Locator;
17
+ Network: typeof Network;
18
+ expect: typeof expect;
19
+ E2EError: typeof E2EError;
20
+ E2EErrorCode: typeof E2EErrorCode;
21
+ MCPClient: typeof MCPClient;
22
+ connect: typeof connect;
23
+ createMCPClient: typeof createMCPClient;
24
+ loadEnv: typeof loadEnv;
25
+ logger: Logger;
26
+ getLogger: typeof getLogger;
27
+ setDebugMode: typeof setDebugMode;
28
+ isDebugMode: typeof isDebugMode;
29
+ VERSION: string;
30
+ };
31
+ export default _default;
32
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,QAAQ,EAAE,YAAY,EAAE,KAAK,QAAQ,EAAE,MAAM,sBAAsB,CAAA;AAC5E,OAAO,EAAE,SAAS,EAAE,KAAK,gBAAgB,EAAE,KAAK,UAAU,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAA;AAC1G,OAAO,EAAE,KAAK,iBAAiB,EAAE,KAAK,cAAc,EAAE,YAAY,EAAE,MAAM,wBAAwB,CAAA;AAClG,OAAO,EAAE,OAAO,EAAE,KAAK,cAAc,EAAE,KAAK,QAAQ,EAAE,OAAO,EAAE,MAAM,sBAAsB,CAAA;AAC3F,OAAO,EAAE,IAAI,EAAE,gBAAgB,EAAE,KAAK,cAAc,EAAE,KAAK,iBAAiB,EAAE,KAAK,aAAa,EAAE,KAAK,uBAAuB,EAAE,KAAK,WAAW,EAAE,KAAK,SAAS,EAAE,KAAK,cAAc,EAAE,KAAK,oBAAoB,EAAE,KAAK,cAAc,EAAE,MAAM,mBAAmB,CAAA;AAChQ,OAAO,EAAE,OAAO,EAAE,KAAK,cAAc,EAAE,MAAM,sBAAsB,CAAA;AACnE,OAAO,EAAE,OAAO,EAAE,KAAK,cAAc,EAAE,KAAK,eAAe,EAAE,KAAK,sBAAsB,EAAE,KAAK,kBAAkB,EAAE,KAAK,YAAY,EAAE,MAAM,sBAAsB,CAAA;AAClK,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,cAAc,EAAE,cAAc,EAAE,KAAK,aAAa,EAAE,MAAM,0BAA0B,CAAA;AAC7G,OAAO,EAAE,MAAM,EAAE,SAAS,EAAE,YAAY,EAAE,WAAW,EAAE,KAAK,MAAM,EAAE,MAAM,aAAa,CAAA;AACvF,OAAO,EAAE,OAAO,EAAE,KAAK,cAAc,EAAE,KAAK,aAAa,EAAE,MAAM,kBAAkB,CAAA;AAGnF,OAAO,EACL,QAAQ,EACR,YAAY,EACZ,KAAK,QAAQ,EACb,SAAS,EACT,KAAK,gBAAgB,EACrB,KAAK,UAAU,EACf,eAAe,EACf,KAAK,iBAAiB,EACtB,KAAK,cAAc,EACnB,YAAY,EACZ,OAAO,EACP,KAAK,cAAc,EACnB,KAAK,QAAQ,EACb,OAAO,EACP,IAAI,EACJ,gBAAgB,EAChB,KAAK,cAAc,EACnB,KAAK,iBAAiB,EACtB,KAAK,aAAa,EAClB,KAAK,uBAAuB,EAC5B,KAAK,WAAW,EAChB,KAAK,SAAS,EACd,KAAK,cAAc,EACnB,KAAK,oBAAoB,EACzB,KAAK,cAAc,EACnB,OAAO,EACP,KAAK,cAAc,EACnB,OAAO,EACP,KAAK,cAAc,EACnB,KAAK,eAAe,EACpB,KAAK,sBAAsB,EAC3B,KAAK,kBAAkB,EACvB,KAAK,YAAY,EACjB,MAAM,EACN,MAAM,EACN,cAAc,EACd,cAAc,EACd,KAAK,aAAa,EAClB,MAAM,EACN,SAAS,EACT,YAAY,EACZ,WAAW,EACX,OAAO,EACP,KAAK,cAAc,EACnB,KAAK,aAAa,EAClB,KAAK,MAAM,EACZ,CAAA;AAGD,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAA;;;;;;;;;;;;;;;;;;;AAItC,wBAiBC"}
package/dist/index.js ADDED
@@ -0,0 +1,37 @@
1
+ // Chrome E2E SDK - Main Entry Point
2
+ // Browser automation SDK based on chrome-devtools-mcp
3
+ import { E2EError, E2EErrorCode } from './errors/E2EError.js';
4
+ import { MCPClient, createMCPClient } from './client/MCPClient.js';
5
+ import { buildMCPArgs } from './client/MCPCommand.js';
6
+ import { Browser, connect } from './browser/Browser.js';
7
+ import { Page, PageLocalStorage } from './browser/Page.js';
8
+ import { Locator } from './browser/Locator.js';
9
+ import { Network } from './network/Network.js';
10
+ import { expect, Expect, AssertionError, SoftAssertions } from './assertion/Assertion.js';
11
+ import { logger, getLogger, setDebugMode, isDebugMode } from './logger.js';
12
+ import { loadEnv } from './env/loadEnv.js';
13
+ // Re-export all
14
+ export { E2EError, E2EErrorCode, MCPClient, createMCPClient, buildMCPArgs, Browser, connect, Page, PageLocalStorage, Locator, Network, expect, Expect, AssertionError, SoftAssertions, logger, getLogger, setDebugMode, isDebugMode, loadEnv };
15
+ // Version, generated from package.json at build time
16
+ export { VERSION } from './version.js';
17
+ import { VERSION } from './version.js';
18
+ // Default export for convenience
19
+ export default {
20
+ Browser,
21
+ Page,
22
+ Locator,
23
+ Network,
24
+ expect,
25
+ E2EError,
26
+ E2EErrorCode,
27
+ MCPClient,
28
+ connect,
29
+ createMCPClient,
30
+ loadEnv,
31
+ logger,
32
+ getLogger,
33
+ setDebugMode,
34
+ isDebugMode,
35
+ VERSION
36
+ };
37
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,oCAAoC;AACpC,sDAAsD;AAEtD,OAAO,EAAE,QAAQ,EAAE,YAAY,EAAiB,MAAM,sBAAsB,CAAA;AAC5E,OAAO,EAAE,SAAS,EAA0C,eAAe,EAAE,MAAM,uBAAuB,CAAA;AAC1G,OAAO,EAA+C,YAAY,EAAE,MAAM,wBAAwB,CAAA;AAClG,OAAO,EAAE,OAAO,EAAsC,OAAO,EAAE,MAAM,sBAAsB,CAAA;AAC3F,OAAO,EAAE,IAAI,EAAE,gBAAgB,EAAwM,MAAM,mBAAmB,CAAA;AAChQ,OAAO,EAAE,OAAO,EAAuB,MAAM,sBAAsB,CAAA;AACnE,OAAO,EAAE,OAAO,EAAsH,MAAM,sBAAsB,CAAA;AAClK,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,cAAc,EAAE,cAAc,EAAsB,MAAM,0BAA0B,CAAA;AAC7G,OAAO,EAAE,MAAM,EAAE,SAAS,EAAE,YAAY,EAAE,WAAW,EAAe,MAAM,aAAa,CAAA;AACvF,OAAO,EAAE,OAAO,EAA2C,MAAM,kBAAkB,CAAA;AAEnF,gBAAgB;AAChB,OAAO,EACL,QAAQ,EACR,YAAY,EAEZ,SAAS,EAGT,eAAe,EAGf,YAAY,EACZ,OAAO,EAGP,OAAO,EACP,IAAI,EACJ,gBAAgB,EAUhB,OAAO,EAEP,OAAO,EAMP,MAAM,EACN,MAAM,EACN,cAAc,EACd,cAAc,EAEd,MAAM,EACN,SAAS,EACT,YAAY,EACZ,WAAW,EACX,OAAO,EAIR,CAAA;AAED,qDAAqD;AACrD,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAA;AACtC,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAA;AAEtC,iCAAiC;AACjC,eAAe;IACb,OAAO;IACP,IAAI;IACJ,OAAO;IACP,OAAO;IACP,MAAM;IACN,QAAQ;IACR,YAAY;IACZ,SAAS;IACT,OAAO;IACP,eAAe;IACf,OAAO;IACP,MAAM;IACN,SAAS;IACT,YAAY;IACZ,WAAW;IACX,OAAO;CACR,CAAA"}
@@ -0,0 +1,12 @@
1
+ interface Logger {
2
+ debug(message: string, ...args: unknown[]): void;
3
+ info(message: string, ...args: unknown[]): void;
4
+ warn(message: string, ...args: unknown[]): void;
5
+ error(message: string, ...args: unknown[]): void;
6
+ }
7
+ export declare const logger: Logger;
8
+ export declare function getLogger(name: string): Logger;
9
+ export declare function setDebugMode(enabled: boolean): void;
10
+ export declare function isDebugMode(): boolean;
11
+ export type { Logger };
12
+ //# sourceMappingURL=logger.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logger.d.ts","sourceRoot":"","sources":["../src/logger.ts"],"names":[],"mappings":"AAIA,UAAU,MAAM;IACd,KAAK,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI,CAAA;IAChD,IAAI,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI,CAAA;IAC/C,IAAI,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI,CAAA;IAC/C,KAAK,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI,CAAA;CACjD;AAuCD,eAAO,MAAM,MAAM,QAAsB,CAAA;AAGzC,wBAAgB,SAAS,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAE9C;AAGD,wBAAgB,YAAY,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI,CAWnD;AAGD,wBAAgB,WAAW,IAAI,OAAO,CAErC;AAED,YAAY,EAAE,MAAM,EAAE,CAAA"}
package/dist/logger.js ADDED
@@ -0,0 +1,57 @@
1
+ // Logging utility for Chrome E2E SDK
2
+ const RESET_COLOR = '\x1b[0m';
3
+ const LOG_LEVEL_COLORS = {
4
+ debug: '\x1b[90m',
5
+ info: '\x1b[32m',
6
+ warn: '\x1b[33m',
7
+ error: '\x1b[31m'
8
+ };
9
+ function createLogger(prefix) {
10
+ const isDebug = process.env['DEBUG']?.includes('chrome-e2e') === true;
11
+ const formatMessage = (level, message) => {
12
+ const timestamp = new Date().toISOString();
13
+ const coloredLevel = `${LOG_LEVEL_COLORS[level]}${level.toUpperCase()}${RESET_COLOR}`;
14
+ return `[ChromeE2E:${prefix}] ${timestamp} ${coloredLevel}: ${message}`;
15
+ };
16
+ return {
17
+ debug(message, ...args) {
18
+ if (isDebug) {
19
+ console.debug(formatMessage('debug', message), ...args);
20
+ }
21
+ },
22
+ info(message, ...args) {
23
+ console.info(formatMessage('info', message), ...args);
24
+ },
25
+ warn(message, ...args) {
26
+ console.warn(formatMessage('warn', message), ...args);
27
+ },
28
+ error(message, ...args) {
29
+ console.error(formatMessage('error', message), ...args);
30
+ }
31
+ };
32
+ }
33
+ // Default logger
34
+ export const logger = createLogger('SDK');
35
+ // Create named logger
36
+ export function getLogger(name) {
37
+ return createLogger(name);
38
+ }
39
+ // Set debug mode programmatically
40
+ export function setDebugMode(enabled) {
41
+ if (enabled) {
42
+ process.env['DEBUG'] = (process.env['DEBUG'] ? process.env['DEBUG'] + ',' : '') + 'chrome-e2e';
43
+ }
44
+ else {
45
+ if (process.env['DEBUG']) {
46
+ process.env['DEBUG'] = process.env['DEBUG']
47
+ .split(',')
48
+ .filter((d) => d !== 'chrome-e2e')
49
+ .join(',');
50
+ }
51
+ }
52
+ }
53
+ // Check if debug mode is enabled
54
+ export function isDebugMode() {
55
+ return process.env['DEBUG']?.includes('chrome-e2e') === true;
56
+ }
57
+ //# sourceMappingURL=logger.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logger.js","sourceRoot":"","sources":["../src/logger.ts"],"names":[],"mappings":"AAAA,qCAAqC;AAWrC,MAAM,WAAW,GAAG,SAAS,CAAA;AAE7B,MAAM,gBAAgB,GAA6B;IACjD,KAAK,EAAE,UAAU;IACjB,IAAI,EAAE,UAAU;IAChB,IAAI,EAAE,UAAU;IAChB,KAAK,EAAE,UAAU;CAClB,CAAA;AAED,SAAS,YAAY,CAAC,MAAc;IAClC,MAAM,OAAO,GAAG,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,EAAE,QAAQ,CAAC,YAAY,CAAC,KAAK,IAAI,CAAA;IAErE,MAAM,aAAa,GAAG,CAAC,KAAe,EAAE,OAAe,EAAU,EAAE;QACjE,MAAM,SAAS,GAAG,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE,CAAA;QAC1C,MAAM,YAAY,GAAG,GAAG,gBAAgB,CAAC,KAAK,CAAC,GAAG,KAAK,CAAC,WAAW,EAAE,GAAG,WAAW,EAAE,CAAA;QACrF,OAAO,cAAc,MAAM,KAAK,SAAS,IAAI,YAAY,KAAK,OAAO,EAAE,CAAA;IACzE,CAAC,CAAA;IAED,OAAO;QACL,KAAK,CAAC,OAAe,EAAE,GAAG,IAAe;YACvC,IAAI,OAAO,EAAE,CAAC;gBACZ,OAAO,CAAC,KAAK,CAAC,aAAa,CAAC,OAAO,EAAE,OAAO,CAAC,EAAE,GAAG,IAAI,CAAC,CAAA;YACzD,CAAC;QACH,CAAC;QACD,IAAI,CAAC,OAAe,EAAE,GAAG,IAAe;YACtC,OAAO,CAAC,IAAI,CAAC,aAAa,CAAC,MAAM,EAAE,OAAO,CAAC,EAAE,GAAG,IAAI,CAAC,CAAA;QACvD,CAAC;QACD,IAAI,CAAC,OAAe,EAAE,GAAG,IAAe;YACtC,OAAO,CAAC,IAAI,CAAC,aAAa,CAAC,MAAM,EAAE,OAAO,CAAC,EAAE,GAAG,IAAI,CAAC,CAAA;QACvD,CAAC;QACD,KAAK,CAAC,OAAe,EAAE,GAAG,IAAe;YACvC,OAAO,CAAC,KAAK,CAAC,aAAa,CAAC,OAAO,EAAE,OAAO,CAAC,EAAE,GAAG,IAAI,CAAC,CAAA;QACzD,CAAC;KACF,CAAA;AACH,CAAC;AAED,iBAAiB;AACjB,MAAM,CAAC,MAAM,MAAM,GAAG,YAAY,CAAC,KAAK,CAAC,CAAA;AAEzC,sBAAsB;AACtB,MAAM,UAAU,SAAS,CAAC,IAAY;IACpC,OAAO,YAAY,CAAC,IAAI,CAAC,CAAA;AAC3B,CAAC;AAED,kCAAkC;AAClC,MAAM,UAAU,YAAY,CAAC,OAAgB;IAC3C,IAAI,OAAO,EAAE,CAAC;QACZ,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,GAAG,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,GAAG,YAAY,CAAA;IAChG,CAAC;SAAM,CAAC;QACN,IAAI,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,EAAE,CAAC;YACzB,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,GAAG,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC;iBACxC,KAAK,CAAC,GAAG,CAAC;iBACV,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,KAAK,YAAY,CAAC;iBACjC,IAAI,CAAC,GAAG,CAAC,CAAA;QACd,CAAC;IACH,CAAC;AACH,CAAC;AAED,iCAAiC;AACjC,MAAM,UAAU,WAAW;IACzB,OAAO,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,EAAE,QAAQ,CAAC,YAAY,CAAC,KAAK,IAAI,CAAA;AAC9D,CAAC"}
@@ -0,0 +1,72 @@
1
+ import { MCPClient } from '../client/MCPClient.js';
2
+ export type ResourceType = 'Document' | 'Stylesheet' | 'Image' | 'Media' | 'Font' | 'Script' | 'TextTrack' | 'XHR' | 'Fetch' | 'EventSource' | 'WebSocket' | 'Manifest' | 'Other';
3
+ export interface NetworkRequest {
4
+ requestId: string;
5
+ url: string;
6
+ method: string;
7
+ resourceType: ResourceType;
8
+ requestHeaders: Record<string, string>;
9
+ requestBody?: string;
10
+ requestBodyFilePath?: string;
11
+ responseHeaders?: Record<string, string>;
12
+ responseBody?: string;
13
+ responseBodyFilePath?: string;
14
+ /** Set when the request failed, e.g. `net::ERR_CONNECTION_REFUSED`. */
15
+ failure?: string;
16
+ redirectChain?: NetworkRequest[];
17
+ /** Populated only for requests that are still in flight. */
18
+ pending?: boolean;
19
+ timestamp: number;
20
+ response?: NetworkResponse;
21
+ }
22
+ export interface NetworkResponse {
23
+ status: number;
24
+ statusText: string;
25
+ headers: Record<string, string>;
26
+ body?: string;
27
+ mimeType: string;
28
+ fromCache: boolean;
29
+ timestamp: number;
30
+ }
31
+ export interface WaitForResponseOptions {
32
+ url: string | RegExp | ((request: NetworkRequest) => boolean);
33
+ timeout?: number;
34
+ resourceTypes?: ResourceType[];
35
+ }
36
+ export interface ListNetworkOptions {
37
+ resourceTypes?: ResourceType[];
38
+ since?: number;
39
+ }
40
+ export declare class Network {
41
+ private mcpClient;
42
+ private pageId;
43
+ private defaultTimeout;
44
+ private readonly logger;
45
+ constructor(mcpClient: MCPClient, pageId: number, defaultTimeout: number);
46
+ private createLogger;
47
+ list(options?: ListNetworkOptions): Promise<NetworkRequest[]>;
48
+ /**
49
+ * Fetch a single request with full headers and bodies.
50
+ * Returns `null` only when the request is unknown; transport failures propagate.
51
+ */
52
+ get(requestId: string | number): Promise<NetworkRequest | null>;
53
+ private isUnknownRequestError;
54
+ waitForResponse(options: WaitForResponseOptions): Promise<NetworkResponse>;
55
+ waitForRequest(options: WaitForResponseOptions): Promise<NetworkRequest>;
56
+ private waitForRequestResponse;
57
+ private matches;
58
+ private describeMatcher;
59
+ getDefaultTimeout(): number;
60
+ setDefaultTimeout(timeout: number): void;
61
+ private sleep;
62
+ private matchesResourceTypes;
63
+ private fromMCPConciseRequest;
64
+ private fromMCPDetailedRequest;
65
+ /**
66
+ * `chrome-devtools-mcp` reports status as a string that is either a numeric
67
+ * HTTP status, the literal `pending`, or a network failure error text.
68
+ */
69
+ private parseStatus;
70
+ private buildResponse;
71
+ }
72
+ //# sourceMappingURL=Network.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Network.d.ts","sourceRoot":"","sources":["../../src/network/Network.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,236 @@
1
+ import { MCPClient } from '../client/MCPClient.js';
2
+ import { E2EError, E2EErrorCode } from '../errors/E2EError.js';
3
+ /**
4
+ * Since chrome-devtools-mcp 1.9.0 concise network output caps URLs at 255
5
+ * characters and appends this marker, so a long request URL is only ever a
6
+ * prefix. Matching has to account for that or long URLs never match.
7
+ */
8
+ const TRUNCATION = /\.\.\. <truncated>$/;
9
+ function escapeRegExp(value) {
10
+ return value.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
11
+ }
12
+ export class Network {
13
+ mcpClient;
14
+ pageId;
15
+ defaultTimeout;
16
+ logger;
17
+ constructor(mcpClient, pageId, defaultTimeout) {
18
+ this.mcpClient = mcpClient;
19
+ this.pageId = pageId;
20
+ this.defaultTimeout = defaultTimeout;
21
+ this.logger = this.createLogger();
22
+ }
23
+ createLogger() {
24
+ return (level, message) => {
25
+ if (process.env['DEBUG']?.includes('chrome-e2e')) {
26
+ console.error(`[ChromeE2E:Network:${this.pageId}] ${level.toUpperCase()}: ${message}`);
27
+ }
28
+ };
29
+ }
30
+ async list(options = {}) {
31
+ this.logger('debug', `Listing network requests${options.resourceTypes ? ` (types: ${options.resourceTypes.join(', ')})` : ''}`);
32
+ const result = await this.mcpClient.call('list_network_requests', {
33
+ pageId: this.pageId,
34
+ resourceTypes: options.resourceTypes?.map((type) => type.toLowerCase())
35
+ });
36
+ if (!Array.isArray(result.networkRequests)) {
37
+ return [];
38
+ }
39
+ return result.networkRequests
40
+ .map((request) => this.fromMCPConciseRequest(request, options.resourceTypes?.[0] ?? 'Other'))
41
+ .filter((request) => this.matchesResourceTypes(request, options.resourceTypes))
42
+ .filter((request) => !options.since || request.timestamp >= options.since);
43
+ }
44
+ /**
45
+ * Fetch a single request with full headers and bodies.
46
+ * Returns `null` only when the request is unknown; transport failures propagate.
47
+ */
48
+ async get(requestId) {
49
+ this.logger('debug', `Getting network request: ${requestId}`);
50
+ let result;
51
+ try {
52
+ result = await this.mcpClient.call('get_network_request', {
53
+ pageId: this.pageId,
54
+ reqid: Number(requestId)
55
+ });
56
+ }
57
+ catch (error) {
58
+ if (this.isUnknownRequestError(error)) {
59
+ return null;
60
+ }
61
+ throw error;
62
+ }
63
+ return result.networkRequest ? this.fromMCPDetailedRequest(result.networkRequest) : null;
64
+ }
65
+ isUnknownRequestError(error) {
66
+ if (!(error instanceof Error)) {
67
+ return false;
68
+ }
69
+ return /no network request|not found|invalid reqid/i.test(error.message);
70
+ }
71
+ async waitForResponse(options) {
72
+ const timeout = options.timeout ?? this.defaultTimeout;
73
+ const startTime = Date.now();
74
+ const pollInterval = 100;
75
+ this.logger('debug', `Waiting for response matching: ${this.describeMatcher(options.url)}`);
76
+ while (Date.now() - startTime < timeout) {
77
+ const requests = await this.list({ resourceTypes: options.resourceTypes });
78
+ for (const request of requests) {
79
+ if (this.matches(request, options.url)) {
80
+ if (request.response) {
81
+ this.logger('debug', `Found matching response: ${request.url}`);
82
+ return request.response;
83
+ }
84
+ // Request found but no response yet, wait for it
85
+ const response = await this.waitForRequestResponse(request.requestId, timeout - (Date.now() - startTime));
86
+ if (response) {
87
+ return response;
88
+ }
89
+ }
90
+ }
91
+ await this.sleep(pollInterval);
92
+ }
93
+ throw E2EError.networkTimeout(this.describeMatcher(options.url), timeout);
94
+ }
95
+ async waitForRequest(options) {
96
+ const timeout = options.timeout ?? this.defaultTimeout;
97
+ const startTime = Date.now();
98
+ const pollInterval = 100;
99
+ this.logger('debug', `Waiting for request matching: ${this.describeMatcher(options.url)}`);
100
+ while (Date.now() - startTime < timeout) {
101
+ const requests = await this.list({ resourceTypes: options.resourceTypes });
102
+ for (const request of requests) {
103
+ if (this.matches(request, options.url)) {
104
+ this.logger('debug', `Found matching request: ${request.url}`);
105
+ return request;
106
+ }
107
+ }
108
+ await this.sleep(pollInterval);
109
+ }
110
+ throw E2EError.networkTimeout(this.describeMatcher(options.url), timeout);
111
+ }
112
+ async waitForRequestResponse(requestId, remainingTimeout) {
113
+ const startTime = Date.now();
114
+ const pollInterval = 50;
115
+ while (Date.now() - startTime < remainingTimeout) {
116
+ const request = await this.get(requestId);
117
+ if (request?.response) {
118
+ return request.response;
119
+ }
120
+ await this.sleep(pollInterval);
121
+ }
122
+ return null;
123
+ }
124
+ matches(request, matcher) {
125
+ if (typeof matcher === 'function') {
126
+ return matcher(request);
127
+ }
128
+ const truncated = TRUNCATION.test(request.url);
129
+ const url = truncated ? request.url.replace(TRUNCATION, '') : request.url;
130
+ if (matcher instanceof RegExp) {
131
+ return matcher.test(url);
132
+ }
133
+ if (matcher.includes('*')) {
134
+ const regex = new RegExp('^' + escapeRegExp(matcher).replace(/\\\*/g, '.*') + '$');
135
+ // An end-anchored pattern cannot be satisfied by a truncated URL, so
136
+ // fall back to a prefix match rather than silently missing.
137
+ return truncated ? regex.test(url) || new RegExp(escapeRegExp(url) + '.*$').test(matcher) : regex.test(url);
138
+ }
139
+ if (truncated) {
140
+ // Only the visible prefix is available: the matcher either appears in it
141
+ // or the visible prefix is the start of the matcher.
142
+ return url.includes(matcher) || matcher.startsWith(url);
143
+ }
144
+ return url.includes(matcher);
145
+ }
146
+ describeMatcher(matcher) {
147
+ if (typeof matcher === 'function')
148
+ return 'function';
149
+ if (matcher instanceof RegExp)
150
+ return matcher.toString();
151
+ return matcher;
152
+ }
153
+ getDefaultTimeout() {
154
+ return this.defaultTimeout;
155
+ }
156
+ setDefaultTimeout(timeout) {
157
+ this.defaultTimeout = timeout;
158
+ }
159
+ sleep(ms) {
160
+ return new Promise((resolve) => setTimeout(resolve, ms));
161
+ }
162
+ matchesResourceTypes(request, resourceTypes) {
163
+ return !resourceTypes || resourceTypes.length === 0 || resourceTypes.includes(request.resourceType);
164
+ }
165
+ fromMCPConciseRequest(request, resourceType) {
166
+ const timestamp = Date.now();
167
+ const parsedStatus = this.parseStatus(request.status);
168
+ const response = parsedStatus.kind === 'http'
169
+ ? this.buildResponse(parsedStatus.status, {}, undefined, timestamp)
170
+ : undefined;
171
+ return {
172
+ requestId: String(request.requestId),
173
+ url: request.url,
174
+ method: request.method,
175
+ resourceType,
176
+ requestHeaders: {},
177
+ ...(parsedStatus.kind === 'failure' ? { failure: parsedStatus.failure } : {}),
178
+ ...(parsedStatus.kind === 'pending' ? { pending: true } : {}),
179
+ timestamp,
180
+ response
181
+ };
182
+ }
183
+ fromMCPDetailedRequest(request) {
184
+ const timestamp = Date.now();
185
+ const parsedStatus = this.parseStatus(request.status);
186
+ const responseHeaders = request.responseHeaders;
187
+ const response = parsedStatus.kind === 'http'
188
+ ? this.buildResponse(parsedStatus.status, responseHeaders ?? {}, request.responseBody, timestamp)
189
+ : undefined;
190
+ return {
191
+ requestId: String(request.requestId),
192
+ url: request.url,
193
+ method: request.method,
194
+ resourceType: 'Other',
195
+ requestHeaders: request.requestHeaders ?? {},
196
+ requestBody: request.requestBody,
197
+ requestBodyFilePath: request.requestBodyFilePath,
198
+ responseHeaders,
199
+ responseBody: request.responseBody,
200
+ responseBodyFilePath: request.responseBodyFilePath,
201
+ ...(request.failure ? { failure: request.failure } : {}),
202
+ ...(parsedStatus.kind === 'pending' ? { pending: true } : {}),
203
+ ...(request.redirectChain
204
+ ? { redirectChain: request.redirectChain.map((hop) => this.fromMCPConciseRequest(hop, 'Other')) }
205
+ : {}),
206
+ timestamp,
207
+ response
208
+ };
209
+ }
210
+ /**
211
+ * `chrome-devtools-mcp` reports status as a string that is either a numeric
212
+ * HTTP status, the literal `pending`, or a network failure error text.
213
+ */
214
+ parseStatus(status) {
215
+ if (status === undefined || status === 'pending') {
216
+ return { kind: 'pending' };
217
+ }
218
+ const numericStatus = typeof status === 'number' ? status : Number(status);
219
+ if (Number.isFinite(numericStatus)) {
220
+ return { kind: 'http', status: numericStatus };
221
+ }
222
+ return { kind: 'failure', failure: String(status) };
223
+ }
224
+ buildResponse(status, headers, body, timestamp) {
225
+ return {
226
+ status,
227
+ statusText: '',
228
+ headers,
229
+ body,
230
+ mimeType: headers['content-type'] ?? headers['Content-Type'] ?? '',
231
+ fromCache: false,
232
+ timestamp
233
+ };
234
+ }
235
+ }
236
+ //# sourceMappingURL=Network.js.map