@gtkx/mcp 1.6.0 → 2.0.0-beta.2

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/README.md CHANGED
@@ -13,7 +13,7 @@
13
13
  <p align="center">
14
14
  <a href="https://www.npmjs.com/package/create-gtkx"><img src="https://img.shields.io/npm/v/create-gtkx?color=cb3837&logo=npm&label=create-gtkx" alt="npm version" /></a>
15
15
  <a href="https://www.npmjs.com/package/create-gtkx"><img src="https://img.shields.io/npm/dm/create-gtkx?color=cb3837&logo=npm&label=downloads" alt="npm downloads" /></a>
16
- <img src="https://img.shields.io/badge/node-%E2%89%A524-339933?logo=node.js&logoColor=white" alt="Node >= 24" />
16
+ <img src="https://img.shields.io/badge/node-%E2%89%A526.7-339933?logo=node.js&logoColor=white" alt="Node >= 26.7" />
17
17
  <a href="https://github.com/gtkx-org/gtkx/blob/main/LICENSE"><img src="https://img.shields.io/badge/license-MPL--2.0-blue.svg" alt="License: MPL-2.0" /></a>
18
18
  <a href="https://github.com/gtkx-org/gtkx/actions/workflows/ci.yml"><img src="https://img.shields.io/github/actions/workflow/status/gtkx-org/gtkx/ci.yml?branch=main&logo=github&label=CI" alt="CI status" /></a>
19
19
  <img src="https://img.shields.io/badge/TypeScript-strict-3178c6?logo=typescript&logoColor=white" alt="TypeScript" />
@@ -116,7 +116,7 @@ At runtime, the native Rust core calls straight into the system GTK4, Adwaita, a
116
116
 
117
117
  ## Quick start
118
118
 
119
- GTKX is Linux-only and needs Node.js 24 or later. See [Requirements](#requirements).
119
+ GTKX is Linux-only and needs Node.js 26.7 or later. See [Requirements](#requirements).
120
120
 
121
121
  Scaffold a new app with the `create-gtkx` initializer:
122
122
 
@@ -145,8 +145,8 @@ The documentation at **[gtkx.dev](https://gtkx.dev)** includes a step-by-step tu
145
145
 
146
146
  GTKX is Linux-only. You need:
147
147
 
148
- - Linux with the GTK4 (4.20 or later) and GLib development libraries, plus Adwaita (1.8 or later) once your project binds `Adw-1`
149
- - Node.js 24 or later
148
+ - Linux with the GTK4 (4.20 or later), Adwaita (1.8 or later), and GLib development libraries
149
+ - Node.js 26.7 or later
150
150
 
151
151
  The `@gtkx/native` addon ships prebuilt for x64 and arm64 glibc Linux; other targets need to build it from the GTKX repository, which requires a Rust toolchain.
152
152
 
@@ -167,7 +167,7 @@ GTKX is stable and ready for production use.
167
167
 
168
168
  ## Contributing
169
169
 
170
- Contributions are welcome. See [CONTRIBUTING.md](https://github.com/gtkx-org/gtkx/blob/main/CONTRIBUTING.md), the [Code of Conduct](https://github.com/gtkx-org/gtkx/blob/main/CODE_OF_CONDUCT.md), and the [security policy](https://github.com/gtkx-org/gtkx/blob/main/SECURITY.md). Building the repo needs Node.js 24 or later, pnpm, and a Rust toolchain.
170
+ Contributions are welcome. See [CONTRIBUTING.md](https://github.com/gtkx-org/gtkx/blob/main/CONTRIBUTING.md), the [Code of Conduct](https://github.com/gtkx-org/gtkx/blob/main/CODE_OF_CONDUCT.md), and the [security policy](https://github.com/gtkx-org/gtkx/blob/main/SECURITY.md). Building the repo needs Node.js 26.7 or later, pnpm, and a Rust toolchain.
171
171
 
172
172
  ## License
173
173
 
@@ -12,6 +12,8 @@ declare class AppRouter extends EventTarget {
12
12
  private connectionToApp;
13
13
  private requestTimeout;
14
14
  private connections;
15
+ private pendingAppWaits;
16
+ private isDisposed;
15
17
  constructor(connections: AppConnections, options?: {
16
18
  requestTimeout?: number;
17
19
  });
@@ -20,12 +22,14 @@ declare class AppRouter extends EventTarget {
20
22
  private handleRegister;
21
23
  private toAppError;
22
24
  private removeApp;
25
+ private waitForRegistration;
23
26
  getApps(): AppInfo[];
24
27
  hasConnectedApps(): boolean;
25
28
  getDefaultApp(): RegisteredApp | undefined;
26
29
  getProjectRoot(): string | undefined;
27
- waitForApp(timeout?: number): Promise<AppInfo>;
28
- sendToApp<T>(applicationId: string | undefined, method: string, params?: RequestParams): Promise<T>;
30
+ dispose(): void;
31
+ waitForApp(applicationId?: string, timeout?: number): Promise<AppInfo>;
32
+ sendToApp<T>(applicationId: string | undefined, method: string, params?: RequestParams, waitTimeout?: number): Promise<T>;
29
33
  }
30
34
  export { AppRouter, type AppRegisteredEvent, type AppUnregisteredEvent };
31
35
  //# sourceMappingURL=app-router.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"app-router.d.ts","sourceRoot":"","sources":["../src/app-router.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,cAAc,EAAmB,kBAAkB,EAAE,aAAa,EAAE,MAAM,gBAAgB,CAAC;AAazG,OAAO,EAAE,KAAK,OAAO,EAAwB,MAAM,uBAAuB,CAAC;AAE3E,KAAK,kBAAkB,GAAG,WAAW,CAAC,OAAO,CAAC,CAAC;AAC/C,KAAK,oBAAoB,GAAG,WAAW,CAAC,MAAM,CAAC,CAAC;AAEhD,KAAK,aAAa,GAAG;IACjB,IAAI,EAAE,OAAO,CAAC;IACd,UAAU,EAAE,kBAAkB,CAAC;CAClC,CAAC;AAYF,cAAM,SAAU,SAAQ,WAAW;IAC/B,OAAO,CAAC,MAAM,CAAC,kBAAkB,CAAU;IAE3C,OAAO,CAAC,IAAI,CAAyC;IAErD,OAAO,CAAC,eAAe,CAAkC;IAEzD,OAAO,CAAC,cAAc,CAAS;IAE/B,OAAO,CAAC,WAAW,CAAiB;gBAExB,WAAW,EAAE,cAAc,EAAE,OAAO,GAAE;QAAE,cAAc,CAAC,EAAE,MAAM,CAAA;KAAO;IAWlF,OAAO,CAAC,gBAAgB;IAcxB,OAAO,CAAC,aAAa;IAcrB,OAAO,CAAC,cAAc;IAsBtB,OAAO,CAAC,UAAU;IAclB,OAAO,CAAC,SAAS;IAgBjB,OAAO,IAAI,OAAO,EAAE;IAIpB,gBAAgB,IAAI,OAAO;IAI3B,aAAa,IAAI,aAAa,GAAG,SAAS;IAM1C,cAAc,IAAI,MAAM,GAAG,SAAS;IAIpC,UAAU,CAAC,OAAO,GAAE,MAAqC,GAAG,OAAO,CAAC,OAAO,CAAC;IA6BtE,SAAS,CAAC,CAAC,EAAE,aAAa,EAAE,MAAM,GAAG,SAAS,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,aAAa,GAAG,OAAO,CAAC,CAAC,CAAC;CAa5G;AAED,OAAO,EAAE,SAAS,EAAE,KAAK,kBAAkB,EAAE,KAAK,oBAAoB,EAAE,CAAC"}
1
+ {"version":3,"file":"app-router.d.ts","sourceRoot":"","sources":["../src/app-router.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,cAAc,EAAmB,kBAAkB,EAAE,aAAa,EAAE,MAAM,gBAAgB,CAAC;AAazG,OAAO,EAAE,KAAK,OAAO,EAAwB,MAAM,uBAAuB,CAAC;AAE3E,KAAK,kBAAkB,GAAG,WAAW,CAAC,OAAO,CAAC,CAAC;AAC/C,KAAK,oBAAoB,GAAG,WAAW,CAAC,MAAM,CAAC,CAAC;AAGhD,KAAK,aAAa,GAAG;IACjB,IAAI,EAAE,OAAO,CAAC;IACd,UAAU,EAAE,kBAAkB,CAAC;CAClC,CAAC;AAoBF,cAAM,SAAU,SAAQ,WAAW;IAC/B,OAAO,CAAC,MAAM,CAAC,kBAAkB,CAAU;IAE3C,OAAO,CAAC,IAAI,CAAyC;IAErD,OAAO,CAAC,eAAe,CAAkC;IAEzD,OAAO,CAAC,cAAc,CAAS;IAE/B,OAAO,CAAC,WAAW,CAAiB;IAEpC,OAAO,CAAC,eAAe,CAAkC;IAEzD,OAAO,CAAC,UAAU,CAAS;gBAEf,WAAW,EAAE,cAAc,EAAE,OAAO,GAAE;QAAE,cAAc,CAAC,EAAE,MAAM,CAAA;KAAO;IAWlF,OAAO,CAAC,gBAAgB;IAcxB,OAAO,CAAC,aAAa;IAkBrB,OAAO,CAAC,cAAc;IAsBtB,OAAO,CAAC,UAAU;IAclB,OAAO,CAAC,SAAS;YAgBH,mBAAmB;IAkCjC,OAAO,IAAI,OAAO,EAAE;IAIpB,gBAAgB,IAAI,OAAO;IAI3B,aAAa,IAAI,aAAa,GAAG,SAAS;IAM1C,cAAc,IAAI,MAAM,GAAG,SAAS;IAIpC,OAAO,IAAI,IAAI;IAaf,UAAU,CAAC,aAAa,CAAC,EAAE,MAAM,EAAE,OAAO,GAAE,MAAqC,GAAG,OAAO,CAAC,OAAO,CAAC;IAc9F,SAAS,CAAC,CAAC,EACb,aAAa,EAAE,MAAM,GAAG,SAAS,EACjC,MAAM,EAAE,MAAM,EACd,MAAM,CAAC,EAAE,aAAa,EACtB,WAAW,CAAC,EAAE,MAAM,GACrB,OAAO,CAAC,CAAC,CAAC;CAchB;AAED,OAAO,EAAE,SAAS,EAAE,KAAK,kBAAkB,EAAE,KAAK,oBAAoB,EAAE,CAAC"}
@@ -2,6 +2,9 @@ import { McpError } from "@modelcontextprotocol/sdk/types.js";
2
2
  import { appNotFoundError, CONNECTION_CLOSED_CODE, connectionWriteFailedError, invalidRequestError, methodNotFoundError, noAppConnectedError, protocolErrorFrom, REQUEST_TIMEOUT_CODE, requestTimeoutError, } from "./protocol/errors.js";
3
3
  import { RegisterParamsSchema } from "./protocol/schemas.js";
4
4
  const DEFAULT_REQUEST_TIMEOUT_MS = 30_000;
5
+ const routerStoppedError = () => new Error("GTKX MCP server stopped while waiting for an application");
6
+ const appWaitTimeoutError = (timeout) => new Error(`Timeout waiting for app registration after ${String(timeout)}ms. ` +
7
+ "Make sure your GTKX app is running with 'gtkx dev'.");
5
8
  function appRegisteredEvent(info) {
6
9
  return new CustomEvent("appRegistered", { detail: info });
7
10
  }
@@ -14,6 +17,8 @@ class AppRouter extends EventTarget {
14
17
  connectionToApp = new Map();
15
18
  requestTimeout;
16
19
  connections;
20
+ pendingAppWaits = new Set();
21
+ isDisposed = false;
17
22
  constructor(connections, options = {}) {
18
23
  super();
19
24
  this.connections = connections;
@@ -34,6 +39,9 @@ class AppRouter extends EventTarget {
34
39
  throw noAppConnectedError();
35
40
  }
36
41
  handleRequest(connection, request) {
42
+ if (this.isDisposed) {
43
+ return Promise.reject(routerStoppedError());
44
+ }
37
45
  if (request.method === "app.register") {
38
46
  return Promise.resolve(this.handleRegister(connection, request));
39
47
  }
@@ -81,6 +89,33 @@ class AppRouter extends EventTarget {
81
89
  this.apps.delete(applicationId);
82
90
  this.dispatchEvent(appUnregisteredEvent(applicationId));
83
91
  }
92
+ async waitForRegistration(applicationId, timeout) {
93
+ const controller = new AbortController();
94
+ const { promise, reject, resolve } = Promise.withResolvers();
95
+ const rejectWait = (error) => {
96
+ controller.abort();
97
+ reject(error);
98
+ };
99
+ const pendingWait = { reject: rejectWait };
100
+ const timeoutId = setTimeout(() => {
101
+ rejectWait(appWaitTimeoutError(timeout));
102
+ }, timeout);
103
+ this.addEventListener("appRegistered", (event) => {
104
+ const info = event.detail;
105
+ if (applicationId === undefined || info.applicationId === applicationId) {
106
+ resolve(info);
107
+ }
108
+ }, { signal: controller.signal });
109
+ this.pendingAppWaits.add(pendingWait);
110
+ try {
111
+ return await promise;
112
+ }
113
+ finally {
114
+ clearTimeout(timeoutId);
115
+ controller.abort();
116
+ this.pendingAppWaits.delete(pendingWait);
117
+ }
118
+ }
84
119
  getApps() {
85
120
  return this.apps.values().map((app) => app.info).toArray();
86
121
  }
@@ -94,26 +129,28 @@ class AppRouter extends EventTarget {
94
129
  getProjectRoot() {
95
130
  return this.getDefaultApp()?.info.projectRoot;
96
131
  }
97
- waitForApp(timeout = AppRouter.defaultWaitTimeout) {
98
- const defaultApp = this.getDefaultApp();
99
- if (defaultApp) {
100
- return Promise.resolve(defaultApp.info);
101
- }
102
- return new Promise((resolve, reject) => {
103
- const timeoutId = setTimeout(() => {
104
- this.removeEventListener("appRegistered", onRegister);
105
- reject(new Error(`Timeout waiting for app registration after ${String(timeout)}ms. ` +
106
- "Make sure your GTKX app is running with 'gtkx dev'."));
107
- }, timeout);
108
- const onRegister = (event) => {
109
- clearTimeout(timeoutId);
110
- this.removeEventListener("appRegistered", onRegister);
111
- resolve(event.detail);
112
- };
113
- this.addEventListener("appRegistered", onRegister);
114
- });
132
+ dispose() {
133
+ if (this.isDisposed) {
134
+ return;
135
+ }
136
+ this.isDisposed = true;
137
+ const error = routerStoppedError();
138
+ for (const pendingWait of this.pendingAppWaits) {
139
+ pendingWait.reject(error);
140
+ }
141
+ }
142
+ waitForApp(applicationId, timeout = AppRouter.defaultWaitTimeout) {
143
+ if (this.isDisposed) {
144
+ return Promise.reject(routerStoppedError());
145
+ }
146
+ const app = applicationId === undefined ? this.getDefaultApp() : this.apps.get(applicationId);
147
+ if (app) {
148
+ return Promise.resolve(app.info);
149
+ }
150
+ return this.waitForRegistration(applicationId, timeout);
115
151
  }
116
- async sendToApp(applicationId, method, params) {
152
+ async sendToApp(applicationId, method, params, waitTimeout) {
153
+ await this.waitForApp(applicationId, waitTimeout);
117
154
  const app = this.resolveTargetApp(applicationId);
118
155
  try {
119
156
  return await app.connection.send(method, params, this.requestTimeout);
@@ -1 +1 @@
1
- {"version":3,"file":"app-router.js","sourceRoot":"","sources":["../src/app-router.ts"],"names":[],"mappings":"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","sourcesContent":["import { type JSONRPCRequest, McpError, type Result } from \"@modelcontextprotocol/sdk/types.js\";\nimport type { AppConnections, ConnectionEvent, ProtocolConnection, RequestParams } from \"./transport.js\";\nimport {\n appNotFoundError,\n CONNECTION_CLOSED_CODE,\n connectionWriteFailedError,\n invalidRequestError,\n methodNotFoundError,\n noAppConnectedError,\n type ProtocolError,\n protocolErrorFrom,\n REQUEST_TIMEOUT_CODE,\n requestTimeoutError,\n} from \"./protocol/errors.js\";\nimport { type AppInfo, RegisterParamsSchema } from \"./protocol/schemas.js\";\n\ntype AppRegisteredEvent = CustomEvent<AppInfo>;\ntype AppUnregisteredEvent = CustomEvent<string>;\n\ntype RegisteredApp = {\n info: AppInfo;\n connection: ProtocolConnection;\n};\n\nconst DEFAULT_REQUEST_TIMEOUT_MS = 30_000;\n\nfunction appRegisteredEvent(info: AppInfo): AppRegisteredEvent {\n return new CustomEvent(\"appRegistered\", { detail: info });\n}\n\nfunction appUnregisteredEvent(applicationId: string): AppUnregisteredEvent {\n return new CustomEvent(\"appUnregistered\", { detail: applicationId });\n}\n\nclass AppRouter extends EventTarget {\n private static defaultWaitTimeout = 10_000;\n\n private apps: Map<string, RegisteredApp> = new Map();\n\n private connectionToApp: Map<string, string> = new Map();\n\n private requestTimeout: number;\n\n private connections: AppConnections;\n\n constructor(connections: AppConnections, options: { requestTimeout?: number } = {}) {\n super();\n this.connections = connections;\n this.requestTimeout = options.requestTimeout ?? DEFAULT_REQUEST_TIMEOUT_MS;\n this.connections.onRequest = (connection, request) => this.handleRequest(connection, request);\n\n this.connections.addEventListener(\"disconnection\", (event) => {\n this.removeApp((event as ConnectionEvent).detail);\n });\n }\n\n private resolveTargetApp(applicationId: string | undefined): RegisteredApp {\n const app = applicationId ? this.apps.get(applicationId) : this.getDefaultApp();\n\n if (app) {\n return app;\n }\n\n if (applicationId) {\n throw appNotFoundError(applicationId);\n }\n\n throw noAppConnectedError();\n }\n\n private handleRequest(connection: ProtocolConnection, request: JSONRPCRequest): Promise<Result> {\n if (request.method === \"app.register\") {\n return Promise.resolve(this.handleRegister(connection, request));\n }\n\n if (request.method === \"app.unregister\") {\n this.removeApp(connection);\n\n return Promise.resolve({ success: true });\n }\n\n return Promise.reject(methodNotFoundError(request.method));\n }\n\n private handleRegister(connection: ProtocolConnection, request: JSONRPCRequest): Result {\n const parseResult = RegisterParamsSchema.safeParse(request.params);\n\n if (!parseResult.success) {\n throw invalidRequestError(parseResult.error.message);\n }\n\n const params = parseResult.data;\n\n const appInfo: AppInfo = {\n applicationId: params.applicationId,\n pid: params.pid,\n ...(params.projectRoot !== undefined && { projectRoot: params.projectRoot }),\n };\n\n this.apps.set(params.applicationId, { info: appInfo, connection });\n this.connectionToApp.set(connection.id, params.applicationId);\n this.dispatchEvent(appRegisteredEvent(appInfo));\n\n return { success: true };\n }\n\n private toAppError(app: RegisteredApp, error: McpError): ProtocolError {\n if (error.code === CONNECTION_CLOSED_CODE) {\n this.removeApp(app.connection);\n\n return connectionWriteFailedError(app.info.applicationId);\n }\n\n if (error.code === REQUEST_TIMEOUT_CODE) {\n return requestTimeoutError(this.requestTimeout);\n }\n\n return protocolErrorFrom(error);\n }\n\n private removeApp(connection: ProtocolConnection): void {\n const applicationId = this.connectionToApp.get(connection.id);\n this.connectionToApp.delete(connection.id);\n\n if (applicationId === undefined) {\n return;\n }\n\n if (this.apps.get(applicationId)?.connection !== connection) {\n return;\n }\n\n this.apps.delete(applicationId);\n this.dispatchEvent(appUnregisteredEvent(applicationId));\n }\n\n getApps(): AppInfo[] {\n return this.apps.values().map((app) => app.info).toArray();\n }\n\n hasConnectedApps(): boolean {\n return this.apps.size > 0;\n }\n\n getDefaultApp(): RegisteredApp | undefined {\n const first = this.apps.values().next();\n\n return first.done ? undefined : first.value;\n }\n\n getProjectRoot(): string | undefined {\n return this.getDefaultApp()?.info.projectRoot;\n }\n\n waitForApp(timeout: number = AppRouter.defaultWaitTimeout): Promise<AppInfo> {\n const defaultApp = this.getDefaultApp();\n\n if (defaultApp) {\n return Promise.resolve(defaultApp.info);\n }\n\n return new Promise((resolve, reject) => {\n const timeoutId = setTimeout(() => {\n this.removeEventListener(\"appRegistered\", onRegister);\n\n reject(\n new Error(\n `Timeout waiting for app registration after ${String(timeout)}ms. ` +\n \"Make sure your GTKX app is running with 'gtkx dev'.\",\n ),\n );\n }, timeout);\n\n const onRegister = (event: Event): void => {\n clearTimeout(timeoutId);\n this.removeEventListener(\"appRegistered\", onRegister);\n resolve((event as AppRegisteredEvent).detail);\n };\n\n this.addEventListener(\"appRegistered\", onRegister);\n });\n }\n\n async sendToApp<T>(applicationId: string | undefined, method: string, params?: RequestParams): Promise<T> {\n const app = this.resolveTargetApp(applicationId);\n\n try {\n return await app.connection.send<T>(method, params, this.requestTimeout);\n } catch (error) {\n if (error instanceof McpError) {\n throw this.toAppError(app, error);\n }\n\n throw error;\n }\n }\n}\n\nexport { AppRouter, type AppRegisteredEvent, type AppUnregisteredEvent };\n"]}
1
+ {"version":3,"file":"app-router.js","sourceRoot":"","sources":["../src/app-router.ts"],"names":[],"mappings":"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","sourcesContent":["import { type JSONRPCRequest, McpError, type Result } from \"@modelcontextprotocol/sdk/types.js\";\nimport type { AppConnections, ConnectionEvent, ProtocolConnection, RequestParams } from \"./transport.js\";\nimport {\n appNotFoundError,\n CONNECTION_CLOSED_CODE,\n connectionWriteFailedError,\n invalidRequestError,\n methodNotFoundError,\n noAppConnectedError,\n type ProtocolError,\n protocolErrorFrom,\n REQUEST_TIMEOUT_CODE,\n requestTimeoutError,\n} from \"./protocol/errors.js\";\nimport { type AppInfo, RegisterParamsSchema } from \"./protocol/schemas.js\";\n\ntype AppRegisteredEvent = CustomEvent<AppInfo>;\ntype AppUnregisteredEvent = CustomEvent<string>;\ntype PendingAppWait = { reject: (error: Error) => void };\n\ntype RegisteredApp = {\n info: AppInfo;\n connection: ProtocolConnection;\n};\n\nconst DEFAULT_REQUEST_TIMEOUT_MS = 30_000;\n\nconst routerStoppedError = (): Error => new Error(\"GTKX MCP server stopped while waiting for an application\");\n\nconst appWaitTimeoutError = (timeout: number): Error =>\n new Error(\n `Timeout waiting for app registration after ${String(timeout)}ms. ` +\n \"Make sure your GTKX app is running with 'gtkx dev'.\",\n );\n\nfunction appRegisteredEvent(info: AppInfo): AppRegisteredEvent {\n return new CustomEvent(\"appRegistered\", { detail: info });\n}\n\nfunction appUnregisteredEvent(applicationId: string): AppUnregisteredEvent {\n return new CustomEvent(\"appUnregistered\", { detail: applicationId });\n}\n\nclass AppRouter extends EventTarget {\n private static defaultWaitTimeout = 10_000;\n\n private apps: Map<string, RegisteredApp> = new Map();\n\n private connectionToApp: Map<string, string> = new Map();\n\n private requestTimeout: number;\n\n private connections: AppConnections;\n\n private pendingAppWaits: Set<PendingAppWait> = new Set();\n\n private isDisposed = false;\n\n constructor(connections: AppConnections, options: { requestTimeout?: number } = {}) {\n super();\n this.connections = connections;\n this.requestTimeout = options.requestTimeout ?? DEFAULT_REQUEST_TIMEOUT_MS;\n this.connections.onRequest = (connection, request) => this.handleRequest(connection, request);\n\n this.connections.addEventListener(\"disconnection\", (event) => {\n this.removeApp((event as ConnectionEvent).detail);\n });\n }\n\n private resolveTargetApp(applicationId: string | undefined): RegisteredApp {\n const app = applicationId ? this.apps.get(applicationId) : this.getDefaultApp();\n\n if (app) {\n return app;\n }\n\n if (applicationId) {\n throw appNotFoundError(applicationId);\n }\n\n throw noAppConnectedError();\n }\n\n private handleRequest(connection: ProtocolConnection, request: JSONRPCRequest): Promise<Result> {\n if (this.isDisposed) {\n return Promise.reject(routerStoppedError());\n }\n\n if (request.method === \"app.register\") {\n return Promise.resolve(this.handleRegister(connection, request));\n }\n\n if (request.method === \"app.unregister\") {\n this.removeApp(connection);\n\n return Promise.resolve({ success: true });\n }\n\n return Promise.reject(methodNotFoundError(request.method));\n }\n\n private handleRegister(connection: ProtocolConnection, request: JSONRPCRequest): Result {\n const parseResult = RegisterParamsSchema.safeParse(request.params);\n\n if (!parseResult.success) {\n throw invalidRequestError(parseResult.error.message);\n }\n\n const params = parseResult.data;\n\n const appInfo: AppInfo = {\n applicationId: params.applicationId,\n pid: params.pid,\n ...(params.projectRoot !== undefined && { projectRoot: params.projectRoot }),\n };\n\n this.apps.set(params.applicationId, { info: appInfo, connection });\n this.connectionToApp.set(connection.id, params.applicationId);\n this.dispatchEvent(appRegisteredEvent(appInfo));\n\n return { success: true };\n }\n\n private toAppError(app: RegisteredApp, error: McpError): ProtocolError {\n if (error.code === CONNECTION_CLOSED_CODE) {\n this.removeApp(app.connection);\n\n return connectionWriteFailedError(app.info.applicationId);\n }\n\n if (error.code === REQUEST_TIMEOUT_CODE) {\n return requestTimeoutError(this.requestTimeout);\n }\n\n return protocolErrorFrom(error);\n }\n\n private removeApp(connection: ProtocolConnection): void {\n const applicationId = this.connectionToApp.get(connection.id);\n this.connectionToApp.delete(connection.id);\n\n if (applicationId === undefined) {\n return;\n }\n\n if (this.apps.get(applicationId)?.connection !== connection) {\n return;\n }\n\n this.apps.delete(applicationId);\n this.dispatchEvent(appUnregisteredEvent(applicationId));\n }\n\n private async waitForRegistration(applicationId: string | undefined, timeout: number): Promise<AppInfo> {\n const controller = new AbortController();\n const { promise, reject, resolve } = Promise.withResolvers<AppInfo>();\n const rejectWait = (error: Error): void => {\n controller.abort();\n reject(error);\n };\n const pendingWait: PendingAppWait = { reject: rejectWait };\n const timeoutId = setTimeout(() => {\n rejectWait(appWaitTimeoutError(timeout));\n }, timeout);\n\n this.addEventListener(\n \"appRegistered\",\n (event) => {\n const info = (event as AppRegisteredEvent).detail;\n\n if (applicationId === undefined || info.applicationId === applicationId) {\n resolve(info);\n }\n },\n { signal: controller.signal },\n );\n this.pendingAppWaits.add(pendingWait);\n\n try {\n return await promise;\n } finally {\n clearTimeout(timeoutId);\n controller.abort();\n this.pendingAppWaits.delete(pendingWait);\n }\n }\n\n getApps(): AppInfo[] {\n return this.apps.values().map((app) => app.info).toArray();\n }\n\n hasConnectedApps(): boolean {\n return this.apps.size > 0;\n }\n\n getDefaultApp(): RegisteredApp | undefined {\n const first = this.apps.values().next();\n\n return first.done ? undefined : first.value;\n }\n\n getProjectRoot(): string | undefined {\n return this.getDefaultApp()?.info.projectRoot;\n }\n\n dispose(): void {\n if (this.isDisposed) {\n return;\n }\n\n this.isDisposed = true;\n const error = routerStoppedError();\n\n for (const pendingWait of this.pendingAppWaits) {\n pendingWait.reject(error);\n }\n }\n\n waitForApp(applicationId?: string, timeout: number = AppRouter.defaultWaitTimeout): Promise<AppInfo> {\n if (this.isDisposed) {\n return Promise.reject(routerStoppedError());\n }\n\n const app = applicationId === undefined ? this.getDefaultApp() : this.apps.get(applicationId);\n\n if (app) {\n return Promise.resolve(app.info);\n }\n\n return this.waitForRegistration(applicationId, timeout);\n }\n\n async sendToApp<T>(\n applicationId: string | undefined,\n method: string,\n params?: RequestParams,\n waitTimeout?: number,\n ): Promise<T> {\n await this.waitForApp(applicationId, waitTimeout);\n const app = this.resolveTargetApp(applicationId);\n\n try {\n return await app.connection.send<T>(method, params, this.requestTimeout);\n } catch (error) {\n if (error instanceof McpError) {\n throw this.toAppError(app, error);\n }\n\n throw error;\n }\n }\n}\n\nexport { AppRouter, type AppRegisteredEvent, type AppUnregisteredEvent };\n"]}
@@ -1,5 +1,6 @@
1
1
  export { invalidRequestError, isConnectionClosedError, methodNotFoundError, propertyNotFoundError, widgetNotFoundError, } from "./protocol/errors.js";
2
- export { DEFAULT_SOCKET_PATH, DEFAULT_SUBTREE_DEPTH, MAX_SUBTREE_WIDGETS, type ParamsSchema, type SerializedProperty, type SerializedWidget, type ServerInitiatedMethod, type ServerRequestParams, ServerRequestParamsSchemas, } from "./protocol/schemas.js";
2
+ export { DEFAULT_SUBTREE_DEPTH, MAX_SUBTREE_WIDGETS, type ParamsSchema, type SerializedProperty, type SerializedWidget, type ServerInitiatedMethod, type ServerRequestParams, ServerRequestParamsSchemas, } from "./protocol/schemas.js";
3
+ export { MCP_SOCKET_PATH_ENV, resolveMcpSocketPath, } from "./socket-path.js";
3
4
  export { ProtocolConnection } from "./transport.js";
4
5
  export type { JSONRPCRequest, Result } from "@modelcontextprotocol/sdk/types.js";
5
6
  //# sourceMappingURL=internal.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"internal.d.ts","sourceRoot":"","sources":["../src/internal.ts"],"names":[],"mappings":"AAAA,OAAO,EACH,mBAAmB,EACnB,uBAAuB,EACvB,mBAAmB,EACnB,qBAAqB,EACrB,mBAAmB,GACtB,MAAM,sBAAsB,CAAC;AAC9B,OAAO,EACH,mBAAmB,EACnB,qBAAqB,EACrB,mBAAmB,EACnB,KAAK,YAAY,EACjB,KAAK,kBAAkB,EACvB,KAAK,gBAAgB,EACrB,KAAK,qBAAqB,EAC1B,KAAK,mBAAmB,EACxB,0BAA0B,GAC7B,MAAM,uBAAuB,CAAC;AAC/B,OAAO,EAAE,kBAAkB,EAAE,MAAM,gBAAgB,CAAC;AACpD,YAAY,EAAE,cAAc,EAAE,MAAM,EAAE,MAAM,oCAAoC,CAAC"}
1
+ {"version":3,"file":"internal.d.ts","sourceRoot":"","sources":["../src/internal.ts"],"names":[],"mappings":"AAAA,OAAO,EACH,mBAAmB,EACnB,uBAAuB,EACvB,mBAAmB,EACnB,qBAAqB,EACrB,mBAAmB,GACtB,MAAM,sBAAsB,CAAC;AAC9B,OAAO,EACH,qBAAqB,EACrB,mBAAmB,EACnB,KAAK,YAAY,EACjB,KAAK,kBAAkB,EACvB,KAAK,gBAAgB,EACrB,KAAK,qBAAqB,EAC1B,KAAK,mBAAmB,EACxB,0BAA0B,GAC7B,MAAM,uBAAuB,CAAC;AAC/B,OAAO,EACH,mBAAmB,EACnB,oBAAoB,GACvB,MAAM,kBAAkB,CAAC;AAC1B,OAAO,EAAE,kBAAkB,EAAE,MAAM,gBAAgB,CAAC;AACpD,YAAY,EAAE,cAAc,EAAE,MAAM,EAAE,MAAM,oCAAoC,CAAC"}
package/dist/internal.js CHANGED
@@ -1,4 +1,5 @@
1
1
  export { invalidRequestError, isConnectionClosedError, methodNotFoundError, propertyNotFoundError, widgetNotFoundError, } from "./protocol/errors.js";
2
- export { DEFAULT_SOCKET_PATH, DEFAULT_SUBTREE_DEPTH, MAX_SUBTREE_WIDGETS, ServerRequestParamsSchemas, } from "./protocol/schemas.js";
2
+ export { DEFAULT_SUBTREE_DEPTH, MAX_SUBTREE_WIDGETS, ServerRequestParamsSchemas, } from "./protocol/schemas.js";
3
+ export { MCP_SOCKET_PATH_ENV, resolveMcpSocketPath, } from "./socket-path.js";
3
4
  export { ProtocolConnection } from "./transport.js";
4
5
  //# sourceMappingURL=internal.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"internal.js","sourceRoot":"","sources":["../src/internal.ts"],"names":[],"mappings":"AAAA,OAAO,EACH,mBAAmB,EACnB,uBAAuB,EACvB,mBAAmB,EACnB,qBAAqB,EACrB,mBAAmB,GACtB,MAAM,sBAAsB,CAAC;AAC9B,OAAO,EACH,mBAAmB,EACnB,qBAAqB,EACrB,mBAAmB,EAMnB,0BAA0B,GAC7B,MAAM,uBAAuB,CAAC;AAC/B,OAAO,EAAE,kBAAkB,EAAE,MAAM,gBAAgB,CAAC","sourcesContent":["export {\n invalidRequestError,\n isConnectionClosedError,\n methodNotFoundError,\n propertyNotFoundError,\n widgetNotFoundError,\n} from \"./protocol/errors.js\";\nexport {\n DEFAULT_SOCKET_PATH,\n DEFAULT_SUBTREE_DEPTH,\n MAX_SUBTREE_WIDGETS,\n type ParamsSchema,\n type SerializedProperty,\n type SerializedWidget,\n type ServerInitiatedMethod,\n type ServerRequestParams,\n ServerRequestParamsSchemas,\n} from \"./protocol/schemas.js\";\nexport { ProtocolConnection } from \"./transport.js\";\nexport type { JSONRPCRequest, Result } from \"@modelcontextprotocol/sdk/types.js\";\n"]}
1
+ {"version":3,"file":"internal.js","sourceRoot":"","sources":["../src/internal.ts"],"names":[],"mappings":"AAAA,OAAO,EACH,mBAAmB,EACnB,uBAAuB,EACvB,mBAAmB,EACnB,qBAAqB,EACrB,mBAAmB,GACtB,MAAM,sBAAsB,CAAC;AAC9B,OAAO,EACH,qBAAqB,EACrB,mBAAmB,EAMnB,0BAA0B,GAC7B,MAAM,uBAAuB,CAAC;AAC/B,OAAO,EACH,mBAAmB,EACnB,oBAAoB,GACvB,MAAM,kBAAkB,CAAC;AAC1B,OAAO,EAAE,kBAAkB,EAAE,MAAM,gBAAgB,CAAC","sourcesContent":["export {\n invalidRequestError,\n isConnectionClosedError,\n methodNotFoundError,\n propertyNotFoundError,\n widgetNotFoundError,\n} from \"./protocol/errors.js\";\nexport {\n DEFAULT_SUBTREE_DEPTH,\n MAX_SUBTREE_WIDGETS,\n type ParamsSchema,\n type SerializedProperty,\n type SerializedWidget,\n type ServerInitiatedMethod,\n type ServerRequestParams,\n ServerRequestParamsSchemas,\n} from \"./protocol/schemas.js\";\nexport {\n MCP_SOCKET_PATH_ENV,\n resolveMcpSocketPath,\n} from \"./socket-path.js\";\nexport { ProtocolConnection } from \"./transport.js\";\nexport type { JSONRPCRequest, Result } from \"@modelcontextprotocol/sdk/types.js\";\n"]}
@@ -84,6 +84,5 @@ declare const ServerRequestParamsSchemas: {
84
84
  "widget.fireEvent": typeof fireEventParams;
85
85
  "widget.screenshot": typeof screenshotParams;
86
86
  };
87
- declare const DEFAULT_SOCKET_PATH: string;
88
- export { DEFAULT_SUBTREE_DEPTH, MAX_SUBTREE_WIDGETS, RegisterParamsSchema, widgetIdParams, widgetPropsParams, treeParams, queryParams, typeParams, fireEventParams, screenshotParams, ServerRequestParamsSchemas, DEFAULT_SOCKET_PATH, type SerializedWidget, type SerializedProperty, type AppInfo, type ServerRequestParams, type ParamsSchema, type ServerInitiatedMethod, };
87
+ export { DEFAULT_SUBTREE_DEPTH, MAX_SUBTREE_WIDGETS, RegisterParamsSchema, widgetIdParams, widgetPropsParams, treeParams, queryParams, typeParams, fireEventParams, screenshotParams, ServerRequestParamsSchemas, type SerializedWidget, type SerializedProperty, type AppInfo, type ServerRequestParams, type ParamsSchema, type ServerInitiatedMethod, };
89
88
  //# sourceMappingURL=schemas.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"schemas.d.ts","sourceRoot":"","sources":["../../src/protocol/schemas.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"schemas.d.ts","sourceRoot":"","sources":["../../src/protocol/schemas.ts"],"names":[],"mappings":"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"}
@@ -1,5 +1,3 @@
1
- import { tmpdir } from "node:os";
2
- import { join } from "node:path";
3
1
  import { z } from "zod";
4
2
  const RegisterParamsSchema = z.object({
5
3
  applicationId: z.string(),
@@ -47,9 +45,5 @@ const ServerRequestParamsSchemas = {
47
45
  "widget.fireEvent": fireEventParams,
48
46
  "widget.screenshot": screenshotParams,
49
47
  };
50
- const DEFAULT_SOCKET_PATH = join(getRuntimeDir(), "gtkx-mcp.sock");
51
- function getRuntimeDir() {
52
- return process.env.XDG_RUNTIME_DIR ?? tmpdir();
53
- }
54
- export { DEFAULT_SUBTREE_DEPTH, MAX_SUBTREE_WIDGETS, RegisterParamsSchema, widgetIdParams, widgetPropsParams, treeParams, queryParams, typeParams, fireEventParams, screenshotParams, ServerRequestParamsSchemas, DEFAULT_SOCKET_PATH, };
48
+ export { DEFAULT_SUBTREE_DEPTH, MAX_SUBTREE_WIDGETS, RegisterParamsSchema, widgetIdParams, widgetPropsParams, treeParams, queryParams, typeParams, fireEventParams, screenshotParams, ServerRequestParamsSchemas, };
55
49
  //# sourceMappingURL=schemas.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"schemas.js","sourceRoot":"","sources":["../../src/protocol/schemas.ts"],"names":[],"mappings":"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","sourcesContent":["import { tmpdir } from \"node:os\";\nimport { join } from \"node:path\";\nimport { z } from \"zod\";\n\ntype SerializedWidget = {\n id: string;\n type: string;\n role: string;\n name: string | null;\n text: string | null;\n isSensitive: boolean;\n isVisible: boolean;\n cssClasses: string[];\n children: SerializedWidget[];\n hiddenChildren?: number;\n};\n\ntype SerializedProperty = {\n type: string;\n value: string | number | boolean | string[] | null;\n widgetId?: string;\n note?: string;\n};\n\ntype AppInfo = {\n applicationId: string;\n pid: number;\n projectRoot?: string;\n};\n\ntype ServerRequestParams<Method extends keyof typeof ServerRequestParamsSchemas> = z.infer<\n (typeof ServerRequestParamsSchemas)[Method]\n>;\n\ntype ParamsSchema<Output> = z.ZodType<Output>;\ntype ServerInitiatedMethod = keyof typeof ServerRequestParamsSchemas;\n\nconst RegisterParamsSchema: z.ZodObject<\n {\n applicationId: z.ZodString;\n pid: z.ZodNumber;\n projectRoot: z.ZodOptional<z.ZodString>;\n }\n> = z.object({\n applicationId: z.string(),\n pid: z.number(),\n projectRoot: z.string().optional(),\n});\n\nconst emptyParams: z.ZodObject<Record<string, never>> = z.object({});\n\nconst widgetIdParams: z.ZodObject<{ widgetId: z.ZodString }> = z.object({\n widgetId: z.string(),\n});\n\nconst DEFAULT_SUBTREE_DEPTH = 8;\nconst MAX_SUBTREE_WIDGETS = 30;\n\nconst widgetPropsParams: z.ZodObject<\n {\n widgetId: z.ZodString;\n properties: z.ZodOptional<z.ZodArray<z.ZodString>>;\n maxDepth: z.ZodOptional<z.ZodNumber>;\n }\n> = z.object({\n widgetId: z.string(),\n properties: z.array(z.string()).optional(),\n maxDepth: z.number().int().nonnegative().optional(),\n});\n\nconst treeParams: z.ZodObject<\n { rootId: z.ZodOptional<z.ZodString>; maxDepth: z.ZodOptional<z.ZodNumber> }\n> = z.object({\n rootId: z.string().optional(),\n maxDepth: z.number().int().nonnegative().optional(),\n});\n\nconst queryOptionsSchema: z.ZodObject<\n { name: z.ZodOptional<z.ZodString>; exact: z.ZodOptional<z.ZodBoolean>; timeout: z.ZodOptional<z.ZodNumber> }\n> = z.object({\n name: z.string().optional(),\n exact: z.boolean().optional(),\n timeout: z.number().optional(),\n});\n\nconst queryParams: z.ZodObject<\n {\n by: z.ZodEnum<{ role: \"role\"; text: \"text\"; name: \"name\"; labelText: \"labelText\" }>;\n value: z.ZodUnion<[z.ZodString, z.ZodNumber]>;\n options: z.ZodOptional<typeof queryOptionsSchema>;\n }\n> = z.object({\n by: z.enum([\"role\", \"text\", \"name\", \"labelText\"]),\n value: z.union([z.string(), z.number()]),\n options: queryOptionsSchema.optional(),\n});\n\nconst typeParams: z.ZodObject<\n { widgetId: z.ZodString; text: z.ZodString; clear: z.ZodOptional<z.ZodBoolean> }\n> = z.object({ widgetId: z.string(), text: z.string(), clear: z.boolean().optional() });\n\nconst fireEventParams: z.ZodObject<\n { widgetId: z.ZodString; signal: z.ZodString; args: z.ZodOptional<z.ZodArray<z.ZodUnknown>> }\n> = z.object({ widgetId: z.string(), signal: z.string(), args: z.array(z.unknown()).optional() });\n\nconst screenshotParams: z.ZodObject<\n { windowId: z.ZodOptional<z.ZodString>; path: z.ZodOptional<z.ZodString> }\n> = z.object({\n windowId: z.string().optional(),\n path: z.string().optional(),\n});\n\nconst ServerRequestParamsSchemas: {\n \"app.getWindows\": typeof emptyParams;\n \"widget.getTree\": typeof treeParams;\n \"widget.query\": typeof queryParams;\n \"widget.getProps\": typeof widgetPropsParams;\n \"widget.click\": typeof widgetIdParams;\n \"widget.type\": typeof typeParams;\n \"widget.fireEvent\": typeof fireEventParams;\n \"widget.screenshot\": typeof screenshotParams;\n} = {\n \"app.getWindows\": emptyParams,\n \"widget.getTree\": treeParams,\n \"widget.query\": queryParams,\n \"widget.getProps\": widgetPropsParams,\n \"widget.click\": widgetIdParams,\n \"widget.type\": typeParams,\n \"widget.fireEvent\": fireEventParams,\n \"widget.screenshot\": screenshotParams,\n};\n\nconst DEFAULT_SOCKET_PATH: string = join(getRuntimeDir(), \"gtkx-mcp.sock\");\n\nfunction getRuntimeDir(): string {\n return process.env.XDG_RUNTIME_DIR ?? tmpdir();\n}\n\nexport {\n DEFAULT_SUBTREE_DEPTH,\n MAX_SUBTREE_WIDGETS,\n RegisterParamsSchema,\n widgetIdParams,\n widgetPropsParams,\n treeParams,\n queryParams,\n typeParams,\n fireEventParams,\n screenshotParams,\n ServerRequestParamsSchemas,\n DEFAULT_SOCKET_PATH,\n type SerializedWidget,\n type SerializedProperty,\n type AppInfo,\n type ServerRequestParams,\n type ParamsSchema,\n type ServerInitiatedMethod,\n};\n"]}
1
+ {"version":3,"file":"schemas.js","sourceRoot":"","sources":["../../src/protocol/schemas.ts"],"names":[],"mappings":"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","sourcesContent":["import { z } from \"zod\";\n\ntype SerializedWidget = {\n id: string;\n type: string;\n role: string;\n name: string | null;\n text: string | null;\n isSensitive: boolean;\n isVisible: boolean;\n cssClasses: string[];\n children: SerializedWidget[];\n hiddenChildren?: number;\n};\n\ntype SerializedProperty = {\n type: string;\n value: string | number | boolean | string[] | null;\n widgetId?: string;\n note?: string;\n};\n\ntype AppInfo = {\n applicationId: string;\n pid: number;\n projectRoot?: string;\n};\n\ntype ServerRequestParams<Method extends keyof typeof ServerRequestParamsSchemas> = z.infer<\n (typeof ServerRequestParamsSchemas)[Method]\n>;\n\ntype ParamsSchema<Output> = z.ZodType<Output>;\ntype ServerInitiatedMethod = keyof typeof ServerRequestParamsSchemas;\n\nconst RegisterParamsSchema: z.ZodObject<\n {\n applicationId: z.ZodString;\n pid: z.ZodNumber;\n projectRoot: z.ZodOptional<z.ZodString>;\n }\n> = z.object({\n applicationId: z.string(),\n pid: z.number(),\n projectRoot: z.string().optional(),\n});\n\nconst emptyParams: z.ZodObject<Record<string, never>> = z.object({});\n\nconst widgetIdParams: z.ZodObject<{ widgetId: z.ZodString }> = z.object({\n widgetId: z.string(),\n});\n\nconst DEFAULT_SUBTREE_DEPTH = 8;\nconst MAX_SUBTREE_WIDGETS = 30;\n\nconst widgetPropsParams: z.ZodObject<\n {\n widgetId: z.ZodString;\n properties: z.ZodOptional<z.ZodArray<z.ZodString>>;\n maxDepth: z.ZodOptional<z.ZodNumber>;\n }\n> = z.object({\n widgetId: z.string(),\n properties: z.array(z.string()).optional(),\n maxDepth: z.number().int().nonnegative().optional(),\n});\n\nconst treeParams: z.ZodObject<\n { rootId: z.ZodOptional<z.ZodString>; maxDepth: z.ZodOptional<z.ZodNumber> }\n> = z.object({\n rootId: z.string().optional(),\n maxDepth: z.number().int().nonnegative().optional(),\n});\n\nconst queryOptionsSchema: z.ZodObject<\n { name: z.ZodOptional<z.ZodString>; exact: z.ZodOptional<z.ZodBoolean>; timeout: z.ZodOptional<z.ZodNumber> }\n> = z.object({\n name: z.string().optional(),\n exact: z.boolean().optional(),\n timeout: z.number().optional(),\n});\n\nconst queryParams: z.ZodObject<\n {\n by: z.ZodEnum<{ role: \"role\"; text: \"text\"; name: \"name\"; labelText: \"labelText\" }>;\n value: z.ZodUnion<[z.ZodString, z.ZodNumber]>;\n options: z.ZodOptional<typeof queryOptionsSchema>;\n }\n> = z.object({\n by: z.enum([\"role\", \"text\", \"name\", \"labelText\"]),\n value: z.union([z.string(), z.number()]),\n options: queryOptionsSchema.optional(),\n});\n\nconst typeParams: z.ZodObject<\n { widgetId: z.ZodString; text: z.ZodString; clear: z.ZodOptional<z.ZodBoolean> }\n> = z.object({ widgetId: z.string(), text: z.string(), clear: z.boolean().optional() });\n\nconst fireEventParams: z.ZodObject<\n { widgetId: z.ZodString; signal: z.ZodString; args: z.ZodOptional<z.ZodArray<z.ZodUnknown>> }\n> = z.object({ widgetId: z.string(), signal: z.string(), args: z.array(z.unknown()).optional() });\n\nconst screenshotParams: z.ZodObject<\n { windowId: z.ZodOptional<z.ZodString>; path: z.ZodOptional<z.ZodString> }\n> = z.object({\n windowId: z.string().optional(),\n path: z.string().optional(),\n});\n\nconst ServerRequestParamsSchemas: {\n \"app.getWindows\": typeof emptyParams;\n \"widget.getTree\": typeof treeParams;\n \"widget.query\": typeof queryParams;\n \"widget.getProps\": typeof widgetPropsParams;\n \"widget.click\": typeof widgetIdParams;\n \"widget.type\": typeof typeParams;\n \"widget.fireEvent\": typeof fireEventParams;\n \"widget.screenshot\": typeof screenshotParams;\n} = {\n \"app.getWindows\": emptyParams,\n \"widget.getTree\": treeParams,\n \"widget.query\": queryParams,\n \"widget.getProps\": widgetPropsParams,\n \"widget.click\": widgetIdParams,\n \"widget.type\": typeParams,\n \"widget.fireEvent\": fireEventParams,\n \"widget.screenshot\": screenshotParams,\n};\n\nexport {\n DEFAULT_SUBTREE_DEPTH,\n MAX_SUBTREE_WIDGETS,\n RegisterParamsSchema,\n widgetIdParams,\n widgetPropsParams,\n treeParams,\n queryParams,\n typeParams,\n fireEventParams,\n screenshotParams,\n ServerRequestParamsSchemas,\n type SerializedWidget,\n type SerializedProperty,\n type AppInfo,\n type ServerRequestParams,\n type ParamsSchema,\n type ServerInitiatedMethod,\n};\n"]}
@@ -1 +1 @@
1
- {"version":3,"file":"reference.d.ts","sourceRoot":"","sources":["../src/reference.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,YAAY,EAAsE,MAAM,eAAe,CAAC;AAGtH,OAAO,EAAE,KAAK,SAAS,EAAoB,MAAM,yCAAyC,CAAC;AAK3F,OAAO,EAAsC,KAAK,IAAI,EAAiB,MAAM,WAAW,CAAC;AAEzF,KAAK,YAAY,GAAG,IAAI,CACpB,YAAY,EACZ,QAAQ,GAAG,mBAAmB,GAAG,YAAY,GAAG,UAAU,GAAG,QAAQ,GAAG,aAAa,CACxF,CAAC;AAEF,KAAK,aAAa,GAAG,UAAU,GAAG,kBAAkB,GAAG,KAAK,CAAC;AAE7D,KAAK,eAAe,GAAG;IACnB,IAAI,EAAE,MAAM,CAAC;IACb,MAAM,EAAE,aAAa,CAAC;CACzB,CAAC;AAEF,KAAK,eAAe,GAAG,eAAe,GAAG;IACrC,SAAS,EAAE,YAAY,CAAC;CAC3B,CAAC;AAEF,KAAK,wBAAwB,GAAG;IAC5B,UAAU,EAAE,MAAM,MAAM,GAAG,SAAS,CAAC;IACrC,mBAAmB,CAAC,EAAE,MAAM,MAAM,CAAC;CACtC,CAAC;AAEF,KAAK,iBAAiB,GAAG;IACrB,GAAG,CAAC,WAAW,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,eAAe,CAAC,CAAC;IACpD,IAAI,CAAC,OAAO,EAAE,eAAe,GAAG,OAAO,CAAC,eAAe,CAAC,CAAC;IACzD,OAAO,CAAC,WAAW,CAAC,EAAE,MAAM,GAAG,eAAe,CAAC;CAClD,CAAC;AAsBF,KAAK,cAAc,GAAG,IAAI,CAAC,SAAS,EAAE,kBAAkB,CAAC,CAAC;AA8M1D,QAAA,MAAM,uBAAuB,GAAI,SAAS,wBAAwB,KAAG,iBAgBpE,CAAC;AAqIF,QAAA,MAAM,mBAAmB,GAAI,UAAU,iBAAiB,KAAG,IAAI,EAI9D,CAAC;AAsJF,QAAA,MAAM,0BAA0B,GAAI,QAAQ,cAAc,EAAE,UAAU,iBAAiB,KAAG,IAIzF,CAAC;AAEF,OAAO,EACH,uBAAuB,EACvB,mBAAmB,EACnB,0BAA0B,EAC1B,KAAK,iBAAiB,GACzB,CAAC"}
1
+ {"version":3,"file":"reference.d.ts","sourceRoot":"","sources":["../src/reference.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,YAAY,EAAsE,MAAM,eAAe,CAAC;AAEtH,OAAO,EAAE,KAAK,SAAS,EAAoB,MAAM,yCAAyC,CAAC;AAK3F,OAAO,EAAsC,KAAK,IAAI,EAAiB,MAAM,WAAW,CAAC;AAEzF,KAAK,YAAY,GAAG,IAAI,CACpB,YAAY,EACZ,QAAQ,GAAG,mBAAmB,GAAG,YAAY,GAAG,UAAU,GAAG,QAAQ,GAAG,aAAa,CACxF,CAAC;AAEF,KAAK,aAAa,GAAG,UAAU,GAAG,kBAAkB,GAAG,KAAK,CAAC;AAE7D,KAAK,eAAe,GAAG;IACnB,IAAI,EAAE,MAAM,CAAC;IACb,MAAM,EAAE,aAAa,CAAC;CACzB,CAAC;AAEF,KAAK,eAAe,GAAG,eAAe,GAAG;IACrC,SAAS,EAAE,YAAY,CAAC;CAC3B,CAAC;AAEF,KAAK,wBAAwB,GAAG;IAC5B,UAAU,EAAE,MAAM,MAAM,GAAG,SAAS,CAAC;IACrC,mBAAmB,CAAC,EAAE,MAAM,MAAM,CAAC;CACtC,CAAC;AAEF,KAAK,iBAAiB,GAAG;IACrB,GAAG,CAAC,WAAW,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,eAAe,CAAC,CAAC;IACpD,IAAI,CAAC,OAAO,EAAE,eAAe,GAAG,OAAO,CAAC,eAAe,CAAC,CAAC;IACzD,OAAO,CAAC,WAAW,CAAC,EAAE,MAAM,GAAG,eAAe,CAAC;CAClD,CAAC;AAsBF,KAAK,cAAc,GAAG,IAAI,CAAC,SAAS,EAAE,kBAAkB,CAAC,CAAC;AAkM1D,QAAA,MAAM,uBAAuB,GAAI,SAAS,wBAAwB,KAAG,iBAgBpE,CAAC;AA0HF,QAAA,MAAM,mBAAmB,GAAI,UAAU,iBAAiB,KAAG,IAAI,EAI9D,CAAC;AAmJF,QAAA,MAAM,0BAA0B,GAAI,QAAQ,cAAc,EAAE,UAAU,iBAAiB,KAAG,IAIzF,CAAC;AAEF,OAAO,EACH,uBAAuB,EACvB,mBAAmB,EACnB,0BAA0B,EAC1B,KAAK,iBAAiB,GACzB,CAAC"}
package/dist/reference.js CHANGED
@@ -1,6 +1,5 @@
1
1
  import { loadApiReference, resolveGirPath, resolveLibraries } from "@gtkx/codegen";
2
2
  import { loadConfig } from "@gtkx/config";
3
- import { resolveFuture } from "@gtkx/config/internal";
4
3
  import { ResourceTemplate } from "@modelcontextprotocol/sdk/server/mcp.js";
5
4
  import { ErrorCode, McpError } from "@modelcontextprotocol/sdk/types.js";
6
5
  import { existsSync, statSync } from "node:fs";
@@ -9,7 +8,7 @@ import { z } from "zod";
9
8
  import { defineTool, textContent, textError } from "./tool.js";
10
9
  const FRESHNESS_INTERVAL_MS = 2000;
11
10
  const FAILURE_RETRY_MS = 5000;
12
- const CONFIG_EXTENSIONS = ["ts", "mts", "cts", "js", "mjs", "cjs", "json"];
11
+ const CONFIG_EXTENSIONS = ["ts", "mts", "js", "mjs", "json"];
13
12
  const PROJECT_SOURCE_LABELS = {
14
13
  argument: "requested with `projectRoot`",
15
14
  workingDirectory: "found from the working directory",
@@ -105,31 +104,19 @@ const loadReference = async (requestedRoot) => {
105
104
  "(Linux: `sudo dnf install gobject-introspection-devel` or `sudo apt install libgirepository1.0-dev`), " +
106
105
  "or set `girPath` in gtkx.config.ts.");
107
106
  }
108
- const future = resolveFuture(config.future);
109
- const libraries = resolveLibraries(config.libraries, girPath, future.isAdwaitaDefault);
107
+ const libraries = resolveLibraries(config.libraries);
110
108
  const reference = loadApiReference({
111
109
  libraries,
112
110
  girPath,
113
- isByteArrayTyped: future.isByteArrayTyped,
114
- isValueUnwrapped: future.isValueUnwrapped,
115
- isFinishTrimmed: future.isFinishTrimmed,
116
- isInoutInPlace: future.isInoutInPlace,
117
- isTreeShaken: future.isTreeShaken,
118
111
  });
119
112
  const watched = [watchFile(resolve(root, configFile)), ...reference.girFiles.map((file) => watchFile(file))];
120
113
  return { reference, root, watched };
121
114
  };
122
- const markFailed = async (entry) => {
123
- try {
124
- await entry.pending;
125
- }
126
- catch {
127
- entry.failedAt = Date.now();
128
- }
129
- };
130
115
  const startLoad = (cache, root) => {
131
116
  const entry = { pending: loadReference(root), verifiedAt: Date.now(), failedAt: undefined };
132
- void markFailed(entry);
117
+ void entry.pending.catch(() => {
118
+ entry.failedAt = Date.now();
119
+ });
133
120
  cache.set(root, entry);
134
121
  return entry;
135
122
  };
@@ -154,10 +141,9 @@ const currentReference = async (cache, root) => {
154
141
  }
155
142
  return revalidate(cache, root, entry).pending;
156
143
  };
157
- const defaultWorkingDirectory = () => process.cwd();
158
144
  const createReferenceProvider = (options) => {
159
145
  const cache = new Map();
160
- const getWorkingDirectory = options.getWorkingDirectory ?? defaultWorkingDirectory;
146
+ const getWorkingDirectory = options.getWorkingDirectory ?? (() => process.cwd());
161
147
  const resolve = (projectRoot) => resolveProject(getWorkingDirectory(), options.getAppRoot, projectRoot);
162
148
  const load = async (project) => {
163
149
  const loaded = await currentReference(cache, project.root);
@@ -183,19 +169,12 @@ const scopedResult = async (provider, projectRoot, render) => {
183
169
  }
184
170
  };
185
171
  const formatCandidates = (candidates) => candidates.map((candidate) => `- ${candidate.namespace}.${candidate.name} (${candidate.kind})`).join("\n");
186
- const buildSearchOptions = (args) => {
187
- const options = { query: args.query };
188
- if (args.namespace !== undefined) {
189
- options.namespace = args.namespace;
190
- }
191
- if (args.kind !== undefined) {
192
- options.kinds = [args.kind];
193
- }
194
- if (args.limit !== undefined) {
195
- options.limit = args.limit;
196
- }
197
- return options;
198
- };
172
+ const buildSearchOptions = (args) => ({
173
+ query: args.query,
174
+ ...(args.namespace !== undefined && { namespace: args.namespace }),
175
+ ...(args.kind !== undefined && { kinds: [args.kind] }),
176
+ ...(args.limit !== undefined && { limit: args.limit }),
177
+ });
199
178
  const listApiResult = (reference, namespace) => {
200
179
  if (namespace === undefined) {
201
180
  return textContent(reference.overview());
@@ -273,10 +252,9 @@ const withLoadFallback = async (load, fallback) => {
273
252
  return fallback;
274
253
  }
275
254
  };
276
- const namesStartingWith = (names, value) => names.filter((name) => name.toLowerCase().startsWith(value.toLowerCase()));
277
255
  const completeNames = (provider, value, collect) => withLoadFallback(async () => {
278
256
  const { reference } = await provider.get();
279
- return namesStartingWith(collect(reference), value);
257
+ return collect(reference).filter((name) => name.toLowerCase().startsWith(value.toLowerCase()));
280
258
  }, []);
281
259
  const namespaceCompleter = (provider) => (value) => completeNames(provider, value, (reference) => reference.namespaces().map((summary) => summary.name));
282
260
  const completeSymbol = (provider, namespace, value) => {