-
Notifications
You must be signed in to change notification settings - Fork 520
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
Make integration with create-react-app easier #373
Comments
I tried to run the project in mac os x without docker.
and I got problem with compilation of jsx
Is there a chance to solve the problem? |
Thanks for raising this, @pward123 Let's back up a step - create-react-app sets up a build toolchain for your react app. Under Bazel we expect the toolchain to be quite different. For example, to run babel I'd expect a What you've done here is just use Bazel to launch the prior toolchain, which might be a step in migrating from one to another, but by itself this gives you no incrementality/customizability of your build, so you get none of the Bazel benefits. What are you trying to accomplish? I imagine the right formulation of the question is "how could we patch/plugin to create-react-app so that it stamps out a Bazel-based toolchain for the new app rather than the default one" |
In my case, I'm fighting with a build environment that (due to some tools we're working hard to eliminate) uses Lerna but we're unable to use yarn workspaces. The resulting node_modules trees are in the realm of 2.1+gb (500k+ files). Our environment has reached a level of complexity where we've implemented docker-compose for our development environment. Since we're using OSX machines for development, we have to use a virtual machine for docker. The synchronization of node_modules files between host and guest vm is crushing the development machines. I've tried moving everything into a full vm and running docker-compose, git, etc from there, but the devs aren't keen on that development experience. I've also tried using docker-sync-stack, but it gets pretty rickety once you throw this many files at it. At a future date, I could see us going through the create-react-apps we have and replacing their toolchains with a bazel-centric system. However at this point, I'm just interested in moving node_modules out of the development source file structure as quickly as I can. |
@olegsmetanin I'm not surprised you ran into problems trying to run it outside docker. There's a lot of stuff in the cra setup that is not very friendly to pathing changes. I'd start by fixing the paths here and here. To really change the paths properly, you'd need to do a fs.realPath based conversion of process.cwd. Since I'm only interested in running this from docker, it's easier just to hard code the path. You may also need to play around with this. I would console.log that value somewhere and |
@olegsmetanin You may also want to just look at the individual commits in that repo. I've broken my own customizations of cra code out into their own commits. @alexeagle Even though I agree that migrating toolchains is ideal, you may find better js community adoption if you give new users a way to reuse their existing webpack/cra toolchains. Subjectively, it feels like the rollup support still requires me to do starlark scripting for anything non-trivial. If you want me to close this issue, I'm cool with it. I've managed to get my cra apps converted to at least launch/build from bazel now. I'm excited about being able to use your rules to resolve the issues I've been fighting for a while now. Thanks! |
So you're just using Bazel as a means to dynamically install npm dependencies outside of the project tree, but otherwise run the same tools as today? Seems like it could be a lot simpler to just run the yarn/npm install with some option to put the output in a different directory (like bazel does) and then change the |
Our use of webpack is limited to ui applications, so using webpack-dev-server is fine for us. We don't need to take the output of webpack as a js_library to feed into anything else. Our back end is mostly node. Some of those backend npm packages have browser code used by the webpack apps. We're currently using lerna to run a watch process on each package that babelifies. My next step is to swap lerna for bazel. We also have some golang, so the hope is to integrate that in with Bazel down the road. |
@pward123 so I want to do the exact same thing for an almost identical setup: webpack ui + node backend + golang server + lerna/babel. Is your example repo https://github.com/pward123/bazel-cra-example something I can look as a starting point? |
For my own project, I plan to take bits and pieces (but mostly knowledge) from that example. The WORKSPACE file is useful as well as the scripts/merge file and its associated templates. I won't be using scripts/setup, nor templates/webpack.config.*. Those only exist because I was scripting the commits for the example and it was too difficult to For now, I've worked around the original issue that brought me to Bazel by tossing a couple dozen named docker volumes into my docker-compose.yml. As it turns out, named volumes are only mounted from the containers to the Docker VM and not the Mac host. Each time I create a new monorepo package, I'll be creating a named volume to hold the node_modules that aren't hoisted by yarn. I still think there are significant benefits to switching to Bazel. For example, I am currently wasting a lot of CI cycles rebuilding stuff that hasn't changed. For now, I've just been throwing hardware at the problem since its cheap. However, the feedback loop between qa/support and development is still limited by the time it takes for an individual build to finish. I still plan on moving forward with Bazel, but the learning/adoption curve is so steep that I'm going to take a slow burn route getting there. One thing that I will experiment with as I move forward is whether I really want to merge all package.json files together and force the devs to use the same version of npm packages in every monorepo package. This line tells Bazel that it should install npm packages into its own sandbox. However, as far as I can tell, it doesn't support multiple package.json files. My guess is because it probably doesn't handle version conflicts. If you run I'm not really sure yet what the implications are for incrementally building items by using the latter, but now that I know about the Docker named volume workaround, it is a possibility. Forcing devs to upgrade all packages in the monorepo when we want to upgrade an npm package creates development friction that I'd rather do without. Sorry for the long post, but I figured since you're in the same boat, the extra info might be useful. |
Any solution to this ? |
I actually got this working today with help of a colleague.
You can probably change the ln -s command by using NODE_PATH. react-scripts must use relative node_path. |
@ayinlaaji were u able to resolve ur issue? i'm facing the same and i dont really want to eject from CRA. |
Bump, this would be very useful for a project I'm working on. |
I have been building using bazel in production (dev environment still uses yarn) for the last three months and it's working out so far. See my post above. |
The idiomatic way btw, would be to write a custom |
In fact if you are using typescript there might even be a way to integrate it directly with ts_library: https://www.typescriptlang.org/docs/handbook/jsx.html Or one could even have a two-step compilation of The other way, if you want to have something working today it would probably also be possible to use |
We have a |
Hi, I'm currently looking to integrate some JSX into our Bazel build, is JSX syntax supported already by the ts_* rules? If not, can I pass some assortment of flags to the ts_* rules to get JSX compilation working? Thank you! I'm in a similar situation where we started with create-react-app to get something working, and are migrating it over to Bazel for production use. EDIT: also happy to file a separate issue, or a PR if needed. EDIT 2: I am seeing some success with using typescript and setting a |
@Rustacian yes you can include |
Does anyone know the actual reason this fails? The following loader I believe handles this part and both the |
you needn't eject react-scripts, you can use These are my configurations, it works for me. // configs/overrides.js
const getYarnWorkspaces = require('get-yarn-workspaces');
const { override, babelInclude } = require('customize-cra');
module.exports = override(
babelInclude(getYarnWorkspaces())
); // scripts/start.js
const path = require('path')
const spawn = require('cross-spawn')
const fs = require('fs')
const getAppRoot = (root = __dirname) => {
if (fs.existsSync(path.resolve(root, 'package.json'))) {
return root
}
return getAppRoot(path.dirname(root))
}
const getWorkspaceRoot = () => path.resolve(process.env['RUNFILES'], process.env['BAZEL_WORKSPACE'])
const relativeAppPath = path.relative(getWorkspaceRoot(), getAppRoot())
const rewiredBinPath = require.resolve('react-app-rewired/bin/index.js')
const overridesPath = './configs/overrides.js'
const start = spawn('bash', [
'-c',
`cd ${relativeAppPath} && node --preserve-symlinks ${rewiredBinPath} start --config-overrides ${overridesPath}`
], {stdio: 'inherit'}) # BUILD.bazel
load("@build_bazel_rules_nodejs//:index.bzl", "nodejs_binary")
deps = [
"//:package.json",
"@npm//react",
"@npm//react-dom",
"@npm//react-scripts",
"@npm//react-app-rewired",
"@npm//customize-cra",
"@npm//get-yarn-workspaces",
]
srcs = glob([
"package.json",
"src/**",
"public/**",
"configs/**",
"scripts/**",
])
nodejs_binary(
name = "start",
data = srcs + deps,
entry_point = ":scripts/start.js",
) # Root BUILD.bazel
package(default_visibility = ["//visibility:public"])
exports_files([
"package.json",
]) |
There's a create-react-app example now within the examples directory, and some more extended docs on the different approaches that could be taken. There is going to be further work on what an ejected and custom toolchain for CRA would look like, but I think the initial examples are there. |
I was originally going to post this as a response to #97, but figured this deserved its own issue since create-react-app is fairly heavily used in the community.
While researching these problems, I believe I ran across some mention of plans to restructure how the sandbox used by these rules works so that you don't have to monkey-patch require. I'm creating this issue in the hopes that you may find ways to incorporate fixes for these problems into that effort.
I've created an example repo that gets create-react-apps minimally working with this set of rules. If you look at the commits, I think I've broken them up into clean steps I had to take.
Here are the issues I ran into while getting this working. It's a block copy of the readme from the repo above.
nodejs_binary uses a different working directory than npm when launching the build/start/test scripts. I worked around this by injecting code into the top of these scripts that changes the directory based on
__dirname
cra resolves symlinks when executing webpack, but uses working directory when building the webpack config. This results in name mismatches. I worked around this by adding the resolved paths to some of the webpack config 'includes' entries
bazel monkey-patches require, but babel uses the
resolve
npm package to load packages which bypasses the require patches. I got around this by adding the bazel sandbox npm folder to the resolve/modules section of the webpack config.cra uses a
babel
section in the package.json, but this also has problems (I believe due to theresolve
issue above). To get around this, I explicitly added arequire('babel-preset-react-app')
to the babel-loader section of the webpack config that handles the cra app code.Thanks for all your hard work on this project. Your efforts are greatly appreciated!
The text was updated successfully, but these errors were encountered: