[Feature]: Publish an OpenAPI 3.0 spec + Swagger UI for the Flask ML API
Summary
The Node/Express backend already ships interactive API docs (backend/config/swagger.js, mounted in server.js). The Flask ML API — which owns ~20 routes (/predict, /bulk-predict, /feedback, /feedback/stats, /spam-insights, /importance, /analyze-email-header, /gmail/*, /outlook/*, /scan-emails, /imap/connect, /health, …) — has no machine-readable contract at all. Integrators (the Node gateway, the browser extension, the mobile app) have to read api.py to learn request/response shapes.
This proposes a hand-authored OpenAPI 3.0 document served at /openapi.json, plus a Swagger UI page at /docs.
Motivation / current state
grep for openapi/swagger returns only backend/config/swagger.js and server.js — i.e. Node only. Nothing describes the Python service.
- The
/predict response schema is rich and evolving (confidence, confidence_level, domain_analysis, url_risk, explanation, severity, translated), and the README is the only "spec" — it drifts from code easily.
Proposed solution & PR split
This is delivered as two standalone, independently-mergeable PRs, each substantial enough to stand on its own. PR-2 builds on PR-1 but PR-1 is fully functional and useful on its own, and PR-2 does not break anything if PR-1 is already merged.
PR 1/2 — OpenAPI spec + /openapi.json (Hard)
Serve a validated OpenAPI 3.0 document for the core routes.
| File |
Change |
backend/openapi_spec.py (new) |
build_spec() returning the OpenAPI dict: info, servers, security scheme (X-Internal-Secret), and paths/components for /predict, /feedback, /feedback/stats, /spam-insights, /importance, /analyze-email-header, /health |
backend/api.py |
/openapi.json route (added to PUBLIC_PATHS) |
backend/tests/test_openapi_spec.py (new) |
asserts openapi == "3.0.x", required paths present, each documented path is a real registered rule, components resolve |
README.md |
link to /openapi.json |
Standalone value: clients can generate typed SDKs / validate against the spec immediately. ~4 files, ~340 LOC.
PR 2/2 — Swagger UI at /docs + full route coverage (Hard)
| File |
Change |
backend/openapi_spec.py |
extend paths to email/imap/gmail/outlook/scan-emails/bulk-predict |
backend/api.py |
/docs route rendering Swagger UI (served from the CDN bundle, reading /openapi.json); add to PUBLIC_PATHS |
backend/tests/test_openapi_coverage.py (new) |
iterate app.url_map and assert every non-static rule appears in the spec (prevents future drift) |
README.md |
"API Reference (/docs)" section |
Standalone value: human-browsable docs + a CI guard that the spec never drifts from the routes. ~4 files, ~295 LOC. Depends on PR-1's openapi_spec.py (merge order 1 → 2), but does not modify or break any runtime behaviour introduced by PR-1.
Difficulty: Hard (each sub-PR)
Authoring an accurate OpenAPI document for a large, non-trivial response schema, wiring a UI, and adding a drift-guard test that reflects the live route table is real depth
[Feature]: Publish an OpenAPI 3.0 spec + Swagger UI for the Flask ML API
Summary
The Node/Express backend already ships interactive API docs (
backend/config/swagger.js, mounted inserver.js). The Flask ML API — which owns ~20 routes (/predict,/bulk-predict,/feedback,/feedback/stats,/spam-insights,/importance,/analyze-email-header,/gmail/*,/outlook/*,/scan-emails,/imap/connect,/health, …) — has no machine-readable contract at all. Integrators (the Node gateway, the browser extension, the mobile app) have to readapi.pyto learn request/response shapes.This proposes a hand-authored OpenAPI 3.0 document served at
/openapi.json, plus a Swagger UI page at/docs.Motivation / current state
grepforopenapi/swaggerreturns onlybackend/config/swagger.jsandserver.js— i.e. Node only. Nothing describes the Python service./predictresponse schema is rich and evolving (confidence,confidence_level,domain_analysis,url_risk,explanation,severity,translated), and the README is the only "spec" — it drifts from code easily.Proposed solution & PR split
This is delivered as two standalone, independently-mergeable PRs, each substantial enough to stand on its own. PR-2 builds on PR-1 but PR-1 is fully functional and useful on its own, and PR-2 does not break anything if PR-1 is already merged.
PR 1/2 — OpenAPI spec +
/openapi.json(Hard)Serve a validated OpenAPI 3.0 document for the core routes.
backend/openapi_spec.py(new)build_spec()returning the OpenAPI dict:info,servers, security scheme (X-Internal-Secret), and paths/components for/predict,/feedback,/feedback/stats,/spam-insights,/importance,/analyze-email-header,/healthbackend/api.py/openapi.jsonroute (added toPUBLIC_PATHS)backend/tests/test_openapi_spec.py(new)openapi == "3.0.x", required paths present, each documented path is a real registered rule, components resolveREADME.md/openapi.jsonStandalone value: clients can generate typed SDKs / validate against the spec immediately. ~4 files, ~340 LOC.
PR 2/2 — Swagger UI at
/docs+ full route coverage (Hard)backend/openapi_spec.pyscan-emails/bulk-predictbackend/api.py/docsroute rendering Swagger UI (served from the CDN bundle, reading/openapi.json); add toPUBLIC_PATHSbackend/tests/test_openapi_coverage.py(new)app.url_mapand assert every non-static rule appears in the spec (prevents future drift)README.md/docs)" sectionStandalone value: human-browsable docs + a CI guard that the spec never drifts from the routes. ~4 files, ~295 LOC. Depends on PR-1's
openapi_spec.py(merge order 1 → 2), but does not modify or break any runtime behaviour introduced by PR-1.Difficulty: Hard (each sub-PR)
Authoring an accurate OpenAPI document for a large, non-trivial response schema, wiring a UI, and adding a drift-guard test that reflects the live route table is real depth