Skip to content

Tailwind 2.0 poor performance as part of a webpack PostCSS build system #2820

Closed
@khalwat

Description

@khalwat

Description of the problem

Tailwind CSS 2.0 builds slowly as part of a HMR webpack build system. It is slower than the release, but that could just be due to the amount of CSS generated increasing.

I filed a very similar issue a month ago #2544 and worked around the problem by splitting the CSS up into separate chunks. Global @apply still worked, and everything was great.

It's all written up in the article Speeding Up Tailwind CSS Builds

However with Tailwind CSS 2.0, the technique described in the article breaks.

Desired solution

I'm hoping to have the DX of working with Tailwind CSS 2.0 be improved from a HMR build time perspective.

I realize that you can only optimize your generation of CSS so much, and a PR is in the works to do just that with esbuild. I also realize that part of the slowness here is simply webpack and the surrounding ecosystem being slow when dealing with massive amounts of CSS (though I've optimized that quite a bit here).

However, the paradigm that Tailwind CSS is using is what generates a massive amount of CSS, and webpack is a very widely used tool that many things are built upon.

Some way to address the DX here would be great; huge gains can be made using the CSS splitting technique described in the article, maybe there could be a way to restore that functionality to Tailwind 2.x?

Link to a minimal reproduction:

I made a new branch with Tailwind 2.0, webpack 5, PostCSS 8, and all the goodness:

https://github.com/nystudio107/tailwind-css-performance/tree/problem-tailwind-2.x

webpack_1  | ℹ 「wdm」: Compiled successfully.
webpack_1  | ℹ 「wdm」: Compiling...
webpack_1  | ℹ 「wdm」: assets by status 72.8 KiB [cached] 2 assets
webpack_1  | assets by status 9.21 MiB [emitted]
webpack_1  |   assets by info 3.62 MiB [immutable]
webpack_1  |     asset app.53801fed2ee43ce850f5.hot-update.js 3.62 MiB [emitted] [immutable] [hmr] (name: app)
webpack_1  |     asset runtime.53801fed2ee43ce850f5.hot-update.js 881 bytes [emitted] [immutable] [hmr] (name: runtime)
webpack_1  |     asset 53801fed2ee43ce850f5.hot-update.json 37 bytes [emitted] [immutable] [hmr]
webpack_1  |   assets by path js/*.js 5.6 MiB
webpack_1  |     asset js/app.js 5.55 MiB [emitted] (name: app)
webpack_1  |     asset js/runtime.js 43.9 KiB [emitted] (name: runtime)
webpack_1  |   asset manifest.json 303 bytes [emitted]
webpack_1  | Entrypoint app 9.21 MiB = js/runtime.js 43.9 KiB runtime.53801fed2ee43ce850f5.hot-update.js 881 bytes js/app.js 5.55 MiB app.53801fed2ee43ce850f5.hot-update.js 3.62 MiB
webpack_1  | cached modules 711 KiB [cached] 61 modules
webpack_1  | runtime modules 28.9 KiB 14 modules
webpack_1  | ./node_modules/css-loader/dist/cjs.js??clonedRuleSet-4.use[1]!./node_modules/postcss-loader/dist/cjs.js??clonedRuleSet-4.use[2]!../src/css/app.pcss 3.61 MiB [built] [code generated]
webpack_1  | example-project (webpack 5.4.0) compiled successfully in 2527 ms

While 2.5s isn't awful, this is in a pretty minimal CSS setup, where I was getting about 1.2s for the equivalent builds in Tailwind 1.x, and using the technique described in the article, the builds were around 182ms

Metadata

Metadata

Assignees

Labels

No labels
No labels

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions