@roarkanalytics/sdk-mcp 4.10.0 → 4.12.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 (52) hide show
  1. package/CHANGELOG.md +21 -0
  2. package/README.md +58 -0
  3. package/code-tool.js +10 -0
  4. package/code-tool.js.map +1 -1
  5. package/code-tool.mjs +10 -0
  6. package/code-tool.mjs.map +1 -1
  7. package/http.d.mts.map +1 -1
  8. package/http.d.ts.map +1 -1
  9. package/http.js +95 -2
  10. package/http.js.map +1 -1
  11. package/http.mjs +95 -2
  12. package/http.mjs.map +1 -1
  13. package/local-docs-search.js +12 -12
  14. package/local-docs-search.js.map +1 -1
  15. package/local-docs-search.mjs +12 -12
  16. package/local-docs-search.mjs.map +1 -1
  17. package/oauth.d.mts +70 -0
  18. package/oauth.d.mts.map +1 -0
  19. package/oauth.d.ts +70 -0
  20. package/oauth.d.ts.map +1 -0
  21. package/oauth.js +101 -0
  22. package/oauth.js.map +1 -0
  23. package/oauth.mjs +93 -0
  24. package/oauth.mjs.map +1 -0
  25. package/options.d.mts +8 -0
  26. package/options.d.mts.map +1 -1
  27. package/options.d.ts +8 -0
  28. package/options.d.ts.map +1 -1
  29. package/options.js +26 -0
  30. package/options.js.map +1 -1
  31. package/options.mjs +26 -0
  32. package/options.mjs.map +1 -1
  33. package/package.json +12 -2
  34. package/server.d.mts.map +1 -1
  35. package/server.d.ts.map +1 -1
  36. package/server.js +2 -1
  37. package/server.js.map +1 -1
  38. package/server.mjs +2 -1
  39. package/server.mjs.map +1 -1
  40. package/src/code-tool.ts +10 -0
  41. package/src/http.ts +111 -3
  42. package/src/local-docs-search.ts +12 -12
  43. package/src/oauth.ts +137 -0
  44. package/src/options.ts +39 -0
  45. package/src/server.ts +2 -1
  46. package/src/types.ts +10 -0
  47. package/types.d.mts +10 -0
  48. package/types.d.mts.map +1 -1
  49. package/types.d.ts +10 -0
  50. package/types.d.ts.map +1 -1
  51. package/types.js.map +1 -1
  52. package/types.mjs.map +1 -1
package/src/oauth.ts ADDED
@@ -0,0 +1,137 @@
1
+ // Remote OAuth resource-server support.
2
+ //
3
+ // This file is hand-maintained (not generated). It turns the HTTP transport into
4
+ // an MCP OAuth *resource server* (RFC 9728): it advertises Protected Resource
5
+ // Metadata pointing at Roark's authorization server (bern `mcp-oauth`) and
6
+ // answers requests without a bearer with 401 + WWW-Authenticate so clients know
7
+ // where to go. The access token the authorization server issues is a Roark API
8
+ // key (minted at consent with the permissions the user picked, expiring and
9
+ // rotated by the client's refresh token), so it is forwarded to customer-api as
10
+ // the SDK bearer unchanged: customer-api validates it on every call.
11
+
12
+ import { IncomingMessage } from 'node:http';
13
+ import { ClientOptions } from '@roarkanalytics/sdk';
14
+
15
+ export type OAuthConfig = {
16
+ /** Authorization server issuer, e.g. https://mcp-oauth.api.roark.ai */
17
+ issuer: string;
18
+ /** Public origin of this resource server, e.g. https://mcp.api.roark.ai; connector URLs are `<base>/mcp/<projectId>`. */
19
+ resourceBaseUrl: string;
20
+ };
21
+
22
+ /** Thrown when a request cannot be authorized; carries the WWW-Authenticate value to return. */
23
+ export class UnauthorizedError extends Error {
24
+ constructor(
25
+ message: string,
26
+ readonly wwwAuthenticate: string,
27
+ readonly status: 401 | 403 = 401,
28
+ ) {
29
+ super(message);
30
+ this.name = 'UnauthorizedError';
31
+ }
32
+ }
33
+
34
+ const stripSlash = (url: string): string => url.replace(/\/+$/, '');
35
+
36
+ /**
37
+ * Which connector URL a request arrived on. There are three, and the difference is the whole
38
+ * point of this PR:
39
+ *
40
+ * - `origin` the bare server origin, the legacy `/` transport.
41
+ * - `mcp` the single connector, `<base>/mcp`. No project in the URL: the credential is
42
+ * user-scoped and names a project per request. This is what a person adds to
43
+ * Claude or Cursor once and never revisits.
44
+ * - `project` a pinned connector, `<base>/mcp/<projectId>`. Still supported, and now actually
45
+ * enforced: the project in the path becomes the SDK's project, so a user-scoped
46
+ * credential used on a pinned URL acts only on that project.
47
+ */
48
+ export type Connector = { kind: 'origin' } | { kind: 'mcp' } | { kind: 'project'; projectId: string };
49
+
50
+ export const ORIGIN_CONNECTOR: Connector = { kind: 'origin' };
51
+
52
+ /** The path a connector is served on, relative to the origin. */
53
+ const connectorPath = (connector: Connector): string =>
54
+ connector.kind === 'origin' ? ''
55
+ : connector.kind === 'mcp' ? '/mcp'
56
+ : `/mcp/${connector.projectId}`;
57
+
58
+ /**
59
+ * The resource identifier (RFC 8707) for a request: the connector URL it arrived on. Clients
60
+ * send it back to the authorization server as `resource`, which is how consent learns whether
61
+ * the grant is for one project or for the person.
62
+ */
63
+ export const resourceIdentifier = (config: OAuthConfig, connector: Connector = ORIGIN_CONNECTOR): string =>
64
+ `${stripSlash(config.resourceBaseUrl)}${connectorPath(connector)}`;
65
+
66
+ /**
67
+ * Where this server publishes its Protected Resource Metadata, per resource.
68
+ *
69
+ * RFC 9728 puts the resource's path after the well-known segment, so this is literally the
70
+ * origin, the well-known path, and the connector path, in that order.
71
+ */
72
+ export const protectedResourceMetadataUrl = (
73
+ config: OAuthConfig,
74
+ connector: Connector = ORIGIN_CONNECTOR,
75
+ ): string =>
76
+ `${stripSlash(config.resourceBaseUrl)}/.well-known/oauth-protected-resource${connectorPath(connector)}`;
77
+
78
+ /** RFC 9728 Protected Resource Metadata document. */
79
+ export const protectedResourceMetadata = (config: OAuthConfig, connector: Connector = ORIGIN_CONNECTOR) => ({
80
+ resource: resourceIdentifier(config, connector),
81
+ authorization_servers: [stripSlash(config.issuer)],
82
+ bearer_methods_supported: ['header'],
83
+ scopes_supported: ['mcp'],
84
+ resource_documentation: 'https://docs.roark.ai',
85
+ });
86
+
87
+ const bearerChallenge = (
88
+ config: OAuthConfig,
89
+ connector: Connector,
90
+ error?: string,
91
+ description?: string,
92
+ ): string => {
93
+ const parts = [`Bearer resource_metadata="${protectedResourceMetadataUrl(config, connector)}"`];
94
+ if (error) parts.push(`error="${error}"`);
95
+ if (description) parts.push(`error_description="${description}"`);
96
+ return parts.join(', ');
97
+ };
98
+
99
+ const extractBearer = (req: IncomingMessage): string | undefined => {
100
+ const header = req.headers.authorization;
101
+ if (!header) return undefined;
102
+ const [scheme, ...rest] = header.split(' ');
103
+ if (scheme !== 'Bearer' || rest.length === 0) return undefined;
104
+ const token = rest.join(' ').trim();
105
+ return token.length > 0 ? token : undefined;
106
+ };
107
+
108
+ /**
109
+ * Requires a bearer token and hands it to the SDK as-is. Throws
110
+ * {@link UnauthorizedError} (401 + challenge) when it is missing, which is the
111
+ * signal an MCP client needs to start the OAuth flow. Validity is decided by
112
+ * customer-api on each call; an expired or revoked key surfaces there.
113
+ *
114
+ * A pinned connector also fixes the SDK's `project`. This is `project` rather than a
115
+ * `defaultHeaders` entry deliberately: code the model writes inside the execution tool can still
116
+ * call `client.withOptions({ project })` to reach another project the credential covers, which a
117
+ * default header would silently override. On the unpinned `/mcp` connector no project is set at
118
+ * all, and choosing one is the caller's job.
119
+ */
120
+ export const requireBearer = (
121
+ req: IncomingMessage,
122
+ config: OAuthConfig,
123
+ connector: Connector = ORIGIN_CONNECTOR,
124
+ ): Partial<ClientOptions> => {
125
+ const token = extractBearer(req);
126
+ if (!token) {
127
+ throw new UnauthorizedError('Missing bearer token', bearerChallenge(config, connector));
128
+ }
129
+ // Assigned rather than conditionally spread: a spread of `cond && { project }` is not checked
130
+ // against `ClientOptions`, so on an SDK without the option the pin would compile and then
131
+ // silently vanish. This way the dependency is enforced by the build.
132
+ const options: Partial<ClientOptions> = { bearerToken: token };
133
+ if (connector.kind === 'project') {
134
+ options.project = connector.projectId;
135
+ }
136
+ return options;
137
+ };
package/src/options.ts CHANGED
@@ -5,6 +5,7 @@ import yargs from 'yargs';
5
5
  import { hideBin } from 'yargs/helpers';
6
6
  import z from 'zod';
7
7
  import { readEnv } from './util';
8
+ import type { OAuthConfig } from './oauth';
8
9
 
9
10
  export type CLIOptions = McpOptions & {
10
11
  debug: boolean;
@@ -25,6 +26,13 @@ export type McpOptions = {
25
26
  codeBlockedMethods?: string[] | undefined;
26
27
  codeExecutionMode: McpCodeExecutionMode;
27
28
  customInstructionsPath?: string | undefined;
29
+ /**
30
+ * Remote OAuth resource-server config. When set (http transport), every request
31
+ * must carry a bearer and a missing one is answered with a 401 challenge that
32
+ * points at the authorization server; when unset the server keeps the legacy
33
+ * optional-bearer behavior (local stdio + API-key installs).
34
+ */
35
+ oauth?: OAuthConfig | undefined;
28
36
  };
29
37
 
30
38
  export type McpCodeExecutionMode = 'stainless-sandbox' | 'local';
@@ -114,6 +122,16 @@ export function parseCLIOptions(): CLIOptions {
114
122
  default: 'stdio',
115
123
  description: 'What transport to use; stdio for local servers or http for remote servers',
116
124
  })
125
+ .option('oauth-issuer', {
126
+ type: 'string',
127
+ default: readEnv('MCP_OAUTH_ISSUER'),
128
+ description: 'Authorization server issuer URL. Enables remote OAuth resource-server mode.',
129
+ })
130
+ .option('oauth-resource-base-url', {
131
+ type: 'string',
132
+ default: readEnv('MCP_OAUTH_RESOURCE_BASE_URL'),
133
+ description: 'Public base URL of this resource server, used to build metadata and resource URLs.',
134
+ })
117
135
  .env('MCP_SERVER')
118
136
  .version(true)
119
137
  .help();
@@ -144,6 +162,10 @@ export function parseCLIOptions(): CLIOptions {
144
162
  : process.stderr.isTTY ? 'pretty'
145
163
  : 'json';
146
164
 
165
+ // When unset, an http server runs in legacy optional-bearer mode (a static
166
+ // token in the Authorization header). Remote account-based auth needs this set.
167
+ const oauth = buildOAuthConfig(argv);
168
+
147
169
  return {
148
170
  ...(includeCodeTool !== undefined && { includeCodeTool }),
149
171
  ...(includeDocsTools !== undefined && { includeDocsTools }),
@@ -156,6 +178,7 @@ export function parseCLIOptions(): CLIOptions {
156
178
  codeBlockedMethods: argv.codeBlockedMethods,
157
179
  codeExecutionMode,
158
180
  customInstructionsPath: argv.customInstructionsPath,
181
+ ...(oauth && { oauth }),
159
182
  transport,
160
183
  logFormat,
161
184
  port: argv.port,
@@ -163,6 +186,22 @@ export function parseCLIOptions(): CLIOptions {
163
186
  };
164
187
  }
165
188
 
189
+ /**
190
+ * Assembles the OAuth resource-server config from CLI/env, or returns undefined
191
+ * when either field is absent (legacy optional-bearer mode). Both the issuer and
192
+ * this server's public base URL are required together.
193
+ */
194
+ const buildOAuthConfig = (argv: {
195
+ oauthIssuer?: string | undefined;
196
+ oauthResourceBaseUrl?: string | undefined;
197
+ }): OAuthConfig | undefined => {
198
+ const { oauthIssuer, oauthResourceBaseUrl } = argv;
199
+ if (!oauthIssuer || !oauthResourceBaseUrl) {
200
+ return undefined;
201
+ }
202
+ return { issuer: oauthIssuer, resourceBaseUrl: oauthResourceBaseUrl };
203
+ };
204
+
166
205
  const coerceArray = <T extends z.ZodTypeAny>(zodType: T) =>
167
206
  z.preprocess(
168
207
  (val) =>
package/src/server.ts CHANGED
@@ -28,7 +28,7 @@ export const newMcpServer = async ({
28
28
  new McpServer(
29
29
  {
30
30
  name: 'roarkanalytics_sdk_api',
31
- version: '4.10.0', // x-release-please-version
31
+ version: '4.12.0', // x-release-please-version
32
32
  },
33
33
  {
34
34
  instructions: await getInstructions({ stainlessApiKey, customInstructionsPath }),
@@ -167,6 +167,7 @@ export async function initMcpServer(params: {
167
167
  handler: mcpTool.handler,
168
168
  reqContext: {
169
169
  client,
170
+ project: params.clientOptions?.project ?? undefined,
170
171
  stainlessApiKey: params.stainlessApiKey ?? params.mcpOptions?.stainlessApiKey,
171
172
  upstreamClientEnvs: params.upstreamClientEnvs,
172
173
  mcpSessionId: params.mcpSessionId,
package/src/types.ts CHANGED
@@ -44,6 +44,16 @@ export type ToolCallResult = {
44
44
 
45
45
  export type McpRequestContext = {
46
46
  client: Roark;
47
+ /**
48
+ * The project a pinned `/mcp/<projectId>` connector fixed, carried so the code tool can pass it
49
+ * to its Deno worker. Taken from the client options rather than read back off the client:
50
+ * `client.project` is the `/v1/projects` resource accessor, not the option.
51
+ *
52
+ * Required rather than optional even though the value may be undefined: forgetting to carry it
53
+ * is exactly the regression that loses a pinned connector's project, and it would be silent.
54
+ * This way the compiler asks every construction site.
55
+ */
56
+ project: string | undefined;
47
57
  stainlessApiKey?: string | undefined;
48
58
  upstreamClientEnvs?: Record<string, string> | undefined;
49
59
  mcpSessionId?: string | undefined;
package/types.d.mts CHANGED
@@ -33,6 +33,16 @@ export type ToolCallResult = {
33
33
  };
34
34
  export type McpRequestContext = {
35
35
  client: Roark;
36
+ /**
37
+ * The project a pinned `/mcp/<projectId>` connector fixed, carried so the code tool can pass it
38
+ * to its Deno worker. Taken from the client options rather than read back off the client:
39
+ * `client.project` is the `/v1/projects` resource accessor, not the option.
40
+ *
41
+ * Required rather than optional even though the value may be undefined: forgetting to carry it
42
+ * is exactly the regression that loses a pinned connector's project, and it would be silent.
43
+ * This way the compiler asks every construction site.
44
+ */
45
+ project: string | undefined;
36
46
  stainlessApiKey?: string | undefined;
37
47
  upstreamClientEnvs?: Record<string, string> | undefined;
38
48
  mcpSessionId?: string | undefined;
package/types.d.mts.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"types.d.mts","sourceRoot":"","sources":["src/types.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,MAAM,qBAAqB,CAAC;AACxC,OAAO,EAAE,IAAI,EAAE,MAAM,oCAAoC,CAAC;AAE1D,KAAK,gBAAgB,GAAG;IACtB,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;CACd,CAAC;AAEF,KAAK,iBAAiB,GAAG;IACvB,IAAI,EAAE,OAAO,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;CAClB,CAAC;AAEF,KAAK,iBAAiB,GAAG;IACvB,IAAI,EAAE,OAAO,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;CAClB,CAAC;AAEF,KAAK,oBAAoB,GAAG;IAC1B,IAAI,EAAE,UAAU,CAAC;IACjB,QAAQ,EACJ;QACE,GAAG,EAAE,MAAM,CAAC;QACZ,QAAQ,EAAE,MAAM,CAAC;QACjB,IAAI,EAAE,MAAM,CAAC;KACd,GACD;QACE,GAAG,EAAE,MAAM,CAAC;QACZ,QAAQ,EAAE,MAAM,CAAC;QACjB,IAAI,EAAE,MAAM,CAAC;KACd,CAAC;CACP,CAAC;AAEF,MAAM,MAAM,YAAY,GAAG,gBAAgB,GAAG,iBAAiB,GAAG,iBAAiB,GAAG,oBAAoB,CAAC;AAE3G,MAAM,MAAM,cAAc,GAAG;IAC3B,OAAO,EAAE,YAAY,EAAE,CAAC;IACxB,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB,CAAC;AAEF,MAAM,MAAM,iBAAiB,GAAG;IAC9B,MAAM,EAAE,KAAK,CAAC;IACd,eAAe,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IACrC,kBAAkB,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,SAAS,CAAC;IACxD,YAAY,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IAClC,aAAa,CAAC,EAAE;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,OAAO,EAAE,MAAM,CAAA;KAAE,GAAG,SAAS,CAAC;CAC/D,CAAC;AAEF,MAAM,MAAM,eAAe,GAAG,CAAC,EAC7B,UAAU,EACV,IAAI,GACL,EAAE;IACD,UAAU,EAAE,iBAAiB,CAAC;IAC9B,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,SAAS,CAAC;CAC3C,KAAK,OAAO,CAAC,cAAc,CAAC,CAAC;AAE9B,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,OAAO,GAAG,cAAc,CASnE;AAED,wBAAsB,qBAAqB,CAAC,QAAQ,EAAE,QAAQ,GAAG,OAAO,CAAC,cAAc,CAAC,CA2BvF;AAED,wBAAgB,aAAa,CAAC,OAAO,EAAE,MAAM,GAAG,cAAc,CAU7D;AAED,MAAM,MAAM,QAAQ,GAAG;IACrB,QAAQ,EAAE,MAAM,CAAC;IACjB,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC;IAC5B,IAAI,EAAE,MAAM,EAAE,CAAC;IACf,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB,CAAC;AAEF,MAAM,MAAM,OAAO,GAAG;IACpB,QAAQ,EAAE,QAAQ,CAAC;IACnB,IAAI,EAAE,IAAI,CAAC;IACX,OAAO,EAAE,eAAe,CAAC;CAC1B,CAAC"}
1
+ {"version":3,"file":"types.d.mts","sourceRoot":"","sources":["src/types.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,MAAM,qBAAqB,CAAC;AACxC,OAAO,EAAE,IAAI,EAAE,MAAM,oCAAoC,CAAC;AAE1D,KAAK,gBAAgB,GAAG;IACtB,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;CACd,CAAC;AAEF,KAAK,iBAAiB,GAAG;IACvB,IAAI,EAAE,OAAO,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;CAClB,CAAC;AAEF,KAAK,iBAAiB,GAAG;IACvB,IAAI,EAAE,OAAO,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;CAClB,CAAC;AAEF,KAAK,oBAAoB,GAAG;IAC1B,IAAI,EAAE,UAAU,CAAC;IACjB,QAAQ,EACJ;QACE,GAAG,EAAE,MAAM,CAAC;QACZ,QAAQ,EAAE,MAAM,CAAC;QACjB,IAAI,EAAE,MAAM,CAAC;KACd,GACD;QACE,GAAG,EAAE,MAAM,CAAC;QACZ,QAAQ,EAAE,MAAM,CAAC;QACjB,IAAI,EAAE,MAAM,CAAC;KACd,CAAC;CACP,CAAC;AAEF,MAAM,MAAM,YAAY,GAAG,gBAAgB,GAAG,iBAAiB,GAAG,iBAAiB,GAAG,oBAAoB,CAAC;AAE3G,MAAM,MAAM,cAAc,GAAG;IAC3B,OAAO,EAAE,YAAY,EAAE,CAAC;IACxB,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB,CAAC;AAEF,MAAM,MAAM,iBAAiB,GAAG;IAC9B,MAAM,EAAE,KAAK,CAAC;IACd;;;;;;;;OAQG;IACH,OAAO,EAAE,MAAM,GAAG,SAAS,CAAC;IAC5B,eAAe,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IACrC,kBAAkB,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,SAAS,CAAC;IACxD,YAAY,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IAClC,aAAa,CAAC,EAAE;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,OAAO,EAAE,MAAM,CAAA;KAAE,GAAG,SAAS,CAAC;CAC/D,CAAC;AAEF,MAAM,MAAM,eAAe,GAAG,CAAC,EAC7B,UAAU,EACV,IAAI,GACL,EAAE;IACD,UAAU,EAAE,iBAAiB,CAAC;IAC9B,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,SAAS,CAAC;CAC3C,KAAK,OAAO,CAAC,cAAc,CAAC,CAAC;AAE9B,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,OAAO,GAAG,cAAc,CASnE;AAED,wBAAsB,qBAAqB,CAAC,QAAQ,EAAE,QAAQ,GAAG,OAAO,CAAC,cAAc,CAAC,CA2BvF;AAED,wBAAgB,aAAa,CAAC,OAAO,EAAE,MAAM,GAAG,cAAc,CAU7D;AAED,MAAM,MAAM,QAAQ,GAAG;IACrB,QAAQ,EAAE,MAAM,CAAC;IACjB,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC;IAC5B,IAAI,EAAE,MAAM,EAAE,CAAC;IACf,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB,CAAC;AAEF,MAAM,MAAM,OAAO,GAAG;IACpB,QAAQ,EAAE,QAAQ,CAAC;IACnB,IAAI,EAAE,IAAI,CAAC;IACX,OAAO,EAAE,eAAe,CAAC;CAC1B,CAAC"}
package/types.d.ts CHANGED
@@ -33,6 +33,16 @@ export type ToolCallResult = {
33
33
  };
34
34
  export type McpRequestContext = {
35
35
  client: Roark;
36
+ /**
37
+ * The project a pinned `/mcp/<projectId>` connector fixed, carried so the code tool can pass it
38
+ * to its Deno worker. Taken from the client options rather than read back off the client:
39
+ * `client.project` is the `/v1/projects` resource accessor, not the option.
40
+ *
41
+ * Required rather than optional even though the value may be undefined: forgetting to carry it
42
+ * is exactly the regression that loses a pinned connector's project, and it would be silent.
43
+ * This way the compiler asks every construction site.
44
+ */
45
+ project: string | undefined;
36
46
  stainlessApiKey?: string | undefined;
37
47
  upstreamClientEnvs?: Record<string, string> | undefined;
38
48
  mcpSessionId?: string | undefined;
package/types.d.ts.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["src/types.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,MAAM,qBAAqB,CAAC;AACxC,OAAO,EAAE,IAAI,EAAE,MAAM,oCAAoC,CAAC;AAE1D,KAAK,gBAAgB,GAAG;IACtB,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;CACd,CAAC;AAEF,KAAK,iBAAiB,GAAG;IACvB,IAAI,EAAE,OAAO,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;CAClB,CAAC;AAEF,KAAK,iBAAiB,GAAG;IACvB,IAAI,EAAE,OAAO,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;CAClB,CAAC;AAEF,KAAK,oBAAoB,GAAG;IAC1B,IAAI,EAAE,UAAU,CAAC;IACjB,QAAQ,EACJ;QACE,GAAG,EAAE,MAAM,CAAC;QACZ,QAAQ,EAAE,MAAM,CAAC;QACjB,IAAI,EAAE,MAAM,CAAC;KACd,GACD;QACE,GAAG,EAAE,MAAM,CAAC;QACZ,QAAQ,EAAE,MAAM,CAAC;QACjB,IAAI,EAAE,MAAM,CAAC;KACd,CAAC;CACP,CAAC;AAEF,MAAM,MAAM,YAAY,GAAG,gBAAgB,GAAG,iBAAiB,GAAG,iBAAiB,GAAG,oBAAoB,CAAC;AAE3G,MAAM,MAAM,cAAc,GAAG;IAC3B,OAAO,EAAE,YAAY,EAAE,CAAC;IACxB,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB,CAAC;AAEF,MAAM,MAAM,iBAAiB,GAAG;IAC9B,MAAM,EAAE,KAAK,CAAC;IACd,eAAe,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IACrC,kBAAkB,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,SAAS,CAAC;IACxD,YAAY,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IAClC,aAAa,CAAC,EAAE;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,OAAO,EAAE,MAAM,CAAA;KAAE,GAAG,SAAS,CAAC;CAC/D,CAAC;AAEF,MAAM,MAAM,eAAe,GAAG,CAAC,EAC7B,UAAU,EACV,IAAI,GACL,EAAE;IACD,UAAU,EAAE,iBAAiB,CAAC;IAC9B,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,SAAS,CAAC;CAC3C,KAAK,OAAO,CAAC,cAAc,CAAC,CAAC;AAE9B,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,OAAO,GAAG,cAAc,CASnE;AAED,wBAAsB,qBAAqB,CAAC,QAAQ,EAAE,QAAQ,GAAG,OAAO,CAAC,cAAc,CAAC,CA2BvF;AAED,wBAAgB,aAAa,CAAC,OAAO,EAAE,MAAM,GAAG,cAAc,CAU7D;AAED,MAAM,MAAM,QAAQ,GAAG;IACrB,QAAQ,EAAE,MAAM,CAAC;IACjB,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC;IAC5B,IAAI,EAAE,MAAM,EAAE,CAAC;IACf,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB,CAAC;AAEF,MAAM,MAAM,OAAO,GAAG;IACpB,QAAQ,EAAE,QAAQ,CAAC;IACnB,IAAI,EAAE,IAAI,CAAC;IACX,OAAO,EAAE,eAAe,CAAC;CAC1B,CAAC"}
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["src/types.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,MAAM,qBAAqB,CAAC;AACxC,OAAO,EAAE,IAAI,EAAE,MAAM,oCAAoC,CAAC;AAE1D,KAAK,gBAAgB,GAAG;IACtB,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;CACd,CAAC;AAEF,KAAK,iBAAiB,GAAG;IACvB,IAAI,EAAE,OAAO,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;CAClB,CAAC;AAEF,KAAK,iBAAiB,GAAG;IACvB,IAAI,EAAE,OAAO,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;CAClB,CAAC;AAEF,KAAK,oBAAoB,GAAG;IAC1B,IAAI,EAAE,UAAU,CAAC;IACjB,QAAQ,EACJ;QACE,GAAG,EAAE,MAAM,CAAC;QACZ,QAAQ,EAAE,MAAM,CAAC;QACjB,IAAI,EAAE,MAAM,CAAC;KACd,GACD;QACE,GAAG,EAAE,MAAM,CAAC;QACZ,QAAQ,EAAE,MAAM,CAAC;QACjB,IAAI,EAAE,MAAM,CAAC;KACd,CAAC;CACP,CAAC;AAEF,MAAM,MAAM,YAAY,GAAG,gBAAgB,GAAG,iBAAiB,GAAG,iBAAiB,GAAG,oBAAoB,CAAC;AAE3G,MAAM,MAAM,cAAc,GAAG;IAC3B,OAAO,EAAE,YAAY,EAAE,CAAC;IACxB,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB,CAAC;AAEF,MAAM,MAAM,iBAAiB,GAAG;IAC9B,MAAM,EAAE,KAAK,CAAC;IACd;;;;;;;;OAQG;IACH,OAAO,EAAE,MAAM,GAAG,SAAS,CAAC;IAC5B,eAAe,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IACrC,kBAAkB,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,SAAS,CAAC;IACxD,YAAY,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IAClC,aAAa,CAAC,EAAE;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,OAAO,EAAE,MAAM,CAAA;KAAE,GAAG,SAAS,CAAC;CAC/D,CAAC;AAEF,MAAM,MAAM,eAAe,GAAG,CAAC,EAC7B,UAAU,EACV,IAAI,GACL,EAAE;IACD,UAAU,EAAE,iBAAiB,CAAC;IAC9B,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,SAAS,CAAC;CAC3C,KAAK,OAAO,CAAC,cAAc,CAAC,CAAC;AAE9B,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,OAAO,GAAG,cAAc,CASnE;AAED,wBAAsB,qBAAqB,CAAC,QAAQ,EAAE,QAAQ,GAAG,OAAO,CAAC,cAAc,CAAC,CA2BvF;AAED,wBAAgB,aAAa,CAAC,OAAO,EAAE,MAAM,GAAG,cAAc,CAU7D;AAED,MAAM,MAAM,QAAQ,GAAG;IACrB,QAAQ,EAAE,MAAM,CAAC;IACjB,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC;IAC5B,IAAI,EAAE,MAAM,EAAE,CAAC;IACf,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB,CAAC;AAEF,MAAM,MAAM,OAAO,GAAG;IACpB,QAAQ,EAAE,QAAQ,CAAC;IACnB,IAAI,EAAE,IAAI,CAAC;IACX,OAAO,EAAE,eAAe,CAAC;CAC1B,CAAC"}
package/types.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"types.js","sourceRoot":"","sources":["src/types.ts"],"names":[],"mappings":";AAAA,sFAAsF;;AA4DtF,kDASC;AAED,sDA2BC;AAED,sCAUC;AAlDD,SAAgB,mBAAmB,CAAC,MAAe;IACjD,OAAO;QACL,OAAO,EAAE;YACP;gBACE,IAAI,EAAE,MAAM;gBACZ,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC;aACtC;SACF;KACF,CAAC;AACJ,CAAC;AAEM,KAAK,UAAU,qBAAqB,CAAC,QAAkB;IAC5D,MAAM,IAAI,GAAG,MAAM,QAAQ,CAAC,IAAI,EAAE,CAAC;IACnC,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC;IAC3B,MAAM,IAAI,GAAG,MAAM,CAAC,IAAI,CAAC,MAAM,IAAI,CAAC,WAAW,EAAE,CAAC,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAC;IACtE,IAAI,QAAQ,CAAC,UAAU,CAAC,QAAQ,CAAC,EAAE,CAAC;QAClC,OAAO;YACL,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,QAAQ,EAAE,IAAI,EAAE,CAAC;SAC7C,CAAC;IACJ,CAAC;SAAM,IAAI,QAAQ,CAAC,UAAU,CAAC,QAAQ,CAAC,EAAE,CAAC;QACzC,OAAO;YACL,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,QAAQ,EAAE,IAAI,EAAE,CAAC;SAC7C,CAAC;IACJ,CAAC;SAAM,CAAC;QACN,OAAO;YACL,OAAO,EAAE;gBACP;oBACE,IAAI,EAAE,UAAU;oBAChB,QAAQ,EAAE;wBACR,uEAAuE;wBACvE,GAAG,EAAE,0BAA0B;wBAC/B,QAAQ;wBACR,IAAI,EAAE,IAAI;qBACX;iBACF;aACF;SACF,CAAC;IACJ,CAAC;AACH,CAAC;AAED,SAAgB,aAAa,CAAC,OAAe;IAC3C,OAAO;QACL,OAAO,EAAE;YACP;gBACE,IAAI,EAAE,MAAM;gBACZ,IAAI,EAAE,OAAO;aACd;SACF;QACD,OAAO,EAAE,IAAI;KACd,CAAC;AACJ,CAAC"}
1
+ {"version":3,"file":"types.js","sourceRoot":"","sources":["src/types.ts"],"names":[],"mappings":";AAAA,sFAAsF;;AAsEtF,kDASC;AAED,sDA2BC;AAED,sCAUC;AAlDD,SAAgB,mBAAmB,CAAC,MAAe;IACjD,OAAO;QACL,OAAO,EAAE;YACP;gBACE,IAAI,EAAE,MAAM;gBACZ,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC;aACtC;SACF;KACF,CAAC;AACJ,CAAC;AAEM,KAAK,UAAU,qBAAqB,CAAC,QAAkB;IAC5D,MAAM,IAAI,GAAG,MAAM,QAAQ,CAAC,IAAI,EAAE,CAAC;IACnC,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC;IAC3B,MAAM,IAAI,GAAG,MAAM,CAAC,IAAI,CAAC,MAAM,IAAI,CAAC,WAAW,EAAE,CAAC,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAC;IACtE,IAAI,QAAQ,CAAC,UAAU,CAAC,QAAQ,CAAC,EAAE,CAAC;QAClC,OAAO;YACL,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,QAAQ,EAAE,IAAI,EAAE,CAAC;SAC7C,CAAC;IACJ,CAAC;SAAM,IAAI,QAAQ,CAAC,UAAU,CAAC,QAAQ,CAAC,EAAE,CAAC;QACzC,OAAO;YACL,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,QAAQ,EAAE,IAAI,EAAE,CAAC;SAC7C,CAAC;IACJ,CAAC;SAAM,CAAC;QACN,OAAO;YACL,OAAO,EAAE;gBACP;oBACE,IAAI,EAAE,UAAU;oBAChB,QAAQ,EAAE;wBACR,uEAAuE;wBACvE,GAAG,EAAE,0BAA0B;wBAC/B,QAAQ;wBACR,IAAI,EAAE,IAAI;qBACX;iBACF;aACF;SACF,CAAC;IACJ,CAAC;AACH,CAAC;AAED,SAAgB,aAAa,CAAC,OAAe;IAC3C,OAAO;QACL,OAAO,EAAE;YACP;gBACE,IAAI,EAAE,MAAM;gBACZ,IAAI,EAAE,OAAO;aACd;SACF;QACD,OAAO,EAAE,IAAI;KACd,CAAC;AACJ,CAAC"}
package/types.mjs.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"types.mjs","sourceRoot":"","sources":["src/types.ts"],"names":[],"mappings":"AAAA,sFAAsF;AA4DtF,MAAM,UAAU,mBAAmB,CAAC,MAAe;IACjD,OAAO;QACL,OAAO,EAAE;YACP;gBACE,IAAI,EAAE,MAAM;gBACZ,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC;aACtC;SACF;KACF,CAAC;AACJ,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,qBAAqB,CAAC,QAAkB;IAC5D,MAAM,IAAI,GAAG,MAAM,QAAQ,CAAC,IAAI,EAAE,CAAC;IACnC,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC;IAC3B,MAAM,IAAI,GAAG,MAAM,CAAC,IAAI,CAAC,MAAM,IAAI,CAAC,WAAW,EAAE,CAAC,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAC;IACtE,IAAI,QAAQ,CAAC,UAAU,CAAC,QAAQ,CAAC,EAAE,CAAC;QAClC,OAAO;YACL,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,QAAQ,EAAE,IAAI,EAAE,CAAC;SAC7C,CAAC;IACJ,CAAC;SAAM,IAAI,QAAQ,CAAC,UAAU,CAAC,QAAQ,CAAC,EAAE,CAAC;QACzC,OAAO;YACL,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,QAAQ,EAAE,IAAI,EAAE,CAAC;SAC7C,CAAC;IACJ,CAAC;SAAM,CAAC;QACN,OAAO;YACL,OAAO,EAAE;gBACP;oBACE,IAAI,EAAE,UAAU;oBAChB,QAAQ,EAAE;wBACR,uEAAuE;wBACvE,GAAG,EAAE,0BAA0B;wBAC/B,QAAQ;wBACR,IAAI,EAAE,IAAI;qBACX;iBACF;aACF;SACF,CAAC;IACJ,CAAC;AACH,CAAC;AAED,MAAM,UAAU,aAAa,CAAC,OAAe;IAC3C,OAAO;QACL,OAAO,EAAE;YACP;gBACE,IAAI,EAAE,MAAM;gBACZ,IAAI,EAAE,OAAO;aACd;SACF;QACD,OAAO,EAAE,IAAI;KACd,CAAC;AACJ,CAAC"}
1
+ {"version":3,"file":"types.mjs","sourceRoot":"","sources":["src/types.ts"],"names":[],"mappings":"AAAA,sFAAsF;AAsEtF,MAAM,UAAU,mBAAmB,CAAC,MAAe;IACjD,OAAO;QACL,OAAO,EAAE;YACP;gBACE,IAAI,EAAE,MAAM;gBACZ,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC;aACtC;SACF;KACF,CAAC;AACJ,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,qBAAqB,CAAC,QAAkB;IAC5D,MAAM,IAAI,GAAG,MAAM,QAAQ,CAAC,IAAI,EAAE,CAAC;IACnC,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC;IAC3B,MAAM,IAAI,GAAG,MAAM,CAAC,IAAI,CAAC,MAAM,IAAI,CAAC,WAAW,EAAE,CAAC,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAC;IACtE,IAAI,QAAQ,CAAC,UAAU,CAAC,QAAQ,CAAC,EAAE,CAAC;QAClC,OAAO;YACL,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,QAAQ,EAAE,IAAI,EAAE,CAAC;SAC7C,CAAC;IACJ,CAAC;SAAM,IAAI,QAAQ,CAAC,UAAU,CAAC,QAAQ,CAAC,EAAE,CAAC;QACzC,OAAO;YACL,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,QAAQ,EAAE,IAAI,EAAE,CAAC;SAC7C,CAAC;IACJ,CAAC;SAAM,CAAC;QACN,OAAO;YACL,OAAO,EAAE;gBACP;oBACE,IAAI,EAAE,UAAU;oBAChB,QAAQ,EAAE;wBACR,uEAAuE;wBACvE,GAAG,EAAE,0BAA0B;wBAC/B,QAAQ;wBACR,IAAI,EAAE,IAAI;qBACX;iBACF;aACF;SACF,CAAC;IACJ,CAAC;AACH,CAAC;AAED,MAAM,UAAU,aAAa,CAAC,OAAe;IAC3C,OAAO;QACL,OAAO,EAAE;YACP;gBACE,IAAI,EAAE,MAAM;gBACZ,IAAI,EAAE,OAAO;aACd;SACF;QACD,OAAO,EAAE,IAAI;KACd,CAAC;AACJ,CAAC"}