|
| 1 | +import { NextRequest, NextResponse } from "next/server"; |
| 2 | +import type { Destination } from "./lib/destination"; |
| 3 | +import specsToDiff from "./lib/utils/specsToDiff"; |
| 4 | +import splitParts from "./lib/utils/splitParts"; |
| 5 | + |
| 6 | +enum STATUS_CODES { |
| 7 | + TEMPORARY_REDIRECT = 307, |
| 8 | + PERMANENT_REDIRECT = 308, |
| 9 | +} |
| 10 | + |
| 11 | +export const config = { |
| 12 | + matcher: "/((?!(?:about|api|_next|diff)(?:/.*)?|favicon.ico|icon.png).+)", |
| 13 | +}; |
| 14 | + |
| 15 | +export async function middleware(request: NextRequest) { |
| 16 | + console.log("[middleware]", request.nextUrl.pathname); |
| 17 | + |
| 18 | + const parts = request.nextUrl.pathname.split("/")[1]; |
| 19 | + |
| 20 | + const specsOrVersions = splitParts(parts); |
| 21 | + |
| 22 | + const url = new URL(`/api/-/destination`, request.url); |
| 23 | + specsOrVersions.forEach((spec) => url.searchParams.append("specs", spec)); |
| 24 | + |
| 25 | + console.log("[middleware] fetching", url.toString()); |
| 26 | + |
| 27 | + const { redirect: red, canonicalSpecs }: Destination = await fetch( |
| 28 | + url.toString(), |
| 29 | + ).then((res) => res.json()); |
| 30 | + |
| 31 | + if (red) { |
| 32 | + console.log("[middleware] redirecting to", red); |
| 33 | + return NextResponse.redirect( |
| 34 | + new URL(`/${specsToDiff(canonicalSpecs)}`, request.nextUrl), |
| 35 | + red === "permanent" |
| 36 | + ? STATUS_CODES.PERMANENT_REDIRECT |
| 37 | + : STATUS_CODES.TEMPORARY_REDIRECT, |
| 38 | + ); |
| 39 | + } else { |
| 40 | + const url = new URL( |
| 41 | + `/diff/${encodeURIComponent( |
| 42 | + canonicalSpecs[0], |
| 43 | + )}/${encodeURIComponent(canonicalSpecs[1])}`, |
| 44 | + request.url, |
| 45 | + ); |
| 46 | + console.log("[middleware] rewriting", url.toString()); |
| 47 | + return NextResponse.rewrite(url.toString()); |
| 48 | + } |
| 49 | + |
| 50 | + return NextResponse.next(); |
| 51 | +} |
0 commit comments