req()'s fetch init merged headers as { headers: {Content-Type, ...opts.headers}, ...opts }
— spreading ...opts LAST meant opts.headers (e.g. just Authorization) fully
overwrote the merged headers object, silently dropping Content-Type:
application/json from every call that also passed custom headers (i.e.
every authenticated request: addCredential, deleteCredential, createApiKey,
revokeApiKey, regenKey, all adminApi mutations).
Confirmed via direct reproduction against production: without Content-Type,
the request body arrived at the backend re-wrapped as a JSON string instead
of parsed as an object, producing "Input should be a valid dictionary or
object to extract fields from" on every POST/PATCH/DELETE with a body.
Reordered the spread so headers merge correctly.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
OdooMCP Cloud — Frontend
Vite + React + TypeScript dashboard for the multi-tenant Odoo MCP server.
Stack
- Vite 5 + React 18 + TypeScript
- react-router-dom v6 for client-side routing
- Tailwind CSS
- recharts for analytics charts
Development
npm install
npm run dev # http://localhost:3000
Requires the backend (Multi-Tenant-ODOO-MCP) running and .env pointing VITE_API_URL at it.
Build
npm run build # type-checks then builds to dist/
npm run preview # serve the production build locally
Structure
src/pages/— route components (landing, auth,dashboard/,admin/)src/components/landing/— marketing page sectionssrc/lib/api.ts— typed API client + localStorage session helperssrc/App.tsx— route tree
Description
Languages
TypeScript
98.9%
CSS
0.4%
JavaScript
0.4%
HTML
0.3%