Fix streaming auth locally (#2357)

This commit is contained in:
Chris Weaver
2024-09-08 14:01:26 -07:00
committed by GitHub
parent ace041415a
commit be4b6189d2
2 changed files with 116 additions and 41 deletions

View File

@@ -0,0 +1,116 @@
import { INTERNAL_URL } from "@/lib/constants";
import { NextRequest, NextResponse } from "next/server";
/* NextJS is annoying and makes use use a separate function for
each request type >:( */
export async function GET(
request: NextRequest,
{ params }: { params: { path: string[] } }
) {
return handleRequest(request, params.path);
}
export async function POST(
request: NextRequest,
{ params }: { params: { path: string[] } }
) {
return handleRequest(request, params.path);
}
export async function PUT(
request: NextRequest,
{ params }: { params: { path: string[] } }
) {
return handleRequest(request, params.path);
}
export async function PATCH(
request: NextRequest,
{ params }: { params: { path: string[] } }
) {
return handleRequest(request, params.path);
}
export async function DELETE(
request: NextRequest,
{ params }: { params: { path: string[] } }
) {
return handleRequest(request, params.path);
}
export async function HEAD(
request: NextRequest,
{ params }: { params: { path: string[] } }
) {
return handleRequest(request, params.path);
}
export async function OPTIONS(
request: NextRequest,
{ params }: { params: { path: string[] } }
) {
return handleRequest(request, params.path);
}
async function handleRequest(request: NextRequest, path: string[]) {
if (process.env.NODE_ENV !== "development") {
return NextResponse.json(
{
message:
"This API is only available in development mode. In production, something else (e.g. nginx) should handle this.",
},
{ status: 404 }
);
}
try {
const backendUrl = new URL(`${INTERNAL_URL}/${path.join("/")}`);
// Get the URL parameters from the request
const urlParams = new URLSearchParams(request.url.split("?")[1]);
// Append the URL parameters to the backend URL
urlParams.forEach((value, key) => {
backendUrl.searchParams.append(key, value);
});
const response = await fetch(backendUrl, {
method: request.method,
headers: request.headers,
body: request.body,
// @ts-ignore
duplex: "half",
});
// Check if the response is a stream
if (
response.headers.get("Transfer-Encoding") === "chunked" ||
response.headers.get("Content-Type")?.includes("stream")
) {
// If it's a stream, create a TransformStream to pass the data through
const { readable, writable } = new TransformStream();
response.body?.pipeTo(writable);
return new NextResponse(readable, {
status: response.status,
headers: response.headers,
});
} else {
return new NextResponse(response.body, {
status: response.status,
headers: response.headers,
});
}
} catch (error: unknown) {
console.error("Proxy error:", error);
return NextResponse.json(
{
message: "Proxy error",
error:
error instanceof Error ? error.message : "An unknown error occurred",
},
{ status: 500 }
);
}
}