Skip to content

Commit ceb11d9

Browse files
committed
made changes based on the comments made by reviewrs
Signed-off-by: Jitesh Nair <jiteshnair@ibm.com>
1 parent 63576ba commit ceb11d9

4 files changed

Lines changed: 126 additions & 137 deletions

File tree

.secrets.baseline

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
"files": "(?x)( package-lock\\.json$ |Cargo\\.lock$ |uv\\.lock$ |go\\.sum$ |mcpgateway/sri_hashes\\.json$ )|^.secrets.baseline$",
44
"lines": null
55
},
6-
"generated_at": "2026-06-16T17:54:16Z",
6+
"generated_at": "2026-06-17T14:01:31Z",
77
"plugins_used": [
88
{
99
"name": "AWSKeyDetector"

mcpgateway/main.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12054,7 +12054,6 @@ async def cleanup_import_statuses(max_age_hours: int = 24, user=Depends(get_curr
1205412054
app.include_router(tag_router)
1205512055
app.include_router(export_import_router)
1205612056
app.include_router(openapi_schema_router)
12057-
logger.info("OpenAPI schema generation router included")
1205812057

1205912058
# Compliance report router (admin API)
1206012059
if settings.mcpgateway_admin_api_enabled:
@@ -12295,8 +12294,9 @@ async def cleanup_import_statuses(max_age_hours: int = 24, user=Depends(get_curr
1229512294
# Lazy import: mcpgateway.admin is a large module (~19k lines, ~120ms cold).
1229612295
# Only load it when the admin API is actually mounted.
1229712296
# First-Party
12298-
from mcpgateway.admin import admin_router, enforce_admin_csrf, validate_section_permissions # pylint: disable=import-outside-toplevel
12297+
from mcpgateway.admin import admin_router, enforce_admin_csrf, set_logging_service, validate_section_permissions # pylint: disable=import-outside-toplevel
1229912298

12299+
set_logging_service(logging_service)
1230012300
app.include_router(admin_router) # Admin routes imported from admin.py
1230112301

1230212302
# Validate section-to-permission mapping consistency at startup

mcpgateway/routers/openapi_schema_router.py

Lines changed: 18 additions & 53 deletions
Original file line numberDiff line numberDiff line change
@@ -16,12 +16,12 @@
1616
import urllib.parse
1717

1818
# Third-Party
19-
from fastapi import APIRouter, Depends, Request
19+
from fastapi import APIRouter, Body, Depends
2020
from fastapi.responses import JSONResponse
2121
import httpx
22+
from pydantic import BaseModel, Field
2223

2324
# First-Party
24-
from mcpgateway.admin import _read_request_json
2525
from mcpgateway.common.validators import SecurityValidator
2626
from mcpgateway.middleware.rbac import get_current_user_with_permissions, require_permission
2727
from mcpgateway.services.openapi_service import fetch_and_extract_schemas
@@ -32,10 +32,18 @@
3232
logger = logging.getLogger(__name__)
3333

3434

35-
@router.post("/generate-schema-from-openapi")
35+
class GenerateSchemaRequest(BaseModel):
36+
"""Request body for generating schemas from OpenAPI specification."""
37+
38+
url: str = Field(..., description="The tool URL (e.g., http://localhost:8100/calculate)")
39+
request_type: str = Field("GET", description="HTTP method (GET, POST, etc.)")
40+
openapi_url: str = Field("", description="Direct OpenAPI spec URL (optional, auto-discovered if empty)")
41+
42+
43+
@router.post("/generate-schemas-from-openapi")
3644
@require_permission("tools.create", allow_admin_bypass=False)
37-
async def generate_schema_from_openapi(
38-
request: Request,
45+
async def generate_schemas_from_openapi(
46+
body: GenerateSchemaRequest = Body(...),
3947
_user=Depends(get_current_user_with_permissions),
4048
) -> JSONResponse:
4149
"""
@@ -45,65 +53,24 @@ async def generate_schema_from_openapi(
4553
admin UI access. It delegates to the same service logic as the admin
4654
endpoint but without CSRF protection.
4755
48-
Expects JSON body with:
49-
- url: The tool URL (e.g., http://localhost:8100/calculate)
50-
- request_type: HTTP method (GET, POST, etc.) - defaults to GET
51-
- openapi_url: (optional) Direct OpenAPI spec URL
52-
5356
Args:
54-
request: FastAPI Request object containing JSON body
57+
body: Request body with url, request_type, and openapi_url
5558
_user: Authenticated user from RBAC dependency
5659
5760
Returns:
5861
JSONResponse with generated schemas or error message.
5962
"""
60-
# Read and validate request body
61-
try:
62-
body = await _read_request_json(request)
63-
except Exception:
64-
return ORJSONResponse(
65-
content={"message": "Invalid JSON in request body", "success": False},
66-
status_code=400,
67-
)
68-
69-
if not isinstance(body, dict):
70-
return ORJSONResponse(
71-
content={"message": "Request body must be a JSON object", "success": False},
72-
status_code=400,
73-
)
74-
75-
# Extract and validate fields
76-
tool_url = body.get("url", "")
77-
request_type = body.get("request_type", "GET")
78-
openapi_url = body.get("openapi_url", "")
79-
80-
if not isinstance(tool_url, str) or not isinstance(request_type, str) or not isinstance(openapi_url, str):
81-
return ORJSONResponse(
82-
content={"message": "'url', 'request_type', and 'openapi_url' must be strings", "success": False},
83-
status_code=400,
84-
)
85-
86-
tool_url = tool_url.strip()
87-
request_type = request_type.strip()
88-
openapi_url = openapi_url.strip()
89-
90-
if not tool_url:
91-
return ORJSONResponse(
92-
content={"message": "'url' is required to identify the API path and base URL", "success": False},
93-
status_code=400,
94-
)
95-
9663
# Security validation
9764
try:
98-
SecurityValidator.validate_url(tool_url, "Tool URL")
65+
SecurityValidator.validate_url(body.url, "Tool URL")
9966
except ValueError as e:
10067
return ORJSONResponse(
10168
content={"message": str(e), "success": False},
10269
status_code=400,
10370
)
10471

10572
# Parse URL to extract base and path
106-
parsed = urllib.parse.urlparse(tool_url)
73+
parsed = urllib.parse.urlparse(body.url)
10774
base_url = f"{parsed.scheme}://{parsed.netloc}"
10875
tool_path = parsed.path
10976

@@ -112,8 +79,8 @@ async def generate_schema_from_openapi(
11279
input_schema, output_schema, spec_url = await fetch_and_extract_schemas(
11380
base_url=base_url,
11481
path=tool_path,
115-
method=request_type,
116-
openapi_url=openapi_url,
82+
method=body.request_type,
83+
openapi_url=body.openapi_url or "",
11784
timeout=10.0,
11885
)
11986
except ValueError as e:
@@ -155,5 +122,3 @@ async def generate_schema_from_openapi(
155122
},
156123
status_code=200,
157124
)
158-
159-
# Made with Bob

0 commit comments

Comments
 (0)