Summary
All 8 Edge Functions set Access-Control-Allow-Origin: *, permitting cross-origin requests from any domain. Because several functions are also unauthenticated (no JWT required) and return credentials (Mapbox token, GEE access token), wildcard CORS elevates those vulnerabilities from "server-side attack" to "browser-based cross-site exfiltration."
Evidence
All eight functions share the same CORS header block:
// supabase/functions/analyze-field/index.ts
// supabase/functions/crop-planning/index.ts
// supabase/functions/gee-analytics/index.ts
// supabase/functions/gee-ndvi-tiles/index.ts
// supabase/functions/get-mapbox-token/index.ts
// supabase/functions/keepalive/index.ts
// supabase/functions/ndvi-timeseries/index.ts
// supabase/functions/soil-data/index.ts
const corsHeaders = {
"Access-Control-Allow-Origin": "*",
"Access-Control-Allow-Headers": "authorization, x-client-info, apikey, content-type, ...",
};
The wildcard origin is returned on both preflight OPTIONS responses and all actual responses.
Why this matters
With Access-Control-Allow-Origin: * and verify_jwt = false:
- Any web page (malicious ad, XSS payload, third-party script) can call these endpoints from a user's browser and read the response.
- For
get-mapbox-token: any cross-origin page can fetch {"token":"..."} and exfiltrate the Mapbox key to an attacker's server.
- For
gee-ndvi-tiles: any cross-origin page can fetch {"tileUrl":"...", "token":"ya29..."} and exfiltrate the GEE OAuth token.
- For AI functions: any cross-origin page can trigger Lovable AI gateway calls using the owner's quota.
Note: wildcard CORS with credentials: 'include' is blocked by the browser spec, but these functions don't use cookies — they return tokens in response bodies, which wildcard CORS does not protect.
Root cause
Lovable's scaffold generates wildcard CORS headers for Edge Functions to simplify development and preview environments. This default was never tightened for production deployment.
Recommended fix
Restrict Access-Control-Allow-Origin to the production origin:
const ALLOWED_ORIGIN = Deno.env.get("ALLOWED_ORIGIN") ?? "https://your-production-domain.com";
const corsHeaders = {
"Access-Control-Allow-Origin": ALLOWED_ORIGIN,
"Access-Control-Allow-Headers": "authorization, x-client-info, apikey, content-type",
"Vary": "Origin",
};
For local development, set ALLOWED_ORIGIN=http://localhost:5173 in local Supabase config. For production, set ALLOWED_ORIGIN=https://<production-domain> in Supabase project secrets.
If multiple origins must be allowed (e.g., preview deployments), implement an allowlist:
const ALLOWED_ORIGINS = new Set([
"https://production.example.com",
"https://staging.example.com",
]);
const origin = req.headers.get("Origin") ?? "";
const corsOrigin = ALLOWED_ORIGINS.has(origin) ? origin : "null";
Acceptance criteria
Suggested labels
security, bug
Priority
P2
Severity
Medium in isolation; escalates the severity of the token exposure issues (P0) by enabling browser-based cross-origin exfiltration of API credentials.
Confidence
Confirmed — all 8 functions hardcode "Access-Control-Allow-Origin": "*".
Summary
All 8 Edge Functions set
Access-Control-Allow-Origin: *, permitting cross-origin requests from any domain. Because several functions are also unauthenticated (no JWT required) and return credentials (Mapbox token, GEE access token), wildcard CORS elevates those vulnerabilities from "server-side attack" to "browser-based cross-site exfiltration."Evidence
All eight functions share the same CORS header block:
The wildcard origin is returned on both preflight
OPTIONSresponses and all actual responses.Why this matters
With
Access-Control-Allow-Origin: *andverify_jwt = false:get-mapbox-token: any cross-origin page can fetch{"token":"..."}and exfiltrate the Mapbox key to an attacker's server.gee-ndvi-tiles: any cross-origin page can fetch{"tileUrl":"...", "token":"ya29..."}and exfiltrate the GEE OAuth token.Note: wildcard CORS with
credentials: 'include'is blocked by the browser spec, but these functions don't use cookies — they return tokens in response bodies, which wildcard CORS does not protect.Root cause
Lovable's scaffold generates wildcard CORS headers for Edge Functions to simplify development and preview environments. This default was never tightened for production deployment.
Recommended fix
Restrict
Access-Control-Allow-Originto the production origin:For local development, set
ALLOWED_ORIGIN=http://localhost:5173in local Supabase config. For production, setALLOWED_ORIGIN=https://<production-domain>in Supabase project secrets.If multiple origins must be allowed (e.g., preview deployments), implement an allowlist:
Acceptance criteria
Access-Control-Allow-Origin: *in productionVary: Originheader is set where dynamic origin reflection is usedSuggested labels
security, bug
Priority
P2
Severity
Medium in isolation; escalates the severity of the token exposure issues (P0) by enabling browser-based cross-origin exfiltration of API credentials.
Confidence
Confirmed — all 8 functions hardcode
"Access-Control-Allow-Origin": "*".