3

I am trying to configure mini-css-extract-plugin to produce a single or chunks of CSS files from SCSS after building, but as it seems I am not very familiar with webpack and I fail somewhere.

Using "webpack": "^4.29.0", "mini-css-extract-plugin": "^0.5.0" what I managed to produce are JS files where they should have been CSS files.

const webpack = require('webpack')

const HtmlWebpackPlugin = require('html-webpack-plugin')
const CopyWebpackPlugin = require('copy-webpack-plugin')
const MiniCssExtractPlugin = require('mini-css-extract-plugin')

const isProd = (process.env.NODE_ENV === 'production')

const port = 3000,
    host = 'localhost'

const styles = [
    { loader: isProd? MiniCssExtractPlugin.loader : 'style-loader' },
    {
        loader: 'css-loader',
        options: {
            sourceMap: !isProd,
            modules: true,
        }
    },
    { loader: 'postcss-loader' },
    {
        loader: 'sass-loader',
        options: {
            sourceMap: !isProd,
        }
    }]

module.exports = {
    mode: isProd? 'production': 'development',
    entry: ['@babel/polyfill', './src/index.js'],
    module: {
        rules: [
            {
                test: /\.(sa|sc|c)ss$/,
                exclude: /node_modules/,
                use: styles
            },
            {
                test: /\.(js|jsx)$/,
                exclude: /node_modules/,
                use: ['babel-loader']
            },
            {
                test: /\.(woff(2)?|ttf|eot|svg)(\?v=\d+\.\d+\.\d+)?$/,
                exclude: /node_modules/,
                use: [{
                    loader: 'file-loader',
                    options: {
                        name: '[name].[ext]',
                        outputPath: 'content/fonts/'
                    }
                }]
            }
        ]
    },
    resolve: {
        extensions: ['.scss', '.js', '.jsx']
    },
    output: {
        path: __dirname + '/dist',
        publicPath: '',
        filename: 'bundle.js'
    },
    plugins: [
        new webpack.HotModuleReplacementPlugin(),
        new CopyWebpackPlugin([
            { from:'src/content/images', to: 'content/images' },
        ]),
        new HtmlWebpackPlugin({
            template: './src/index.html',
            inject: 'body',
        }),
        new MiniCssExtractPlugin({
            chunkFilename: '[name].css',
            filename: 'styles.css'
        })
    ],
    optimization: {
        splitChunks: {
            chunks: 'all',
            cacheGroups: {
                styles: {
                    name: 'styles',
                    test: /\.(css|sass|scss)$/,
                    chunks: 'all',
                    enforce: true,
                    minChunks: 1,
                    reuseExistingChunk: true,
                }
            }
        }
    },
    devtool: 'source-map',
    devServer: {
        contentBase: './dist',
        hot: true,
        host: host,
        port: port,
        historyApiFallback: true,
        compress: true,
    }
}

I want to able to produce a big single CSS file or multiple chunks of CSS and files.

2
  • And what you are back instead? An error? No CSS at all? Commented Feb 3, 2019 at 9:18
  • The result I get from bundling scss is a file named styles.bundle.js... Commented Feb 3, 2019 at 9:27

1 Answer 1

2

The problem is that the isProd is always false, that's why webpack creates your style chunk as a js file (styles.bundle.js). Set the isProd to true and give it a try. It should work. Actually I tried it on my machine and it did work.

const isProd = true // just for debugging purpose. (process.env.NODE_ENV === 'production')

And one more thing, I recommend to not to use Sass and PostCss together. I think that cost your project with more complexity. Because I don't think you'll need Sass or any other preprocessor with a tool like PostCSS. But if you insist on that, PostCSS has a nice parser for sass files, that way your webpack config will be more readable at least. Good luck!

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.