facebook / create-react-app

Set up a modern web app by running one command.
https://create-react-app.dev
MIT License
102.34k stars 26.74k forks source link

postcss plugins not found when compiling with CRA v5.0.0 and fomantic-ui #12177

Open davegravy opened 2 years ago

davegravy commented 2 years ago

Describe the bug

CRA v5 appears to be incompatible with fomantic-ui, since installing this package causes compile errors about postcss plugins not existing

Did you try recovering your dependencies?

Yes

❯ npm --version 8.5.4

Which terms did you search for in User Guide?

I searched for postcss

Environment

Environment Info:

current version of create-react-app: 5.0.0 running from /home/davidg/.npm/_npx/c67e74de0542c87c/node_modules/create-react-app

System: OS: Linux 5.10 Ubuntu 18.04.6 LTS (Bionic Beaver) CPU: (8) x64 Intel(R) Core(TM) i7-6700 CPU @ 3.40GHz Binaries: Node: 16.8.0 - ~/.nvm/versions/node/v16.8.0/bin/node Yarn: Not Found npm: 8.5.4 - ~/.nvm/versions/node/v16.8.0/bin/npm Browsers: Chrome: 99.0.4844.51 Firefox: Not Found npmPackages: react: ^17.0.2 => 17.0.2 react-dom: ^17.0.2 => 17.0.2 react-scripts: 5.0.0 => 5.0.0 npmGlobalPackages: create-react-app: Not Found

Steps to reproduce

  1. npx create-react-app@latest cra-test --use-npm

Follow documented fomantic-ui install instructions:

  1. npm install --ignore-scripts fomantic-ui
  2. cd node_modules/fomantic-ui
  3. npx gulp install (select defaults)
  4. npx gulp build
  5. npm start (this works normally)
  6. rm node_modules package-lock.json -Rf
  7. npm install
  8. npm start

Expected behavior

Successful compilation

Actual behavior

ERROR in ./src/index.css (./node_modules/css-loader/dist/cjs.js??ruleSet[1].rules[1].oneOf[5].use[1]!./node_modules/postcss-loader/dist/cjs.js??ruleSet[1].rules[1].oneOf[5].use[2]!./node_modules/source-map-loader/dist/cjs.js!./src/index.css) Module Error (from ./node_modules/postcss-loader/dist/cjs.js): Loading PostCSS "postcss-flexbugs-fixes" plugin failed: Cannot find module 'postcss-flexbugs-fixes' Require stack:

/home/davidg/cra-test/node_modules/postcss-loader/dist/utils.js /home/davidg/cra-test/node_modules/postcss-loader/dist/index.js /home/davidg/cra-test/node_modules/postcss-loader/dist/cjs.js /home/davidg/cra-test/node_modules/loader-runner/lib/loadLoader.js /home/davidg/cra-test/node_modules/loader-runner/lib/LoaderRunner.js /home/davidg/cra-test/node_modules/webpack/lib/NormalModule.js /home/davidg/cra-test/node_modules/webpack-manifest-plugin/dist/index.js /home/davidg/cra-test/node_modules/react-scripts/config/webpack.config.js /home/davidg/cra-test/node_modules/react-scripts/scripts/start.js

image

Reproducible demo

I hope the steps above are concise enough to serve as a reproducible demo also

davegravy commented 2 years ago

Additional notes:

Workaround:

npm install postcss-flexbugs-fixes postcss-normalize postcss-preset-env (even though according to npm ls these are all already installed as dependencies of react-scripts

samuliasmala commented 2 years ago

I have the same issue except I'm not using fomantic-ui but Material-UI. The npm install postcss-flexbugs-fixes postcss-normalize postcss-preset-env workaround also fixes the issue for me.

I believe something in my codebase is triggering the postcss which is failing since the packages are installed under node_modules/react-scripts/node_modules/

Before running npm install postcss-flexbugs-fixes

$ find node_modules/ -name 'postcss-flexbugs-fixes'
node_modules/react-scripts/node_modules/postcss-flexbugs-fixes

After running npm install postcss-flexbugs-fixes

$ find node_modules/ -name 'postcss-flexbugs-fixes'
node_modules/postcss-flexbugs-fixes

I'm pretty sure the above change in postcss-flexbugs-fixes package location is the reason why it starts working. Do you know if there's a way to fix it other than installing those three packages? Also any idea what is triggering the postcss processing in cra application? I tried but couldn't find the culprit from my fairly large codebase.

tluchowski commented 2 years ago

I'm also using Material-UI, tried upgrading from react-scripts 4.0.3 to 5.0.0 today and I get the same error:

Loading PostCSS "postcss-normalize" plugin failed: Cannot find module 'postcss-normalize'

milotoor commented 2 years ago

I believe @samuliasmala is correct that the relative positioning between packages is the fundamental issue.

Solution 1

I was able to solve the issue by manually relocating the postcss-loader package in my package-lock.json file.

Git diff package-lock.json ```diff diff --git a/package-lock.json b/package-lock.json index 1bbfc8b..b096334 100644 --- a/package-lock.json +++ b/package-lock.json @@ -18122,43 +18122,6 @@ "url": "https://tidelift.com/funding/github/npm/postcss" } }, - "node_modules/postcss-loader": { - "version": "6.2.1", - "resolved": "https://registry.npmjs.org/postcss-loader/-/postcss-loader-6.2.1.tgz", - "integrity": "sha512-WbbYpmAaKcux/P66bZ40bpWsBucjx/TTgVVzRZ9yUO8yQfVBlameJ0ZGVaPfH64hNSBh63a+ICP5nqOpBA0w+Q==", - "dev": true, - "dependencies": { - "cosmiconfig": "^7.0.0", - "klona": "^2.0.5", - "semver": "^7.3.5" - }, - "engines": { - "node": ">= 12.13.0" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/webpack" - }, - "peerDependencies": { - "postcss": "^7.0.0 || ^8.0.1", - "webpack": "^5.0.0" - } - }, - "node_modules/postcss-loader/node_modules/semver": { - "version": "7.3.7", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.7.tgz", - "integrity": "sha512-QlYTucUYOews+WeEujDoEGziz4K6c47V/Bd+LjSSYcA94p+DmINdf7ncaUinThfvZyu13lN9OY1XDxt8C0Tw0g==", - "dev": true, - "dependencies": { - "lru-cache": "^6.0.0" - }, - "bin": { - "semver": "bin/semver.js" - }, - "engines": { - "node": ">=10" - } - }, "node_modules/postcss-opacity-percentage": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/postcss-opacity-percentage/-/postcss-opacity-percentage-1.1.2.tgz", @@ -19787,6 +19750,28 @@ "postcss": "^8.4" } }, + "node_modules/react-scripts/node_modules/postcss-loader": { + "version": "6.2.1", + "resolved": "https://registry.npmjs.org/postcss-loader/-/postcss-loader-6.2.1.tgz", + "integrity": "sha512-WbbYpmAaKcux/P66bZ40bpWsBucjx/TTgVVzRZ9yUO8yQfVBlameJ0ZGVaPfH64hNSBh63a+ICP5nqOpBA0w+Q==", + "dev": true, + "dependencies": { + "cosmiconfig": "^7.0.0", + "klona": "^2.0.5", + "semver": "^7.3.5" + }, + "engines": { + "node": ">= 12.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + }, + "peerDependencies": { + "postcss": "^7.0.0 || ^8.0.1", + "webpack": "^5.0.0" + } + }, "node_modules/react-scripts/node_modules/postcss-logical": { "version": "5.0.4", "resolved": "https://registry.npmjs.org/postcss-logical/-/postcss-logical-5.0.4.tgz", ```

In short, I changed the node_modules/postcss-loader key under the packages section of package-lock.json to node_modules/react-scripts/node_modules/postcss-loader and relocated that entry so the packages section remained in tidy alphabetical order. After this, running npm i will make a few other small modifications to the file (for me it removed the node_modules/postcss-loader/node_modules/semver key from packages and removed the postcss-loader entry from the dependencies section, nesting it under dependencies['react-scripts'].dependencies instead.

From here, npm run build succeeds just fine. I have no idea why postcss-loader was not already located under react-scripts, as that's the only package that depends on it. Perhaps I previously had another package installed that depended on it? Unsure.


Solution 2

I wasn't entirely comfortable with manually editing this generated file (though after it's committed to version control there it shouldn't be an issue), so I also messed around with rebuilding the package-lock.json file altogether. This approach worked too, though it was a little more complicated and involved updating thousands of sub-dependencies. My project depends on two packages which themselves depend on postcss: react-scripts and madge, which I use in a script to detect cyclical imports in my codebase:

➜ npm ls postcss
my_project@1.0.0 /path/to/my/repo
├─┬ madge@3.10.0
│ └─┬ detective-postcss@3.0.1
│   └── postcss@7.0.34
└─┬ react-scripts@5.0.1
  ├── postcss@8.4.12
  └ [60 other sub-dependencies also depending on postcss]

Because both react-scripts and madge depend on postcss, the postcss package is hoisted up the tree to their common ancestor package, which is the repository root. If I uninstall madge, this alone does not solve the problem. However, if I delete the package-lock.json file, delete my node_modules directory and rerun npm install, things are different:

➜ npm run build

> my_project@0.1.0 build
> react-scripts build

Creating an optimized production build...
Failed to compile.

Loading PostCSS "postcss-flexbugs-fixes" plugin failed: Cannot find module 'postcss-flexbugs-fixes'
[snip]

➜ npm uninstall madge

removed 89 packages, and audited 1860 packages in 1s
[snip]

➜ rm package-lock.json
➜ rm -rf node_modules
➜ npm i
added 1727 packages, and audited 1729 packages in 37s

# Force installation of specific versions--my project already depended on these.
# This was necessary because my package.json permitted subsequent minor releases of these
# packages to be installed, and these introduced minor breaking changes. So I am downgrading.
➜ npm i @material-ui/core@4.11.0 @material-ui/lab@4.0.0-alpha.56 @reduxjs/toolkit@1.4.0
➜ npm run build

Creating an optimized production build...
Compiled successfully.

In other words, forcing npm to rebuild the package-lock.json file solved the issue. What makes this extra frustrating is that, after doing all this, I can reinstall the exact same version of madge and my build will continue to run just fine:

➜ npm i -D madge@3.10.0
➜ npm run build
[snip]
Compiled successfully.

Deleting the node_modules directory now and running npm i again (using the newly generated lockfile) does not break the build. At this point, my package.json file has not changed at all, only the package-lock.json file which has thousands of lines changed so I can't possibly determine which of those changes resolved the problem. However, following the re-generation of the lockfile:

➜ find node_modules -name 'postcss-flexbugs-fixes'
node_modules/postcss-flexbugs-fixes
➜ find node_modules -name 'postcss-normalize'
node_modules/postcss-normalize
➜ find node_modules -name 'postcss-preset-env'
node_modules/postcss-preset-env

At the end of the day, I have no idea why rebuilding the lockfile caused these packages to be hoisted to the repository root, but I strongly suspect that's why the build now succeeds.

toresenneseth commented 2 years ago

Rebuilding the lockfile worked for me as well.

andreperegrina commented 2 years ago

For those still struggling with this problem. I use craco to customize the webpack config and remove postcss.


   webpack: {
      configure: (webpackConfig, {env, paths}) => {
         // Remove post css loader from webpack config
         webpackConfig.module.rules[1].oneOf.map((e)=>{
            if(e.use!=null){
               e.use=e.use.filter((e)=>e?.options?.postcssOptions==null);
            }
            return e;
         });
kevinfiol commented 1 year ago

For those still struggling with this problem. I use craco to customize the webpack config and remove postcss.


   webpack: {
      configure: (webpackConfig, {env, paths}) => {
         // Remove post css loader from webpack config
         webpackConfig.module.rules[1].oneOf.map((e)=>{
            if(e.use!=null){
               e.use=e.use.filter((e)=>e?.options?.postcssOptions==null);
            }
            return e;
         });

Facing this issue now. My team does use craco, but what does this actually do? I'm hesitant to rebuild the lockfile since that will imply many dependency changes.

alioshr commented 1 year ago

For those still struggling with this problem. I use craco to customize the webpack config and remove postcss.


   webpack: {
      configure: (webpackConfig, {env, paths}) => {
         // Remove post css loader from webpack config
         webpackConfig.module.rules[1].oneOf.map((e)=>{
            if(e.use!=null){
               e.use=e.use.filter((e)=>e?.options?.postcssOptions==null);
            }
            return e;
         });

Facing this issue now. My team does use craco, but what does this actually do? I'm hesitant to rebuild the lockfile since that will imply many dependency changes.

Did you discover the implications of doing such change? I have tried this out on my craco config and it also worked, but I am also worried of what could be the outcome.

kevinfiol commented 1 year ago

For those still struggling with this problem. I use craco to customize the webpack config and remove postcss.


   webpack: {
      configure: (webpackConfig, {env, paths}) => {
         // Remove post css loader from webpack config
         webpackConfig.module.rules[1].oneOf.map((e)=>{
            if(e.use!=null){
               e.use=e.use.filter((e)=>e?.options?.postcssOptions==null);
            }
            return e;
         });

Facing this issue now. My team does use craco, but what does this actually do? I'm hesitant to rebuild the lockfile since that will imply many dependency changes.

Did you discover the implications of doing such change? I have tried this out on my craco config and it also worked, but I am also worried of what could be the outcome.

I did not. In my case, one of our engineers ended up merging a PR that rebuilt the lockfile (which I was not thrilled about) but it fixed our issue.

alioshr commented 1 year ago

I see, so you dropped this webpack override. Thanks for replying back to me.

In my case I was getting this error, which was also cleared by this dangerous workaround:

I am also worried about applying this =D

Syntax error: postcss-custom-properties: <css input> Unknown word (1:1)
> 1 | var(--spectrum-table-cell-text-size,var(--spectrum-alias-font-size-default))*var(--spectrum-table-cell-text-line-height,var(--spectrum-alias-body-text-line-height)) - 1px
    | ^
milotoor commented 1 year ago

@alioshr Have you tried my "Solution 1" above? That involves minimal changes to the lockfile.

alioshr commented 1 year ago

Hey @milotoor! Thanks for the help.

Actually, in my dependency tree, using yarn here, I see no direct postcss-loader dependency. I have no such node_modules/postcss-loader.

It seems to be correctly installed, with an unique version, consumed just by and under react-scripts.

I have other bunch of other postcss packages directly installed though. Not sure if it could be related.

Joe-Degler commented 1 year ago

For me, updating the postcss dependency to ^8.4.23 fixed my issues.

vathsav commented 1 year ago

yarn list postcss returned two different major versions in my project.

Adding postcss to resolutions in my package.json solved the issue for me.

Make sure to resolve the version you want:

  "resolutions": {
    "postcss": "<version>"
  }
Yukigamine commented 12 months ago

I am also running into this exact issue, but only when Yarn is configured for pnpm with the global cache enabled.

I've tried adding postcss and other packages to both the devDeps and resolutions to no avail. Every time I add one package to devDeps, it says another is missing, and resolutions has managed to consolidate packages to one version, but doesn't change the error that the module is missing. I tried figuring out the "solution 1" listed in this thread, but yarn.lock has a different structure from package-lock and I haven't yet figured out exactly how it should look.

Anyone have any more suggestions? Thanks!

kintz09 commented 9 months ago

I ran into this today too. I chose to rebuild the package-lock.json file which fixed my issue.

We have a base project that we fork to build new apps from. I had already upgraded one of the app projects to CRA5 and did not run into this issue with postcss and postcss-flexbugs-fixes. Some other dependency may have prevented the issue.

In the base project I did run into this issue. Deleting the package-lock.json file and running npm install to recreate it fixed the issue.

Before I rebuilt the package-lock.json file, there were only 4 packages that started with postcss in the root of the node_modules folder. After rebuilding the package-lock.json file, there are now 71 packages that start with postcss in the root node_modules folder.

Interestingly, the postcss-flexbugs-fixes package is still nested under react-scripts in the node_modules folder.

kintz09 commented 9 months ago

Something else I discovered today while fixing this in my project...

My node_modules root folder contained about 70 packages starting with the name postcss. I upgraded only react-scripts from 4.0.3 to 5.0.1 by updating the version number manually in package.json and then running npm install. After the install my node_modules root folder contained only 4 packages starting with the name postcss.

I reverted and tested a different route. I didn't touch package.lock and simply ran npm i react-scripts@5.0.1 and had the same outcome.

I reverted and tried updating a variety of packages at the same time including: react-scripts, react, react-dom, @types/react, @types/react-dom, and typescript. After running npm install the issue still occurred.

I kept my package.json file with those 6 packages updated and I deleted my node_modules folder and the package-lock.json file. I ran npm install again and this time it installed the postcss packages in the root of the node_modules folder and I did not run into the error.

I didn't take the time to check all the packages to see if there's a happy combination, but its pretty clear something about the creation of the package-lock.json file fixes this particular issue.

dfyz011 commented 6 months ago

I had no direct dependency on postcss-normalize. And install it directly fixed issue for me