-
Notifications
You must be signed in to change notification settings - Fork 2.4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Dev server HMR and *.server.ts naming convention doesn't work with monorepos using shared routes #6711
Comments
I had the same problem |
HMR is working fine for me with NX monorepo |
Are you using typescript path aliases to share code in the monorepo or a separate build for the shared packages? I think path aliases are causing the issue since it means the linked source code is outside the app dir. We use path aliases to share feature routes and code between multiple remix/react-router apps. Would be great to hear what your Nx setup with Remix looks like. |
I have a few typescript libs in de |
Thanks, this is the key. If the route files are shared outside the app dir then HMR and naming conventions don't work. I've created a minimal reproduction repo at https://github.com/jrestall/remix-nx-monorepo/ which shows the issue is with sharing routes that exist outside the app dir. Editing a shared route file or any file referenced by the shared route will not work with HMR or *.server.ts conventions. I'm using mostly the same approach to share routes between many apps as Logan does here except using the flat routes package as configured here. Moving routes to each of our apps isn't an option as it would duplicate 100's of file-based routing configs that would get out of sync, even if the route module's implementation was shared. |
Same problem preventing code move to mono repro packages. Seems common isecase can we please have a fix for this asap?🙏 |
I want to move routes to packages too to prevent duplication. Maybe as a bonus this van be made possible |
I can already see me running into this, so yeah, fixing this would make future me very happy 😃 |
Talked with @pcattori about this. There are two concepts here that we need to be able to tell the compiler: a. what to watch for changes for HMR For (a) we already have For (b) we have I'm thinking we rename We also discussed that this is something we can add after v2 ships. Thoughts? |
Hi @ryanflorence and @pcattori, thanks for looking into this, your proposed solution looks elegant and I believe would solve the issue. Tooling like Vite uses complex logic to determine the workspace root for such cases but reusing the watched source files seems nice and simple. |
This issue seems to be almost fixed if using the vite plugin, there's just one bit of code that incorrectly assumes routes are always under the app directory. remix/packages/remix-dev/vite/plugin.ts Line 1300 in c821253
|
Closing as completed by #8795 🎉 The Vite plugin now has very good monorepo support, can load routes from anywhere in the workspace and doesn't require any patches, the presets functionality is especially useful for configuring multiple apps without duplicating config. The *.server.ts naming convention also works well in the monorepo. |
@jrestall Oh, that's cool you're using the presets feature too! Out of interest, do you mind sharing your preset? I'd love to see it! |
We are using presets to avoid duplicating the way shared library routes are defined. Each monorepo app can reference shared functionality which can contain remix routes, so we use Nx (createGlobPatternsForDependencies) to get the route folders for each of the app's workspace dependencies and then remix-flat-routes to define them since it supports multiple route folders. Not all libraries are shared but we also structure the repo in this way to enforce separation between features as the banking domain is very large, so this enables us to scale the Remix site to very many teams and features whilst enforcing modularity. The preset is written in JS rather than TypeScript due to vitejs/vite#5370. // remixPreset.mjs
import fs from "fs";
import path from "path";
import { createGlobPatternsForDependencies } from "@nx/react/tailwind.js";
import { flatRoutes } from "remix-flat-routes";
/** @type {(base: string, appdir: string) => import('@remix-run/dev').Preset} */
export function remixPreset(base, appdir) {
async function defineRoutes(defineRoutes) {
const appFolder = path.join(appdir, "app");
const routeDirs = createGlobPatternsForDependencies(
appdir,
"/src/routes"
)
.filter((routePath) => fs.existsSync(routePath))
.map((routePath) => path.relative(appFolder, routePath));
return flatRoutes(["routes", ...routeDirs], defineRoutes, {
basePath: base,
ignoredRouteFiles: ["**/*.test.{js,jsx,ts,tsx}", "**/*.snap"],
});
}
return {
name: "default-monorepo-preset",
remixConfig: () => ({
// ignore all files in routes folder
ignoredRouteFiles: ["**/.*"],
// add routes from all referenced lib projects
routes: defineRoutes,
}),
};
} |
😍 I knew that feature would come in handy Also, since Remix now supports One more thing. Your |
Thanks so much @kiliman! Your work on remix-flat-routes made the modular monorepo architecture possible with how flexible your package is. Your support for basePath was also really useful. Appreciate the tips, we definitely plan to move to |
What version of Remix are you using?
v1.18
Are all your remix dependencies & dev-dependencies using the same version?
Steps to Reproduce
Minimal Reproduction: https://github.com/jrestall/remix-nx-monorepo/
Expected Behavior
HMR and *.server.ts naming convention works with code outside the app dir that uses shared routes.
Actual Behavior
Following are the areas of code that limit HMR and *.server conventions to only work with routes in the app dir. I'm happy to submit a PR to fix this if a better approach can be agreed.
HMR
remix/packages/remix-dev/compiler/js/plugins/hmr.ts
Lines 118 to 122 in 40a4d7d
remix/packages/remix-dev/compiler/js/plugins/hmr.ts
Lines 134 to 136 in 40a4d7d
If the goal here is to not add react refresh to node_modules code, could we perhaps explicitly check whether the file is in node_modules instead?
Naming Convention
remix/packages/remix-dev/compiler/plugins/emptyModules.ts
Lines 24 to 28 in 40a4d7d
Instead of limiting this convention to the app dir, if the goal is to exclude node_modules, could we change it to something like the following?
The text was updated successfully, but these errors were encountered: