Skip to content

fix: regenerate agents-mcp package with pnpm monorepo compatibility#2770

Open
amikofalvy wants to merge 6 commits intomainfrom
update/agents-mcp-1
Open

fix: regenerate agents-mcp package with pnpm monorepo compatibility#2770
amikofalvy wants to merge 6 commits intomainfrom
update/agents-mcp-1

Conversation

@amikofalvy
Copy link
Collaborator

@amikofalvy amikofalvy commented Mar 19, 2026

Summary

  • Regenerates the @inkeep/agents-mcp Speakeasy MCP server from the latest public OpenAPI spec at https://api.pilot.inkeep.com/openapi.json
  • Adds .genignore with package.json to prevent Speakeasy from overwriting manually-managed dependency versions (which caused three-way merge conflicts on every generation)
  • Updates the generate script to use speakeasy run --skip-compile, bypassing the hardcoded npm install step that fails in pnpm monorepos (npm walks into pnpm's .pnpm store and tries to rebuild incompatible packages like globals@16.5.0)

Why --skip-compile is needed

The mcp-typescript Speakeasy target does not support the compileCommand config option (only the typescript target does). Its compile step always runs npm install --ignore-scripts, which conflicts with pnpm's content-addressable store layout. After code generation, pnpm install && pnpm build handles compilation correctly.

Test plan

  • speakeasy run --skip-compile completes successfully
  • pnpm install && pnpm build compiles the generated SDK without errors
  • Verify MCP server starts correctly: npx @inkeep/agents-mcp start --help

Made with Cursor

@changeset-bot
Copy link

changeset-bot bot commented Mar 19, 2026

🦋 Changeset detected

Latest commit: 21db81d

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 10 packages
Name Type
@inkeep/agents-mcp Patch
@inkeep/agents-api Patch
@inkeep/agents-manage-ui Patch
@inkeep/agents-cli Patch
@inkeep/agents-core Patch
@inkeep/agents-email Patch
@inkeep/agents-sdk Patch
@inkeep/agents-work-apps Patch
@inkeep/ai-sdk-provider Patch
@inkeep/create-agents Patch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@vercel
Copy link

vercel bot commented Mar 19, 2026

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
agents-api Ready Ready Preview, Comment Mar 19, 2026 7:55am
agents-docs Ready Ready Preview, Comment Mar 19, 2026 7:55am
agents-manage-ui Ready Ready Preview, Comment Mar 19, 2026 7:55am

Request Review

@pullfrog
Copy link
Contributor

pullfrog bot commented Mar 19, 2026

TL;DR — Regenerates the @inkeep/agents-mcp Speakeasy MCP server from the latest production OpenAPI spec, while fixing the code-generation workflow to be compatible with pnpm monorepos by skipping Speakeasy's hardcoded npm install compile step. Follow-up commits revert the auto-versioning bump back to 0.0.1, fix a TS1261 case-sensitivity conflict with a two-step git mv for Linux CI, and disable validateResponse to unbreak apps endpoint tests.

Key changes

  • .genignore + package.json generate script — Adds --skip-compile to the speakeasy run command and tells Speakeasy to stop overwriting package.json, preventing pnpm store conflicts and three-way merge issues on every regeneration.
  • .npmignore refinement — Narrows the JSON allowlist from !/**/*.json to explicit !/package.json, !/jsr.json, !/dist/**/*.json, !/esm/**/*.json, keeping unneeded JSON out of the published package.
  • gen.yaml / workflow.lock — Bumps Speakeasy to 1.757.1, enables versioningStrategy: automatic, pins SDK version at 0.0.1 (reverted from the auto-assigned 0.1.1), and sets validateResponse: false to avoid response-validation errors on endpoints that intentionally strip fields.
  • cliGetManageApiCliMecliGetManageApiCLIMe — Two-step git mv through an intermediate name to record the case-only rename in git's index, fixing TS1261 on case-sensitive filesystems (Linux CI) where macOS HFS+ silently treated it as a no-op.
  • ~1,180 regenerated source files — Bulk output refresh from the new OpenAPI spec: updated operation names, corrected endpoint mappings, new @generated-id annotations, and new operations for Apps, Channels/Slack, Auth, and Conversations.
  • Changeset brave-mcp-regen — Adds a patch changeset for @inkeep/agents-mcp to track this regeneration in the release pipeline.

Summary | 1183 files | 6 commits | base: mainupdate/agents-mcp-1


--skip-compile and .genignore for pnpm compatibility

Before: speakeasy run executed npm install --ignore-scripts internally, which walked into pnpm's .pnpm content-addressable store and failed on incompatible transitive packages. Speakeasy also overwrote package.json on every run, causing merge conflicts.
After: speakeasy run --skip-compile skips the built-in compile step entirely. .genignore excludes package.json from generation. Post-generation compilation is handled by pnpm install && pnpm build.

Why can't compileCommand be used instead?

The mcp-typescript Speakeasy target does not support the compileCommand config option — only the typescript target does. The only way to bypass the hardcoded npm install is the --skip-compile CLI flag.

.genignore · package.json · gen.yaml


validateResponse: false to fix apps test failures

Before: Speakeasy auto-added validateResponse: true during regeneration. The API intentionally strips tenantId/projectId from app responses via sanitizeAppConfig, causing the SDK's response validator to reject valid responses with ROUTE-5 and EDGE-1 errors on apps-create-app and apps-list-apps endpoints.
After: validateResponse is explicitly set to false in gen.yaml, matching the prior default behavior. This triggered a secondary regeneration that removed response-validation scaffolding from ~300 generated files.

gen.yaml


Version revert and cliGetManageApiCLIMe casing fix

Before: Speakeasy's auto-versioning bumped the SDK to 0.1.1 across gen.yaml, manifest.json, config.ts, and MCP server files. The function cliGetManageApiCliMe used inconsistent casing between filename and export, triggering TS1261 on case-sensitive file systems.
After: Regenerated with --skip-versioning to keep the version at 0.0.1. The file rename is performed via a two-step git mv (through an intermediate name) so the case-only change is recorded in git's index — macOS HFS+ is case-insensitive and silently ignored the direct rename.

manifest.json · core.ts · cliGetManageApiCLIMe.ts


Regenerated SDK from latest OpenAPI spec

Before: Generated code reflected an older OpenAPI revision (sha256:e3138b30…) with stale operation IDs and missing endpoints.
After: Code is generated from the current production spec (sha256:02795cb3…), adding operations for Apps CRUD, Slack channel management, anonymous auth/PoW, conversation media/bounds, and more. Every generated file now includes a @generated-id annotation for traceability.

The bulk of the ~1,180 changed files are machine-generated src/funcs/, src/models/, and src/mcp-server/ modules — no hand-written logic changes outside the config files above.

workflow.lock · .npmignore

Pullfrog  | View workflow run | Triggered by Pullfrogpullfrog.com𝕏

Regenerated with --skip-versioning to keep gen.yaml version at 0.0.1.
Renamed cliGetManageApiCliMe -> cliGetManageApiCLIMe to fix TS1261
case-sensitivity error between filename and import path.

Made-with: Cursor
Copy link
Contributor

@pullfrog pullfrog bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Low urgency — the core approach is sound, but two items need attention before merge.

This PR regenerates @inkeep/agents-mcp from the latest OpenAPI spec (Speakeasy 1.698.0 → 1.757.1, SDK version 0.0.1 → 0.1.1). All 1174 changed files are scoped to packages/agents-mcp/. The manual changes — .genignore to protect package.json, --skip-compile to avoid npm-in-pnpm conflicts, and the narrowed .npmignore — are correct and well-motivated.

Two items to address:

  1. Missing changeset. @inkeep/agents-mcp is not in the changeset ignore list, yet no changeset was added. This regeneration adds ~279 new files (new API surface for apps, skills, scheduled triggers, Slack channels, etc.), deletes 31 files (renamed/removed endpoints), and bumps the SDK generation version. Consumers of @inkeep/agents-mcp (currently agents-api) will see new exports and potentially removed ones. A changeset is warranted.

  2. Unchecked test plan item. The PR description lists "Verify MCP server starts correctly: npx @inkeep/agents-mcp start --help" as unchecked. Since bin/mcp-server.js is a build artifact that doesn't exist in the source tree (produced by bun build), this verification would need a local build first. Worth confirming this passes before merge.

Pullfrog  | Fix all ➔Fix 👍s ➔View workflow runpullfrog.com𝕏

"lint": "eslint --cache --max-warnings=0 src",
"prepublishOnly": "npm run build",
"generate": "speakeasy run"
"generate": "speakeasy run --skip-compile"
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The --skip-compile change is the right fix for the pnpm monorepo conflict. Worth noting that the build script still runs bun i (line 20), which installs via bun's own resolver and bypasses pnpm's lockfile. This is a pre-existing concern outside the scope of this PR, but if the goal is full pnpm compatibility, it's the next thing to address.

@@ -0,0 +1 @@
package.json
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is correct — prevents Speakeasy from overwriting the manually-managed package.json with its own template that lacks the pnpm-specific adjustments. However, this means future dependency additions from Speakeasy regeneration (e.g., if a new SDK feature requires a new package) will need manual intervention. Consider documenting this in a comment or the README's generation instructions so future regenerators know to diff the generated package.json against the existing one.

!/**/*.js
!/**/*.mjs
!/**/*.json
!/package.json
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The narrowing from !/**/*.json to explicit paths is correct — manifest.json is build-time only (used by build.mts and mcpb:build), not needed by npm consumers. The !/jsr.json pattern is a no-op since jsr.json doesn't exist in this package. The !/dist/**/*.json and !/esm/**/*.json patterns are also currently no-ops (tsc doesn't emit JSON files with the current tsconfig.json), but they're reasonable future-proofing.

Copy link
Contributor

@claude claude bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

PR Review Summary

(1) Total Issues | Risk: Medium

🟠⚠️ Major (1) 🟠⚠️

🟠 1) scope Missing changeset for published package

Issue: The @inkeep/agents-mcp package (version 0.58.20) has been regenerated with significant changes, but no changeset was added. Per AGENTS.md, any change to a published package requires a changeset.

Why: This regeneration includes:

  • New --skip-compile flag in the generate script (workflow change)
  • New .genignore to prevent package.json overwrites
  • Updated Speakeasy from 1.698.0 → 1.757.1
  • Regenerated ~1,170 SDK files from updated OpenAPI spec
  • New operations (Apps CRUD, Slack channels, Auth/PoW, Conversations)
  • Removed operations (tool approvals, pending invitations, user organizations)
  • New dynamic tool discovery pattern (list_tools, describe_tool_input, execute_tool)

Without a changeset, consumers won't have changelog documentation and the package version won't be bumped appropriately.

Fix: Run:

pnpm bump patch --pkg agents-mcp "Regenerate MCP server with pnpm monorepo compatibility and updated OpenAPI spec"

Note: Given the scope of changes (new operations, removed operations, workflow changes), a minor bump may be more appropriate depending on semver policy for this package.

Refs:

💭 Consider (1) 💭

Inline Comments:

  • 💭 Consider: gen.yaml:27 versioningStrategy: automatic interaction with .genignore

✅ What's Good

  • .genignore approach — Correctly prevents Speakeasy from overwriting the manually-managed package.json, solving the three-way merge conflict issue
  • .npmignore refinement — More restrictive JSON allowlist (!/package.json, !/jsr.json, !/dist/**/*.json, !/esm/**/*.json) is safer than the previous !/**/*.json
  • --skip-compile workaround — Appropriate solution for pnpm monorepo compatibility since mcp-typescript target doesn't support compileCommand
  • Dynamic tool discovery — The new list_tools/describe_tool_input/execute_tool pattern is a modern MCP approach

📋 Test Plan Verification

The PR description includes:

  • speakeasy run --skip-compile completes successfully
  • pnpm install && pnpm build compiles the generated SDK without errors
  • Verify MCP server starts correctly: npx @inkeep/agents-mcp start --help

Please complete the final test plan item before merging.


💡 APPROVE WITH SUGGESTIONS

Summary: This is a well-structured PR that correctly solves the pnpm monorepo compatibility issue with Speakeasy code generation. The .genignore + --skip-compile approach is the right solution. A changeset is required for this published package — please add one before merging.

Discarded (5)
Location Issue Reason Discarded
manifest.json tools array removed Intentional — replaced by dynamic tool discovery pattern
manifest.json Auth required changed to false Intentional — supports new anonymous session auth
models/ Tool approvals endpoint removed Reflects OpenAPI spec change, not a PR bug
models/ Invitations/organizations endpoints removed Reflects OpenAPI spec change, not a PR bug
README.md:6 MIT license badge vs Elastic License 2.0 Pre-existing Speakeasy template issue, out of scope
Reviewers (2)
Reviewer Returned Main Findings Consider Inline Comments Discarded
pr-review-devops 6 1 1 1 3
pr-review-breaking-changes 7 0 0 0 7
Total 13 1 1 1 10

Note: Breaking changes findings were discarded after validation — the removed endpoints and manifest changes reflect intentional OpenAPI spec updates, not PR bugs.

schemas:
allOfMergeStrategy: shallowMerge
requestBodyFieldName: body
versioningStrategy: automatic
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💭 Consider: versioningStrategy: automatic interaction with .genignore

Issue: The versioningStrategy: automatic setting was added, but package.json is now in .genignore, meaning Speakeasy cannot update the version field.

Why: This may cause version drift between what Speakeasy expects and what's in the manually-managed package.json. Since version bumps are handled via changesets in this monorepo, this setting may be harmless—but the interaction should be verified.

Fix: Consider removing versioningStrategy: automatic since versioning is handled via changesets and package.json is protected by .genignore. Alternatively, verify with Speakeasy docs that this combination works as expected.

Refs:

@github-actions github-actions bot deleted a comment from claude bot Mar 19, 2026
macOS HFS+ is case-insensitive, so `mv Cli -> CLI` was a no-op.
Use two-step git mv through intermediate name to record the rename
in git's index for case-sensitive filesystems (Linux CI runners).

Made-with: Cursor
Copy link
Contributor

@claude claude bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

PR Review Summary

(0) Total Issues | Risk: Low

Delta Review

This is a re-review scoped to changes since the previous automated review.

Changes since last review:

  • 1 commit: fix: case-sensitive file rename for cliGetManageApiCLIMe on Linux CI
  • 2 files renamed (no content changes):
    • src/funcs/cliGetManageApiCliMe.tssrc/funcs/cliGetManageApiCLIMe.ts
    • src/mcp-server/tools/cliGetManageApiCliMe.tssrc/mcp-server/tools/cliGetManageApiCLIMe.ts

Assessment: The delta is a correct fix for case-sensitivity issues on Linux CI. The filename casing now matches the import/export identifiers (cliGetManageApiCLIMe). No new issues introduced.

🕐 Pending Recommendations (1)

  • 🟠 scope Missing changeset for published package — still unresolved

💡 APPROVE WITH SUGGESTIONS

Summary: The delta (case-sensitive file rename) is correct and resolves the TS1261 build issue on Linux CI. The changeset requirement from the previous review remains unresolved — please run pnpm bump patch --pkg agents-mcp "Regenerate MCP server with pnpm monorepo compatibility and updated OpenAPI spec" before merging.

Reviewers (0)
Reviewer Returned Main Findings Consider While You're Here Inline Comments Pending Recs Discarded
Total 0 0 0 0 0 1 0

Note: Delta review — no sub-reviewers dispatched as the change was a trivial file rename with no content changes.

@github-actions github-actions bot deleted a comment from claude bot Mar 19, 2026
@itoqa
Copy link

itoqa bot commented Mar 19, 2026

Ito Test Report ❌

15 test cases ran. 13 passed, 2 failed.

This run confirms core transport and safety behaviors are stable (CORS, SSE lifecycle, invalid-session handling, injection safety, and auth boundary checks). Two apps CRUD scenarios consistently fail for the same reason: strict MCP response validation rejects app payloads when projectId/tenantId are omitted in returned app objects, which blocks successful create/list flows through execute_tool.

✅ Passed (13)
Test Case Summary Timestamp Screenshot
ROUTE-1 Serve-mode root endpoint returned 200 and landing page loaded with expected MCP content. 0:00 ROUTE-1_0-00.png
ROUTE-2 OPTIONS preflight to /mcp returned 204 with permissive CORS origin and expected methods. 0:00 ROUTE-2_0-00.png
ROUTE-3 Dynamic mode /mcp tools/list returned list_tools, describe_tool_input, and execute_tool. 4:24 ROUTE-3_4-24.png
ROUTE-4 Filtered list_tools response included expected apps tool family entries. 4:24 ROUTE-4_4-24.png
ROUTE-6 SSE handshake returned an endpoint and posting a valid MCP message returned 202 Accepted. 18:48 ROUTE-6_18-48.png
ROUTE-7 Root endpoint returned 200 and served landing content while SSE mode was active. 18:48 ROUTE-7_18-48.png
LOGIC-1 Server remained usable without auth context; dynamic list_tools succeeded. 4:24 LOGIC-1_4-24.png
EDGE-3 Posting to a non-existent session path returned controlled 404 with no crash. 18:48 EDGE-3_18-48.png
EDGE-4 Large search_terms payload completed successfully with valid protocol response. 4:24 EDGE-4_4-24.png
ADV-1 Injection-like tool_name produced controlled unknown-tool handling and recovery. 4:24 ADV-1_4-24.png
ADV-2 Malformed apps-create-app payload produced structured validation issues and recovery succeeded. 14:31 ADV-2_14-31.png
ADV-3 Unauthenticated apps-list-apps call returned controlled 401 semantics and list_tools remained functional. 14:31 ADV-3_14-31.png
ADV-5 Closed session replay returned 404 while active session accepted valid messages. 18:48 ADV-5_18-48.png
❌ Failed (2)
Test Case Summary Timestamp Screenshot
ROUTE-5 apps-create-app and apps-list-apps fail with response-validation errors for missing app projectId/tenantId. 14:31 ROUTE-5_14-31.png
EDGE-1 Concurrent create-app executions both fail with the same response-validation error for missing app projectId/tenantId. 14:31 EDGE-1_14-31.png
Apps CRUD through execute_tool succeeds end-to-end – Failed
  • Where: Dynamic MCP mode (/mcp) using execute_tool for apps CRUD.

  • Steps to reproduce: Start in dynamic mode with valid auth, call execute_tool for apps-create-app, then call apps-list-apps.

  • What failed: Both calls return Response validation failed errors because returned app objects are missing projectId and tenantId, so CRUD cannot complete even though API calls execute.

  • Code analysis: I traced MCP tool execution from apps-create-app/apps-list-apps into generated SDK response parsing. The SDK enforces AppResponseItem where projectId and tenantId are required keys (nullable values allowed, but key presence is mandatory), and matchers.ts converts parse failures into hard tool errors.

  • Relevant code:

    packages/agents-mcp/src/models/appresponseitem.ts (lines 12–16)

    export type AppResponseItem = {
      id: string;
      tenantId: string | null;
      projectId: string | null;
      name: string;

    packages/agents-mcp/src/models/appresponseitem.ts (lines 28–40)

    export const AppResponseItem$zodSchema: z.ZodType<AppResponseItem> = z.object({
      config: AppConfigResponse$zodSchema,
      createdAt: z.string(),
      defaultAgentId: z.string().nullable(),
      defaultProjectId: z.string().nullable(),
      description: z.string().nullable(),
      enabled: z.boolean(),
      id: z.string(),
      lastUsedAt: z.string().nullable(),
      name: z.string(),
      projectId: z.string().nullable(),
      tenantId: z.string().nullable(),

    packages/agents-mcp/src/lib/matchers.ts (lines 295–310)

    if ("err" in matcher) {
      const result = safeParse(
        data,
        (v: unknown) => matcher.schema.parse(v),
        "Response validation failed",
      );
      return [result.ok ? { ok: false, error: result.value } : result, raw];
    } else {
      return [
        safeParse(valueToParse, (v: unknown) => matcher.schema.parse(v), "Response validation failed"),
      ];
    }
  • Why this is likely a bug: The production MCP server path rejects otherwise usable app responses due schema-key strictness, breaking core apps-create/list behavior in normal dynamic-mode usage.

  • Introduced by this PR: Yes – this PR modified the relevant code.

  • Timestamp: 14:31

Rapid double execution on create app – Failed
  • Where: Dynamic MCP mode (/mcp) during concurrent apps-create-app execution.

  • Steps to reproduce: Trigger two execute_tool calls for apps-create-app in rapid succession with the same payload.

  • What failed: Both requests fail with the same response-validation error (projectId/tenantId missing), preventing duplicate-policy verification and leaving the flow blocked at response parsing.

  • Code analysis: The concurrency aspect does not change failure shape; each call independently hits the same generated response schema gate and is surfaced as an MCP error by the same parser path.

  • Relevant code:

    packages/agents-mcp/src/funcs/appsCreateApp.ts (lines 169–180)

    const [result$] = await M.match<
      CreateAppResponse,
      | APIError
      | SDKValidationError
      | UnexpectedClientError
      | InvalidRequestError
      | RequestAbortedError
      | RequestTimeoutError
      | ConnectionError
    >(
      M.json(201, CreateAppResponse$zodSchema, { key: "object" }),

    packages/agents-mcp/src/models/createappop.ts (lines 39–43)

    export type CreateAppData = { app: AppResponseItem };
    
    export const CreateAppData$zodSchema: z.ZodType<CreateAppData> = z.object({
      app: AppResponseItem$zodSchema,
    });

    packages/agents-mcp/src/models/appresponseitem.ts (lines 38–39)

    projectId: z.string().nullable(),
    tenantId: z.string().nullable(),
  • Why this is likely a bug: Repeated calls deterministically fail at the same production response-validation boundary, showing a real SDK/contract mismatch rather than transient test behavior.

  • Introduced by this PR: Yes – this PR modified the relevant code.

  • Timestamp: 14:31

📋 View Recording

Screen Recording

Speakeasy auto-added validateResponse: true during regeneration, but
the API intentionally strips tenantId/projectId from app responses via
sanitizeAppConfig. This caused ROUTE-5 and EDGE-1 test failures for
apps-create-app and apps-list-apps endpoints. Revert to the default
(false) to match prior behavior.

Made-with: Cursor
@vercel vercel bot temporarily deployed to Preview – agents-docs March 19, 2026 07:41 Inactive
Copy link
Contributor

@claude claude bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

PR Review Summary

(0) Total Issues | Risk: Low

Delta Review

This is a re-review scoped to changes since the previous automated review.

Changes since last review (2 commits):

Commit Summary
fcf22e830 fix: disable validateResponse to fix apps response-validation errors
5dbc3c214 chore: add changeset for agents-mcp regeneration

Key changes:

  1. Changeset added (.changeset/brave-mcp-regen.md) — resolves the major issue from all prior reviews
  2. validateResponse: false in gen.yaml — disables Speakeasy's runtime response validation
  3. matchers.ts deleted (352 lines) — response validation logic removed as consequence

Assessment:

Changeset requirement satisfied — The changeset correctly describes the regeneration with pnpm monorepo compatibility fixes.

Response validation fix is appropriate — Disabling validateResponse is the correct approach for a generated SDK where the OpenAPI spec may not perfectly match all API responses (especially for polymorphic/union types in the apps CRUD operations). This is a common pattern for Speakeasy-generated SDKs.

No regressions introduced — The delta only contains the two targeted fixes; no unrelated changes.


✅ APPROVE

Summary: All prior review feedback has been addressed. The changeset is in place, and disabling response validation is the appropriate fix for the apps CRUD errors. This PR is ready to merge.

Note: Submitting as COMMENT due to bot permissions — this review recommends approval.

Reviewers (0)
Reviewer Returned Main Findings Consider While You're Here Inline Comments Pending Recs Discarded
Total 0 0 0 0 0 0 0

Note: Delta review — no sub-reviewers dispatched. The changes were two targeted fixes (changeset + config flag) with no new code logic requiring domain-specific review.

Copy link
Contributor

@claude claude bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

PR Review Summary

(0) Total Issues | Risk: Low

Delta Review

This is a re-review scoped to changes since the previous automated review (5dbc3c214ac7).

Changes since last review (3 commits):

Commit Summary
21db81dfa Merge branch 'main' into update/agents-mcp-1
4f7555014 Version Packages (#2766)
75da86cd1 fix(manage-ui): handle __Secure- cookie prefix in auth middleware (#2769)

Files changed (17):

  • CHANGELOG files added for all packages (version 0.58.20 → 0.58.21)
  • Version bumps in package.json files
  • New packages/agents-core/src/auth/cookie-names.ts — utilities for __Secure- cookie prefix handling
  • Updates to api-config.ts and proxy.ts to use new auth cookie helpers

Assessment:

No changes to PR scope — The delta is a merge from main bringing in routine version bumps and an unrelated auth middleware fix. No changes to the core PR work (packages/agents-mcp/ regeneration, .genignore, --skip-compile, validateResponse: false).

Previous approval stands — All prior review feedback was addressed in earlier commits. The changeset is in place, response validation is disabled to fix apps CRUD tests, and the casing fix resolved Linux CI issues.

Merged-in changes are correct — The cookie-names.ts addition and its usages follow good patterns (centralized constants, helper functions for secure cookie detection).


✅ APPROVE

Summary: The delta is a routine merge from main (version bumps + unrelated auth fix). The core PR work was already reviewed and approved. This PR is ready to merge.

Note: Submitting as COMMENT due to bot permissions — this review recommends approval.

Reviewers (0)
Reviewer Returned Main Findings Consider While You're Here Inline Comments Pending Recs Discarded
Total 0 0 0 0 0 0 0

Note: Delta review — no sub-reviewers dispatched. The delta contained only merged-in main branch changes (version bumps, auth cookie fix) with no impact on the PR's core changes.

@itoqa
Copy link

itoqa bot commented Mar 19, 2026

Ito Test Report ❌

17 test cases ran. 14 passed, 3 failed.

✅ Most core MCP flows, auth checks, and CRUD scenarios behaved as expected in this run. 🔍 Code-first verification found three likely product defects: Streamable HTTP protocol sequencing is not enforced, the advertised SSE endpoint is unavailable in the Streamable HTTP server path, and a generated available-agents operation is not registered as an MCP tool.

✅ Passed (14)
Test Case Summary Timestamp Screenshot
ROUTE-1 Recovered unavailable port 2718 by starting local MCP HTTP server, then verified HTTP 200, landing page title/identity text, install blocks, and no uncaught runtime exception. 0:00 ROUTE-1_0-00.png
ROUTE-2 At 390x844 and 768-width viewports, core landing content remained visible and usable with no horizontal overflow detected. 0:00 ROUTE-2_0-00.png
ROUTE-3 Recovered initial 406/invalid initialize request issues by applying required Accept header and valid initialize payload; initialize succeeded, initialized notification accepted (202), and tools/list returned a valid JSON-RPC tool list. 5:08 ROUTE-3_5-08.png
LOGIC-4 tools/list returned canonical regenerated namespaces (apps-, agents-, artifact-components-) and representative health-health tool invocation succeeded without server instability. 5:08 LOGIC-4_5-08.png
EDGE-2 After correcting protocol/header setup, 20 parallel tools/list requests completed with valid response envelopes under a shared MCP session and a final health-health call succeeded. 5:09 EDGE-2_5-09.png
ROUTE-4 After restarting server with --mode dynamic, tools/list exposed meta-tools (list_tools, describe_tool_input, execute_tool) and execute_tool successfully invoked health-health. 8:16 ROUTE-4_8-16.png
EDGE-1 Posting to an invalid SSE message session returned 404 Not Found as expected. 23:24 EDGE-1_23-24.png
ADV-1 Spoofed cookieauth and bearer-auth header variants failed to access protected apps-list-apps, returning unauthorized errors. 23:28 ADV-1_23-28.png
LOGIC-1 Public tool call health-health succeeded on /mcp without static auth credentials configured. 27:08 LOGIC-1_27-08.png
LOGIC-2 Protected apps-list-apps returned clear unauthorized error with isError=true, and subsequent health-health call still succeeded. 27:08 LOGIC-2_27-08.png
ROUTE-6 Executed full CRUD via MCP with valid request schema: app created, listed, fetched, updated, deleted, and confirmed absent afterward. 51:39 ROUTE-6_51-39.png
EDGE-4 Malformed app id produced a controlled validation error, and a follow-up list request succeeded, showing stable behavior after invalid input. 51:39 EDGE-4_51-39.png
ADV-2 Injection-like fields were handled as data by the API response path, and the created record was deleted successfully during cleanup. 51:39 ADV-2_51-39.png
ADV-4 Parallel delete replay produced one successful delete and one controlled not-found response, with consistent final state afterward. 51:39 ADV-4_51-39.png
❌ Failed (3)
Test Case Summary Timestamp Screenshot
EDGE-3 Pre-initialize tools/call returned success instead of a protocol-sequence rejection; code indicates per-request transport/server creation that bypasses handshake state. 5:09 EDGE-3_5-09.png
ROUTE-5 SSE session establishment failed with 404 on /sse; server code path used for Streamable HTTP does not register /sse while landing page config still advertises it. 14:01 ROUTE-5_14-01.png
LOGIC-3 available-agents operation exists in generated client code, but MCP server registration omits a corresponding tool, causing discoverability gap. 27:08 LOGIC-3_27-08.png
Out-of-order MCP sequence handling – Failed
  • Where: Streamable HTTP /mcp request lifecycle in server startup path.

  • Steps to reproduce: Send tools/call before initialize to /mcp; observe successful result instead of protocol-order rejection.

  • What failed: The server accepts a pre-initialize tool call, while expected behavior is to reject out-of-sequence requests.

  • Code analysis: The Streamable HTTP handler constructs a fresh transport and fresh MCP server inside each POST request, then connects and handles the request immediately. This request-local lifecycle prevents durable protocol session state enforcement.

  • Relevant code:

    packages/agents-mcp/src/mcp-server/cli/serve/impl.ts (lines 53-74)

    app.post("/mcp", async (req, res) => {
      const headers = new Headers();
      // ...
      const transport = new StreamableHTTPServerTransport({});
    
      const { server: mcpServer } = createMCPServer({
        logger,
        allowedTools: cliFlags.tool,
        dynamic: cliFlags.mode === "dynamic",
        serverURL: cliFlags["server-url"],
        getSDK: () => buildSDK(headers, cliFlags, cliFlags["disable-static-auth"], logger),
      });
    });

    packages/agents-mcp/src/mcp-server/cli/serve/impl.ts (lines 82-84)

    await mcpServer.connect(transport as Transport);
    await transport.handleRequest(req, res, req.body);
  • Why this is likely a bug: Creating a new server/transport for each request makes protocol sequencing effectively stateless in this path, which explains pre-initialize calls being accepted.

  • Introduced by this PR: Yes – this PR modified the relevant code.

  • Timestamp: 5:09

SSE transport session lifecycle – Failed
  • Where: HTTP transport route surface for MCP server startup.

  • Steps to reproduce: Run the Streamable HTTP server and request GET /sse; observe a 404 response.

  • What failed: SSE endpoint is unavailable in the tested server path, despite install/connection config generation still pointing clients at /sse.

  • Code analysis: The Streamable HTTP implementation defines /mcp and / routes but no /sse. At the same time, the landing page generator hard-codes /sse in client configuration output.

  • Relevant code:

    packages/agents-mcp/src/mcp-server/cli/serve/impl.ts (lines 53-54)

    app.post("/mcp", async (req, res) => {
      const headers = new Headers();

    packages/agents-mcp/src/mcp-server/cli/serve/impl.ts (lines 86-87)

    app.get("/", landingPageExpress);

    packages/agents-mcp/src/landing-page.ts (lines 33-46)

    const mcpConfig = {
      "args": ["-y", "mcp-remote@0.1.25", `${o}/sse`, "--header", "cookie-auth:${COOKIE_AUTH}"]
    };
    const codexConfig = `[mcp_servers.InkeepAgents]
    url = "${o}/sse"
    http_headers = { "cookie-auth" = "YOUR_COOKIE_AUTH", "bearer-auth" = "YOUR_BEARER_AUTH" }`;
  • Why this is likely a bug: The product advertises /sse to clients while the active HTTP server path does not implement it, producing deterministic connection failure.

  • Introduced by this PR: Yes – this PR modified the relevant code.

  • Timestamp: 14:01

Available-agents route reachable but not MCP-discoverable – Failed
  • Where: MCP tool registration for agent-related operations.

  • Steps to reproduce: Compare generated API function set to MCP tool registry, then query tools list and note absence of available-agents tool.

  • What failed: The available-agents API operation exists in generated function code, but no corresponding MCP tool is registered/exposed.

  • Code analysis: The generated function for /manage/available-agents exists and is routable in client code, but server tool registration covers agentsListAgents and many adjacent agent tools without registering an available-agents tool.

  • Relevant code:

    packages/agents-mcp/src/funcs/agentsListAvailableAgents.ts (lines 24-33)

    /**
     * List available agents
     *
     * @remarks
     * List all agents the user can invoke. Requires a valid JWT token.
     */
    export function agentsListAvailableAgents(
      client$: InkeepAgentsCore,
      security: ListAvailableAgentsSecurity,

    packages/agents-mcp/src/funcs/agentsListAvailableAgents.ts (lines 72-73)

    const path$ = pathToFunc("/manage/available-agents")();

    packages/agents-mcp/src/mcp-server/server.ts (lines 400-407)

    tool(tool$agentsListAgents);
    tool(tool$agentsCreateAgent);
    tool(tool$agentsGetAgent);
    tool(tool$agentsUpdateAgent);
    tool(tool$agentsDeleteAgent);
    tool(tool$agentsGetRelatedAgentInfos);
    tool(tool$agentsGetFullAgentDefinition);
  • Why this is likely a bug: A generated, documented operation exists but is not surfaced through MCP tool registration, creating a real capability gap for MCP clients.

  • Introduced by this PR: Yes – this PR modified the relevant code.

  • Timestamp: 27:08

📋 View Recording

Screen Recording

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant