winterspec
Version:
Write Winter-CG compatible routes with filesystem routing and tons of features
46 lines (45 loc) • 2.33 kB
JavaScript
import { createWinterSpecRequest, } from "./web-handler.js";
import { wrapMiddlewares } from "../create-with-winter-spec.js";
import { getDefaultContext } from "./context.js";
export function makeRequestAgainstWinterSpec(winterSpec, options = {}) {
return async (request) => {
const { routeMatcher, routeMapWithHandlers, handle404 = () => new Response("Not found", {
status: 404,
}), } = winterSpec;
const { removePathnamePrefix, automaticallyRemovePathnamePrefix = true } = options;
let pathname = new URL(request.url).pathname;
if (removePathnamePrefix) {
if (automaticallyRemovePathnamePrefix) {
throw new Error("automaticallyRemovePathnamePrefix and removePathnamePrefix cannot both be specified");
}
pathname = pathname.replace(removePathnamePrefix, "");
}
else {
if (request.routeParams) {
// These are the route params of the parent route hosting the WinterSpec service
const routeParams = request
.routeParams;
// If the child service is hosted at /foo/[...path], we want to find the [...path] parameter
const wildcardRouteParameters = Object.values(routeParams).filter((p) => Array.isArray(p));
if (wildcardRouteParameters.length === 0) {
throw new Error("No wildcard route parameters found");
}
if (wildcardRouteParameters.length > 1) {
throw new Error("Only one wildcard route parameter is supported");
}
const wildcardRouteParameter = wildcardRouteParameters[0];
pathname = `/${wildcardRouteParameter.join("/")}`;
}
}
const { matchedRoute, routeParams } = routeMatcher(pathname) ?? {};
let routeFn = matchedRoute && routeMapWithHandlers[matchedRoute];
const winterSpecRequest = createWinterSpecRequest(request, {
winterSpec,
routeParams: routeParams ?? {},
});
if (!routeFn) {
return await handle404(winterSpecRequest, getDefaultContext());
}
return wrapMiddlewares(options.middleware ?? [], routeFn, winterSpecRequest, getDefaultContext());
};
}