You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Fails to build in bun-only environment when using virtualRouteConfig #6061
When using virtualRouteConfig with tanstack/start, loadConfigFile uses tsx behind the scenes to load the config file. The problem is that tsx is node specific and doesn't work with bun.
The hacky solution is to make sure your environment also has node installed. (So I've updated our Dockerfile to install node before running vite build, but then it continues to use bun to serve the server).
I am unsure what the full solution should be... change how the virtualRouteConfig gets loaded? add a "bun" flag?
Your Example Website or App
I could build a full reproduction but it would take a lot of time when the issue is easy to see in the code (it uses tsx!)
Steps to Reproduce the Bug or Issue
use virtualRouteConfig and try to build with only bun.
Expected behavior
I would expect tanstack/start to work with bun when using virtualRouteConfig.
Screenshots or Videos
No response
Platform
Router / Start Version: 1.134.10 (but the issue is there in latest)
Enable TanStack Start's virtualRouteConfig feature to work in Bun runtime by making the config file loading mechanism runtime-aware, allowing it to use Bun's native TypeScript import instead of the Node-specific tsx loader.
Observations
The router-generator package provides utilities for generating TanStack Router route trees from both physical file system structures and virtual route configurations. The virtual route config loader (loadConfigFile.ts) currently uses tsx's tsImport API to dynamically load TypeScript configuration files at runtime. This function is used by both virtual and physical route node generators when loading external or inline route configuration files. The codebase currently assumes a Node.js runtime and uses Node-specific APIs (node:fs, node:path, node:url) throughout.
AssumptionsAssumption 1: Runtime Detection Method
Options Considered:
Check typeof Bun !== "undefined" - requires bun-types to avoid TypeScript errors
Check process.versions.bun - safer in TypeScript environments and more idiomatic
Chosen Option: Use process.versions.bun for detection
Rationale: This approach is TypeScript-safe, doesn't require additional type definitions, and aligns with standard Node.js version detection patterns. Developers familiar with Node.js will recognize this pattern immediately.
Assumption 2: Scope of Runtime Support
Options Considered:
Add support for Bun only
Add abstraction layer for multiple runtimes (Bun, Deno, Node)
Chosen Option: Focus solely on Bun support for now
Rationale: The ticket specifically requests Bun support, and adding a more complex abstraction layer would be over-engineering. If Deno or other runtime support is needed later, the runtime detection pattern can be extended following the same approach established here.
💡 User Tips
Regenerate the plan with different choices with @coderabbitai <feedback>.
Plan
Add Bun Runtime Support to Config File Loading
This phase modifies the config file loading mechanism to detect and handle both Node.js and Bun runtimes, ensuring the virtualRouteConfig feature works in both environments without requiring Node.js installation in Bun-only environments.
Task 1: Add Runtime Detection Logic
Implement runtime detection to determine whether code is executing in Bun or Node.js environment.
Add conditional check using process.versions.bun at the start of loadConfigFile function in packages/router-generator/src/filesystem/virtual/loadConfigFile.ts
The check should determine which import strategy to use without adding external dependencies
Task 2: Implement Dual Import Strategy
Create separate code paths for Bun's native TypeScript import and Node.js tsx import.
For Bun runtime: Use native import() function with the file URL, which Bun handles natively without requiring tsx
For Node.js runtime: Preserve existing tsx tsImport logic to maintain backward compatibility
Both paths should convert file paths to URLs using pathToFileURL from node:url
Both paths must return the same module exports object structure to ensure consistent behavior for downstream consumers
Task 3: Ensure Error Handling Consistency
Update error handling to provide clear feedback regardless of runtime.
Catch and handle import failures from both the native import() (Bun) and tsImport (Node) paths
Ensure error messages indicate which runtime was detected if import fails
Maintain the existing error contract expected by getRouteNodes.ts in both virtual and physical filesystem modules
🤖 Prompt for AI agents
Modify the config file loading mechanism to support both Bun and Node.js
runtimes, enabling virtualRouteConfig to work in Bun environments.
In `packages/router-generator/src/filesystem/virtual/loadConfigFile.ts`:
- Add runtime detection at the start of `loadConfigFile` using
`process.versions.bun` check
- Implement conditional import strategy: use native `import()` with
`pathToFileURL` for Bun runtime, preserve existing tsx `tsImport` for Node.js
- Ensure both paths convert file paths to URLs and return consistent module
exports structure
- Add error handling for both import paths with runtime-specific error messages
- Maintain backward compatibility and existing error contract for downstream
consumers
🚀 Next Steps
🤖 All AI agent prompts combined
Modify the config file loading mechanism to support both Bun and Node.js
runtimes, enabling virtualRouteConfig to work in Bun environments.
In `packages/router-generator/src/filesystem/virtual/loadConfigFile.ts`:
- Add runtime detection at the start of `loadConfigFile` using
`process.versions.bun` check
- Implement conditional import strategy: use native `import()` with
`pathToFileURL` for Bun runtime, preserve existing tsx `tsImport` for Node.js
- Ensure both paths convert file paths to URLs and return consistent module
exports structure
- Add error handling for both import paths with runtime-specific error messages
- Maintain backward compatibility and existing error contract for downstream
consumers
💡 Iterate on the plan with:
@coderabbitai <feedback>
Example Feedback
- @coderabbitai You can skip phase 3. Add a simple unit test case for phase 2.
- @coderabbitai For assumption 1 go ahead with option 3 and replan.
Activity
coderabbitai commentedon Dec 10, 2025
📝 CodeRabbit Plan Mode
Generate an implementation plan and agent prompts for this issue.
✅ Successfully generated implementation plan.
💡 Use
@coderabbitai <feedback>to replanExamples
🔗 Similar Issues
Related Issues
🔗 Related PRs
#5422 - fix(router-devtools-core): actually bundle solid [merged]
#5816 - docs(solid-start): start-bun example [merged]
#5847 - docs(solid-start): start-large example [merged]
#5849 - docs(solid-start): start-tailwind-v4 [merged]
👤 Suggested Assignees
🧪 Issue enrichment is currently in early access.
To disable automatic issue enrichment, add the following to your
.coderabbit.yaml:schiller-manuel commentedon Dec 10, 2025
for now you should be able to import the config yourself and pass it in instead of the filename
willhoney7 commentedon Dec 10, 2025
oh. that is a much better solution! thank you!
Maybe passing in a file path should be deprecated and the docs should guide towards passing in the route config object itself?
coderabbitai commentedon Dec 10, 2025
Implementation Plan
Approach
Enable TanStack Start's
virtualRouteConfigfeature to work in Bun runtime by making the config file loading mechanism runtime-aware, allowing it to use Bun's native TypeScript import instead of the Node-specific tsx loader.Observations
The router-generator package provides utilities for generating TanStack Router route trees from both physical file system structures and virtual route configurations. The virtual route config loader (
loadConfigFile.ts) currently uses tsx'stsImportAPI to dynamically load TypeScript configuration files at runtime. This function is used by both virtual and physical route node generators when loading external or inline route configuration files. The codebase currently assumes a Node.js runtime and uses Node-specific APIs (node:fs,node:path,node:url) throughout.Assumptions
Assumption 1: Runtime Detection Method
Options Considered:
typeof Bun !== "undefined"- requires bun-types to avoid TypeScript errorsprocess.versions.bun- safer in TypeScript environments and more idiomaticChosen Option: Use
process.versions.bunfor detectionRationale: This approach is TypeScript-safe, doesn't require additional type definitions, and aligns with standard Node.js version detection patterns. Developers familiar with Node.js will recognize this pattern immediately.
Assumption 2: Scope of Runtime Support
Options Considered:
Chosen Option: Focus solely on Bun support for now
Rationale: The ticket specifically requests Bun support, and adding a more complex abstraction layer would be over-engineering. If Deno or other runtime support is needed later, the runtime detection pattern can be extended following the same approach established here.
💡 User Tips
Regenerate the plan with different choices with
@coderabbitai <feedback>.Plan
Add Bun Runtime Support to Config File Loading
This phase modifies the config file loading mechanism to detect and handle both Node.js and Bun runtimes, ensuring the virtualRouteConfig feature works in both environments without requiring Node.js installation in Bun-only environments.
Task 1: Add Runtime Detection Logic
Implement runtime detection to determine whether code is executing in Bun or Node.js environment.
process.versions.bunat the start ofloadConfigFilefunction inpackages/router-generator/src/filesystem/virtual/loadConfigFile.tsTask 2: Implement Dual Import Strategy
Create separate code paths for Bun's native TypeScript import and Node.js tsx import.
import()function with the file URL, which Bun handles natively without requiring tsxtsImportlogic to maintain backward compatibilitypathToFileURLfromnode:urlTask 3: Ensure Error Handling Consistency
Update error handling to provide clear feedback regardless of runtime.
import()(Bun) andtsImport(Node) pathsgetRouteNodes.tsin both virtual and physical filesystem modules🤖 Prompt for AI agents
🚀 Next Steps
🤖 All AI agent prompts combined
💡 Iterate on the plan with:
@coderabbitai <feedback>schiller-manuel commentedon Apr 25, 2026
migrated to jiti now