File
Blob: src/worker/auth/origin.ts
| 1 | import type { AppContext } from "@/worker/routes/hono"; |
| 2 | |
| 3 | const SAFE_METHODS: ReadonlySet<string> = new Set(["GET", "HEAD", "OPTIONS"]); |
| 4 | |
| 5 | // Returns a 403 Response if a non-safe method lacks an Origin header that |
| 6 | // matches the request origin. SameSite=Lax already keeps cookies off most |
| 7 | // cross-site mutations; this is the explicit defense for cookie-mutating |
| 8 | // POST routes (sign-out, PAT mutations) without resorting to a custom CSRF |
| 9 | // header. Returns null when the request is allowed to proceed. |
| 10 | export function sameOriginViolation(c: AppContext): Response | null { |
| 11 | if (SAFE_METHODS.has(c.req.method)) return null; |
| 12 | const origin = c.req.header("origin"); |
| 13 | if (!origin) { |
| 14 | return new Response("Forbidden\n", { status: 403 }); |
| 15 | } |
| 16 | let originUrl: URL; |
| 17 | try { |
| 18 | originUrl = new URL(origin); |
| 19 | } catch { |
| 20 | return new Response("Forbidden\n", { status: 403 }); |
| 21 | } |
| 22 | if (originUrl.origin !== new URL(c.req.url).origin) { |
| 23 | return new Response("Forbidden\n", { status: 403 }); |
| 24 | } |
| 25 | return null; |
| 26 | } |