When using webpack and babel together, one needs to configure both in order to use React CSS Modules. For example:
webpack.config.js
will need a rule like this:
{
// Translates CSS into CommonJS modules
loader: 'css-loader',
options: {
modules: {
mode: "local",
localIdentName: CSS_CLASS_NAME_PATTERN,
},
sourceMap: true
}
babel.config.js
will need a plugin like this:
[
'react-css-modules',
{
generateScopedName: CSS_CLASS_NAME_PATTERN,
filetypes: {
'.scss': {
syntax: 'postcss-scss',
plugins: ['postcss-nested']
}
},
}
]
Why the need to configure CSS Modules in two places? How the two work together? I.e. what happens in what order?
They don't.
css-loader
does its own thing: class name transformation in CSS, and replacement of CSS imports in JS code by mappings between original and generated names.babel-plugin-react-css-modules
works independently, and it replacesstyleName
attributes of react components byclassName
with correct generated names. To do so it calculates class name mappings independently fromcss-loader
, that's why it needs separate configuration matching that ofcss-loader
, and that's why after a few years being abandoned by its creators it has compatibility issues with latestcss-loader
(css-loader changed internal class name generation logic).Shameless self-promo: I maintain an up-to-date fork of
babel-plugin-react-css-modules
which solves compatibility issues with latestcss-loader
versions.