How OmniRoute Handles CORS Requests: A Complete Technical Guide
OmniRoute implements a centralized, declarative CORS strategy using static headers in src/shared/utils/cors.ts and dynamic origin resolution in src/server/cors/origins.ts, with environment-driven configuration for flexible cross-origin policies.
Every modern API needs robust Cross-Origin Resource Sharing (CORS) handling to serve browser-based clients securely. The OmniRoute repository takes a configuration-first approach that keeps CORS logic maintainable across dozens of API routes. This guide breaks down exactly how the system resolves origins, sets headers, and handles pre-flight requests.
The Core CORS Architecture
OmniRoute separates CORS concerns into two modules: static header definitions and dynamic origin resolution. This separation lets developers change cross-origin policies without touching individual route files.
Static CORS Headers (src/shared/utils/cors.ts)
The foundation is the CORS_HEADERS object exported from src/shared/utils/cors.ts. This constant defines the mandatory headers for every API response:
// src/shared/utils/cors.ts
export const CORS_HEADERS = {
"Access-Control-Allow-Methods": "OPTIONS, GET, POST, PUT, DELETE, PATCH",
"Access-Control-Allow-Headers":
"Authorization, Content-Type, Accept, X-Omni-Request-ID, X-Omni-Client",
// Access-Control-Allow-Origin is injected at request time
};
Routes compose these headers into response-specific variants. For JSON endpoints, the code spreads CORS_HEADERS and adds the content type:
const JSON_HEADERS = { ...CORS_HEADERS, "Content-Type": "application/json" };
Pre-Flight Request Handling
The handleCorsOptions() helper in the same file standardizes OPTIONS request responses. It returns a 204 No Content status with the complete CORS header set:
// src/shared/utils/cors.ts
export function handleCorsOptions(): Response {
return new Response(null, { status: 204, headers: CORS_HEADERS });
}
Every public API route imports this function. For example, src/app/api/v1/route.ts delegates its OPTIONS handler directly to this utility.
Dynamic Origin Resolution
Static headers cannot know the requesting origin at build time. OmniRoute solves this through src/server/cors/origins.ts, which computes Access-Control-Allow-Origin at runtime.
Environment-Driven Configuration
Three environment variables control origin behavior:
CORS_ALLOW_ALL— When truthy, echoes back anyOriginheader from the incoming request (mirror mode)CORS_ALLOWED_ORIGINS— Comma-separated whitelist of explicit allowed originsCORS_ORIGIN— Legacy single-origin variable maintained for backward compatibility
The Origin Resolution Logic
The resolveOrigin() function inspects the request's Origin header and returns the permitted value:
// src/server/cors/origins.ts (conceptual)
function resolveOrigin(request: Request): string {
const requestOrigin = request.headers.get("Origin");
if (process.env.CORS_ALLOW_ALL) {
return requestOrigin ?? "*";
}
const allowed = process.env.CORS_ALLOWED_ORIGINS?.split(",") ?? [];
if (allowed.includes(requestOrigin)) {
return requestOrigin;
}
// Fallback to CORS_ORIGIN or deny
return process.env.CORS_ORIGIN ?? "";
}
The module exports STATIC_CORS_HEADERS as a frozen, immutable object combining the base headers with the resolved origin:
export const STATIC_CORS_HEADERS: Readonly<Record<string, string>> = Object.freeze({
...CORS_HEADERS,
"Access-Control-Allow-Origin": resolveOrigin(request),
});
This freeze prevents accidental mutation across requests.
CORS Integration in Route Handlers
OmniRoute's pattern ensures every response carries correct CORS headers, including error responses. Here's how different route types implement the pattern.
Standard JSON Endpoints
// src/app/api/v1/relay/chat/completions/route.ts
import { CORS_HEADERS, handleCorsOptions } from "@/shared/utils/cors";
export async function POST(req: Request) {
const completion = await generateCompletion(req);
return new Response(JSON.stringify(completion), {
status: 200,
headers: { ...CORS_HEADERS, "Content-Type": "application/json" },
});
}
export async function OPTIONS() {
return handleCorsOptions();
}
Middleware Integration
The requireJsonContentType middleware in src/shared/middleware/requireJsonContentType.ts merges CORS_HEADERS into its error responses. This guarantees CORS compliance even when requests fail validation:
return new Response(JSON.stringify({ error: "Content-Type required" }), {
status: 415,
headers: CORS_HEADERS,
});
CORS Testing Strategy
OmniRoute validates CORS behavior through layered testing that prevents regressions as routes evolve.
Unit Tests: Origin Resolution
tests/unit/cors/origins.test.ts exercises the core logic:
- Allow-all mode: Verifies that
CORS_ALLOW_ALL=truemirrors any incoming origin - Whitelist parsing: Confirms comma-separated origins are correctly split and matched
- Immutable headers: Asserts that
Object.freeze()prevents accidental mutation - Legacy fallback: Ensures
CORS_ORIGINworks when other variables are unset
Integration Tests: End-to-End Validation
tests/integration/proxy-pipeline.test.ts and route-specific OPTIONS tests verify that:
- Every public endpoint responds to pre-flight requests
- Actual responses include matching CORS headers
- Error responses maintain CORS compliance
Configuration Examples
Development: Allow All Origins
CORS_ALLOW_ALL=true
This echoes the request's Origin header back, enabling local development with any frontend port.
Production: Explicit Whitelist
CORS_ALLOWED_ORIGINS=https://app.example.com,https://admin.example.com
Only the two specified origins receive Access-Control-Allow-Origin responses. Requests from unauthorized origins get no CORS headers (browser blocks them).
Legacy Compatibility
CORS_ORIGIN=https://legacy.example.com
Supported for existing deployments migrating to newer OmniRoute versions.
Summary
- Static headers in
src/shared/utils/cors.tsprovide the canonicalAccess-Control-Allow-MethodsandAccess-Control-Allow-Headersvalues used across all routes - Dynamic origin resolution in
src/server/cors/origins.tscomputesAccess-Control-Allow-Originfrom environment variables at request time - Pre-flight standardization through
handleCorsOptions()ensures uniform 204 responses for every OPTIONS request - Immutable header objects prevent accidental cross-request pollution
- Comprehensive test coverage in
tests/unit/cors/andtests/integration/validates policy enforcement
Frequently Asked Questions
How do I enable CORS for all origins in OmniRoute?
Set CORS_ALLOW_ALL=true in your environment. According to the OmniRoute source code, this triggers mirror-mode behavior in src/server/cors/origins.ts where the server echoes back whatever Origin header the browser sends. This is ideal for development but should be avoided in production.
Why does OmniRoute use a frozen headers object?
The Object.freeze() call on STATIC_CORS_HEADERS prevents accidental mutation. In src/server/cors/origins.ts, the frozen object ensures that one request's origin resolution cannot leak into subsequent requests—a critical safety measure for multi-tenant API servers.
Where are CORS headers actually applied to responses?
Every public route file imports from src/shared/utils/cors.ts. For example, src/app/api/v1/vscode/raw/[token]/route.ts returns handleCorsOptions() for OPTIONS requests, while POST handlers spread CORS_HEADERS into their response init objects. Middleware like requireJsonContentType.ts also merges these headers into error responses.
What happens if no CORS environment variables are set?
Per the implementation in src/server/cors/origins.ts, the system falls back to an empty string for Access-Control-Allow-Origin when no origin matches and no legacy CORS_ORIGIN is configured. Browsers will reject cross-origin requests in this scenario, effectively defaulting to a same-origin-only policy.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →