-
-
Notifications
You must be signed in to change notification settings - Fork 209
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
[Feature] add CSS Modules (postcss-modules
) support
#227
Comments
postcss-modules
)
@michael-ciniawsky Looks like with 2.x my CSS modules are now broken. Is this related? Is there a workaround? Thanks! |
@felixsanz Are you using |
Shouldn't |
@michael-ciniawsky I'm using css-loader's |
postcss-modules
)postcss-modules
)
postcss-modules
)postcss-modules
)
postcss-modules
)postcss-modules
)
postcss-modules
)postcss-modules
) support
Could this issue be the reason why webpack HMR no longer detects when I change the style of an existing class? |
I don't think so, show your config |
When did it exactly stop working? |
I've narrowed it down to the following updates (older version of postcss works without issue): - "postcss": "^5.2.18",
+ "postcss": "^6.0.13",
- "postcss-loader": "^0.8.0",
+ "postcss-loader": "^2.0.8",
- "postcss-modules": "^0.3.0",
+ "postcss-modules": "^1.1.0",
- "postcss-nested": "^1.0.0",
+ "postcss-nested": "^2.1.2", Webpack config looks like: 'use strict';
var path = require('path');
var webpack = require('webpack');
var DotenvPlugin = require('dotenv-to-webpack');
var ExtractTextPlugin = require('extract-text-webpack-plugin');
var envPath;
if (process.env.DOTENV_PATH) {
envPath = path.join(process.env.DOTENV_PATH, './.env.development');
} else {
envPath = path.join(__dirname, './.env.development');
}
module.exports = {
devtool: 'cheap-module-eval-source-map',
entry: {
App: [
'webpack-hot-middleware/client',
'babel-polyfill',
'./src/renderApp.js'
],
BasicTheme: [
'webpack-hot-middleware/client',
'./src/themes/BasicTheme/BasicTheme.js'
]
},
resolve: {
extensions: ['.js']
},
output: {
path: path.join(__dirname, 'dist'),
filename: '[name].js',
chunkFilename: '[id].js',
publicPath: '/dist/',
library: '[name]',
libraryTarget: 'umd'
},
plugins: [
new DotenvPlugin({ path: envPath }),
new webpack.HotModuleReplacementPlugin(),
new webpack.NoEmitOnErrorsPlugin(),
new ExtractTextPlugin('[name].css')
],
module: {
noParse: /dist\/localforage(|\.min).js/,
rules: [
{
test: /\.js$/,
use: ['babel-loader?'+JSON.stringify({
plugins: [
['react-transform', {
transforms: [{
transform: 'react-transform-hmr',
imports: ['react'],
locals: ['module']
}]
}]
]
})],
include: [
path.resolve(__dirname, 'src')
]
},
{
test: /\.css$/,
use: ExtractTextPlugin.extract({
fallback: 'style-loader',
use: 'css-loader?modules&sourceMap&importLoaders=1&localIdentName=[name]__[local]___[hash:base64:5]!postcss-loader'
}),
include: [
path.resolve(__dirname, 'src')
]
}
]
}
}; The CSS files are imported like so (from within the theme's .js file which maps the class names from their original class name to their import root from './root.css';
import App from './App.css';
import Foo from './Foo.css';
import Bar from './Bar.css';
export default {
classes: {
...root,
...App,
...Foo,
...Bar
}
};
if (process.env.NODE_ENV !== 'production') {
if (module.hot) {
const reloadTheme = require('provide-theme').reloadTheme;
module.hot.accept([
'./root.css',
'./App.css',
'./Foo.css',
'./Bar.css'
], () => {
reloadTheme('BasicTheme', {
classes: {
...require('./root.css'),
...require('./App.css'),
...require('./Foo.css'),
...require('./Bar.css')
}
});
});
}
} The problem is that, after upgrading the postcss dependencies above, it no longer detects when one of the CSS files have changed... unless a new class name is added or a class name is removed. For example, if we start with: .App {
background: red;
} And change the background: .App {
background: blue;
} It no longer detects that the CSS has changed. Only if we add a new class name will it say the CSS has changed: .App {
background: blue;
}
.SomeNewClass {
background: green;
} |
You can't really use the import styles from './file.css' // <= only works with 'css-loader' atm
export default (props) => (
<div className={styles.container}></div>
) import './file.css'
import styles from './modules.json' // <= `postcss-modules` (Crap, don't use it)
export default (props) => (
<div className={styles.container}></div>
) |
That's why this issue exists 😛 |
I'm confused as to what to do here. Is the problem with |
You are using {
test: /\.css$/,
use: env === 'production'
? ExtractTextPlugin.extract({
fallback: 'style-loader',
use: [
{
loader: 'css-loader',
options: {
modules: true,
localIdentName: '[name]__[local]___[hash:base64:5]',
importLoaders: 1
},
'postcss-loader'
]
}),
: [ // `style-loader` pitches the HMR Code and enables HMR
{ loader: 'style-loader', options: { sourceMap: true } },
{
loader: 'css-loader',
options: {
modules: true,
localIdentName: '[name]__[local]___[hash:base64:5]',
importLoaders: 1,
sourceMap: true
},
{ loader: 'postcss-loader', options: { sourceMap: true } }
],
include: [
path.resolve(__dirname, 'src')
]
} Also remove your custom HMR Code from the component, |
The problem is that, for theming, I need the object which comes from the generated CSS class names so that it may be provided to components as a /* App.css */
.App {
background: red;
}
.AppContainer {
margin: 0 auto;
} /* BasicTheme.js */
import App from './App.css';
export default {
classes: {
...App
}
}; import theme from './BasicTheme';
console.log(theme);
/*
{
classes: {
App: '_someMinifiedClassName',
AppContainer: '_anotherMinifiedClassName'
}
}
*/ The minified class names are used within components like so: import React from 'react';
import PropTypes from 'prop-types';
const App = ({ classes }) => (
<div className={classes.App}>
etcetera
</div>
);
App.propTypes = {
classes: PropTypes.object.isRequired
};
export default App; When the CSS changes, these class names (the |
if (process.env.NODE_ENV !== 'production') {
if (module.hot) {
const reloadTheme = require('provide-theme').reloadTheme;
module.hot.accept([
'./root.css',
'./App.css',
'./Foo.css',
'./Bar.css'
], () => {
reloadTheme('BasicTheme', {
classes: {
- ...require('./root.css'),
+ ...require('./root.css').default,
- ...require('./App.css'),
+ ...require('./App.css').default,
- ...require('./Foo.css'),
+ ...require('./Foo.css').default,
- ...require('./Bar.css')
+ ...require('./Bar.css').default
}
});
});
}
} |
from.js const x = {}
export default x toCJS.js const x = require('./from.js').default toESM.js import x from './from.js' |
Otherwise please post your issue on e.g StackOverflow as it is unrelated to this issue and |
The The issue is that it never even makes it to this block of code because it doesn't accept the css files as being changed (when they are in fact changed): if (process.env.NODE_ENV !== 'production') {
if (module.hot) {
const reloadTheme = require('provide-theme').reloadTheme;
module.hot.accept([
'./root.css',
'./App.css',
'./Foo.css',
'./Bar.css'
], () => {
/*
* NEVER REACHES THIS POINT
*/
reloadTheme('BasicTheme', {
classes: {
...require('./root.css'),
...require('./App.css'),
...require('./Foo.css'),
...require('./Bar.css')
}
});
});
}
} As far as I can tell, the issue is related to - "postcss": "^5.2.18",
+ "postcss": "^6.0.13",
- "postcss-loader": "^0.8.0",
+ "postcss-loader": "^2.0.8",
- "postcss-nested": "^1.0.0",
+ "postcss-nested": "^2.1.2", |
It is entirely possible the issue is actually with |
https://medium.com/@sokra/79583bd107d7
css-modules/css-modules#240
css-modules/css-modules#241
The text was updated successfully, but these errors were encountered: