Update API documentation for certificate management and introduce new platform API endpoints - #2987
Conversation
… platform API endpoints - Removed the `developer` role requirement for uploading TLS certificates in the certificate management documentation. - Added new documentation files for API key management, application management, authentication, gateway policies, gateway tokens, and LLM provider deployments, detailing their respective operations, parameters, and responses. - Enhanced overall clarity and structure of the API documentation to improve usability for developers.
|
Note Reviews pausedIt looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the Use the following commands to manage reviews:
Use the checkboxes below for quick actions:
No actionable comments were generated in the recent review. 🎉 ℹ️ Recent review info⚙️ Run configurationConfiguration used: Path: .coderabbit.yaml Review profile: CHILL Plan: Pro Plus Run ID: 📒 Files selected for processing (2)
📝 WalkthroughWalkthroughAdds Platform API v0.9 documentation, OpenAPI contract and generation updates, upstream/MCP validation, guarded outbound HTTP clients, project-handle response mapping, and permission-aware workspace routing. Certificate upload documentation now requires ChangesPlatform API documentation and runtime changes
Estimated code review effort: 5 (Critical) | ~120 minutes Possibly related PRs
Suggested reviewers: 🚥 Pre-merge checks | ✅ 3 | ❌ 2❌ Failed checks (2 warnings)
✅ Passed checks (3 passed)
✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Actionable comments posted: 14
Note
Due to the large number of review comments, Critical, Major severity comments were prioritized as inline comments.
🟡 Minor comments (17)
docs/rest-apis/platform-api/gateway-tokens.md-46-46 (1)
46-46: 📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick winRemove blank lines inside response blockquotes.
markdownlint-cli2reports MD028 at these lines. Keep each response blockquote contiguous.Also applies to: 147-147, 275-275
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/gateway-tokens.md` at line 46, Remove the blank lines within the response blockquotes in gateway-tokens.md, including the instances around the referenced locations, so each blockquote remains contiguous and satisfies markdownlint MD028.Source: Linters/SAST tools
docs/rest-apis/platform-api/gateways.md-63-63 (1)
63-63: 📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick winRemove blank lines inside response blockquotes.
markdownlint-cli2reports MD028 at these lines. Keep each response blockquote contiguous.Also applies to: 224-224, 347-347, 498-498, 634-634, 754-754
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/gateways.md` at line 63, Remove the blank lines within each response blockquote in gateways.md, including the instances around the referenced response sections. Keep every contiguous blockquote uninterrupted so markdownlint MD028 passes.Source: Linters/SAST tools
docs/rest-apis/platform-api/gateways.md-681-688 (1)
681-688: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick winCorrect the repeated 409 conflict examples.
Each example says the resource “already exists,” but these operations return conflicts because deletion is blocked by endpoint-specific state or usage constraints.
docs/rest-apis/platform-api/gateways.md#L681-L688: describe active API deployments or WebSocket connections.docs/rest-apis/platform-api/gateway-policies.md#L401-L408: describe the policy being referenced by an API.docs/rest-apis/platform-api/rest-api-deployments.md#L476-L483: describe the deployment not being inUNDEPLOYEDstatus.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/gateways.md` around lines 681 - 688, The repeated 409 conflict examples use an incorrect “resource already exists” message. Update docs/rest-apis/platform-api/gateways.md lines 681-688 to describe active API deployments or WebSocket connections; update docs/rest-apis/platform-api/gateway-policies.md lines 401-408 to describe the policy being referenced by an API; and update docs/rest-apis/platform-api/rest-api-deployments.md lines 476-483 to describe deployments not having UNDEPLOYED status, while preserving the existing response structure.docs/rest-apis/platform-api/rest-api-deployments.md-60-60 (1)
60-60: 📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick winRemove blank lines inside response blockquotes.
markdownlint-cli2reports MD028 at these lines. Keep each response blockquote contiguous.Also applies to: 208-208, 332-332, 429-429, 554-554, 695-695
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/rest-api-deployments.md` at line 60, Remove blank lines within the response blockquotes in rest-api-deployments.md, including the occurrences at the referenced sections. Keep each blockquote’s consecutive lines contiguous so markdownlint MD028 is satisfied, without changing the response content.Source: Linters/SAST tools
docs/rest-apis/platform-api/rest-apis.md-60-60 (1)
60-60: 📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick winRemove blank lines inside response blockquotes.
markdownlint-cli2reports MD028 at these lines. Keep each> Example responses/status blockquote contiguous, or remove the blank line before the response status.Also applies to: 360-360, 584-584, 879-879, 1097-1097, 1208-1208, 1363-1363, 1535-1535, 1693-1693, 1825-1825
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/rest-apis.md` at line 60, Remove blank lines within each response blockquote in rest-apis.md, including the `> Example responses` sections and their status lines at all referenced locations. Keep each blockquote contiguous so markdownlint-cli2 no longer reports MD028, without changing the response content.Source: Linters/SAST tools
docs/rest-apis/platform-api/gateway-policies.md-40-40 (1)
40-40: 📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick winRemove blank lines inside response blockquotes.
markdownlint-cli2reports MD028 at these lines. Keep each response blockquote contiguous.Also applies to: 138-138, 279-279, 370-370
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/gateway-policies.md` at line 40, Remove blank lines inside the response blockquotes in gateway-policies.md, including the instances near the referenced locations, so each blockquote remains contiguous and passes markdownlint MD028.Source: Linters/SAST tools
docs/rest-apis/platform-api/rest-api-deployments.md-167-169 (1)
167-169: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick winMake the deployment list gateway filter contract and example match.
GET /rest-apis/{restApiId}/deploymentsdocuments/query parameterizesgatewayIdas a gateway UUID, but the response example showsgatewayId: "prod-gateway-01"in the deployment artifact. Use a UUID in that example, or update the query-parameter contract if UUID is only the deployment artifact value andgatewayIdis also accepted as a handle for filtering.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/rest-api-deployments.md` around lines 167 - 169, Update the deployment list documentation around the GET deployments endpoint so the gatewayId query-parameter contract and deployment artifact example use the same identifier format. Either replace the example’s gatewayId value with a gateway UUID, or revise the documented filter contract to explicitly support gateway handles when that is the actual behavior.docs/rest-apis/platform-api/projects.md-256-288 (1)
256-288: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick winUse one project identifier contract.
The page alternates between “UUID” and “handle,” while the parameter descriptions and examples use a handle/slug. Normalize all references to the actual accepted identifier.
docs/rest-apis/platform-api/projects.md#L256-L288: align the lookup heading and description with theprojectIdcontract.docs/rest-apis/platform-api/README.md#L50-L53: update the table-of-contents label.docs/rest-apis/platform-api/projects.md#L514-L550: align the delete description with the same identifier terminology.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/projects.md` around lines 256 - 288, Normalize project identifier terminology to the accepted handle/slug contract: in docs/rest-apis/platform-api/projects.md lines 256-288, update the lookup heading and description; in docs/rest-apis/platform-api/README.md lines 50-53, update the table-of-contents label; and in docs/rest-apis/platform-api/projects.md lines 514-550, update the delete description. Remove conflicting “UUID” references while preserving the projectId parameter name.docs/rest-apis/platform-api/mcp-proxies.md-282-288 (1)
282-288: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick winCorrect the
projectIddescription.This MCP proxy listing documentation says the parameter filters “APIs.” Describe it as filtering MCP proxies for the specified project.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/mcp-proxies.md` around lines 282 - 288, Update the projectId description in the MCP proxy listing documentation, including its detailed description, to state that the handle filters MCP proxies for the specified project rather than APIs.docs/rest-apis/platform-api/mcp-proxies.md-177-191 (1)
177-191: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick winRemove the copied
spec.contextvalidation error from unrelated API examples.The same stale error payload is reused across MCP proxy, subscription-plan, subscription, and secret operations. Replace each instance with an operation-specific validation response or a generic error that does not claim an unrelated field failed.
docs/rest-apis/platform-api/mcp-proxies.md: Lines 177-191, 667-680, 770-783, and 907-920.docs/rest-apis/platform-api/subscriptionplans.md: Lines 89-103 and 449-463.docs/rest-apis/platform-api/subscriptions.md: Lines 77-91, 243-256, and 357-370.docs/rest-apis/platform-api/secrets.md: Lines 66-80 and 442-455.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/mcp-proxies.md` around lines 177 - 191, Replace the copied spec.context validation payload with an operation-specific validation response or generic error that does not reference unrelated fields. Apply this to every listed example in docs/rest-apis/platform-api/mcp-proxies.md (177-191, 667-680, 770-783, 907-920), subscriptionplans.md (89-103, 449-463), subscriptions.md (77-91, 243-256, 357-370), and secrets.md (66-80, 442-455).docs/rest-apis/platform-api/mcp-proxies.md-882-886 (1)
882-886: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick winAlign the server-info parameter description with the payload.
The description says the request contains a gateway ID, base reference, and metadata, but the example uses
url,proxyId, andauth. Update the description or payload so clients receive one consistent contract.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/mcp-proxies.md` around lines 882 - 886, Align the MCPServerInfoFetchRequest parameter documentation with its example by ensuring both describe the same fields. Update the description in the “fetch-server-info-from-mcp-proxy-backend-services” parameters table to reference url, proxyId, and auth, or revise the payload example to use gateway ID, base reference, and metadata; preserve a single consistent client-facing contract.docs/rest-apis/platform-api/mcp-proxies.md-107-107 (1)
107-107: 📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick winRemove blank lines inside response blockquotes across the generated documents.
The same MD028 violation appears throughout the four documents. Remove blank lines between consecutive response blockquote lines in:
docs/rest-apis/platform-api/mcp-proxies.md: Lines 107, 291, 384, 597, 769, and 889.docs/rest-apis/platform-api/subscriptionplans.md: Lines 62, 198, 296, 422, and 560.docs/rest-apis/platform-api/subscriptions.md: Lines 55, 211, 335, 483, and 609.docs/rest-apis/platform-api/secrets.md: Lines 52, 189, 309, 428, and 557.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/mcp-proxies.md` at line 107, Remove blank lines between consecutive response blockquote lines to eliminate MD028 violations in docs/rest-apis/platform-api/mcp-proxies.md at lines 107, 291, 384, 597, 769, and 889; docs/rest-apis/platform-api/subscriptionplans.md at lines 62, 198, 296, 422, and 560; docs/rest-apis/platform-api/subscriptions.md at lines 55, 211, 335, 483, and 609; and docs/rest-apis/platform-api/secrets.md at lines 52, 189, 309, 428, and 557.Source: Linters/SAST tools
docs/rest-apis/platform-api/schemas.md-4874-4885 (1)
4874-4885: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick winResolve the MCP context-path contradiction.
The example uses
"/"while the schema description says the context must have no trailing slash. Either document/as an explicit root-path exception or change the example to a non-root value such as/weather.Also applies to: 4954-4957
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/schemas.md` around lines 4874 - 4885, Resolve the contradiction between the MCP example’s context value and the schema rule by either documenting “/” as the explicit root-path exception or changing the example context to a non-root path such as “/weather”; apply the same correction to the related example identified by the context field.docs/rest-apis/platform-api/llm-provider-templates.md-48-70 (1)
48-70: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick winUse distinct token and model paths in the template example.
completionTokens,totalTokens,remainingTokens,requestModel, andresponseModelall map to$.usage.inputTokens. Replace these with representative paths or clearly mark them as placeholders; otherwise users may copy a configuration that reports incorrect metrics.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/llm-provider-templates.md` around lines 48 - 70, The template example incorrectly assigns $.usage.inputTokens to multiple token and model fields. Update completionTokens, totalTokens, remainingTokens, requestModel, and responseModel with distinct representative JSON paths matching their respective values, or clearly mark each as a placeholder.docs/rest-apis/platform-api/llm-provider-templates.md-1198-1238 (1)
1198-1238: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick winMake the PATCH response reflect the requested state.
The request disables the template with
"enabled": false, while the response reports"enabled": true. The example should show the resulting disabled state.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/llm-provider-templates.md` around lines 1198 - 1238, Update the 200 Response example for the enable-or-disable operation so its enabled field is false, matching the disabled request body. Leave the other response fields unchanged.docs/rest-apis/platform-api/llm-providers.md-32-36 (1)
32-36: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick winKeep the
vhostexample aligned with the OpenAPI contract.The supplied
platform-api/resources/openapi.yamlexample usesapi.openai.com, while this request usesapi.openai. Update the payload to match the upstream contract or explicitly document that this is a custom vhost.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/llm-providers.md` around lines 32 - 36, Update the vhost field in the request payload example to use api.openai.com, matching the OpenAPI contract in the documented Provider API example. Only retain api.openai if the example explicitly identifies it as a custom vhost.docs/rest-apis/platform-api/llm-provider-templates.md-572-585 (1)
572-585: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick winMake the copy response match the requested version.
The request specifies
toVersion: v4.0, but the example response reportsversion: v1.0. Update the response to represent the newly copiedv4.0version.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@docs/rest-apis/platform-api/llm-provider-templates.md` around lines 572 - 585, The OpenAI copy-response example reports the wrong version. Update the response object identified by the "openai" template fields so its version is v4.0, matching the requested toVersion while leaving the other response fields unchanged.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@docs/rest-apis/platform-api/authentication.md`:
- Around line 234-239: Align the OpenAPI OAuth2 security scheme and the
file-mode authentication documentation around the supported login flow: update
the `OAuth2Security` scope reference and token URL so generated clients target
the documented `/api/portal/v0.9/auth/login` username/password endpoint, or
alternatively document and configure the client-credentials endpoint
consistently throughout the file-mode flow.
In `@docs/rest-apis/platform-api/gateway-tokens.md`:
- Around line 150-155: Replace the credential-like value in the response example
with an unmistakable non-functional placeholder such as “<new-token-value>” or
“REDACTED_EXAMPLE”, and explicitly identify it as non-functional while
preserving the rest of the example.
In `@docs/rest-apis/platform-api/llm-provider-deployments.md`:
- Around line 59-69: Update the documented response examples so asynchronous
operations show their initial in-progress status: use DEPLOYING for creation and
restoration examples, and UNDEPLOYING for undeployment examples. Apply this
consistently at docs/rest-apis/platform-api/llm-provider-deployments.md lines
59-69, 539-549, and 676-686;
docs/rest-apis/platform-api/llm-proxy-deployments.md lines 59-69, 539-549, and
676-686; and docs/rest-apis/platform-api/mcp-proxy-deployments.md lines 59-69,
517-527, and 643-653, changing only the status values in those examples.
In `@docs/rest-apis/platform-api/llm-providers.md`:
- Around line 1738-1744: Replace the secret-shaped apiKey example in
docs/rest-apis/platform-api/llm-providers.md lines 1738-1744 with
<generated-api-key> or REDACTED, and state that the real value is returned only
at creation time. Apply the same apiKey replacement and creation-time disclosure
note in docs/rest-apis/platform-api/llm-proxies.md lines 1041-1047.
In `@docs/rest-apis/platform-api/rest-api-deployments.md`:
- Around line 63-74: The deployment response examples should use the documented
transitional initial statuses instead of DEPLOYED. Update the examples
associated with creation and restoration to show DEPLOYING, and the undeployment
example to show UNDEPLOYING, while preserving the remaining response fields.
In `@docs/rest-apis/platform-api/rest-apis.md`:
- Around line 251-257: Update the request examples in the REST API
documentation, including both payloads referenced by the comment, so their
context field uses a value beginning with “/” such as “/pizza”; keep the
remaining example fields unchanged.
- Around line 26-32: Update the Authentication section for GET /rest-apis so its
documented OAuth scope behavior matches the OpenAPI contract: require both
ap:rest_api:read and ap:rest_api:manage, or revise the security requirements to
represent either scope and keep the “at least one” wording.
In `@docs/rest-apis/platform-api/schemas.md`:
- Around line 758-766: Update every referenced upstream example in the
documentation so each UpstreamDefinition contains exactly one of url or ref,
never both; preserve the existing example context and auth fields while choosing
either the direct URL form or the reference form consistently across all listed
examples.
- Around line 5164-5183: Update the value property restrictions in both secret
request schemas, including the schema shown near the secret example and the
corresponding schema near the referenced second section, from none to
write-only. Keep the existing plaintext input and never-returned description
unchanged.
- Around line 746-752: Update the REST API example payloads around the visible
id/displayName fields and the additional occurrences to use a context value
beginning with “/”, changing “pizza” to “/pizza”. Keep the examples consistent
with the documented validation requirement.
- Around line 1867-1872: Replace credential-like token and API-key example
values in the affected documentation response examples with unmistakable
placeholders such as REDACTED_TOKEN and REDACTED_API_KEY. Update the examples
around the shown response and the additional occurrences so no realistic
credential strings remain, while preserving the surrounding response structure.
- Around line 2950-2975: Correct the extraction examples in the response schema
blocks around the resource "/responses", including the repeated sections, so
completionTokens, totalTokens, remainingTokens, requestModel, and responseModel
no longer reuse $.usage.inputTokens. Replace them with distinct representative
provider-response paths or clearly labeled placeholders, preserving inputTokens
only for promptTokens.
In `@docs/rest-apis/platform-api/secrets.md`:
- Around line 13-19: Update all secret request examples, including the
referenced examples, to use a consistent request schema: if sending the shown
payload file, label it as JSON, set Content-Type to application/json, and retain
the raw payload upload; otherwise convert the examples to valid multipart -F
fields with matching payload formatting. Ensure the documented filename, payload
syntax, and media type agree throughout.
In `@docs/rest-apis/platform-api/subscriptions.md`:
- Around line 304-317: Update the GET /subscriptions/{subscriptionId}
documentation to include the required subscriberId query parameter in the curl
URL and add a corresponding required query-parameter table row, preserving the
requirement that it must match the subscription’s subscriber for access control.
---
Minor comments:
In `@docs/rest-apis/platform-api/gateway-policies.md`:
- Line 40: Remove blank lines inside the response blockquotes in
gateway-policies.md, including the instances near the referenced locations, so
each blockquote remains contiguous and passes markdownlint MD028.
In `@docs/rest-apis/platform-api/gateway-tokens.md`:
- Line 46: Remove the blank lines within the response blockquotes in
gateway-tokens.md, including the instances around the referenced locations, so
each blockquote remains contiguous and satisfies markdownlint MD028.
In `@docs/rest-apis/platform-api/gateways.md`:
- Line 63: Remove the blank lines within each response blockquote in
gateways.md, including the instances around the referenced response sections.
Keep every contiguous blockquote uninterrupted so markdownlint MD028 passes.
- Around line 681-688: The repeated 409 conflict examples use an incorrect
“resource already exists” message. Update
docs/rest-apis/platform-api/gateways.md lines 681-688 to describe active API
deployments or WebSocket connections; update
docs/rest-apis/platform-api/gateway-policies.md lines 401-408 to describe the
policy being referenced by an API; and update
docs/rest-apis/platform-api/rest-api-deployments.md lines 476-483 to describe
deployments not having UNDEPLOYED status, while preserving the existing response
structure.
In `@docs/rest-apis/platform-api/llm-provider-templates.md`:
- Around line 48-70: The template example incorrectly assigns
$.usage.inputTokens to multiple token and model fields. Update completionTokens,
totalTokens, remainingTokens, requestModel, and responseModel with distinct
representative JSON paths matching their respective values, or clearly mark each
as a placeholder.
- Around line 1198-1238: Update the 200 Response example for the
enable-or-disable operation so its enabled field is false, matching the disabled
request body. Leave the other response fields unchanged.
- Around line 572-585: The OpenAI copy-response example reports the wrong
version. Update the response object identified by the "openai" template fields
so its version is v4.0, matching the requested toVersion while leaving the other
response fields unchanged.
In `@docs/rest-apis/platform-api/llm-providers.md`:
- Around line 32-36: Update the vhost field in the request payload example to
use api.openai.com, matching the OpenAPI contract in the documented Provider API
example. Only retain api.openai if the example explicitly identifies it as a
custom vhost.
In `@docs/rest-apis/platform-api/mcp-proxies.md`:
- Around line 282-288: Update the projectId description in the MCP proxy listing
documentation, including its detailed description, to state that the handle
filters MCP proxies for the specified project rather than APIs.
- Around line 177-191: Replace the copied spec.context validation payload with
an operation-specific validation response or generic error that does not
reference unrelated fields. Apply this to every listed example in
docs/rest-apis/platform-api/mcp-proxies.md (177-191, 667-680, 770-783, 907-920),
subscriptionplans.md (89-103, 449-463), subscriptions.md (77-91, 243-256,
357-370), and secrets.md (66-80, 442-455).
- Around line 882-886: Align the MCPServerInfoFetchRequest parameter
documentation with its example by ensuring both describe the same fields. Update
the description in the “fetch-server-info-from-mcp-proxy-backend-services”
parameters table to reference url, proxyId, and auth, or revise the payload
example to use gateway ID, base reference, and metadata; preserve a single
consistent client-facing contract.
- Line 107: Remove blank lines between consecutive response blockquote lines to
eliminate MD028 violations in docs/rest-apis/platform-api/mcp-proxies.md at
lines 107, 291, 384, 597, 769, and 889;
docs/rest-apis/platform-api/subscriptionplans.md at lines 62, 198, 296, 422, and
560; docs/rest-apis/platform-api/subscriptions.md at lines 55, 211, 335, 483,
and 609; and docs/rest-apis/platform-api/secrets.md at lines 52, 189, 309, 428,
and 557.
In `@docs/rest-apis/platform-api/projects.md`:
- Around line 256-288: Normalize project identifier terminology to the accepted
handle/slug contract: in docs/rest-apis/platform-api/projects.md lines 256-288,
update the lookup heading and description; in
docs/rest-apis/platform-api/README.md lines 50-53, update the table-of-contents
label; and in docs/rest-apis/platform-api/projects.md lines 514-550, update the
delete description. Remove conflicting “UUID” references while preserving the
projectId parameter name.
In `@docs/rest-apis/platform-api/rest-api-deployments.md`:
- Line 60: Remove blank lines within the response blockquotes in
rest-api-deployments.md, including the occurrences at the referenced sections.
Keep each blockquote’s consecutive lines contiguous so markdownlint MD028 is
satisfied, without changing the response content.
- Around line 167-169: Update the deployment list documentation around the GET
deployments endpoint so the gatewayId query-parameter contract and deployment
artifact example use the same identifier format. Either replace the example’s
gatewayId value with a gateway UUID, or revise the documented filter contract to
explicitly support gateway handles when that is the actual behavior.
In `@docs/rest-apis/platform-api/rest-apis.md`:
- Line 60: Remove blank lines within each response blockquote in rest-apis.md,
including the `> Example responses` sections and their status lines at all
referenced locations. Keep each blockquote contiguous so markdownlint-cli2 no
longer reports MD028, without changing the response content.
In `@docs/rest-apis/platform-api/schemas.md`:
- Around line 4874-4885: Resolve the contradiction between the MCP example’s
context value and the schema rule by either documenting “/” as the explicit
root-path exception or changing the example context to a non-root path such as
“/weather”; apply the same correction to the related example identified by the
context field.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro Plus
Run ID: f8bd7a06-f8ab-4710-a79a-2153fde05514
⛔ Files ignored due to path filters (1)
tools/apidocs/widdershins_templates/code_shell.dotis excluded by!**/*.dot
📒 Files selected for processing (26)
docs/rest-apis/gateway/certificate-management.mddocs/rest-apis/platform-api/README.mddocs/rest-apis/platform-api/api-keys.mddocs/rest-apis/platform-api/applications.mddocs/rest-apis/platform-api/authentication.mddocs/rest-apis/platform-api/gateway-policies.mddocs/rest-apis/platform-api/gateway-tokens.mddocs/rest-apis/platform-api/gateways.mddocs/rest-apis/platform-api/llm-provider-deployments.mddocs/rest-apis/platform-api/llm-provider-templates.mddocs/rest-apis/platform-api/llm-providers.mddocs/rest-apis/platform-api/llm-proxies.mddocs/rest-apis/platform-api/llm-proxy-deployments.mddocs/rest-apis/platform-api/mcp-proxies.mddocs/rest-apis/platform-api/mcp-proxy-deployments.mddocs/rest-apis/platform-api/organizations.mddocs/rest-apis/platform-api/projects.mddocs/rest-apis/platform-api/rest-api-deployments.mddocs/rest-apis/platform-api/rest-apis.mddocs/rest-apis/platform-api/schemas.mddocs/rest-apis/platform-api/secrets.mddocs/rest-apis/platform-api/subscriptionplans.mddocs/rest-apis/platform-api/subscriptions.mdplatform-api/Makefileplatform-api/resources/openapi.yamltools/apidocs/widdershins_templates/authentication.def
There was a problem hiding this comment.
Actionable comments posted: 3
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@platform-api/resources/openapi.yaml`:
- Around line 6748-6766: Update isEmptyUpstreamDefinition and validateUpstream
so upstream definitions accept exactly one non-blank field between url and ref.
Reject definitions where both are blank or both are populated, while preserving
acceptance when only one field has a value.
- Line 7556: Update the description for LLMProvider.context in the OpenAPI
schema to refer to routes exposed by “this provider” instead of “this proxy,”
preserving the existing path requirements and default root-path wording.
- Line 3116: Enforce exactly one of url or proxyId in MCPServerInfoFetchRequest,
reject auth when proxyId is supplied, and reject proxyId in the service/handler
when url is present. Update direct URL fetching to use the existing guarded
spec-fetch dialer, including initialization, tools, and list requests, so
scheme, IP, and redirect SSRF protections apply to the HEAD reachability probe
and subsequent calls.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro Plus
Run ID: df77b06e-f479-4a76-b0da-23e02aac948c
⛔ Files ignored due to path filters (2)
tools/apidocs/widdershins_templates/code_shell.dotis excluded by!**/*.dottools/apidocs/widdershins_templates/operation.dotis excluded by!**/*.dot
📒 Files selected for processing (25)
docs/rest-apis/platform-api/README.mddocs/rest-apis/platform-api/api-keys.mddocs/rest-apis/platform-api/applications.mddocs/rest-apis/platform-api/authentication.mddocs/rest-apis/platform-api/gateway-policies.mddocs/rest-apis/platform-api/gateway-tokens.mddocs/rest-apis/platform-api/gateways.mddocs/rest-apis/platform-api/llm-provider-deployments.mddocs/rest-apis/platform-api/llm-provider-templates.mddocs/rest-apis/platform-api/llm-providers.mddocs/rest-apis/platform-api/llm-proxies.mddocs/rest-apis/platform-api/llm-proxy-deployments.mddocs/rest-apis/platform-api/mcp-proxies.mddocs/rest-apis/platform-api/mcp-proxy-deployments.mddocs/rest-apis/platform-api/organizations.mddocs/rest-apis/platform-api/projects.mddocs/rest-apis/platform-api/rest-api-deployments.mddocs/rest-apis/platform-api/rest-apis.mddocs/rest-apis/platform-api/schemas.mddocs/rest-apis/platform-api/secrets.mddocs/rest-apis/platform-api/subscriptionplans.mddocs/rest-apis/platform-api/subscriptions.mdplatform-api/api/generated.goplatform-api/resources/openapi.yamltools/apidocs/widdershins_templates/responses.def
🚧 Files skipped from review as they are similar to previous changes (21)
- docs/rest-apis/platform-api/api-keys.md
- docs/rest-apis/platform-api/organizations.md
- docs/rest-apis/platform-api/README.md
- docs/rest-apis/platform-api/secrets.md
- docs/rest-apis/platform-api/gateway-policies.md
- docs/rest-apis/platform-api/subscriptionplans.md
- docs/rest-apis/platform-api/subscriptions.md
- docs/rest-apis/platform-api/llm-proxies.md
- docs/rest-apis/platform-api/mcp-proxies.md
- docs/rest-apis/platform-api/authentication.md
- docs/rest-apis/platform-api/gateway-tokens.md
- docs/rest-apis/platform-api/llm-provider-templates.md
- docs/rest-apis/platform-api/projects.md
- docs/rest-apis/platform-api/applications.md
- docs/rest-apis/platform-api/mcp-proxy-deployments.md
- docs/rest-apis/platform-api/llm-provider-deployments.md
- docs/rest-apis/platform-api/rest-api-deployments.md
- docs/rest-apis/platform-api/llm-providers.md
- docs/rest-apis/platform-api/rest-apis.md
- docs/rest-apis/platform-api/gateways.md
- docs/rest-apis/platform-api/llm-proxy-deployments.md
* Refactor project ID handling to use project handles instead of UUIDs - Updated API comments and OpenAPI specifications to clarify that project IDs are now URL-friendly slugs (handles) rather than UUIDs. - Implemented logic in LLMProxyService and MCPProxyService to resolve project UUIDs to handles for API responses. - Adjusted tests to ensure that project handles are correctly returned in service responses. - Enhanced routing functions to accommodate the new project handle structure for gateways and proxies. * Enhance proxy handling and permissions in service provider components * Add GetProjectByUUIDAndOrgID method to ProjectRepository - Introduced GetProjectByUUIDAndOrgID method in ProjectRepository to retrieve projects scoped to an organization, enhancing tenant request handling. - Updated LLMProxyService and MCPProxyService to utilize the new method for project resolution, ensuring proper organization context. - Modified tests to validate the new functionality and ensure correct behavior for cross-organization project access.
There was a problem hiding this comment.
Actionable comments posted: 3
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@platform-api/internal/service/llm.go`:
- Around line 1907-1920: Unify upstream validation through a shared helper for
one api.UpstreamDefinition that requires exactly one non-blank url or ref.
Update platform-api/internal/service/llm.go:1907-1920 so validateUpstream
applies the helper to Main and non-nil Sandbox, and update
platform-api/internal/handler/api.go:298-320 so validateUpstreamDefinitions uses
the same helper for both definitions, rejecting both-set and neither-set cases
consistently.
- Around line 1907-1920: Update validateUpstream to also call
validateUpstreamDefinition for u.Sandbox, using the appropriate sandbox name,
and return that validation error so Sandbox enforces exactly one of url or ref
just like Main.
In `@platform-api/internal/utils/guarded_http_client.go`:
- Around line 137-146: Update the CheckRedirect callbacks in
guarded_http_client.go and openapi_spec_fetcher.go to reject redirects whose
target host differs from the original request host, while preserving the
existing redirect-count and http/https scheme checks. Prefer factoring this
policy into a shared redirect-check builder and use it from both clients so
cross-host redirects cannot forward caller-supplied authentication headers.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro Plus
Run ID: 8f0ae4e6-21f8-46bc-8f80-005099ca5674
📒 Files selected for processing (12)
docs/rest-apis/platform-api/schemas.mdplatform-api/internal/handler/api.goplatform-api/internal/service/api.goplatform-api/internal/service/llm.goplatform-api/internal/service/mcp.goplatform-api/internal/service/mcp_test.goplatform-api/internal/utils/common.goplatform-api/internal/utils/guarded_http_client.goplatform-api/internal/utils/guarded_http_client_test.goplatform-api/internal/utils/mcp.goplatform-api/internal/utils/openapi_spec_fetcher.goplatform-api/resources/openapi.yaml
🚧 Files skipped from review as they are similar to previous changes (1)
- platform-api/resources/openapi.yaml
There was a problem hiding this comment.
Actionable comments posted: 1
Caution
Some comments are outside the diff and can’t be posted inline due to platform limitations.
⚠️ Outside diff range comments (2)
platform-api/resources/openapi.yaml (2)
8399-8403: 🔒 Security & Privacy | 🟠 MajorMake the MCP selector branches mutually exclusive.
The current
oneOfaccepts a payload containingurl,proxyId, andauth: theurlbranch only requiresurland does not forbidproxyId. This reopens the selector ambiguity addressed in the previous review.Suggested schema correction
oneOf: - required: [ "url" ] + not: + required: [ "proxyId" ] - required: [ "proxyId" ] not: - required: [ "auth" ] + anyOf: + - required: [ "url" ] + - required: [ "auth" ]🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@platform-api/resources/openapi.yaml` around lines 8399 - 8403, Update the MCP selector oneOf branches so they are mutually exclusive: make the url branch reject payloads containing proxyId, while preserving the proxyId branch’s existing auth restriction and required fields.
617-617: 🔒 Security & Privacy | 🟠 Major | ⚡ Quick winModel alternative OAuth2 scopes as alternatives.
These
ap:api_key:all:manageentries are in the same OAuth2 requirement as endpoint-specific scopes, so OpenAPI treats them as required together. To allow the global scope as a substitute, split the alternatives into separate security requirement objects, or align the runtime/documentation contract consistently.Suggested structure
- - OAuth2Security: - - endpoint-specific-scope - - artifact-manage-scope - - ap:api_key:all:manage + - OAuth2Security: + - endpoint-specific-scope + - OAuth2Security: + - artifact-manage-scope + - OAuth2Security: + - ap:api_key:all:manageAlso applies to lines 617, 666, 718, 1944, 1992, 2031, 2545, 2592, 2631, 3834, 3870, 3911, 4045, and 4471.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@platform-api/resources/openapi.yaml` at line 617, Update the affected OpenAPI security requirement definitions so ap:api_key:all:manage and each endpoint-specific OAuth2 scope are represented as separate alternative security requirement objects, not keys within the same requirement object. Apply this consistently to all listed occurrences while preserving the existing scopes and endpoint coverage.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In
`@portals/ai-workspace/src/pages/appShell/appShellPages/serviceProvider/ProviderMap/ProviderMapTab.tsx`:
- Around line 726-737: Update handleGatewayClick in
portals/ai-workspace/src/pages/appShell/appShellPages/serviceProvider/ProviderMap/ProviderMapTab.tsx
at lines 726-737 to show the existing proxy-navigation error snackbar before
returning when currentOrganization is unavailable, and add showSnackbar to its
dependency list. Apply the same change to the gateway navigation handler in
portals/ai-workspace/src/pages/appShell/appShellPages/serviceProvider/ServiceProviderOverviewTab.tsx
at lines 650-661.
---
Outside diff comments:
In `@platform-api/resources/openapi.yaml`:
- Around line 8399-8403: Update the MCP selector oneOf branches so they are
mutually exclusive: make the url branch reject payloads containing proxyId,
while preserving the proxyId branch’s existing auth restriction and required
fields.
- Line 617: Update the affected OpenAPI security requirement definitions so
ap:api_key:all:manage and each endpoint-specific OAuth2 scope are represented as
separate alternative security requirement objects, not keys within the same
requirement object. Apply this consistently to all listed occurrences while
preserving the existing scopes and endpoint coverage.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro Plus
Run ID: c8f47366-475d-42c3-bd93-d456d8588912
📒 Files selected for processing (29)
docs/rest-apis/platform-api/README.mddocs/rest-apis/platform-api/gateway-tokens.mddocs/rest-apis/platform-api/gateways.mddocs/rest-apis/platform-api/llm-provider-deployments.mddocs/rest-apis/platform-api/llm-providers.mddocs/rest-apis/platform-api/llm-proxies.mddocs/rest-apis/platform-api/llm-proxy-deployments.mddocs/rest-apis/platform-api/mcp-proxies.mddocs/rest-apis/platform-api/mcp-proxy-deployments.mddocs/rest-apis/platform-api/projects.mddocs/rest-apis/platform-api/rest-api-deployments.mddocs/rest-apis/platform-api/rest-apis.mddocs/rest-apis/platform-api/schemas.mdplatform-api/api/generated.goplatform-api/internal/repository/interfaces.goplatform-api/internal/repository/project.goplatform-api/internal/service/llm.goplatform-api/internal/service/llm_test.goplatform-api/internal/service/mcp.goplatform-api/internal/service/mcp_test.goplatform-api/internal/utils/guarded_http_client.goplatform-api/internal/utils/guarded_http_client_test.goplatform-api/internal/utils/openapi_spec_fetcher.goplatform-api/resources/openapi.yamlportals/ai-workspace/src/pages/appShell/appShellPages/quickStart/lllmStepBanner/LLLMStepBanner.tsxportals/ai-workspace/src/pages/appShell/appShellPages/serviceProvider/ProviderMap/ProviderMapTab.tsxportals/ai-workspace/src/pages/appShell/appShellPages/serviceProvider/ResourceDrawerCards.tsxportals/ai-workspace/src/pages/appShell/appShellPages/serviceProvider/ServiceProviderOverviewTab.tsxportals/ai-workspace/src/utils/projectRouting.ts
🚧 Files skipped from review as they are similar to previous changes (7)
- docs/rest-apis/platform-api/llm-proxy-deployments.md
- docs/rest-apis/platform-api/README.md
- docs/rest-apis/platform-api/mcp-proxies.md
- docs/rest-apis/platform-api/gateways.md
- docs/rest-apis/platform-api/rest-api-deployments.md
- docs/rest-apis/platform-api/rest-apis.md
- docs/rest-apis/platform-api/mcp-proxy-deployments.md
…viceProviderOverviewTab and ProviderMapTab components
|
@CodeRabbit review |
✅ Action performedReview finished.
|
|
@CodeRabbit approve |
✅ Action performedComments resolved and changes approved. |
pt 1
developerrole requirement for uploading TLS certificates in the certificate management documentation.Fixes three issues on the MCP proxy server-info fetch path: an under-constrained request
schema, silently-ignored request fields in the service layer, and an unguarded outbound
fetch (SSRF).
1. Request schema now enforces exactly one target
MCPServerInfoFetchRequesthad every field optional, so{},{url, proxyId}and{proxyId, auth}were all schema-valid. Added aoneOf— mirroring the existingUpstreamDefinitionpattern in the same spec — requiring exactly one ofurl/proxyId,with
not: required [auth]on theproxyIdbranch.Properties are unchanged, so
api/generated.goneeds no regeneration. Property descriptionswere also reworded to state the constraint explicitly, matching the
UpstreamDefinitionhouse style, and the generated REST API docs were refreshed via
make generate-apidocs(
docs/rest-apis/platform-api/schemas.md).2. Service layer rejects ambiguous requests instead of ignoring fields
MCPProxyService.FetchServerInfopreviously letproxyIdsilently win when both were sent,and only logged a warning before discarding a supplied
auth. It now returnsapperror.ValidationFailed— before any outbound call — for:urlandproxyIdpresentauthsent alongsideproxyId(the stored auth is authoritative in the refetch flow)3. Outbound MCP calls go through the SSRF-guarded dialer
The HEAD reachability probe (
CheckURLReachability) and every MCP JSON-RPC call(
initialize,notifications/initialized,tools/list,prompts/list,resources/list)used bare
http.Clients: no dial-time IP validation, redirects followed unchecked. Auser-supplied
urlcould therefore reach loopback, RFC 1918 or the cloud metadata endpoint.Added
utils.NewUpstreamFetchClient, built on a sharedguardedDialContextfactory that theOpenAPI spec fetcher's
ssrfSafeDialContextnow also uses:IP it just approved — closing the DNS-rebinding window
The address policy is deliberately different from the spec fetcher's. An OpenAPI spec URL
points at a vendor endpoint on the public internet, so that path keeps
isPublicIP. An MCPupstream is normally a service the operator deployed — a ClusterIP, a
*.svc.cluster.localname, a localhost port in development — so
isAllowedUpstreamIPpermits private, ULA, CGNATand loopback addresses and refuses only what is never a legitimate upstream: link-local
(
169.254.0.0/16incl. the metadata endpoint,fe80::/10), unspecified, multicast andbroadcast. In-cluster MCP proxies keep working unchanged.
ValidateURLstill gates scheme and credentials up front.4.
UpstreamDefinitionvalidators match the spec'soneOfFound while mirroring
UpstreamDefinition'soneOfin section 1: the spec has declared"exactly one of
url/ref" all along, but the Go validators only enforced "at least one",so
{url, ref}together was accepted and a whitespace-only string counted as populated.internal/handler/api.go—isEmptyUpstreamDefinitionnow trims whitespace (via newhasUpstreamURL/hasUpstreamRefhelpers), and a newvalidateUpstreamDefinitionsrejectsmain or sandbox carrying both fields. Called from
CreateAPIandUpdateAPIafter theexisting "at least one endpoint" check, so the both-blank message is unchanged.
internal/service/llm.go—validateUpstreamdelegates to a newvalidateUpstreamDefinition, which requires exactly one non-blank field (hasUrl == hasRefrejects both-blank and both-set alike). Scope stays main-only, as before.
internal/service/api.go—APIService.isEmptyUpstreamDefinitiontrims whitespace, matchingthe handler.
The spec itself already expressed the constraint correctly and needed no edit.
Behavioural changes
This section tightens validation, so some previously-accepted requests are now rejected:
urlandreftogether is now a400. Previously accepted onPOST/PUT /rest-apisand on LLM provider create/update, with one field implicitly winning downstream. Now
apperror.ValidationFailed— "The upstream main must specify either a url or a ref, notboth." (
sandboxlikewise on the REST API path; LLM validation stays main-only, as before.){"url": " "}used to satisfy the"at least one upstream endpoint" check and persist as a blank endpoint; it now falls through
to the existing "At least one upstream endpoint (main or sandbox) is required" error.
Affects the REST API handler and
APIService;validateUpstreamalready trimmed.must specify either a url or a ref."; it now returns the "…, not both." wording. Same status
and error code — only the string differs, and nothing in the test suites asserts on it.
Unaffected: valid single-field definitions, sandbox-only definitions, and an omitted sandbox all
behave exactly as before. No internal code path can trip the new check either —
mapUpstreamModelToAPIandupstreamEndpointToAPIcopy whichever ofURL/Refis non-empty,and both
validateUpstreamcall sites read the request body rather than stored state.Residual risk: if a record was already persisted with both
URLandRefset — possible,since nothing rejected it before — a client that GETs it and PUTs it back unchanged now gets a
400. The datastore has not been checked for such rows; a query over the upstream columns wouldconfirm whether this is hypothetical or needs a migration/cleanup.
Residual risk (deliberate)
Allowing private upstreams means an authenticated caller holding
ap:mcp_proxy:readcan pointurlat an internal address and learn coarse facts from the response: reachable vs not (400"unreachable"), and 401 vs other (the upstream 401 is surfaced as a 401). That is a limited
internal-reachability oracle, not data exfiltration — response bodies and upstream statuses are
confined to internal logs by the
apperrorcatalog, and the metadata endpoint stays blocked.It is also inherent to the feature: an MCP proxy exists to forward traffic to an internal
backend, so a caller entitled to create one can already cause the gateway to reach it. Worth a
conscious ack rather than a silent assumption.
pt 2
Breaking Changes
This PR changes behaviour that existing clients may depend on. The two items in this section are breaks; additive changes are listed separately below, and doc/spec wording updates are omitted.
1.
projectIdin LLM Proxy and MCP Proxy responses is now a project handle, not a UUIDAffected responses
LLMProxyGET/POST/PUT /llm-proxies/{proxyId}and equivalentsLLMProxyListItemGET /llm-proxies,GET /llm-providers/{providerId}/llm-proxiesMCPProxyGET/POST/PUT /mcp-proxies/{id}and equivalentsMCPProxyListItemGET /mcp-proxies,GET /projects/{projectId}/mcp-proxiesBefore
{ "projectId": "550e8400-e29b-41d4-a716-446655440000" }After
{ "projectId": "default-project" }Why: every other id-shaped field in this API is a handle, and requests already identify a project by handle (
Create,List,ListByProject). A client receiving a UUID had no way to resolve it back to a project, so the response value could not be fed into any other call.Impact / migration
projectIdas a UUID must switch to the handle. A previously persisted UUID will no longer match the value returned by these endpoints.projectIdstraight into a project-scoped request now work correctly (this was previously broken).projectIdis now constrained to^[a-z0-9-]+$, length 3–63 — a UUID no longer satisfies the documented contract.Implemented via
LLMProxyService.resolveProjectHandle/MCPProxyService.resolveProjectHandle, with a per-request memo so list endpoints don't re-query the same project per item.2. Quick Start — the LLM step no longer completes on a non-
DEPLOYEDdeploymentComponent:
LLLMStepBanner.tsx(AI Workspace Quick Start)Before: the step was marked complete when any deployment record existed (
list.length > 0) — includingDEPLOYING,UNDEPLOYED, andFAILED.After: the step is complete only when at least one deployment has
status === 'DEPLOYED'.Impact: users whose deploy failed or is still in progress will now see the Quick Start LLM step as incomplete where it previously showed as done. This is the intended state, but it is a visible regression in "progress" for anyone in that situation.
Additive Changes (not breaking)
Proxy card navigation now explains itself instead of failing silently
Components:
ProviderMapTab.tsx,ServiceProviderOverviewTab.tsx,ResourceDrawerCards.tsx, newbuildProxyPathhelper inutils/projectRouting.tsBefore: clicking a proxy card whose
projectIddid not match any project in the current organization logged an error and did nothing — the click was silently swallowed with no user-visible feedback.After: the navigation outcome is unchanged (the user stays on the page — a proxy lives inside a project, so there is no correct org-level route to send them to), but an error toast now states why.
buildProxyPathreturnsnullwhen the project can't be resolved, and both callers surface that rather than navigating.Permissions: the click is gated on
ap:llm_proxy:read(SCOPES.LLM_PROXY_READ), mirroring the gateway-card gating below. Without the scope the card renders non-interactive rather than navigating to a view whose fetch would fail.ResourceDrawerCards'sonProxyClickbecame optional for this.Note: the resolution path only behaves correctly in combination with change 1 — matching a proxy's project by handle requires
projectIdto be a handle. Before change 1, a UUIDprojectIdnever matched, so every such click hit the failure branch.Gateway cards in the provider view are now clickable
Components:
ProviderMapTab.tsx(GatewayCard),ResourceDrawerCards.tsx,ServiceProviderOverviewTab.tsx, newbuildGatewayPathhelper inutils/projectRouting.tsGateway cards — in both the provider map's gateway column and the "Deployed Gateways" drawer — previously rendered as static, non-interactive cards. They now navigate to the gateway detail view, matching the behaviour proxy cards already had in the same views.
GatewayCardtakes an optionalonClickand, when present, applies the same affordancesProxyCardalready used:role="button",tabIndex={0}, Enter/Space keyboard activation, and a pointer cursor.gateways/view/:gatewayNameroute (GatewaysLayout.tsx). No new route was added.ViewGatewayresolves that param viagw.id === gatewayName, i.e. the gateway handle — the same targetGatewaysListandAddGatewayalready navigate to.buildGatewayPathalways produces an org-level path (/organizations/{orgHandle}/gateways/view/{gatewayId}); there is no project to resolve, unlikebuildProxyPath.Permissions: the click is gated on
ap:gateway:read(SCOPES.GATEWAY_READ). Without the scope the card renders exactly as before — non-interactive — rather than navigating to a view whose fetch would then fail.Impact: purely additive — no previously-working interaction changes. Nothing outside the provider view is affected;
LLMProxiesSummaryCardSection'sonProxyClick(a different, single-argument signature) is untouched.Not a change in this PR
The
gatewayIdspec updates (path params on LLM provider/proxy undeploy & restore, and thegatewayIdQdeployment filter) now document a handle rather than a UUID. This is the spec catching up to behaviour already shipped inresolveGatewayFilterandtoAPIDeploymentResponse— no runtime behaviour changes here.Purpose