UNPKG

one

Version:

One is a new React Framework that makes Vite serve both native and web.

127 lines (123 loc) 5.34 kB
import { join, resolve } from "node:path"; import FSExtra from "fs-extra"; import { isMatching, P } from "ts-pattern"; import { createApiServerlessFunction } from "./generate/createApiServerlessFunction"; import { createSsrServerlessFunction } from "./generate/createSsrServerlessFunction"; import { serverlessVercelPackageJson } from "./config/vc-package-base"; import { vercelBuildOutputConfigBase } from "./config/vc-build-output-config-base"; import { getPathFromRoute } from "./getPathFromRoute"; const { copy, ensureDir, existsSync, writeJSON } = FSExtra; async function moveAllFiles(src, dest) { try { await copy(src, dest, { overwrite: !0, errorOnExist: !1 }); } catch (err) { console.error("Error moving files:", err); } } const buildVercelOutputDirectory = async ({ apiOutput, buildInfoForWriting, clientDir, oneOptionsRoot, postBuildLogs }) => { const { routeToBuildInfo } = buildInfoForWriting; if (apiOutput) { const compiltedApiRoutes = (apiOutput?.output ?? []).filter( (o) => isMatching({ code: P.string, facadeModuleId: P.string }, o) ); for (const route of buildInfoForWriting.manifest.apiRoutes) { const compiledRoute = compiltedApiRoutes.find((compiled) => compiled.facadeModuleId.includes(route.file.replace("./", ""))); compiledRoute ? (postBuildLogs.push( `[one.build][vercel] generating serverless function for apiRoute ${route.page}` ), await createApiServerlessFunction(route, compiledRoute.code, oneOptionsRoot, postBuildLogs)) : console.warn(` \u{1F528}[one.build][vercel] apiRoute missing code compilation for`, route.file); } } const vercelOutputFunctionsDir = join(oneOptionsRoot, ".vercel/output/functions"); await ensureDir(vercelOutputFunctionsDir); for (const route of buildInfoForWriting.manifest.pageRoutes) switch (route.type) { case "ssr": { routeToBuildInfo[route.file] && (postBuildLogs.push( `[one.build][vercel] generate serverless function for ${route.page} with ${route.type}` ), await createSsrServerlessFunction( route, buildInfoForWriting, oneOptionsRoot, postBuildLogs )); break; } default: break; } const distMiddlewareDir = resolve(join(oneOptionsRoot, "dist", "middlewares")); if (existsSync(distMiddlewareDir)) { const vercelMiddlewareDir = resolve( join(oneOptionsRoot, ".vercel/output/functions/_middleware.func") ); await ensureDir(vercelMiddlewareDir), postBuildLogs.push( `[one.build][vercel] copying middlewares from ${distMiddlewareDir} to ${vercelMiddlewareDir}` ), await moveAllFiles(resolve(join(oneOptionsRoot, "dist", "middlewares")), vercelMiddlewareDir); const vercelMiddlewarePackageJsonFilePath = resolve(join(vercelMiddlewareDir, "index.js")); postBuildLogs.push( `[one.build][vercel] writing package.json to ${vercelMiddlewarePackageJsonFilePath}` ), await writeJSON(vercelMiddlewarePackageJsonFilePath, serverlessVercelPackageJson); const wrappedMiddlewareEntryPointFilename = "_wrapped_middleware.js", wrappedMiddlewareEntryPointPath = resolve( join(vercelMiddlewareDir, wrappedMiddlewareEntryPointFilename) ); await FSExtra.writeFile( wrappedMiddlewareEntryPointPath, ` import middlewareFunction from './_middleware.js' const next = (e) => { const t = new Headers(null == e ? void 0 : e.headers) t.set('x-middleware-next', '1') return new Response(null, { ...e, headers: t }) } const wrappedMiddlewareFunction = (request, event) => { return middlewareFunction({ request, event, next }) } export { wrappedMiddlewareFunction as default } ` ); const middlewareVercelConfigFilePath = resolve(join(vercelMiddlewareDir, ".vc-config.json")); postBuildLogs.push( `[one.build][vercel] writing .vc-config.json to ${middlewareVercelConfigFilePath}` ), await writeJSON(middlewareVercelConfigFilePath, { runtime: "edge", // Seems that middlewares only work with edge runtime entrypoint: wrappedMiddlewareEntryPointFilename }); } const vercelOutputStaticDir = resolve(join(oneOptionsRoot, ".vercel/output/static")); await ensureDir(vercelOutputStaticDir), postBuildLogs.push( `[one.build][vercel] copying static files from ${clientDir} to ${vercelOutputStaticDir}` ), await moveAllFiles(clientDir, vercelOutputStaticDir); const vercelConfigFilePath = resolve(join(oneOptionsRoot, ".vercel/output", "config.json")); await writeJSON(vercelConfigFilePath, { ...vercelBuildOutputConfigBase, routes: [ ...vercelBuildOutputConfigBase.routes, ...existsSync(distMiddlewareDir) ? [ { src: "/(.*)", middlewarePath: "_middleware", continue: !0 } ] : [], { handle: "rewrite" }, ...buildInfoForWriting.manifest.allRoutes.filter((r) => r.routeKeys && Object.keys(r.routeKeys).length > 0).map((r) => ({ src: r.namedRegex, dest: `${getPathFromRoute(r)}?${Object.entries(r.routeKeys).map(([k, v]) => `${k}=$${v}`).join("&")}` })) ] }), postBuildLogs.push(`[one.build] wrote vercel config to: ${vercelConfigFilePath}`); }; export { buildVercelOutputDirectory }; //# sourceMappingURL=buildVercelOutputDirectory.js.map