@tanstack/start-server-core 1.120.4-alpha.2 → 1.120.4-alpha.21

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (37) hide show
  1. package/dist/cjs/createStartHandler.cjs +26 -9
  2. package/dist/cjs/createStartHandler.cjs.map +1 -1
  3. package/dist/cjs/index.cjs +0 -3
  4. package/dist/cjs/index.cjs.map +1 -1
  5. package/dist/cjs/index.d.cts +0 -1
  6. package/dist/cjs/server-functions-handler.cjs +1 -10
  7. package/dist/cjs/server-functions-handler.cjs.map +1 -1
  8. package/dist/cjs/server-functions-handler.d.cts +0 -1
  9. package/dist/cjs/serverRoute.cjs.map +1 -1
  10. package/dist/cjs/serverRoute.d.cts +1 -1
  11. package/dist/cjs/ssr-server.cjs +3 -2
  12. package/dist/cjs/ssr-server.cjs.map +1 -1
  13. package/dist/esm/createStartHandler.js +27 -10
  14. package/dist/esm/createStartHandler.js.map +1 -1
  15. package/dist/esm/index.d.ts +0 -1
  16. package/dist/esm/index.js +0 -3
  17. package/dist/esm/index.js.map +1 -1
  18. package/dist/esm/server-functions-handler.d.ts +0 -1
  19. package/dist/esm/server-functions-handler.js +1 -10
  20. package/dist/esm/server-functions-handler.js.map +1 -1
  21. package/dist/esm/serverRoute.d.ts +1 -1
  22. package/dist/esm/serverRoute.js.map +1 -1
  23. package/dist/esm/ssr-server.js +3 -2
  24. package/dist/esm/ssr-server.js.map +1 -1
  25. package/package.json +3 -4
  26. package/src/createStartHandler.ts +31 -13
  27. package/src/index.tsx +0 -2
  28. package/src/server-functions-handler.ts +3 -16
  29. package/src/serverRoute.ts +1 -1
  30. package/src/ssr-server.ts +2 -0
  31. package/dist/cjs/undici.cjs +0 -14
  32. package/dist/cjs/undici.cjs.map +0 -1
  33. package/dist/cjs/undici.d.cts +0 -43
  34. package/dist/esm/undici.d.ts +0 -43
  35. package/dist/esm/undici.js +0 -14
  36. package/dist/esm/undici.js.map +0 -1
  37. package/src/undici.ts +0 -60
@@ -22,7 +22,6 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
22
22
  mod
23
23
  ));
24
24
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
25
- const path = require("node:path");
26
25
  const history = require("@tanstack/history");
27
26
  const startClientCore = require("@tanstack/start-client-core");
28
27
  const routerCore = require("@tanstack/router-core");
@@ -68,7 +67,12 @@ function createStartHandler({
68
67
  "tanstack/start-server-core: TSS_SERVER_FN_BASE must be defined in your environment for createStartHandler()"
69
68
  );
70
69
  }
71
- if (href.startsWith(path.join("/", process.env.TSS_SERVER_FN_BASE, "/"))) {
70
+ const serverFnBase = routerCore.joinPaths([
71
+ "/",
72
+ routerCore.trimPath(process.env.TSS_SERVER_FN_BASE),
73
+ "/"
74
+ ]);
75
+ if (href.startsWith(serverFnBase)) {
72
76
  return await serverFunctionsHandler.handleServerAction({ request });
73
77
  }
74
78
  const serverRouteTreeModule = await (async () => {
@@ -80,7 +84,7 @@ function createStartHandler({
80
84
  }
81
85
  })();
82
86
  if (serverRouteTreeModule) {
83
- const [matchedRoutes, response3] = await handleServerRoutes({
87
+ const [_matchedRoutes, response3] = await handleServerRoutes({
84
88
  routeTree: serverRouteTreeModule.routeTree,
85
89
  request
86
90
  });
@@ -122,6 +126,20 @@ function createStartHandler({
122
126
  }
123
127
  })();
124
128
  if (routerCore.isRedirect(response)) {
129
+ if (routerCore.isResolvedRedirect(response)) {
130
+ if (request.headers.get("x-tsr-redirect") === "manual") {
131
+ return startClientCore.json(
132
+ {
133
+ ...response.options,
134
+ isSerializedRedirect: true
135
+ },
136
+ {
137
+ headers: response.headers
138
+ }
139
+ );
140
+ }
141
+ return response;
142
+ }
125
143
  if (response.options.to && typeof response.options.to === "string" && !response.options.to.startsWith("/")) {
126
144
  throw new Error(
127
145
  `Server side redirects must use absolute paths via the 'href' or 'to' options. Received: ${JSON.stringify(response.options)}`
@@ -144,16 +162,12 @@ function createStartHandler({
144
162
  isSerializedRedirect: true
145
163
  },
146
164
  {
147
- headers: redirect.headers
165
+ headers: response.headers
148
166
  }
149
167
  );
150
168
  }
151
169
  return redirect;
152
170
  }
153
- response.headers.append(
154
- "Access-Control-Expose-Headers",
155
- routerCore.tsrRedirectHeaderKey
156
- );
157
171
  return response;
158
172
  });
159
173
  };
@@ -247,7 +261,10 @@ function handleCtxResult(result) {
247
261
  return result;
248
262
  }
249
263
  function isSpecialResponse(err) {
250
- return err instanceof Response || routerCore.isRedirect(err);
264
+ return isResponse(err) || routerCore.isRedirect(err);
265
+ }
266
+ function isResponse(response) {
267
+ return response instanceof Response;
251
268
  }
252
269
  exports.createStartHandler = createStartHandler;
253
270
  exports.getStartResponseHeaders = getStartResponseHeaders;
@@ -1 +1 @@
1
- {"version":3,"file":"createStartHandler.cjs","sources":["../../src/createStartHandler.ts"],"sourcesContent":["import path from 'node:path'\nimport { createMemoryHistory } from '@tanstack/history'\nimport {\n flattenMiddlewares,\n json,\n mergeHeaders,\n} from '@tanstack/start-client-core'\nimport {\n getMatchedRoutes,\n isRedirect,\n processRouteTree,\n rootRouteId,\n tsrRedirectHeaderKey,\n} from '@tanstack/router-core'\nimport { getResponseHeaders, requestHandler } from './h3'\nimport { attachRouterServerSsrUtils, dehydrateRouter } from './ssr-server'\nimport { getStartManifest } from './router-manifest'\nimport { handleServerAction } from './server-functions-handler'\nimport type { AnyServerRoute, AnyServerRouteWithTypes } from './serverRoute'\nimport type { RequestHandler } from './h3'\nimport type { AnyRouter } from '@tanstack/router-core'\nimport type { HandlerCallback } from './handlerCallback'\n\ntype TODO = any\n\nexport type CustomizeStartHandler<TRouter extends AnyRouter> = (\n cb: HandlerCallback<TRouter>,\n) => RequestHandler\n\nexport function getStartResponseHeaders(opts: { router: AnyRouter }) {\n let headers = mergeHeaders(\n getResponseHeaders(),\n {\n 'Content-Type': 'text/html; charset=UTF-8',\n },\n ...opts.router.state.matches.map((match) => {\n return match.headers\n }),\n )\n // Handle Redirects\n const { redirect } = opts.router.state\n\n if (redirect) {\n headers = mergeHeaders(headers, redirect.headers)\n }\n return headers\n}\n\nexport function createStartHandler<TRouter extends AnyRouter>({\n createRouter,\n}: {\n createRouter: () => TRouter\n}): CustomizeStartHandler<TRouter> {\n return (cb) => {\n return requestHandler(async ({ request }) => {\n const url = new URL(request.url)\n const href = url.href.replace(url.origin, '')\n\n // Create a history for the client-side router\n const history = createMemoryHistory({\n initialEntries: [href],\n })\n\n // Create the client-side router\n const router = createRouter()\n\n // Attach the server-side SSR utils to the client-side router\n attachRouterServerSsrUtils(router, getStartManifest())\n\n // Update the client-side router with the history and context\n router.update({\n history,\n })\n\n const response = await (async () => {\n try {\n if (!process.env.TSS_SERVER_FN_BASE) {\n throw new Error(\n 'tanstack/start-server-core: TSS_SERVER_FN_BASE must be defined in your environment for createStartHandler()',\n )\n }\n\n // First, let's attempt to handle server functions\n if (\n href.startsWith(path.join('/', process.env.TSS_SERVER_FN_BASE, '/'))\n ) {\n return await handleServerAction({ request })\n }\n\n // Then move on to attempting to load server routes\n const serverRouteTreeModule = await (async () => {\n try {\n // @ts-expect-error\n return (await import('tanstack:server-routes')) as {\n routeTree: AnyServerRoute\n }\n } catch (e) {\n console.log(e)\n return undefined\n }\n })()\n\n // If we have a server route tree, then we try matching to see if we have a\n // server route that matches the request.\n if (serverRouteTreeModule) {\n const [matchedRoutes, response] = await handleServerRoutes({\n routeTree: serverRouteTreeModule.routeTree,\n request,\n })\n\n if (response) return response\n }\n\n const requestAcceptHeader = request.headers.get('Accept') || '*/*'\n const splitRequestAcceptHeader = requestAcceptHeader.split(',')\n\n const supportedMimeTypes = ['*/*', 'text/html']\n const isRouterAcceptSupported = supportedMimeTypes.some((mimeType) =>\n splitRequestAcceptHeader.some((acceptedMimeType) =>\n acceptedMimeType.trim().startsWith(mimeType),\n ),\n )\n\n if (!isRouterAcceptSupported) {\n return json(\n {\n error: 'Only HTML requests are supported here',\n },\n {\n status: 500,\n },\n )\n }\n\n // If no Server Routes were found, so fallback to normal SSR matching using\n // the router\n\n await router.load()\n\n // If there was a redirect, skip rendering the page at all\n if (router.state.redirect) return router.state.redirect\n\n dehydrateRouter(router)\n\n const responseHeaders = getStartResponseHeaders({ router })\n const response = await cb({\n request,\n router,\n responseHeaders,\n })\n\n return response\n } catch (err) {\n if (err instanceof Response) {\n return err\n }\n\n throw err\n }\n })()\n\n if (isRedirect(response)) {\n if (\n response.options.to &&\n typeof response.options.to === 'string' &&\n !response.options.to.startsWith('/')\n ) {\n throw new Error(\n `Server side redirects must use absolute paths via the 'href' or 'to' options. Received: ${JSON.stringify(response.options)}`,\n )\n }\n\n if (\n ['params', 'search', 'hash'].some(\n (d) => typeof (response.options as any)[d] === 'function',\n )\n ) {\n throw new Error(\n `Server side redirects must use static search, params, and hash values and do not support functional values. Received functional values for: ${Object.keys(\n response.options,\n )\n .filter((d) => typeof (response.options as any)[d] === 'function')\n .map((d) => `\"${d}\"`)\n .join(', ')}`,\n )\n }\n\n const redirect = router.resolveRedirect(response)\n\n if (request.headers.get('x-tsr-redirect') === 'manual') {\n return json(\n {\n ...response.options,\n isSerializedRedirect: true,\n },\n {\n headers: redirect.headers,\n },\n )\n }\n\n return redirect\n }\n\n response.headers.append(\n 'Access-Control-Expose-Headers',\n tsrRedirectHeaderKey,\n )\n\n return response\n })\n }\n}\n\nasync function handleServerRoutes({\n routeTree,\n request,\n}: {\n routeTree: AnyServerRouteWithTypes\n request: Request\n}) {\n const { flatRoutes, routesById, routesByPath } = processRouteTree({\n routeTree,\n initRoute: (route, i) => {\n route.init({\n originalIndex: i,\n })\n },\n })\n\n const url = new URL(request.url)\n const pathname = url.pathname\n\n const history = createMemoryHistory({\n initialEntries: [pathname],\n })\n\n const { matchedRoutes, foundRoute, routeParams } =\n getMatchedRoutes<AnyServerRouteWithTypes>({\n pathname: history.location.pathname,\n basepath: '/',\n caseSensitive: true,\n routesByPath,\n routesById,\n flatRoutes,\n })\n\n let response: Response | undefined\n\n if (foundRoute && foundRoute.id !== rootRouteId) {\n // We've found a server route that matches the request, so we can call it.\n // TODO: Get the input type-signature correct\n // TODO: Perform the middlewares?\n // TODO: Error handling? What happens when its `throw redirect()` vs `throw new Error()`?\n\n const method = Object.keys(foundRoute.options.methods).find(\n (method) => method.toLowerCase() === request.method.toLowerCase(),\n )\n\n if (method) {\n const handler = foundRoute.options.methods[method]\n\n if (handler) {\n const middlewares = flattenMiddlewares(\n matchedRoutes.flatMap((r) => r.options.middleware).filter(Boolean),\n ).map((d) => d.options.server)\n\n middlewares.push(handlerToMiddleware(handler) as TODO)\n\n // TODO: This is starting to feel too much like a server function\n // Do generalize the existing middleware execution? Or do we need to\n // build a new middleware execution system for server routes?\n const ctx = await executeMiddleware(middlewares, {\n request,\n context: {},\n params: routeParams,\n pathname: history.location.pathname,\n })\n\n response = ctx.response\n }\n }\n }\n\n // We return the matched routes too so if\n // the app router happens to match the same path,\n // it can use any request middleware from server routes\n return [matchedRoutes, response] as const\n}\n\nfunction handlerToMiddleware(\n handler: AnyServerRouteWithTypes['options']['methods'][string],\n) {\n return async ({ next, ...rest }: TODO) => ({\n response: await handler(rest),\n })\n}\n\nfunction executeMiddleware(middlewares: TODO, ctx: TODO) {\n let index = -1\n\n const next = async (ctx: TODO) => {\n index++\n const middleware = middlewares[index]\n if (!middleware) return ctx\n\n const result = await middleware({\n ...ctx,\n // Allow the middleware to call the next middleware in the chain\n next: async (nextCtx: TODO) => {\n // Allow the caller to extend the context for the next middleware\n const nextResult = await next({ ...ctx, ...nextCtx })\n\n // Merge the result into the context\\\n return Object.assign(ctx, handleCtxResult(nextResult))\n },\n // Allow the middleware result to extend the return context\n }).catch((err: TODO) => {\n if (isSpecialResponse(err)) {\n return {\n response: err,\n }\n }\n\n throw err\n })\n\n // Merge the middleware result into the context, just in case it\n // returns a partial context\n return Object.assign(ctx, handleCtxResult(result))\n }\n\n return handleCtxResult(next(ctx))\n}\n\nfunction handleCtxResult(result: TODO) {\n if (isSpecialResponse(result)) {\n return {\n response: result,\n }\n }\n\n return result\n}\n\nfunction isSpecialResponse(err: TODO) {\n return err instanceof Response || isRedirect(err)\n}\n"],"names":["mergeHeaders","getResponseHeaders","requestHandler","history","createMemoryHistory","attachRouterServerSsrUtils","getStartManifest","handleServerAction","response","json","dehydrateRouter","isRedirect","tsrRedirectHeaderKey","processRouteTree","getMatchedRoutes","rootRouteId","method","flattenMiddlewares","ctx"],"mappings":"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"}
1
+ {"version":3,"file":"createStartHandler.cjs","sources":["../../src/createStartHandler.ts"],"sourcesContent":["import { createMemoryHistory } from '@tanstack/history'\nimport {\n flattenMiddlewares,\n json,\n mergeHeaders,\n} from '@tanstack/start-client-core'\nimport {\n getMatchedRoutes,\n isRedirect,\n isResolvedRedirect,\n joinPaths,\n processRouteTree,\n rootRouteId,\n trimPath,\n} from '@tanstack/router-core'\nimport { getResponseHeaders, requestHandler } from './h3'\nimport { attachRouterServerSsrUtils, dehydrateRouter } from './ssr-server'\nimport { getStartManifest } from './router-manifest'\nimport { handleServerAction } from './server-functions-handler'\nimport type { AnyServerRoute, AnyServerRouteWithTypes } from './serverRoute'\nimport type { RequestHandler } from './h3'\nimport type { AnyRouter } from '@tanstack/router-core'\nimport type { HandlerCallback } from './handlerCallback'\n\ntype TODO = any\n\nexport type CustomizeStartHandler<TRouter extends AnyRouter> = (\n cb: HandlerCallback<TRouter>,\n) => RequestHandler\n\nexport function getStartResponseHeaders(opts: { router: AnyRouter }) {\n let headers = mergeHeaders(\n getResponseHeaders(),\n {\n 'Content-Type': 'text/html; charset=UTF-8',\n },\n ...opts.router.state.matches.map((match) => {\n return match.headers\n }),\n )\n // Handle Redirects\n const { redirect } = opts.router.state\n\n if (redirect) {\n headers = mergeHeaders(headers, redirect.headers)\n }\n return headers\n}\n\nexport function createStartHandler<TRouter extends AnyRouter>({\n createRouter,\n}: {\n createRouter: () => TRouter\n}): CustomizeStartHandler<TRouter> {\n return (cb) => {\n return requestHandler(async ({ request }) => {\n const url = new URL(request.url)\n const href = url.href.replace(url.origin, '')\n\n // Create a history for the client-side router\n const history = createMemoryHistory({\n initialEntries: [href],\n })\n\n // Create the client-side router\n const router = createRouter()\n\n // Attach the server-side SSR utils to the client-side router\n attachRouterServerSsrUtils(router, getStartManifest())\n\n // Update the client-side router with the history and context\n router.update({\n history,\n })\n\n const response = await (async () => {\n try {\n if (!process.env.TSS_SERVER_FN_BASE) {\n throw new Error(\n 'tanstack/start-server-core: TSS_SERVER_FN_BASE must be defined in your environment for createStartHandler()',\n )\n }\n\n // First, let's attempt to handle server functions\n // Add trailing slash to sanitise user defined TSS_SERVER_FN_BASE\n const serverFnBase = joinPaths([\n '/',\n trimPath(process.env.TSS_SERVER_FN_BASE),\n '/',\n ])\n if (href.startsWith(serverFnBase)) {\n return await handleServerAction({ request })\n }\n\n // Then move on to attempting to load server routes\n const serverRouteTreeModule = await (async () => {\n try {\n // @ts-expect-error\n return (await import('tanstack:server-routes')) as {\n routeTree: AnyServerRoute\n }\n } catch (e) {\n console.log(e)\n return undefined\n }\n })()\n\n // If we have a server route tree, then we try matching to see if we have a\n // server route that matches the request.\n if (serverRouteTreeModule) {\n const [_matchedRoutes, response] = await handleServerRoutes({\n routeTree: serverRouteTreeModule.routeTree,\n request,\n })\n\n if (response) return response\n }\n\n const requestAcceptHeader = request.headers.get('Accept') || '*/*'\n const splitRequestAcceptHeader = requestAcceptHeader.split(',')\n\n const supportedMimeTypes = ['*/*', 'text/html']\n const isRouterAcceptSupported = supportedMimeTypes.some((mimeType) =>\n splitRequestAcceptHeader.some((acceptedMimeType) =>\n acceptedMimeType.trim().startsWith(mimeType),\n ),\n )\n\n if (!isRouterAcceptSupported) {\n return json(\n {\n error: 'Only HTML requests are supported here',\n },\n {\n status: 500,\n },\n )\n }\n\n // If no Server Routes were found, so fallback to normal SSR matching using\n // the router\n\n await router.load()\n\n // If there was a redirect, skip rendering the page at all\n if (router.state.redirect) return router.state.redirect\n\n dehydrateRouter(router)\n\n const responseHeaders = getStartResponseHeaders({ router })\n const response = await cb({\n request,\n router,\n responseHeaders,\n })\n\n return response\n } catch (err) {\n if (err instanceof Response) {\n return err\n }\n\n throw err\n }\n })()\n\n if (isRedirect(response)) {\n if (isResolvedRedirect(response)) {\n if (request.headers.get('x-tsr-redirect') === 'manual') {\n return json(\n {\n ...response.options,\n isSerializedRedirect: true,\n },\n {\n headers: response.headers,\n },\n )\n }\n return response\n }\n if (\n response.options.to &&\n typeof response.options.to === 'string' &&\n !response.options.to.startsWith('/')\n ) {\n throw new Error(\n `Server side redirects must use absolute paths via the 'href' or 'to' options. Received: ${JSON.stringify(response.options)}`,\n )\n }\n\n if (\n ['params', 'search', 'hash'].some(\n (d) => typeof (response.options as any)[d] === 'function',\n )\n ) {\n throw new Error(\n `Server side redirects must use static search, params, and hash values and do not support functional values. Received functional values for: ${Object.keys(\n response.options,\n )\n .filter((d) => typeof (response.options as any)[d] === 'function')\n .map((d) => `\"${d}\"`)\n .join(', ')}`,\n )\n }\n\n const redirect = router.resolveRedirect(response)\n\n if (request.headers.get('x-tsr-redirect') === 'manual') {\n return json(\n {\n ...response.options,\n isSerializedRedirect: true,\n },\n {\n headers: response.headers,\n },\n )\n }\n\n return redirect\n }\n\n return response\n })\n }\n}\n\nasync function handleServerRoutes({\n routeTree,\n request,\n}: {\n routeTree: AnyServerRouteWithTypes\n request: Request\n}) {\n const { flatRoutes, routesById, routesByPath } = processRouteTree({\n routeTree,\n initRoute: (route, i) => {\n route.init({\n originalIndex: i,\n })\n },\n })\n\n const url = new URL(request.url)\n const pathname = url.pathname\n\n const history = createMemoryHistory({\n initialEntries: [pathname],\n })\n\n const { matchedRoutes, foundRoute, routeParams } =\n getMatchedRoutes<AnyServerRouteWithTypes>({\n pathname: history.location.pathname,\n basepath: '/',\n caseSensitive: true,\n routesByPath,\n routesById,\n flatRoutes,\n })\n\n let response: Response | undefined\n\n if (foundRoute && foundRoute.id !== rootRouteId) {\n // We've found a server route that matches the request, so we can call it.\n // TODO: Get the input type-signature correct\n // TODO: Perform the middlewares?\n // TODO: Error handling? What happens when its `throw redirect()` vs `throw new Error()`?\n\n const method = Object.keys(foundRoute.options.methods).find(\n (method) => method.toLowerCase() === request.method.toLowerCase(),\n )\n\n if (method) {\n const handler = foundRoute.options.methods[method]\n\n if (handler) {\n const middlewares = flattenMiddlewares(\n matchedRoutes.flatMap((r) => r.options.middleware).filter(Boolean),\n ).map((d) => d.options.server)\n\n middlewares.push(handlerToMiddleware(handler) as TODO)\n\n // TODO: This is starting to feel too much like a server function\n // Do generalize the existing middleware execution? Or do we need to\n // build a new middleware execution system for server routes?\n const ctx = await executeMiddleware(middlewares, {\n request,\n context: {},\n params: routeParams,\n pathname: history.location.pathname,\n })\n\n response = ctx.response\n }\n }\n }\n\n // We return the matched routes too so if\n // the app router happens to match the same path,\n // it can use any request middleware from server routes\n return [matchedRoutes, response] as const\n}\n\nfunction handlerToMiddleware(\n handler: AnyServerRouteWithTypes['options']['methods'][string],\n) {\n return async ({ next, ...rest }: TODO) => ({\n response: await handler(rest),\n })\n}\n\nfunction executeMiddleware(middlewares: TODO, ctx: TODO) {\n let index = -1\n\n const next = async (ctx: TODO) => {\n index++\n const middleware = middlewares[index]\n if (!middleware) return ctx\n\n const result = await middleware({\n ...ctx,\n // Allow the middleware to call the next middleware in the chain\n next: async (nextCtx: TODO) => {\n // Allow the caller to extend the context for the next middleware\n const nextResult = await next({ ...ctx, ...nextCtx })\n\n // Merge the result into the context\\\n return Object.assign(ctx, handleCtxResult(nextResult))\n },\n // Allow the middleware result to extend the return context\n }).catch((err: TODO) => {\n if (isSpecialResponse(err)) {\n return {\n response: err,\n }\n }\n\n throw err\n })\n\n // Merge the middleware result into the context, just in case it\n // returns a partial context\n return Object.assign(ctx, handleCtxResult(result))\n }\n\n return handleCtxResult(next(ctx))\n}\n\nfunction handleCtxResult(result: TODO) {\n if (isSpecialResponse(result)) {\n return {\n response: result,\n }\n }\n\n return result\n}\n\nfunction isSpecialResponse(err: TODO) {\n return isResponse(err) || isRedirect(err)\n}\n\nfunction isResponse(response: Response): response is Response {\n return response instanceof Response\n}\n"],"names":["mergeHeaders","getResponseHeaders","requestHandler","history","createMemoryHistory","attachRouterServerSsrUtils","getStartManifest","joinPaths","trimPath","handleServerAction","response","json","dehydrateRouter","isRedirect","isResolvedRedirect","processRouteTree","getMatchedRoutes","rootRouteId","method","flattenMiddlewares","ctx"],"mappings":"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"}
@@ -8,7 +8,6 @@ const ssrServer = require("./ssr-server.cjs");
8
8
  const serverFunctionsHandler = require("./server-functions-handler.cjs");
9
9
  const h3 = require("./h3.cjs");
10
10
  const serverRoute = require("./serverRoute.cjs");
11
- const undici = require("./undici.cjs");
12
11
  const h3$1 = require("h3");
13
12
  exports.transformPipeableStreamWithRouter = transformStreamWithRouter.transformPipeableStreamWithRouter;
14
13
  exports.transformReadableStreamWithRouter = transformStreamWithRouter.transformReadableStreamWithRouter;
@@ -96,8 +95,6 @@ exports.useSession = h3.useSession;
96
95
  exports.writeEarlyHints = h3.writeEarlyHints;
97
96
  exports.createServerFileRoute = serverRoute.createServerFileRoute;
98
97
  exports.createServerRoute = serverRoute.createServerRoute;
99
- exports.__getAbsoluteUrl = undici.__getAbsoluteUrl;
100
- exports.__setGlobalOrigin = undici.__setGlobalOrigin;
101
98
  Object.defineProperty(exports, "H3Error", {
102
99
  enumerable: true,
103
100
  get: () => h3$1.H3Error
@@ -1 +1 @@
1
- {"version":3,"file":"index.cjs","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
1
+ {"version":3,"file":"index.cjs","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
@@ -9,4 +9,3 @@ export { handleServerAction } from './server-functions-handler.cjs';
9
9
  export * from './h3.cjs';
10
10
  export { createServerRoute, createServerFileRoute } from './serverRoute.cjs';
11
11
  export type { CreateServerFileRoute } from './serverRoute.cjs';
12
- export { __getAbsoluteUrl, __setGlobalOrigin } from './undici.cjs';
@@ -37,16 +37,7 @@ const handleServerAction = async ({ request }) => {
37
37
  console.info("serverFnManifest", serverFnManifest);
38
38
  throw new Error("Server function info not found for " + serverFnId);
39
39
  }
40
- let fnModule;
41
- if (process.env.NODE_ENV === "development") {
42
- const serverEnv = globalThis.viteDevServer.environments["server"];
43
- if (!serverEnv) {
44
- throw new Error(`'server' vite dev environment not found`);
45
- }
46
- fnModule = await serverEnv.runner.import(serverFnInfo.extractedFilename);
47
- } else {
48
- fnModule = await serverFnInfo.importer();
49
- }
40
+ const fnModule = await serverFnInfo.importer();
50
41
  if (!fnModule) {
51
42
  console.info("serverFnInfo", serverFnInfo);
52
43
  throw new Error("Server function module not resolved for " + serverFnId);
@@ -1 +1 @@
1
- {"version":3,"file":"server-functions-handler.cjs","sources":["../../src/server-functions-handler.ts"],"sourcesContent":["import { isNotFound } from '@tanstack/router-core'\nimport invariant from 'tiny-invariant'\nimport { startSerializer } from '@tanstack/start-client-core'\n// @ts-expect-error\nimport _serverFnManifest from 'tanstack:server-fn-manifest'\nimport { getEvent, getResponseStatus } from './h3'\n\n// NOTE: This is a dummy export to silence warnings about\n// only having a default export.\nexport const dummy = 2\n\nconst serverFnManifest = _serverFnManifest as Record<\n string,\n {\n functionName: string\n extractedFilename: string\n importer: () => Promise<any>\n }\n>\n\nfunction sanitizeBase(base: string | undefined) {\n if (!base) {\n throw new Error(\n '🚨 process.env.TSS_SERVER_FN_BASE is required in start/server-handler/index',\n )\n }\n\n return base.replace(/^\\/|\\/$/g, '')\n}\n\nexport const handleServerAction = async ({ request }: { request: Request }) => {\n const controller = new AbortController()\n const signal = controller.signal\n const abort = () => controller.abort()\n request.signal.addEventListener('abort', abort)\n\n const method = request.method\n const url = new URL(request.url, 'http://localhost:3000')\n // extract the serverFnId from the url as host/_server/:serverFnId\n // Define a regex to match the path and extract the :thing part\n const regex = new RegExp(\n `${sanitizeBase(process.env.TSS_SERVER_FN_BASE)}/([^/?#]+)`,\n )\n\n // Execute the regex\n const match = url.pathname.match(regex)\n const serverFnId = match ? match[1] : null\n const search = Object.fromEntries(url.searchParams.entries()) as {\n payload?: any\n createServerFn?: boolean\n }\n\n const isCreateServerFn = 'createServerFn' in search\n const isRaw = 'raw' in search\n\n if (typeof serverFnId !== 'string') {\n throw new Error('Invalid server action param for serverFnId: ' + serverFnId)\n }\n\n const serverFnInfo = serverFnManifest[serverFnId]\n\n if (!serverFnInfo) {\n console.info('serverFnManifest', serverFnManifest)\n throw new Error('Server function info not found for ' + serverFnId)\n }\n\n let fnModule: undefined | { [key: string]: any }\n\n if (process.env.NODE_ENV === 'development') {\n const serverEnv = (globalThis as any).viteDevServer.environments['server']\n if (!serverEnv) {\n throw new Error(`'server' vite dev environment not found`)\n }\n fnModule = await serverEnv.runner.import(serverFnInfo.extractedFilename)\n } else {\n fnModule = await serverFnInfo.importer()\n }\n\n if (!fnModule) {\n console.info('serverFnInfo', serverFnInfo)\n throw new Error('Server function module not resolved for ' + serverFnId)\n }\n\n const action = fnModule[serverFnInfo.functionName]\n\n if (!action) {\n console.info('serverFnInfo', serverFnInfo)\n console.info('fnModule', fnModule)\n throw new Error(\n `Server function module export not resolved for serverFn ID: ${serverFnId}`,\n )\n }\n\n // Known FormData 'Content-Type' header values\n const formDataContentTypes = [\n 'multipart/form-data',\n 'application/x-www-form-urlencoded',\n ]\n\n const response = await (async () => {\n try {\n let result = await (async () => {\n // FormData\n if (\n request.headers.get('Content-Type') &&\n formDataContentTypes.some((type) =>\n request.headers.get('Content-Type')?.includes(type),\n )\n ) {\n // We don't support GET requests with FormData payloads... that seems impossible\n invariant(\n method.toLowerCase() !== 'get',\n 'GET requests with FormData payloads are not supported',\n )\n\n return await action(await request.formData(), signal)\n }\n\n // Get requests use the query string\n if (method.toLowerCase() === 'get') {\n // By default the payload is the search params\n let payload: any = search\n\n // If this GET request was created by createServerFn,\n // then the payload will be on the payload param\n if (isCreateServerFn) {\n payload = search.payload\n }\n\n // If there's a payload, we should try to parse it\n payload = payload ? startSerializer.parse(payload) : payload\n\n // Send it through!\n return await action(payload, signal)\n }\n\n // This must be a POST request, likely JSON???\n const jsonPayloadAsString = await request.text()\n\n // We should probably try to deserialize the payload\n // as JSON, but we'll just pass it through for now.\n const payload = startSerializer.parse(jsonPayloadAsString)\n\n // If this POST request was created by createServerFn,\n // it's payload will be the only argument\n if (isCreateServerFn) {\n return await action(payload, signal)\n }\n\n // Otherwise, we'll spread the payload. Need to\n // support `use server` functions that take multiple\n // arguments.\n return await action(...(payload as any), signal)\n })()\n\n // Any time we get a Response back, we should just\n // return it immediately.\n if (result.result instanceof Response) {\n return result.result\n }\n\n // If this is a non createServerFn request, we need to\n // pull out the result from the result object\n if (!isCreateServerFn) {\n result = result.result\n\n // The result might again be a response,\n // and if it is, return it.\n if (result instanceof Response) {\n return result\n }\n }\n\n // if (!search.createServerFn) {\n // result = result.result\n // }\n\n // else if (\n // isPlainObject(result) &&\n // 'result' in result &&\n // result.result instanceof Response\n // ) {\n // return result.result\n // }\n\n // TODO: RSCs Where are we getting this package?\n // if (isValidElement(result)) {\n // const { renderToPipeableStream } = await import(\n // // @ts-expect-error\n // 'react-server-dom/server'\n // )\n\n // const pipeableStream = renderToPipeableStream(result)\n\n // setHeaders(event, {\n // 'Content-Type': 'text/x-component',\n // } as any)\n\n // sendStream(event, response)\n // event._handled = true\n\n // return new Response(null, { status: 200 })\n // }\n\n if (isNotFound(result)) {\n return isNotFoundResponse(result)\n }\n\n return new Response(\n result !== undefined ? startSerializer.stringify(result) : undefined,\n {\n status: getResponseStatus(getEvent()),\n headers: {\n 'Content-Type': 'application/json',\n },\n },\n )\n } catch (error: any) {\n if (error instanceof Response) {\n return error\n }\n // else if (\n // isPlainObject(error) &&\n // 'result' in error &&\n // error.result instanceof Response\n // ) {\n // return error.result\n // }\n\n // Currently this server-side context has no idea how to\n // build final URLs, so we need to defer that to the client.\n // The client will check for __redirect and __notFound keys,\n // and if they exist, it will handle them appropriately.\n\n if (isNotFound(error)) {\n return isNotFoundResponse(error)\n }\n\n console.info()\n console.info('Server Fn Error!')\n console.info()\n console.error(error)\n console.info()\n\n return new Response(startSerializer.stringify(error), {\n status: 500,\n headers: {\n 'Content-Type': 'application/json',\n },\n })\n }\n })()\n\n request.signal.removeEventListener('abort', abort)\n\n if (isRaw) {\n return response\n }\n\n return response\n}\n\nfunction isNotFoundResponse(error: any) {\n const { headers, ...rest } = error\n\n return new Response(JSON.stringify(rest), {\n status: 200,\n headers: {\n 'Content-Type': 'application/json',\n ...(headers || {}),\n },\n })\n}\n"],"names":["payload","startSerializer","isNotFound","getResponseStatus","getEvent"],"mappings":"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"}
1
+ {"version":3,"file":"server-functions-handler.cjs","sources":["../../src/server-functions-handler.ts"],"sourcesContent":["import { isNotFound } from '@tanstack/router-core'\nimport invariant from 'tiny-invariant'\nimport { startSerializer } from '@tanstack/start-client-core'\n// @ts-expect-error\nimport _serverFnManifest from 'tanstack:server-fn-manifest'\nimport { getEvent, getResponseStatus } from './h3'\n\nconst serverFnManifest = _serverFnManifest as Record<\n string,\n {\n functionName: string\n extractedFilename: string\n importer: () => Promise<any>\n }\n>\n\nfunction sanitizeBase(base: string | undefined) {\n if (!base) {\n throw new Error(\n '🚨 process.env.TSS_SERVER_FN_BASE is required in start/server-handler/index',\n )\n }\n\n return base.replace(/^\\/|\\/$/g, '')\n}\n\nexport const handleServerAction = async ({ request }: { request: Request }) => {\n const controller = new AbortController()\n const signal = controller.signal\n const abort = () => controller.abort()\n request.signal.addEventListener('abort', abort)\n\n const method = request.method\n const url = new URL(request.url, 'http://localhost:3000')\n // extract the serverFnId from the url as host/_serverFn/:serverFnId\n // Define a regex to match the path and extract the :thing part\n const regex = new RegExp(\n `${sanitizeBase(process.env.TSS_SERVER_FN_BASE)}/([^/?#]+)`,\n )\n\n // Execute the regex\n const match = url.pathname.match(regex)\n const serverFnId = match ? match[1] : null\n const search = Object.fromEntries(url.searchParams.entries()) as {\n payload?: any\n createServerFn?: boolean\n }\n\n const isCreateServerFn = 'createServerFn' in search\n const isRaw = 'raw' in search\n\n if (typeof serverFnId !== 'string') {\n throw new Error('Invalid server action param for serverFnId: ' + serverFnId)\n }\n\n const serverFnInfo = serverFnManifest[serverFnId]\n\n if (!serverFnInfo) {\n console.info('serverFnManifest', serverFnManifest)\n throw new Error('Server function info not found for ' + serverFnId)\n }\n\n const fnModule: undefined | { [key: string]: any } =\n await serverFnInfo.importer()\n\n if (!fnModule) {\n console.info('serverFnInfo', serverFnInfo)\n throw new Error('Server function module not resolved for ' + serverFnId)\n }\n\n const action = fnModule[serverFnInfo.functionName]\n\n if (!action) {\n console.info('serverFnInfo', serverFnInfo)\n console.info('fnModule', fnModule)\n throw new Error(\n `Server function module export not resolved for serverFn ID: ${serverFnId}`,\n )\n }\n\n // Known FormData 'Content-Type' header values\n const formDataContentTypes = [\n 'multipart/form-data',\n 'application/x-www-form-urlencoded',\n ]\n\n const response = await (async () => {\n try {\n let result = await (async () => {\n // FormData\n if (\n request.headers.get('Content-Type') &&\n formDataContentTypes.some((type) =>\n request.headers.get('Content-Type')?.includes(type),\n )\n ) {\n // We don't support GET requests with FormData payloads... that seems impossible\n invariant(\n method.toLowerCase() !== 'get',\n 'GET requests with FormData payloads are not supported',\n )\n\n return await action(await request.formData(), signal)\n }\n\n // Get requests use the query string\n if (method.toLowerCase() === 'get') {\n // By default the payload is the search params\n let payload: any = search\n\n // If this GET request was created by createServerFn,\n // then the payload will be on the payload param\n if (isCreateServerFn) {\n payload = search.payload\n }\n\n // If there's a payload, we should try to parse it\n payload = payload ? startSerializer.parse(payload) : payload\n\n // Send it through!\n return await action(payload, signal)\n }\n\n // This must be a POST request, likely JSON???\n const jsonPayloadAsString = await request.text()\n\n // We should probably try to deserialize the payload\n // as JSON, but we'll just pass it through for now.\n const payload = startSerializer.parse(jsonPayloadAsString)\n\n // If this POST request was created by createServerFn,\n // it's payload will be the only argument\n if (isCreateServerFn) {\n return await action(payload, signal)\n }\n\n // Otherwise, we'll spread the payload. Need to\n // support `use server` functions that take multiple\n // arguments.\n return await action(...(payload as any), signal)\n })()\n\n // Any time we get a Response back, we should just\n // return it immediately.\n if (result.result instanceof Response) {\n return result.result\n }\n\n // If this is a non createServerFn request, we need to\n // pull out the result from the result object\n if (!isCreateServerFn) {\n result = result.result\n\n // The result might again be a response,\n // and if it is, return it.\n if (result instanceof Response) {\n return result\n }\n }\n\n // if (!search.createServerFn) {\n // result = result.result\n // }\n\n // else if (\n // isPlainObject(result) &&\n // 'result' in result &&\n // result.result instanceof Response\n // ) {\n // return result.result\n // }\n\n // TODO: RSCs Where are we getting this package?\n // if (isValidElement(result)) {\n // const { renderToPipeableStream } = await import(\n // // @ts-expect-error\n // 'react-server-dom/server'\n // )\n\n // const pipeableStream = renderToPipeableStream(result)\n\n // setHeaders(event, {\n // 'Content-Type': 'text/x-component',\n // } as any)\n\n // sendStream(event, response)\n // event._handled = true\n\n // return new Response(null, { status: 200 })\n // }\n\n if (isNotFound(result)) {\n return isNotFoundResponse(result)\n }\n\n return new Response(\n result !== undefined ? startSerializer.stringify(result) : undefined,\n {\n status: getResponseStatus(getEvent()),\n headers: {\n 'Content-Type': 'application/json',\n },\n },\n )\n } catch (error: any) {\n if (error instanceof Response) {\n return error\n }\n // else if (\n // isPlainObject(error) &&\n // 'result' in error &&\n // error.result instanceof Response\n // ) {\n // return error.result\n // }\n\n // Currently this server-side context has no idea how to\n // build final URLs, so we need to defer that to the client.\n // The client will check for __redirect and __notFound keys,\n // and if they exist, it will handle them appropriately.\n\n if (isNotFound(error)) {\n return isNotFoundResponse(error)\n }\n\n console.info()\n console.info('Server Fn Error!')\n console.info()\n console.error(error)\n console.info()\n\n return new Response(startSerializer.stringify(error), {\n status: 500,\n headers: {\n 'Content-Type': 'application/json',\n },\n })\n }\n })()\n\n request.signal.removeEventListener('abort', abort)\n\n if (isRaw) {\n return response\n }\n\n return response\n}\n\nfunction isNotFoundResponse(error: any) {\n const { headers, ...rest } = error\n\n return new Response(JSON.stringify(rest), {\n status: 200,\n headers: {\n 'Content-Type': 'application/json',\n ...(headers || {}),\n },\n })\n}\n"],"names":["payload","startSerializer","isNotFound","getResponseStatus","getEvent"],"mappings":"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"}
@@ -1,4 +1,3 @@
1
- export declare const dummy = 2;
2
1
  export declare const handleServerAction: ({ request }: {
3
2
  request: Request;
4
3
  }) => Promise<any>;
@@ -1 +1 @@
1
- {"version":3,"file":"serverRoute.cjs","sources":["../../src/serverRoute.ts"],"sourcesContent":["import { joinPaths, rootRouteId, trimPathLeft } from '@tanstack/router-core'\nimport type {\n Assign,\n Constrain,\n Expand,\n ResolveParams,\n RouteConstraints,\n TrimPathRight,\n} from '@tanstack/router-core'\nimport type {\n AnyRequestMiddleware,\n AssignAllServerContext,\n} from '@tanstack/start-client-core'\n\ntype TODO = any\n\nexport function createServerFileRoute<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TChildren,\n>(__?: never): ServerRoute<TParentRoute, TId, TPath, TFullPath, TChildren> {\n return createServerRoute<TParentRoute, TId, TPath, TFullPath, TChildren>(\n undefined,\n )\n}\n\nexport interface ServerRouteOptions<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TMiddlewares,\n> {\n id: TId\n path: TPath\n pathname: TFullPath\n originalIndex: number\n getParentRoute?: () => TParentRoute\n middleware: Constrain<TMiddlewares, ReadonlyArray<AnyRequestMiddleware>>\n methods: Record<\n string,\n ServerRouteMethodHandlerFn<TParentRoute, TFullPath, TMiddlewares, any, any>\n >\n caseSensitive?: boolean\n}\n\nexport type ServerRouteManifest = {\n middleware: boolean\n methods: Record<string, { middleware: boolean }>\n}\n\nexport function createServerRoute<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TChildren,\n>(\n __?: never,\n __opts?: Partial<\n ServerRouteOptions<TParentRoute, TId, TPath, TFullPath, undefined>\n >,\n): ServerRoute<TParentRoute, TId, TPath, TFullPath, TChildren> {\n const options = __opts || {}\n\n const route: ServerRoute<TParentRoute, TId, TPath, TFullPath, TChildren> = {\n path: '' as TPath,\n id: '' as TId,\n fullPath: '' as TFullPath,\n to: '' as TrimPathRight<TFullPath>,\n options: options as TODO,\n parentRoute: undefined as unknown as TParentRoute,\n _types: {} as TODO,\n // children: undefined as TChildren,\n middleware: (middlewares: TODO) =>\n createServerRoute(undefined, {\n ...options,\n middleware: middlewares,\n }) as TODO,\n methods: (methodsOrGetMethods: TODO) => {\n const methods = (() => {\n if (typeof methodsOrGetMethods === 'function') {\n return methodsOrGetMethods(createMethodBuilder())\n }\n\n return methodsOrGetMethods\n })()\n\n return createServerRoute(undefined, {\n ...__opts,\n methods,\n }) as TODO\n },\n update: (opts) =>\n createServerRoute(undefined, {\n ...options,\n ...opts,\n }) as TODO,\n init: (opts: { originalIndex: number }): void => {\n options.originalIndex = opts.originalIndex\n\n const isRoot = !options.path && !options.id\n\n route.parentRoute = options.getParentRoute?.() as TParentRoute\n\n if (isRoot) {\n route.path = rootRouteId as TPath\n } else if (!(route.parentRoute as any)) {\n throw new Error(\n `Child Route instances must pass a 'getParentRoute: () => ParentRoute' option that returns a ServerRoute instance.`,\n )\n }\n\n let path: undefined | string = isRoot ? rootRouteId : options.path\n\n // If the path is anything other than an index path, trim it up\n if (path && path !== '/') {\n path = trimPathLeft(path)\n }\n\n const customId = options.id || path\n\n // Strip the parentId prefix from the first level of children\n let id = isRoot\n ? rootRouteId\n : joinPaths([\n route.parentRoute.id === rootRouteId ? '' : route.parentRoute.id,\n customId,\n ])\n\n if (path === rootRouteId) {\n path = '/'\n }\n\n if (id !== rootRouteId) {\n id = joinPaths(['/', id])\n }\n\n const fullPath =\n id === rootRouteId ? '/' : joinPaths([route.parentRoute.fullPath, path])\n\n route.path = path as TPath\n route.id = id as TId\n route.fullPath = fullPath as TFullPath\n route.to = fullPath as TrimPathRight<TFullPath>\n },\n\n _addFileChildren: (children) => {\n if (Array.isArray(children)) {\n route.children = children as TChildren as TODO\n }\n\n if (typeof children === 'object' && children !== null) {\n route.children = Object.values(children) as TChildren as TODO\n }\n\n return route as any\n },\n\n _addFileTypes: <TFileTypes>() => route,\n }\n\n return route\n}\n\nexport type ServerRouteAddFileChildrenFn<\n in out TParentRoute extends AnyServerRouteWithTypes,\n in out TId extends RouteConstraints['TId'],\n in out TPath extends RouteConstraints['TPath'],\n in out TFullPath extends RouteConstraints['TFullPath'],\n in out TMiddlewares,\n in out TMethods,\n in out TChildren,\n> = (\n children: TChildren,\n) => ServerRouteWithTypes<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TMiddlewares,\n TMethods,\n TChildren\n>\n\nconst createMethodBuilder = <\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n>(\n __opts?: TODO,\n): ServerRouteMethodBuilder<TParentRoute, TFullPath, TMiddlewares> => {\n return {\n _options: __opts || {},\n _types: {} as TODO,\n middleware: (middlewares) =>\n createMethodBuilder({\n ...__opts,\n middlewares,\n }) as TODO,\n handler: (handler) =>\n createMethodBuilder({\n ...__opts,\n handler,\n }) as TODO,\n }\n}\n\nexport type CreateServerFileRoute<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TChildren,\n> = (\n options?: undefined,\n) => ServerRoute<TParentRoute, TId, TPath, TFullPath, TChildren>\n\nexport type AnyServerRouteWithTypes = ServerRouteWithTypes<\n any,\n any,\n any,\n any,\n any,\n any,\n any\n>\n\nexport interface ServerRouteWithTypes<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TMiddlewares,\n TMethods,\n TChildren,\n> {\n _types: ServerRouteTypes<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TMiddlewares,\n TMethods\n >\n path: TPath\n id: TId\n fullPath: TFullPath\n to: TrimPathRight<TFullPath>\n parentRoute: TParentRoute\n children?: TChildren\n options: ServerRouteOptions<TParentRoute, TId, TPath, TFullPath, TMiddlewares>\n update: (\n opts: ServerRouteOptions<TParentRoute, TId, TPath, TFullPath, undefined>,\n ) => ServerRoute<TParentRoute, TId, TPath, TFullPath, TChildren>\n init: (opts: { originalIndex: number }) => void\n _addFileChildren: ServerRouteAddFileChildrenFn<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TMiddlewares,\n TMethods,\n TChildren\n >\n _addFileTypes: () => ServerRouteWithTypes<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TMiddlewares,\n TMethods,\n TChildren\n >\n}\n\nexport interface ServerRouteTypes<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TMiddlewares,\n TMethods,\n> {\n id: TId\n path: TPath\n fullPath: TFullPath\n middlewares: TMiddlewares\n methods: TMethods\n parentRoute: TParentRoute\n allContext: ResolveAllServerContext<TParentRoute, TMiddlewares>\n}\n\nexport type ResolveAllServerContext<\n TParentRoute extends AnyServerRouteWithTypes,\n TMiddlewares,\n> = unknown extends TParentRoute\n ? AssignAllServerContext<TMiddlewares>\n : Assign<\n TParentRoute['_types']['allContext'],\n AssignAllServerContext<TMiddlewares>\n >\n\nexport type AnyServerRoute = AnyServerRouteWithTypes\n\nexport interface ServerRoute<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TChildren,\n> extends ServerRouteWithTypes<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n undefined,\n undefined,\n TChildren\n >,\n ServerRouteMiddleware<TParentRoute, TId, TPath, TFullPath, TChildren>,\n ServerRouteMethods<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n undefined,\n TChildren\n > {}\n\nexport interface ServerRouteMiddleware<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TChildren,\n> {\n middleware: <const TNewMiddleware>(\n middleware: Constrain<TNewMiddleware, ReadonlyArray<AnyRequestMiddleware>>,\n ) => ServerRouteAfterMiddleware<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TNewMiddleware,\n TChildren\n >\n}\n\nexport interface ServerRouteAfterMiddleware<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TMiddlewares,\n TChildren,\n> extends ServerRouteWithTypes<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TMiddlewares,\n undefined,\n TChildren\n >,\n ServerRouteMethods<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TMiddlewares,\n TChildren\n > {}\n\nexport interface ServerRouteMethods<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TMiddlewares,\n TChildren,\n> {\n methods: <const TMethods>(\n methodsOrGetMethods: Constrain<\n TMethods,\n ServerRouteMethodsOptions<TParentRoute, TFullPath, TMiddlewares>\n >,\n ) => ServerRouteAfterMethods<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TMiddlewares,\n TMethods,\n TChildren\n >\n}\n\nexport type ServerRouteMethodsOptions<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n> =\n | ServerRouteMethodsRecord<TParentRoute, TFullPath, TMiddlewares>\n | ((\n api: ServerRouteMethodBuilder<TParentRoute, TFullPath, TMiddlewares>,\n ) => ServerRouteMethodsRecord<TParentRoute, TFullPath, TMiddlewares>)\n\nexport interface ServerRouteMethodsRecord<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n> {\n GET?: ServerRouteMethodRecordValue<TParentRoute, TFullPath, TMiddlewares>\n POST?: ServerRouteMethodRecordValue<TParentRoute, TFullPath, TMiddlewares>\n PUT?: ServerRouteMethodRecordValue<TParentRoute, TFullPath, TMiddlewares>\n PATCH?: ServerRouteMethodRecordValue<TParentRoute, TFullPath, TMiddlewares>\n DELETE?: ServerRouteMethodRecordValue<TParentRoute, TFullPath, TMiddlewares>\n OPTIONS?: ServerRouteMethodRecordValue<TParentRoute, TFullPath, TMiddlewares>\n HEAD?: ServerRouteMethodRecordValue<TParentRoute, TFullPath, TMiddlewares>\n}\n\nexport type ServerRouteMethodRecordValue<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n> =\n | ServerRouteMethodHandlerFn<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n undefined,\n any\n >\n | AnyRouteMethodsBuilder\n\nexport type ServerRouteVerb = (typeof ServerRouteVerbs)[number]\n\nexport const ServerRouteVerbs = [\n 'GET',\n 'POST',\n 'PUT',\n 'PATCH',\n 'DELETE',\n 'OPTIONS',\n 'HEAD',\n] as const\n\nexport type ServerRouteMethodHandlerFn<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n TMethodMiddlewares,\n TResponse,\n> = (\n ctx: ServerRouteMethodHandlerCtx<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares\n >,\n) => TResponse | Promise<TResponse>\n\nexport interface ServerRouteMethodHandlerCtx<\n in out TParentRoute extends AnyServerRouteWithTypes,\n in out TFullPath extends string,\n in out TMiddlewares,\n in out TMethodMiddlewares,\n> {\n context: Expand<\n AssignAllMethodContext<TParentRoute, TMiddlewares, TMethodMiddlewares>\n >\n request: Request\n params: ResolveParams<TFullPath>\n pathname: TFullPath\n}\n\nexport type MergeMethodMiddlewares<TMiddlewares, TMethodMiddlewares> =\n TMiddlewares extends ReadonlyArray<any>\n ? TMethodMiddlewares extends ReadonlyArray<any>\n ? readonly [...TMiddlewares, ...TMethodMiddlewares]\n : TMiddlewares\n : TMethodMiddlewares\n\nexport type AssignAllMethodContext<\n TParentRoute extends AnyServerRouteWithTypes,\n TMiddlewares,\n TMethodMiddlewares,\n> = ResolveAllServerContext<\n TParentRoute,\n MergeMethodMiddlewares<TMiddlewares, TMethodMiddlewares>\n>\n\nexport type AnyRouteMethodsBuilder = ServerRouteMethodBuilderWithTypes<\n any,\n any,\n any,\n any\n>\n\nexport interface ServerRouteMethodBuilder<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n> extends ServerRouteMethodBuilderWithTypes<\n TFullPath,\n TMiddlewares,\n undefined,\n undefined\n >,\n ServerRouteMethodBuilderMiddleware<TParentRoute, TFullPath, TMiddlewares>,\n ServerRouteMethodBuilderHandler<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n undefined\n > {}\n\nexport interface ServerRouteMethodBuilderWithTypes<\n TFullPath extends string,\n TMiddlewares,\n TMethodMiddlewares,\n TResponse,\n> {\n _options: TODO\n _types: ServerRouteMethodBuilderTypes<\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares,\n TResponse\n >\n}\n\nexport interface ServerRouteMethodBuilderTypes<\n in out TFullPath extends string,\n in out TMiddlewares,\n in out TMethodMiddlewares,\n in out TResponse,\n> {\n middlewares: TMiddlewares\n methodMiddleware: TMethodMiddlewares\n fullPath: TFullPath\n response: TResponse\n}\n\nexport interface ServerRouteMethodBuilderMiddleware<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n> {\n middleware: <const TNewMethodMiddlewares>(\n middleware: Constrain<\n TNewMethodMiddlewares,\n ReadonlyArray<AnyRequestMiddleware>\n >,\n ) => ServerRouteMethodBuilderAfterMiddleware<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n TNewMethodMiddlewares\n >\n}\n\nexport interface ServerRouteMethodBuilderAfterMiddleware<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n TMethodMiddlewares,\n> extends ServerRouteMethodBuilderWithTypes<\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares,\n undefined\n >,\n ServerRouteMethodBuilderHandler<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares\n > {}\n\nexport interface ServerRouteMethodBuilderHandler<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n TMethodMiddlewares,\n> {\n handler: <TResponse>(\n handler: ServerRouteMethodHandlerFn<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares,\n TResponse\n >,\n ) => ServerRouteMethodBuilderAfterHandler<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares,\n TResponse\n >\n}\n\nexport interface ServerRouteMethodBuilderAfterHandler<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n TMethodMiddlewares,\n TResponse,\n> extends ServerRouteMethodBuilderWithTypes<\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares,\n TResponse\n > {\n opts: ServerRouteMethod<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares\n >\n}\n\nexport interface ServerRouteMethod<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n TMethodMiddlewares,\n> {\n middleware?: Constrain<TMiddlewares, Array<AnyRequestMiddleware>>\n handler?: ServerRouteMethodHandlerFn<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares,\n undefined\n >\n}\n\nexport interface ServerRouteAfterMethods<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TMiddlewares,\n TMethods,\n TChildren,\n> extends ServerRouteWithTypes<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TMiddlewares,\n TMethods,\n TChildren\n > {\n options: ServerRouteOptions<TParentRoute, TId, TPath, TFullPath, TMiddlewares>\n}\n"],"names":["rootRouteId","trimPathLeft","joinPaths"],"mappings":";;;AAgBO,SAAS,sBAMd,IAAyE;AAClE,SAAA,kBAEP;AACF;AA2BgB,SAAA,kBAOd,IACA,QAG6D;AACvD,QAAA,UAAU,UAAU,CAAC;AAE3B,QAAM,QAAqE;AAAA,IACzE,MAAM;AAAA,IACN,IAAI;AAAA,IACJ,UAAU;AAAA,IACV,IAAI;AAAA,IACJ;AAAA,IACA,aAAa;AAAA,IACb,QAAQ,CAAC;AAAA;AAAA,IAET,YAAY,CAAC,gBACX,kBAAkB,QAAW;AAAA,MAC3B,GAAG;AAAA,MACH,YAAY;AAAA,IAAA,CACb;AAAA,IACH,SAAS,CAAC,wBAA8B;AACtC,YAAM,WAAW,MAAM;AACjB,YAAA,OAAO,wBAAwB,YAAY;AACtC,iBAAA,oBAAoB,qBAAqB;AAAA,QAAA;AAG3C,eAAA;AAAA,MAAA,GACN;AAEH,aAAO,kBAAkB,QAAW;AAAA,QAClC,GAAG;AAAA,QACH;AAAA,MAAA,CACD;AAAA,IACH;AAAA,IACA,QAAQ,CAAC,SACP,kBAAkB,QAAW;AAAA,MAC3B,GAAG;AAAA,MACH,GAAG;AAAA,IAAA,CACJ;AAAA,IACH,MAAM,CAAC,SAA0C;;AAC/C,cAAQ,gBAAgB,KAAK;AAE7B,YAAM,SAAS,CAAC,QAAQ,QAAQ,CAAC,QAAQ;AAEnC,YAAA,eAAc,aAAQ,mBAAR;AAEpB,UAAI,QAAQ;AACV,cAAM,OAAOA,WAAA;AAAA,MAAA,WACJ,CAAE,MAAM,aAAqB;AACtC,cAAM,IAAI;AAAA,UACR;AAAA,QACF;AAAA,MAAA;AAGE,UAAA,OAA2B,SAASA,WAAA,cAAc,QAAQ;AAG1D,UAAA,QAAQ,SAAS,KAAK;AACxB,eAAOC,wBAAa,IAAI;AAAA,MAAA;AAGpB,YAAA,WAAW,QAAQ,MAAM;AAG3B,UAAA,KAAK,SACLD,WAAA,cACAE,qBAAU;AAAA,QACR,MAAM,YAAY,OAAOF,WAAAA,cAAc,KAAK,MAAM,YAAY;AAAA,QAC9D;AAAA,MAAA,CACD;AAEL,UAAI,SAASA,WAAAA,aAAa;AACjB,eAAA;AAAA,MAAA;AAGT,UAAI,OAAOA,WAAAA,aAAa;AACtB,aAAKE,WAAU,UAAA,CAAC,KAAK,EAAE,CAAC;AAAA,MAAA;AAGpB,YAAA,WACJ,OAAOF,WAAA,cAAc,MAAME,WAAAA,UAAU,CAAC,MAAM,YAAY,UAAU,IAAI,CAAC;AAEzE,YAAM,OAAO;AACb,YAAM,KAAK;AACX,YAAM,WAAW;AACjB,YAAM,KAAK;AAAA,IACb;AAAA,IAEA,kBAAkB,CAAC,aAAa;AAC1B,UAAA,MAAM,QAAQ,QAAQ,GAAG;AAC3B,cAAM,WAAW;AAAA,MAAA;AAGnB,UAAI,OAAO,aAAa,YAAY,aAAa,MAAM;AAC/C,cAAA,WAAW,OAAO,OAAO,QAAQ;AAAA,MAAA;AAGlC,aAAA;AAAA,IACT;AAAA,IAEA,eAAe,MAAkB;AAAA,EACnC;AAEO,SAAA;AACT;AAsBA,MAAM,sBAAsB,CAK1B,WACoE;AAC7D,SAAA;AAAA,IACL,UAAU,UAAU,CAAC;AAAA,IACrB,QAAQ,CAAC;AAAA,IACT,YAAY,CAAC,gBACX,oBAAoB;AAAA,MAClB,GAAG;AAAA,MACH;AAAA,IAAA,CACD;AAAA,IACH,SAAS,CAAC,YACR,oBAAoB;AAAA,MAClB,GAAG;AAAA,MACH;AAAA,IACD,CAAA;AAAA,EACL;AACF;;;"}
1
+ {"version":3,"file":"serverRoute.cjs","sources":["../../src/serverRoute.ts"],"sourcesContent":["import { joinPaths, rootRouteId, trimPathLeft } from '@tanstack/router-core'\nimport type {\n Assign,\n Constrain,\n Expand,\n ResolveParams,\n RouteConstraints,\n TrimPathRight,\n} from '@tanstack/router-core'\nimport type {\n AnyRequestMiddleware,\n AssignAllServerContext,\n} from '@tanstack/start-client-core'\n\ntype TODO = any\n\nexport function createServerFileRoute<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TChildren,\n>(__?: never): ServerRoute<TParentRoute, TId, TPath, TFullPath, TChildren> {\n return createServerRoute<TParentRoute, TId, TPath, TFullPath, TChildren>(\n undefined,\n )\n}\n\nexport interface ServerRouteOptions<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TMiddlewares,\n> {\n id: TId\n path: TPath\n pathname: TFullPath\n originalIndex: number\n getParentRoute?: () => TParentRoute\n middleware: Constrain<TMiddlewares, ReadonlyArray<AnyRequestMiddleware>>\n methods: Record<\n string,\n ServerRouteMethodHandlerFn<TParentRoute, TFullPath, TMiddlewares, any, any>\n >\n caseSensitive?: boolean\n}\n\nexport type ServerRouteManifest = {\n middleware: boolean\n methods: Record<string, { middleware: boolean }>\n}\n\nexport function createServerRoute<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TChildren,\n>(\n __?: never,\n __opts?: Partial<\n ServerRouteOptions<TParentRoute, TId, TPath, TFullPath, undefined>\n >,\n): ServerRoute<TParentRoute, TId, TPath, TFullPath, TChildren> {\n const options = __opts || {}\n\n const route: ServerRoute<TParentRoute, TId, TPath, TFullPath, TChildren> = {\n path: '' as TPath,\n id: '' as TId,\n fullPath: '' as TFullPath,\n to: '' as TrimPathRight<TFullPath>,\n options: options as TODO,\n parentRoute: undefined as unknown as TParentRoute,\n _types: {} as TODO,\n // children: undefined as TChildren,\n middleware: (middlewares: TODO) =>\n createServerRoute(undefined, {\n ...options,\n middleware: middlewares,\n }) as TODO,\n methods: (methodsOrGetMethods: TODO) => {\n const methods = (() => {\n if (typeof methodsOrGetMethods === 'function') {\n return methodsOrGetMethods(createMethodBuilder())\n }\n\n return methodsOrGetMethods\n })()\n\n return createServerRoute(undefined, {\n ...__opts,\n methods,\n }) as TODO\n },\n update: (opts) =>\n createServerRoute(undefined, {\n ...options,\n ...opts,\n }) as TODO,\n init: (opts: { originalIndex: number }): void => {\n options.originalIndex = opts.originalIndex\n\n const isRoot = !options.path && !options.id\n\n route.parentRoute = options.getParentRoute?.() as TParentRoute\n\n if (isRoot) {\n route.path = rootRouteId as TPath\n } else if (!(route.parentRoute as any)) {\n throw new Error(\n `Child Route instances must pass a 'getParentRoute: () => ParentRoute' option that returns a ServerRoute instance.`,\n )\n }\n\n let path: undefined | string = isRoot ? rootRouteId : options.path\n\n // If the path is anything other than an index path, trim it up\n if (path && path !== '/') {\n path = trimPathLeft(path)\n }\n\n const customId = options.id || path\n\n // Strip the parentId prefix from the first level of children\n let id = isRoot\n ? rootRouteId\n : joinPaths([\n route.parentRoute.id === rootRouteId ? '' : route.parentRoute.id,\n customId,\n ])\n\n if (path === rootRouteId) {\n path = '/'\n }\n\n if (id !== rootRouteId) {\n id = joinPaths(['/', id])\n }\n\n const fullPath =\n id === rootRouteId ? '/' : joinPaths([route.parentRoute.fullPath, path])\n\n route.path = path as TPath\n route.id = id as TId\n route.fullPath = fullPath as TFullPath\n route.to = fullPath as TrimPathRight<TFullPath>\n },\n\n _addFileChildren: (children) => {\n if (Array.isArray(children)) {\n route.children = children as TChildren as TODO\n }\n\n if (typeof children === 'object' && children !== null) {\n route.children = Object.values(children) as TChildren as TODO\n }\n\n return route as any\n },\n\n _addFileTypes: <TFileTypes>() => route,\n }\n\n return route\n}\n\nexport type ServerRouteAddFileChildrenFn<\n in out TParentRoute extends AnyServerRouteWithTypes,\n in out TId extends RouteConstraints['TId'],\n in out TPath extends RouteConstraints['TPath'],\n in out TFullPath extends RouteConstraints['TFullPath'],\n in out TMiddlewares,\n in out TMethods,\n in out TChildren,\n> = (\n children: TChildren,\n) => ServerRouteWithTypes<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TMiddlewares,\n TMethods,\n TChildren\n>\n\nconst createMethodBuilder = <\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n>(\n __opts?: TODO,\n): ServerRouteMethodBuilder<TParentRoute, TFullPath, TMiddlewares> => {\n return {\n _options: __opts || {},\n _types: {} as TODO,\n middleware: (middlewares) =>\n createMethodBuilder({\n ...__opts,\n middlewares,\n }) as TODO,\n handler: (handler) =>\n createMethodBuilder({\n ...__opts,\n handler,\n }) as TODO,\n }\n}\n\nexport type CreateServerFileRoute<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TChildren,\n> = (\n options?: undefined,\n) => ServerRoute<TParentRoute, TId, TPath, TFullPath, TChildren>\n\nexport type AnyServerRouteWithTypes = ServerRouteWithTypes<\n any,\n any,\n any,\n any,\n any,\n any,\n any\n>\n\nexport interface ServerRouteWithTypes<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TMiddlewares,\n TMethods,\n TChildren,\n> {\n _types: ServerRouteTypes<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TMiddlewares,\n TMethods\n >\n path: TPath\n id: TId\n fullPath: TFullPath\n to: TrimPathRight<TFullPath>\n parentRoute: TParentRoute\n children?: TChildren\n options: ServerRouteOptions<TParentRoute, TId, TPath, TFullPath, TMiddlewares>\n update: (\n opts: ServerRouteOptions<TParentRoute, TId, TPath, TFullPath, undefined>,\n ) => ServerRoute<TParentRoute, TId, TPath, TFullPath, TChildren>\n init: (opts: { originalIndex: number }) => void\n _addFileChildren: ServerRouteAddFileChildrenFn<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TMiddlewares,\n TMethods,\n TChildren\n >\n _addFileTypes: () => ServerRouteWithTypes<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TMiddlewares,\n TMethods,\n TChildren\n >\n}\n\nexport interface ServerRouteTypes<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TMiddlewares,\n TMethods,\n> {\n id: TId\n path: TPath\n fullPath: TFullPath\n middlewares: TMiddlewares\n methods: TMethods\n parentRoute: TParentRoute\n allContext: ResolveAllServerContext<TParentRoute, TMiddlewares>\n}\n\nexport type ResolveAllServerContext<\n TParentRoute extends AnyServerRouteWithTypes,\n TMiddlewares,\n> = unknown extends TParentRoute\n ? AssignAllServerContext<TMiddlewares>\n : Assign<\n TParentRoute['_types']['allContext'],\n AssignAllServerContext<TMiddlewares>\n >\n\nexport type AnyServerRoute = AnyServerRouteWithTypes\n\nexport interface ServerRoute<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TChildren,\n> extends ServerRouteWithTypes<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n undefined,\n undefined,\n TChildren\n >,\n ServerRouteMiddleware<TParentRoute, TId, TPath, TFullPath, TChildren>,\n ServerRouteMethods<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n undefined,\n TChildren\n > {}\n\nexport interface ServerRouteMiddleware<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TChildren,\n> {\n middleware: <const TNewMiddleware>(\n middleware: Constrain<TNewMiddleware, ReadonlyArray<AnyRequestMiddleware>>,\n ) => ServerRouteAfterMiddleware<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TNewMiddleware,\n TChildren\n >\n}\n\nexport interface ServerRouteAfterMiddleware<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TMiddlewares,\n TChildren,\n> extends ServerRouteWithTypes<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TMiddlewares,\n undefined,\n TChildren\n >,\n ServerRouteMethods<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TMiddlewares,\n TChildren\n > {}\n\nexport interface ServerRouteMethods<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TMiddlewares,\n TChildren,\n> {\n methods: <const TMethods>(\n methodsOrGetMethods: Constrain<\n TMethods,\n ServerRouteMethodsOptions<TParentRoute, TFullPath, TMiddlewares>\n >,\n ) => ServerRouteAfterMethods<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TMiddlewares,\n TMethods,\n TChildren\n >\n}\n\nexport type ServerRouteMethodsOptions<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n> =\n | ServerRouteMethodsRecord<TParentRoute, TFullPath, TMiddlewares>\n | ((\n api: ServerRouteMethodBuilder<TParentRoute, TFullPath, TMiddlewares>,\n ) => ServerRouteMethodsRecord<TParentRoute, TFullPath, TMiddlewares>)\n\nexport interface ServerRouteMethodsRecord<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n> {\n GET?: ServerRouteMethodRecordValue<TParentRoute, TFullPath, TMiddlewares>\n POST?: ServerRouteMethodRecordValue<TParentRoute, TFullPath, TMiddlewares>\n PUT?: ServerRouteMethodRecordValue<TParentRoute, TFullPath, TMiddlewares>\n PATCH?: ServerRouteMethodRecordValue<TParentRoute, TFullPath, TMiddlewares>\n DELETE?: ServerRouteMethodRecordValue<TParentRoute, TFullPath, TMiddlewares>\n OPTIONS?: ServerRouteMethodRecordValue<TParentRoute, TFullPath, TMiddlewares>\n HEAD?: ServerRouteMethodRecordValue<TParentRoute, TFullPath, TMiddlewares>\n}\n\nexport type ServerRouteMethodRecordValue<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n> =\n | ServerRouteMethodHandlerFn<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n undefined,\n any\n >\n | AnyRouteMethodsBuilder\n\nexport type ServerRouteVerb = (typeof ServerRouteVerbs)[number]\n\nexport const ServerRouteVerbs = [\n 'GET',\n 'POST',\n 'PUT',\n 'PATCH',\n 'DELETE',\n 'OPTIONS',\n 'HEAD',\n] as const\n\nexport type ServerRouteMethodHandlerFn<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n TMethodMiddlewares,\n TResponse,\n> = (\n ctx: ServerRouteMethodHandlerCtx<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares\n >,\n) => TResponse | Promise<TResponse>\n\nexport interface ServerRouteMethodHandlerCtx<\n in out TParentRoute extends AnyServerRouteWithTypes,\n in out TFullPath extends string,\n in out TMiddlewares,\n in out TMethodMiddlewares,\n> {\n context: Expand<\n AssignAllMethodContext<TParentRoute, TMiddlewares, TMethodMiddlewares>\n >\n request: Request\n params: Expand<ResolveParams<TFullPath>>\n pathname: TFullPath\n}\n\nexport type MergeMethodMiddlewares<TMiddlewares, TMethodMiddlewares> =\n TMiddlewares extends ReadonlyArray<any>\n ? TMethodMiddlewares extends ReadonlyArray<any>\n ? readonly [...TMiddlewares, ...TMethodMiddlewares]\n : TMiddlewares\n : TMethodMiddlewares\n\nexport type AssignAllMethodContext<\n TParentRoute extends AnyServerRouteWithTypes,\n TMiddlewares,\n TMethodMiddlewares,\n> = ResolveAllServerContext<\n TParentRoute,\n MergeMethodMiddlewares<TMiddlewares, TMethodMiddlewares>\n>\n\nexport type AnyRouteMethodsBuilder = ServerRouteMethodBuilderWithTypes<\n any,\n any,\n any,\n any\n>\n\nexport interface ServerRouteMethodBuilder<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n> extends ServerRouteMethodBuilderWithTypes<\n TFullPath,\n TMiddlewares,\n undefined,\n undefined\n >,\n ServerRouteMethodBuilderMiddleware<TParentRoute, TFullPath, TMiddlewares>,\n ServerRouteMethodBuilderHandler<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n undefined\n > {}\n\nexport interface ServerRouteMethodBuilderWithTypes<\n TFullPath extends string,\n TMiddlewares,\n TMethodMiddlewares,\n TResponse,\n> {\n _options: TODO\n _types: ServerRouteMethodBuilderTypes<\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares,\n TResponse\n >\n}\n\nexport interface ServerRouteMethodBuilderTypes<\n in out TFullPath extends string,\n in out TMiddlewares,\n in out TMethodMiddlewares,\n in out TResponse,\n> {\n middlewares: TMiddlewares\n methodMiddleware: TMethodMiddlewares\n fullPath: TFullPath\n response: TResponse\n}\n\nexport interface ServerRouteMethodBuilderMiddleware<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n> {\n middleware: <const TNewMethodMiddlewares>(\n middleware: Constrain<\n TNewMethodMiddlewares,\n ReadonlyArray<AnyRequestMiddleware>\n >,\n ) => ServerRouteMethodBuilderAfterMiddleware<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n TNewMethodMiddlewares\n >\n}\n\nexport interface ServerRouteMethodBuilderAfterMiddleware<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n TMethodMiddlewares,\n> extends ServerRouteMethodBuilderWithTypes<\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares,\n undefined\n >,\n ServerRouteMethodBuilderHandler<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares\n > {}\n\nexport interface ServerRouteMethodBuilderHandler<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n TMethodMiddlewares,\n> {\n handler: <TResponse>(\n handler: ServerRouteMethodHandlerFn<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares,\n TResponse\n >,\n ) => ServerRouteMethodBuilderAfterHandler<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares,\n TResponse\n >\n}\n\nexport interface ServerRouteMethodBuilderAfterHandler<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n TMethodMiddlewares,\n TResponse,\n> extends ServerRouteMethodBuilderWithTypes<\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares,\n TResponse\n > {\n opts: ServerRouteMethod<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares\n >\n}\n\nexport interface ServerRouteMethod<\n TParentRoute extends AnyServerRouteWithTypes,\n TFullPath extends string,\n TMiddlewares,\n TMethodMiddlewares,\n> {\n middleware?: Constrain<TMiddlewares, Array<AnyRequestMiddleware>>\n handler?: ServerRouteMethodHandlerFn<\n TParentRoute,\n TFullPath,\n TMiddlewares,\n TMethodMiddlewares,\n undefined\n >\n}\n\nexport interface ServerRouteAfterMethods<\n TParentRoute extends AnyServerRouteWithTypes,\n TId extends RouteConstraints['TId'],\n TPath extends RouteConstraints['TPath'],\n TFullPath extends RouteConstraints['TFullPath'],\n TMiddlewares,\n TMethods,\n TChildren,\n> extends ServerRouteWithTypes<\n TParentRoute,\n TId,\n TPath,\n TFullPath,\n TMiddlewares,\n TMethods,\n TChildren\n > {\n options: ServerRouteOptions<TParentRoute, TId, TPath, TFullPath, TMiddlewares>\n}\n"],"names":["rootRouteId","trimPathLeft","joinPaths"],"mappings":";;;AAgBO,SAAS,sBAMd,IAAyE;AAClE,SAAA,kBAEP;AACF;AA2BgB,SAAA,kBAOd,IACA,QAG6D;AACvD,QAAA,UAAU,UAAU,CAAC;AAE3B,QAAM,QAAqE;AAAA,IACzE,MAAM;AAAA,IACN,IAAI;AAAA,IACJ,UAAU;AAAA,IACV,IAAI;AAAA,IACJ;AAAA,IACA,aAAa;AAAA,IACb,QAAQ,CAAC;AAAA;AAAA,IAET,YAAY,CAAC,gBACX,kBAAkB,QAAW;AAAA,MAC3B,GAAG;AAAA,MACH,YAAY;AAAA,IAAA,CACb;AAAA,IACH,SAAS,CAAC,wBAA8B;AACtC,YAAM,WAAW,MAAM;AACjB,YAAA,OAAO,wBAAwB,YAAY;AACtC,iBAAA,oBAAoB,qBAAqB;AAAA,QAAA;AAG3C,eAAA;AAAA,MAAA,GACN;AAEH,aAAO,kBAAkB,QAAW;AAAA,QAClC,GAAG;AAAA,QACH;AAAA,MAAA,CACD;AAAA,IACH;AAAA,IACA,QAAQ,CAAC,SACP,kBAAkB,QAAW;AAAA,MAC3B,GAAG;AAAA,MACH,GAAG;AAAA,IAAA,CACJ;AAAA,IACH,MAAM,CAAC,SAA0C;;AAC/C,cAAQ,gBAAgB,KAAK;AAE7B,YAAM,SAAS,CAAC,QAAQ,QAAQ,CAAC,QAAQ;AAEnC,YAAA,eAAc,aAAQ,mBAAR;AAEpB,UAAI,QAAQ;AACV,cAAM,OAAOA,WAAA;AAAA,MAAA,WACJ,CAAE,MAAM,aAAqB;AACtC,cAAM,IAAI;AAAA,UACR;AAAA,QACF;AAAA,MAAA;AAGE,UAAA,OAA2B,SAASA,WAAA,cAAc,QAAQ;AAG1D,UAAA,QAAQ,SAAS,KAAK;AACxB,eAAOC,wBAAa,IAAI;AAAA,MAAA;AAGpB,YAAA,WAAW,QAAQ,MAAM;AAG3B,UAAA,KAAK,SACLD,WAAA,cACAE,qBAAU;AAAA,QACR,MAAM,YAAY,OAAOF,WAAAA,cAAc,KAAK,MAAM,YAAY;AAAA,QAC9D;AAAA,MAAA,CACD;AAEL,UAAI,SAASA,WAAAA,aAAa;AACjB,eAAA;AAAA,MAAA;AAGT,UAAI,OAAOA,WAAAA,aAAa;AACtB,aAAKE,WAAU,UAAA,CAAC,KAAK,EAAE,CAAC;AAAA,MAAA;AAGpB,YAAA,WACJ,OAAOF,WAAA,cAAc,MAAME,WAAAA,UAAU,CAAC,MAAM,YAAY,UAAU,IAAI,CAAC;AAEzE,YAAM,OAAO;AACb,YAAM,KAAK;AACX,YAAM,WAAW;AACjB,YAAM,KAAK;AAAA,IACb;AAAA,IAEA,kBAAkB,CAAC,aAAa;AAC1B,UAAA,MAAM,QAAQ,QAAQ,GAAG;AAC3B,cAAM,WAAW;AAAA,MAAA;AAGnB,UAAI,OAAO,aAAa,YAAY,aAAa,MAAM;AAC/C,cAAA,WAAW,OAAO,OAAO,QAAQ;AAAA,MAAA;AAGlC,aAAA;AAAA,IACT;AAAA,IAEA,eAAe,MAAkB;AAAA,EACnC;AAEO,SAAA;AACT;AAsBA,MAAM,sBAAsB,CAK1B,WACoE;AAC7D,SAAA;AAAA,IACL,UAAU,UAAU,CAAC;AAAA,IACrB,QAAQ,CAAC;AAAA,IACT,YAAY,CAAC,gBACX,oBAAoB;AAAA,MAClB,GAAG;AAAA,MACH;AAAA,IAAA,CACD;AAAA,IACH,SAAS,CAAC,YACR,oBAAoB;AAAA,MAClB,GAAG;AAAA,MACH;AAAA,IACD,CAAA;AAAA,EACL;AACF;;;"}
@@ -76,7 +76,7 @@ export type ServerRouteMethodHandlerFn<TParentRoute extends AnyServerRouteWithTy
76
76
  export interface ServerRouteMethodHandlerCtx<in out TParentRoute extends AnyServerRouteWithTypes, in out TFullPath extends string, in out TMiddlewares, in out TMethodMiddlewares> {
77
77
  context: Expand<AssignAllMethodContext<TParentRoute, TMiddlewares, TMethodMiddlewares>>;
78
78
  request: Request;
79
- params: ResolveParams<TFullPath>;
79
+ params: Expand<ResolveParams<TFullPath>>;
80
80
  pathname: TFullPath;
81
81
  }
82
82
  export type MergeMethodMiddlewares<TMiddlewares, TMethodMiddlewares> = TMiddlewares extends ReadonlyArray<any> ? TMethodMiddlewares extends ReadonlyArray<any> ? readonly [...TMiddlewares, ...TMethodMiddlewares] : TMiddlewares : TMethodMiddlewares;
@@ -54,10 +54,11 @@ ${jsesc(script, { quotes: "backtick" })}\`)` : ""}; if (typeof __TSR_SSR__ !== '
54
54
  });
55
55
  }
56
56
  function dehydrateRouter(router) {
57
- var _a, _b;
57
+ var _a, _b, _c;
58
58
  const dehydratedRouter = {
59
59
  manifest: router.ssr.manifest,
60
- dehydratedData: (_b = (_a = router.options).dehydrate) == null ? void 0 : _b.call(_a)
60
+ dehydratedData: (_b = (_a = router.options).dehydrate) == null ? void 0 : _b.call(_a),
61
+ lastMatchId: ((_c = router.state.matches[router.state.matches.length - 1]) == null ? void 0 : _c.id) || ""
61
62
  };
62
63
  router.serverSsr.injectScript(
63
64
  () => `__TSR_SSR__.dehydrated = ${jsesc(
@@ -1 +1 @@
1
- {"version":3,"file":"ssr-server.cjs","sources":["../../src/ssr-server.ts"],"sourcesContent":["import { default as warning } from 'tiny-warning'\nimport {\n TSR_DEFERRED_PROMISE,\n defer,\n isPlainArray,\n isPlainObject,\n pick,\n} from '@tanstack/router-core'\nimport jsesc from 'jsesc'\nimport { startSerializer } from '@tanstack/start-client-core'\nimport minifiedTsrBootStrapScript from './tsrScript?script-string'\nimport type {\n ClientExtractedBaseEntry,\n DehydratedRouter,\n ResolvePromiseState,\n SsrMatch,\n} from '@tanstack/start-client-core'\nimport type {\n AnyRouteMatch,\n AnyRouter,\n DeferredPromise,\n Manifest,\n} from '@tanstack/router-core'\n\nexport type ServerExtractedEntry =\n | ServerExtractedStream\n | ServerExtractedPromise\n\nexport interface ServerExtractedBaseEntry extends ClientExtractedBaseEntry {\n id: number\n matchIndex: number\n}\n\nexport interface ServerExtractedStream extends ServerExtractedBaseEntry {\n type: 'stream'\n stream: ReadableStream\n}\n\nexport interface ServerExtractedPromise extends ServerExtractedBaseEntry {\n type: 'promise'\n promise: DeferredPromise<any>\n}\n\nexport function attachRouterServerSsrUtils(\n router: AnyRouter,\n manifest: Manifest | undefined,\n) {\n router.ssr = {\n manifest,\n serializer: startSerializer,\n }\n\n router.serverSsr = {\n injectedHtml: [],\n streamedKeys: new Set(),\n injectHtml: (getHtml) => {\n const promise = Promise.resolve().then(getHtml)\n router.serverSsr!.injectedHtml.push(promise)\n router.emit({\n type: 'onInjectedHtml',\n promise,\n })\n\n return promise.then(() => {})\n },\n injectScript: (getScript, opts) => {\n return router.serverSsr!.injectHtml(async () => {\n const script = await getScript()\n return `<script class='tsr-once'>${script}${\n process.env.NODE_ENV === 'development' && (opts?.logScript ?? true)\n ? `; console.info(\\`Injected From Server:\n${jsesc(script, { quotes: 'backtick' })}\\`)`\n : ''\n }; if (typeof __TSR_SSR__ !== 'undefined') __TSR_SSR__.cleanScripts()</script>`\n })\n },\n streamValue: (key, value) => {\n warning(\n !router.serverSsr!.streamedKeys.has(key),\n 'Key has already been streamed: ' + key,\n )\n\n router.serverSsr!.streamedKeys.add(key)\n router.serverSsr!.injectScript(\n () =>\n `__TSR_SSR__.streamedValues['${key}'] = { value: ${jsesc(\n router.ssr!.serializer.stringify(value),\n {\n isScriptContext: true,\n wrap: true,\n json: true,\n },\n )}}`,\n )\n },\n onMatchSettled,\n }\n\n router.serverSsr.injectScript(() => minifiedTsrBootStrapScript, {\n logScript: false,\n })\n}\n\nexport function dehydrateRouter(router: AnyRouter) {\n const dehydratedRouter: DehydratedRouter = {\n manifest: router.ssr!.manifest,\n dehydratedData: router.options.dehydrate?.(),\n }\n\n router.serverSsr!.injectScript(\n () =>\n `__TSR_SSR__.dehydrated = ${jsesc(\n router.ssr!.serializer.stringify(dehydratedRouter),\n {\n isScriptContext: true,\n wrap: true,\n json: true,\n },\n )}`,\n )\n}\n\nexport function extractAsyncLoaderData(\n loaderData: any,\n ctx: {\n match: AnyRouteMatch\n router: AnyRouter\n },\n) {\n const extracted: Array<ServerExtractedEntry> = []\n\n const replaced = replaceBy(loaderData, (value, path) => {\n // If it's a stream, we need to tee it so we can read it multiple times\n if (value instanceof ReadableStream) {\n const [copy1, copy2] = value.tee()\n const entry: ServerExtractedStream = {\n type: 'stream',\n path,\n id: extracted.length,\n matchIndex: ctx.match.index,\n stream: copy2,\n }\n\n extracted.push(entry)\n return copy1\n } else if (value instanceof Promise) {\n const deferredPromise = defer(value)\n const entry: ServerExtractedPromise = {\n type: 'promise',\n path,\n id: extracted.length,\n matchIndex: ctx.match.index,\n promise: deferredPromise,\n }\n extracted.push(entry)\n }\n\n return value\n })\n\n return { replaced, extracted }\n}\n\nexport function onMatchSettled(opts: {\n router: AnyRouter\n match: AnyRouteMatch\n}) {\n const { router, match } = opts\n\n let extracted: Array<ServerExtractedEntry> | undefined = undefined\n let serializedLoaderData: any = undefined\n if (match.loaderData !== undefined) {\n const result = extractAsyncLoaderData(match.loaderData, {\n router,\n match,\n })\n match.loaderData = result.replaced\n extracted = result.extracted\n serializedLoaderData = extracted.reduce(\n (acc: any, entry: ServerExtractedEntry) => {\n return deepImmutableSetByPath(acc, ['temp', ...entry.path], undefined)\n },\n { temp: result.replaced },\n ).temp\n }\n\n const initCode = `__TSR_SSR__.initMatch(${jsesc(\n {\n id: match.id,\n __beforeLoadContext: router.ssr!.serializer.stringify(\n match.__beforeLoadContext,\n ),\n loaderData: router.ssr!.serializer.stringify(serializedLoaderData),\n error: router.ssr!.serializer.stringify(match.error),\n extracted: extracted?.map((entry) => pick(entry, ['type', 'path'])),\n updatedAt: match.updatedAt,\n status: match.status,\n } satisfies SsrMatch,\n {\n isScriptContext: true,\n wrap: true,\n json: true,\n },\n )})`\n\n router.serverSsr!.injectScript(() => initCode)\n\n if (extracted) {\n extracted.forEach((entry) => {\n if (entry.type === 'promise') return injectPromise(entry)\n return injectStream(entry)\n })\n }\n\n function injectPromise(entry: ServerExtractedPromise) {\n router.serverSsr!.injectScript(async () => {\n await entry.promise\n\n return `__TSR_SSR__.resolvePromise(${jsesc(\n {\n matchId: match.id,\n id: entry.id,\n promiseState: entry.promise[TSR_DEFERRED_PROMISE],\n } satisfies ResolvePromiseState,\n {\n isScriptContext: true,\n wrap: true,\n json: true,\n },\n )})`\n })\n }\n\n function injectStream(entry: ServerExtractedStream) {\n // Inject a promise that resolves when the stream is done\n // We do this to keep the stream open until we're done\n router.serverSsr!.injectHtml(async () => {\n //\n try {\n const reader = entry.stream.getReader()\n let chunk: ReadableStreamReadResult<any> | null = null\n while (!(chunk = await reader.read()).done) {\n if (chunk.value) {\n const code = `__TSR_SSR__.injectChunk(${jsesc(\n {\n matchId: match.id,\n id: entry.id,\n chunk: chunk.value,\n },\n {\n isScriptContext: true,\n wrap: true,\n json: true,\n },\n )})`\n\n router.serverSsr!.injectScript(() => code)\n }\n }\n\n router.serverSsr!.injectScript(\n () =>\n `__TSR_SSR__.closeStream(${jsesc(\n {\n matchId: match.id,\n id: entry.id,\n },\n {\n isScriptContext: true,\n wrap: true,\n json: true,\n },\n )})`,\n )\n } catch (err) {\n console.error('stream read error', err)\n }\n\n return ''\n })\n }\n}\n\nfunction deepImmutableSetByPath<T>(obj: T, path: Array<string>, value: any): T {\n // immutable set by path retaining array and object references\n if (path.length === 0) {\n return value\n }\n\n const [key, ...rest] = path\n\n if (Array.isArray(obj)) {\n return obj.map((item, i) => {\n if (i === Number(key)) {\n return deepImmutableSetByPath(item, rest, value)\n }\n return item\n }) as T\n }\n\n if (isPlainObject(obj)) {\n return {\n ...obj,\n [key!]: deepImmutableSetByPath((obj as any)[key!], rest, value),\n }\n }\n\n return obj\n}\n\nexport function replaceBy<T>(\n obj: T,\n cb: (value: any, path: Array<string>) => any,\n path: Array<string> = [],\n): T {\n if (isPlainArray(obj)) {\n return obj.map((value, i) => replaceBy(value, cb, [...path, `${i}`])) as any\n }\n\n if (isPlainObject(obj)) {\n // Do not allow objects with illegal\n const newObj: any = {}\n\n for (const key in obj) {\n newObj[key] = replaceBy(obj[key], cb, [...path, key])\n }\n\n return newObj\n }\n\n // // Detect classes, functions, and other non-serializable objects\n // // and return undefined. Exclude some known types that are serializable\n // if (\n // typeof obj === 'function' ||\n // (typeof obj === 'object' &&\n // ![Object, Promise, ReadableStream].includes((obj as any)?.constructor))\n // ) {\n // console.info(obj)\n // warning(false, `Non-serializable value ☝️ found at ${path.join('.')}`)\n // return undefined as any\n // }\n\n const newObj = cb(obj, path)\n\n if (newObj !== obj) {\n return newObj\n }\n\n return obj\n}\n"],"names":["startSerializer","minifiedTsrBootStrapScript","defer","pick","TSR_DEFERRED_PROMISE","isPlainObject","isPlainArray","newObj"],"mappings":"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"}
1
+ {"version":3,"file":"ssr-server.cjs","sources":["../../src/ssr-server.ts"],"sourcesContent":["import { default as warning } from 'tiny-warning'\nimport {\n TSR_DEFERRED_PROMISE,\n defer,\n isPlainArray,\n isPlainObject,\n pick,\n} from '@tanstack/router-core'\nimport jsesc from 'jsesc'\nimport { startSerializer } from '@tanstack/start-client-core'\nimport minifiedTsrBootStrapScript from './tsrScript?script-string'\nimport type {\n ClientExtractedBaseEntry,\n DehydratedRouter,\n ResolvePromiseState,\n SsrMatch,\n} from '@tanstack/start-client-core'\nimport type {\n AnyRouteMatch,\n AnyRouter,\n DeferredPromise,\n Manifest,\n} from '@tanstack/router-core'\n\nexport type ServerExtractedEntry =\n | ServerExtractedStream\n | ServerExtractedPromise\n\nexport interface ServerExtractedBaseEntry extends ClientExtractedBaseEntry {\n id: number\n matchIndex: number\n}\n\nexport interface ServerExtractedStream extends ServerExtractedBaseEntry {\n type: 'stream'\n stream: ReadableStream\n}\n\nexport interface ServerExtractedPromise extends ServerExtractedBaseEntry {\n type: 'promise'\n promise: DeferredPromise<any>\n}\n\nexport function attachRouterServerSsrUtils(\n router: AnyRouter,\n manifest: Manifest | undefined,\n) {\n router.ssr = {\n manifest,\n serializer: startSerializer,\n }\n\n router.serverSsr = {\n injectedHtml: [],\n streamedKeys: new Set(),\n injectHtml: (getHtml) => {\n const promise = Promise.resolve().then(getHtml)\n router.serverSsr!.injectedHtml.push(promise)\n router.emit({\n type: 'onInjectedHtml',\n promise,\n })\n\n return promise.then(() => {})\n },\n injectScript: (getScript, opts) => {\n return router.serverSsr!.injectHtml(async () => {\n const script = await getScript()\n return `<script class='tsr-once'>${script}${\n process.env.NODE_ENV === 'development' && (opts?.logScript ?? true)\n ? `; console.info(\\`Injected From Server:\n${jsesc(script, { quotes: 'backtick' })}\\`)`\n : ''\n }; if (typeof __TSR_SSR__ !== 'undefined') __TSR_SSR__.cleanScripts()</script>`\n })\n },\n streamValue: (key, value) => {\n warning(\n !router.serverSsr!.streamedKeys.has(key),\n 'Key has already been streamed: ' + key,\n )\n\n router.serverSsr!.streamedKeys.add(key)\n router.serverSsr!.injectScript(\n () =>\n `__TSR_SSR__.streamedValues['${key}'] = { value: ${jsesc(\n router.ssr!.serializer.stringify(value),\n {\n isScriptContext: true,\n wrap: true,\n json: true,\n },\n )}}`,\n )\n },\n onMatchSettled,\n }\n\n router.serverSsr.injectScript(() => minifiedTsrBootStrapScript, {\n logScript: false,\n })\n}\n\nexport function dehydrateRouter(router: AnyRouter) {\n const dehydratedRouter: DehydratedRouter = {\n manifest: router.ssr!.manifest,\n dehydratedData: router.options.dehydrate?.(),\n lastMatchId:\n router.state.matches[router.state.matches.length - 1]?.id || '',\n }\n\n router.serverSsr!.injectScript(\n () =>\n `__TSR_SSR__.dehydrated = ${jsesc(\n router.ssr!.serializer.stringify(dehydratedRouter),\n {\n isScriptContext: true,\n wrap: true,\n json: true,\n },\n )}`,\n )\n}\n\nexport function extractAsyncLoaderData(\n loaderData: any,\n ctx: {\n match: AnyRouteMatch\n router: AnyRouter\n },\n) {\n const extracted: Array<ServerExtractedEntry> = []\n\n const replaced = replaceBy(loaderData, (value, path) => {\n // If it's a stream, we need to tee it so we can read it multiple times\n if (value instanceof ReadableStream) {\n const [copy1, copy2] = value.tee()\n const entry: ServerExtractedStream = {\n type: 'stream',\n path,\n id: extracted.length,\n matchIndex: ctx.match.index,\n stream: copy2,\n }\n\n extracted.push(entry)\n return copy1\n } else if (value instanceof Promise) {\n const deferredPromise = defer(value)\n const entry: ServerExtractedPromise = {\n type: 'promise',\n path,\n id: extracted.length,\n matchIndex: ctx.match.index,\n promise: deferredPromise,\n }\n extracted.push(entry)\n }\n\n return value\n })\n\n return { replaced, extracted }\n}\n\nexport function onMatchSettled(opts: {\n router: AnyRouter\n match: AnyRouteMatch\n}) {\n const { router, match } = opts\n\n let extracted: Array<ServerExtractedEntry> | undefined = undefined\n let serializedLoaderData: any = undefined\n if (match.loaderData !== undefined) {\n const result = extractAsyncLoaderData(match.loaderData, {\n router,\n match,\n })\n match.loaderData = result.replaced\n extracted = result.extracted\n serializedLoaderData = extracted.reduce(\n (acc: any, entry: ServerExtractedEntry) => {\n return deepImmutableSetByPath(acc, ['temp', ...entry.path], undefined)\n },\n { temp: result.replaced },\n ).temp\n }\n\n const initCode = `__TSR_SSR__.initMatch(${jsesc(\n {\n id: match.id,\n __beforeLoadContext: router.ssr!.serializer.stringify(\n match.__beforeLoadContext,\n ),\n loaderData: router.ssr!.serializer.stringify(serializedLoaderData),\n error: router.ssr!.serializer.stringify(match.error),\n extracted: extracted?.map((entry) => pick(entry, ['type', 'path'])),\n updatedAt: match.updatedAt,\n status: match.status,\n } satisfies SsrMatch,\n {\n isScriptContext: true,\n wrap: true,\n json: true,\n },\n )})`\n\n router.serverSsr!.injectScript(() => initCode)\n\n if (extracted) {\n extracted.forEach((entry) => {\n if (entry.type === 'promise') return injectPromise(entry)\n return injectStream(entry)\n })\n }\n\n function injectPromise(entry: ServerExtractedPromise) {\n router.serverSsr!.injectScript(async () => {\n await entry.promise\n\n return `__TSR_SSR__.resolvePromise(${jsesc(\n {\n matchId: match.id,\n id: entry.id,\n promiseState: entry.promise[TSR_DEFERRED_PROMISE],\n } satisfies ResolvePromiseState,\n {\n isScriptContext: true,\n wrap: true,\n json: true,\n },\n )})`\n })\n }\n\n function injectStream(entry: ServerExtractedStream) {\n // Inject a promise that resolves when the stream is done\n // We do this to keep the stream open until we're done\n router.serverSsr!.injectHtml(async () => {\n //\n try {\n const reader = entry.stream.getReader()\n let chunk: ReadableStreamReadResult<any> | null = null\n while (!(chunk = await reader.read()).done) {\n if (chunk.value) {\n const code = `__TSR_SSR__.injectChunk(${jsesc(\n {\n matchId: match.id,\n id: entry.id,\n chunk: chunk.value,\n },\n {\n isScriptContext: true,\n wrap: true,\n json: true,\n },\n )})`\n\n router.serverSsr!.injectScript(() => code)\n }\n }\n\n router.serverSsr!.injectScript(\n () =>\n `__TSR_SSR__.closeStream(${jsesc(\n {\n matchId: match.id,\n id: entry.id,\n },\n {\n isScriptContext: true,\n wrap: true,\n json: true,\n },\n )})`,\n )\n } catch (err) {\n console.error('stream read error', err)\n }\n\n return ''\n })\n }\n}\n\nfunction deepImmutableSetByPath<T>(obj: T, path: Array<string>, value: any): T {\n // immutable set by path retaining array and object references\n if (path.length === 0) {\n return value\n }\n\n const [key, ...rest] = path\n\n if (Array.isArray(obj)) {\n return obj.map((item, i) => {\n if (i === Number(key)) {\n return deepImmutableSetByPath(item, rest, value)\n }\n return item\n }) as T\n }\n\n if (isPlainObject(obj)) {\n return {\n ...obj,\n [key!]: deepImmutableSetByPath((obj as any)[key!], rest, value),\n }\n }\n\n return obj\n}\n\nexport function replaceBy<T>(\n obj: T,\n cb: (value: any, path: Array<string>) => any,\n path: Array<string> = [],\n): T {\n if (isPlainArray(obj)) {\n return obj.map((value, i) => replaceBy(value, cb, [...path, `${i}`])) as any\n }\n\n if (isPlainObject(obj)) {\n // Do not allow objects with illegal\n const newObj: any = {}\n\n for (const key in obj) {\n newObj[key] = replaceBy(obj[key], cb, [...path, key])\n }\n\n return newObj\n }\n\n // // Detect classes, functions, and other non-serializable objects\n // // and return undefined. Exclude some known types that are serializable\n // if (\n // typeof obj === 'function' ||\n // (typeof obj === 'object' &&\n // ![Object, Promise, ReadableStream].includes((obj as any)?.constructor))\n // ) {\n // console.info(obj)\n // warning(false, `Non-serializable value ☝️ found at ${path.join('.')}`)\n // return undefined as any\n // }\n\n const newObj = cb(obj, path)\n\n if (newObj !== obj) {\n return newObj\n }\n\n return obj\n}\n"],"names":["startSerializer","minifiedTsrBootStrapScript","defer","pick","TSR_DEFERRED_PROMISE","isPlainObject","isPlainArray","newObj"],"mappings":";;;;;;;AA2CgB,SAAA,2BACd,QACA,UACA;AACA,SAAO,MAAM;AAAA,IACX;AAAA,IACA,YAAYA,gBAAAA;AAAAA,EACd;AAEA,SAAO,YAAY;AAAA,IACjB,cAAc,CAAC;AAAA,IACf,kCAAkB,IAAI;AAAA,IACtB,YAAY,CAAC,YAAY;AACvB,YAAM,UAAU,QAAQ,QAAQ,EAAE,KAAK,OAAO;AACvC,aAAA,UAAW,aAAa,KAAK,OAAO;AAC3C,aAAO,KAAK;AAAA,QACV,MAAM;AAAA,QACN;AAAA,MAAA,CACD;AAEM,aAAA,QAAQ,KAAK,MAAM;AAAA,MAAA,CAAE;AAAA,IAC9B;AAAA,IACA,cAAc,CAAC,WAAW,SAAS;AAC1B,aAAA,OAAO,UAAW,WAAW,YAAY;AACxC,cAAA,SAAS,MAAM,UAAU;AACxB,eAAA,4BAA4B,MAAM,GACvC,QAAQ,IAAI,aAAa,mBAAkB,6BAAM,cAAa,QAC1D;AAAA,EACZ,MAAM,QAAQ,EAAE,QAAQ,WAAY,CAAA,CAAC,QACzB,EACN;AAAA,MAAA,CACD;AAAA,IACH;AAAA,IACA,aAAa,CAAC,KAAK,UAAU;AAC3B;AAAA,QACE,CAAC,OAAO,UAAW,aAAa,IAAI,GAAG;AAAA,QACvC,oCAAoC;AAAA,MACtC;AAEO,aAAA,UAAW,aAAa,IAAI,GAAG;AACtC,aAAO,UAAW;AAAA,QAChB,MACE,+BAA+B,GAAG,iBAAiB;AAAA,UACjD,OAAO,IAAK,WAAW,UAAU,KAAK;AAAA,UACtC;AAAA,YACE,iBAAiB;AAAA,YACjB,MAAM;AAAA,YACN,MAAM;AAAA,UAAA;AAAA,QACR,CACD;AAAA,MACL;AAAA,IACF;AAAA,IACA;AAAA,EACF;AAEO,SAAA,UAAU,aAAa,MAAMC,WAA4B;AAAA,IAC9D,WAAW;AAAA,EAAA,CACZ;AACH;AAEO,SAAS,gBAAgB,QAAmB;;AACjD,QAAM,mBAAqC;AAAA,IACzC,UAAU,OAAO,IAAK;AAAA,IACtB,iBAAgB,kBAAO,SAAQ,cAAf;AAAA,IAChB,eACE,YAAO,MAAM,QAAQ,OAAO,MAAM,QAAQ,SAAS,CAAC,MAApD,mBAAuD,OAAM;AAAA,EACjE;AAEA,SAAO,UAAW;AAAA,IAChB,MACE,4BAA4B;AAAA,MAC1B,OAAO,IAAK,WAAW,UAAU,gBAAgB;AAAA,MACjD;AAAA,QACE,iBAAiB;AAAA,QACjB,MAAM;AAAA,QACN,MAAM;AAAA,MAAA;AAAA,IACR,CACD;AAAA,EACL;AACF;AAEgB,SAAA,uBACd,YACA,KAIA;AACA,QAAM,YAAyC,CAAC;AAEhD,QAAM,WAAW,UAAU,YAAY,CAAC,OAAO,SAAS;AAEtD,QAAI,iBAAiB,gBAAgB;AACnC,YAAM,CAAC,OAAO,KAAK,IAAI,MAAM,IAAI;AACjC,YAAM,QAA+B;AAAA,QACnC,MAAM;AAAA,QACN;AAAA,QACA,IAAI,UAAU;AAAA,QACd,YAAY,IAAI,MAAM;AAAA,QACtB,QAAQ;AAAA,MACV;AAEA,gBAAU,KAAK,KAAK;AACb,aAAA;AAAA,IAAA,WACE,iBAAiB,SAAS;AAC7B,YAAA,kBAAkBC,iBAAM,KAAK;AACnC,YAAM,QAAgC;AAAA,QACpC,MAAM;AAAA,QACN;AAAA,QACA,IAAI,UAAU;AAAA,QACd,YAAY,IAAI,MAAM;AAAA,QACtB,SAAS;AAAA,MACX;AACA,gBAAU,KAAK,KAAK;AAAA,IAAA;AAGf,WAAA;AAAA,EAAA,CACR;AAEM,SAAA,EAAE,UAAU,UAAU;AAC/B;AAEO,SAAS,eAAe,MAG5B;AACK,QAAA,EAAE,QAAQ,MAAA,IAAU;AAE1B,MAAI,YAAqD;AACzD,MAAI,uBAA4B;AAC5B,MAAA,MAAM,eAAe,QAAW;AAC5B,UAAA,SAAS,uBAAuB,MAAM,YAAY;AAAA,MAEtD;AAAA,IAAA,CACD;AACD,UAAM,aAAa,OAAO;AAC1B,gBAAY,OAAO;AACnB,2BAAuB,UAAU;AAAA,MAC/B,CAAC,KAAU,UAAgC;AAClC,eAAA,uBAAuB,KAAK,CAAC,QAAQ,GAAG,MAAM,IAAI,GAAG,MAAS;AAAA,MACvE;AAAA,MACA,EAAE,MAAM,OAAO,SAAS;AAAA,IAAA,EACxB;AAAA,EAAA;AAGJ,QAAM,WAAW,yBAAyB;AAAA,IACxC;AAAA,MACE,IAAI,MAAM;AAAA,MACV,qBAAqB,OAAO,IAAK,WAAW;AAAA,QAC1C,MAAM;AAAA,MACR;AAAA,MACA,YAAY,OAAO,IAAK,WAAW,UAAU,oBAAoB;AAAA,MACjE,OAAO,OAAO,IAAK,WAAW,UAAU,MAAM,KAAK;AAAA,MACnD,WAAW,uCAAW,IAAI,CAAC,UAAUC,gBAAK,OAAO,CAAC,QAAQ,MAAM,CAAC;AAAA,MACjE,WAAW,MAAM;AAAA,MACjB,QAAQ,MAAM;AAAA,IAChB;AAAA,IACA;AAAA,MACE,iBAAiB;AAAA,MACjB,MAAM;AAAA,MACN,MAAM;AAAA,IAAA;AAAA,EAET,CAAA;AAEM,SAAA,UAAW,aAAa,MAAM,QAAQ;AAE7C,MAAI,WAAW;AACH,cAAA,QAAQ,CAAC,UAAU;AAC3B,UAAI,MAAM,SAAS,UAAW,QAAO,cAAc,KAAK;AACxD,aAAO,aAAa,KAAK;AAAA,IAAA,CAC1B;AAAA,EAAA;AAGH,WAAS,cAAc,OAA+B;AAC7C,WAAA,UAAW,aAAa,YAAY;AACzC,YAAM,MAAM;AAEZ,aAAO,8BAA8B;AAAA,QACnC;AAAA,UACE,SAAS,MAAM;AAAA,UACf,IAAI,MAAM;AAAA,UACV,cAAc,MAAM,QAAQC,WAAoB,oBAAA;AAAA,QAClD;AAAA,QACA;AAAA,UACE,iBAAiB;AAAA,UACjB,MAAM;AAAA,UACN,MAAM;AAAA,QAAA;AAAA,MAET,CAAA;AAAA,IAAA,CACF;AAAA,EAAA;AAGH,WAAS,aAAa,OAA8B;AAG3C,WAAA,UAAW,WAAW,YAAY;AAEnC,UAAA;AACI,cAAA,SAAS,MAAM,OAAO,UAAU;AACtC,YAAI,QAA8C;AAClD,eAAO,EAAE,QAAQ,MAAM,OAAO,KAAA,GAAQ,MAAM;AAC1C,cAAI,MAAM,OAAO;AACf,kBAAM,OAAO,2BAA2B;AAAA,cACtC;AAAA,gBACE,SAAS,MAAM;AAAA,gBACf,IAAI,MAAM;AAAA,gBACV,OAAO,MAAM;AAAA,cACf;AAAA,cACA;AAAA,gBACE,iBAAiB;AAAA,gBACjB,MAAM;AAAA,gBACN,MAAM;AAAA,cAAA;AAAA,YAET,CAAA;AAEM,mBAAA,UAAW,aAAa,MAAM,IAAI;AAAA,UAAA;AAAA,QAC3C;AAGF,eAAO,UAAW;AAAA,UAChB,MACE,2BAA2B;AAAA,YACzB;AAAA,cACE,SAAS,MAAM;AAAA,cACf,IAAI,MAAM;AAAA,YACZ;AAAA,YACA;AAAA,cACE,iBAAiB;AAAA,cACjB,MAAM;AAAA,cACN,MAAM;AAAA,YAAA;AAAA,UACR,CACD;AAAA,QACL;AAAA,eACO,KAAK;AACJ,gBAAA,MAAM,qBAAqB,GAAG;AAAA,MAAA;AAGjC,aAAA;AAAA,IAAA,CACR;AAAA,EAAA;AAEL;AAEA,SAAS,uBAA0B,KAAQ,MAAqB,OAAe;AAEzE,MAAA,KAAK,WAAW,GAAG;AACd,WAAA;AAAA,EAAA;AAGT,QAAM,CAAC,KAAK,GAAG,IAAI,IAAI;AAEnB,MAAA,MAAM,QAAQ,GAAG,GAAG;AACtB,WAAO,IAAI,IAAI,CAAC,MAAM,MAAM;AACtB,UAAA,MAAM,OAAO,GAAG,GAAG;AACd,eAAA,uBAAuB,MAAM,MAAM,KAAK;AAAA,MAAA;AAE1C,aAAA;AAAA,IAAA,CACR;AAAA,EAAA;AAGC,MAAAC,WAAAA,cAAc,GAAG,GAAG;AACf,WAAA;AAAA,MACL,GAAG;AAAA,MACH,CAAC,GAAI,GAAG,uBAAwB,IAAY,GAAI,GAAG,MAAM,KAAK;AAAA,IAChE;AAAA,EAAA;AAGK,SAAA;AACT;AAEO,SAAS,UACd,KACA,IACA,OAAsB,CAAA,GACnB;AACC,MAAAC,WAAAA,aAAa,GAAG,GAAG;AACrB,WAAO,IAAI,IAAI,CAAC,OAAO,MAAM,UAAU,OAAO,IAAI,CAAC,GAAG,MAAM,GAAG,CAAC,EAAE,CAAC,CAAC;AAAA,EAAA;AAGlE,MAAAD,WAAAA,cAAc,GAAG,GAAG;AAEtB,UAAME,UAAc,CAAC;AAErB,eAAW,OAAO,KAAK;AACrBA,cAAO,GAAG,IAAI,UAAU,IAAI,GAAG,GAAG,IAAI,CAAC,GAAG,MAAM,GAAG,CAAC;AAAA,IAAA;AAG/CA,WAAAA;AAAAA,EAAA;AAeH,QAAA,SAAS,GAAG,KAAK,IAAI;AAE3B,MAAI,WAAW,KAAK;AACX,WAAA;AAAA,EAAA;AAGF,SAAA;AACT;;;;;;"}
@@ -1,7 +1,6 @@
1
- import path from "node:path";
2
1
  import { createMemoryHistory } from "@tanstack/history";
3
2
  import { mergeHeaders, json, flattenMiddlewares } from "@tanstack/start-client-core";
4
- import { isRedirect, tsrRedirectHeaderKey, processRouteTree, getMatchedRoutes, rootRouteId } from "@tanstack/router-core";
3
+ import { joinPaths, trimPath, isRedirect, isResolvedRedirect, processRouteTree, getMatchedRoutes, rootRouteId } from "@tanstack/router-core";
5
4
  import { getResponseHeaders, requestHandler } from "./h3.js";
6
5
  import { attachRouterServerSsrUtils, dehydrateRouter } from "./ssr-server.js";
7
6
  import { getStartManifest } from "./router-manifest.js";
@@ -44,7 +43,12 @@ function createStartHandler({
44
43
  "tanstack/start-server-core: TSS_SERVER_FN_BASE must be defined in your environment for createStartHandler()"
45
44
  );
46
45
  }
47
- if (href.startsWith(path.join("/", process.env.TSS_SERVER_FN_BASE, "/"))) {
46
+ const serverFnBase = joinPaths([
47
+ "/",
48
+ trimPath(process.env.TSS_SERVER_FN_BASE),
49
+ "/"
50
+ ]);
51
+ if (href.startsWith(serverFnBase)) {
48
52
  return await handleServerAction({ request });
49
53
  }
50
54
  const serverRouteTreeModule = await (async () => {
@@ -56,7 +60,7 @@ function createStartHandler({
56
60
  }
57
61
  })();
58
62
  if (serverRouteTreeModule) {
59
- const [matchedRoutes, response3] = await handleServerRoutes({
63
+ const [_matchedRoutes, response3] = await handleServerRoutes({
60
64
  routeTree: serverRouteTreeModule.routeTree,
61
65
  request
62
66
  });
@@ -98,6 +102,20 @@ function createStartHandler({
98
102
  }
99
103
  })();
100
104
  if (isRedirect(response)) {
105
+ if (isResolvedRedirect(response)) {
106
+ if (request.headers.get("x-tsr-redirect") === "manual") {
107
+ return json(
108
+ {
109
+ ...response.options,
110
+ isSerializedRedirect: true
111
+ },
112
+ {
113
+ headers: response.headers
114
+ }
115
+ );
116
+ }
117
+ return response;
118
+ }
101
119
  if (response.options.to && typeof response.options.to === "string" && !response.options.to.startsWith("/")) {
102
120
  throw new Error(
103
121
  `Server side redirects must use absolute paths via the 'href' or 'to' options. Received: ${JSON.stringify(response.options)}`
@@ -120,16 +138,12 @@ function createStartHandler({
120
138
  isSerializedRedirect: true
121
139
  },
122
140
  {
123
- headers: redirect.headers
141
+ headers: response.headers
124
142
  }
125
143
  );
126
144
  }
127
145
  return redirect;
128
146
  }
129
- response.headers.append(
130
- "Access-Control-Expose-Headers",
131
- tsrRedirectHeaderKey
132
- );
133
147
  return response;
134
148
  });
135
149
  };
@@ -223,7 +237,10 @@ function handleCtxResult(result) {
223
237
  return result;
224
238
  }
225
239
  function isSpecialResponse(err) {
226
- return err instanceof Response || isRedirect(err);
240
+ return isResponse(err) || isRedirect(err);
241
+ }
242
+ function isResponse(response) {
243
+ return response instanceof Response;
227
244
  }
228
245
  export {
229
246
  createStartHandler,