Repository navigation
Add /mcp/chatgpt-app with fixed single-operation tools for the OpenAI plugin - #1226
Merged
Merged
Conversation
… plugin
OpenAI's plugin review refuses the shared endpoint's search/describe/run meta-tools ("operations not individually exposed"). The new endpoint serves a fixed set where each tool is one operation: read-only database queries with schema and dialect examples, connector list and setup state, per-connector activity counts, workspace notes and the dashboard link. Only read-only database connectors are queried. Same auth, grant and role scope as /mcp; /mcp and /mcp/<serverId> are unchanged.
helpcodeai
enabled auto-merge (squash)
October 24, 2026 18:49
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to subscribe to this conversation on GitHub.
Already have an account?
Sign in.
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
OpenAI rejected the AnythingMCP plugin twice. Its review flags the shared endpoint's meta-tools (search_tools, describe_tool, run_read_tool, run_write_tool, run_read_steps, kg_how_to_obtain) as "operations not individually exposed", and the plugin guidelines now say: "Do not use discovery, operation selection, or schema fetching with a generic executor to enable operations not individually exposed for review." The review team confirmed on 23 Oct that they will not discuss it further.
Plugins approved after that rule (a read-only SQL database plugin, an integration-hub status plugin, an organization-data plugin) expose fixed single-operation tools. This PR adds a dedicated endpoint for a new OpenAI plugin submission that does the same, without touching what Claude or existing ChatGPT custom plugins use.
Changes
POST /mcp/chatgpt-app(declared before:serverId; GET/DELETE answer 405 like the other stateless routes). It serves 8 fixed tools, all read-only, each with all hints set explicitly, and none takes a tool name or free-form arguments:anythingmcp_list_connectors,anythingmcp_list_databases,anythingmcp_get_database_schema,anythingmcp_get_query_examples,anythingmcp_query_database,anythingmcp_get_connector_activity,anythingmcp_get_workspace_guide,anythingmcp_get_configuration_urlchatgpt-app-toolset.ts(no Nest, likeshared-toolset.ts): the database tools map to the connector's generatedget_database_schema/get_example_queries/execute_querytools and run through the samedeps.executepath (scope, licence check, audit row). Only read-only database connectors are queried; a connector with write access is listed as not queryable and never run. The engine's existing guard still refuses non-SELECT and stacked statements. Connection URLs never leave the server (the engine is derived from the scheme only).serveSharedToolsettakes avariant; thechatgpt-appvariant skips the setup-permission lookup (no setup tools) and builds the new tool set. Operator credentials without a user (static key) get 403.McpServersService.activityByConnector: calls / failures / last call / last failure per connector over N days, counts only, grouped on the(connector_id, created_at)index.docs/integrations/chatgpt.mdsection on the endpoint.Cloud and self-hosted: the endpoint behaves the same in both modes and is independent of
MCP_SHARED_ENDPOINT_TOOLS./mcp(Claude directory toolset and thechatgptprofile for custom plugins on bare/mcp) and/mcp/<serverId>are unchanged.Type
Testing
Commands (working directory
packages/backend, afternpx prisma generate):npx tsc --noEmit -p tsconfig.json: passednpm run lint: 0 errors, 11 existing warnings in untouched files (its--fixrewrote two unrelated spec files; reverted)npm test: 755 suites passed, 4 skipped; 22,455 tests passed, 1,550 skippedchatgpt-app-toolset.spec.ts(fixed list, no executor shape, read-only only, role hides query tool, ambiguity, no URL leak, activity) andchatgpt-app.controller.spec.ts(fixed + direct mode, tenant isolation, MCP role, no setup lookup, 403 for static credentials)Manual end to end, local backend built from this branch against a separate Postgres database with a small orders/customers dataset, called with a per-user MCP API key:
initializereturns the new instructions;tools/listreturns the 8 tools with explicit hintsanythingmcp_get_database_schemaand an aggregateSELECT … GROUP BYquery returned rowsDELETE FROM orders→ "Only SELECT queries are allowed…";SELECT 1; DROP TABLE orders→ "Only a single SQL statement is allowed…"readOnly: false→ refused, never executedanythingmcp_get_connector_activitycounted the calls aboveresource_metadatapointing at/.well-known/oauth-protected-resource/mcp/chatgpt-app, which returnsresource: …/mcp/chatgpt-app; GET → 405SSRF_ALLOW_LOCALHOST=truewas set for the local run (expected)Checklist
npm test)Related Issues
Relates to the OpenAI plugin directory submission (rejected 29 Sep and 20 Oct 2026).