Welcome to ShenZhenJia Knowledge Sharing Community for programmer and developer-Open, Learning and Share
menu search
person
Welcome To Ask or Share your Answers For Others

Categories

I'm using scss modules so I'm using styleName in my react components and everything works in dev. The elements in prod looks like <div class="row" stylename="table"></div> but no styles have been applied to table.

The webpack configs are split up into multiple files (webpack.profile.js, webpack.base.js, webpack.dev.js, webpack.prod.js)

Side note: I'm also noticing that certain jenkins job can't process @ variables, not sure if it's related to webpack/sass-loader.

webpack.profile.js

const path = require('path')
const UglifyJsPlugin = require('uglifyjs-webpack-plugin')
const OptimizeCSSAssetsPlugin = require('optimize-css-assets-webpack-plugin')
const CleanWebpackPlugin = require('clean-webpack-plugin')
const MiniCssExtractPlugin = require('mini-css-extract-plugin')
const CompressionPlugin = require('compression-webpack-plugin')
const VisualizerPlugin = require('webpack-visualizer-plugin')

module.exports = require('./webpack.base')({
    mode: 'production',
    devServer: {
        port: 3000,
        contentBase: path.join(process.cwd(), 'dist/')
    },
    optimization: {
        minimizer: [
            new UglifyJsPlugin({
                cache: true,
                parallel: true
            }),
            new OptimizeCSSAssetsPlugin()
        ]
    },
    module: {
        rules: [
            {
                test: /.(sc|sa|c)ss$/,
                use: [
                    { loader: MiniCssExtractPlugin.loader },
                        {
                        loader: "css-loader",
                        options: {
                                modules: true,
                                sourceMap: true,
                                localIdentName: "[name]_[local]_[hash:base64:5]"
                        }
                        }
                ]
            }
        ]
    },
    plugins: [
        new CompressionPlugin({
            test: /.(js|css|html)$/
        }),
        new VisualizerPlugin({
            filename: '../stats/bundleStats.html'
        }),
        new MiniCssExtractPlugin({
            filename: '[name].[hash].css',
            chunkFilename: '[id].[hash].css'
        })
    ]
})

webpack.base.js

const path = require('path')
const Dotenv = require('dotenv-webpack')
const HtmlWebPackPlugin = require('html-webpack-plugin')

module.exports = options => {
    let envPath = '.env'
    process.argv.forEach(val => {
        if (val.includes('--env=')) {
            const curEnv = val.slice(6)
            if (['dev', 'stg'].includes(curEnv)) {
                envPath = `.env.${curEnv}`
            }
        }
    })
    return {
        mode: options.mode,
        devServer: options.devServer,
        entry: [path.join(process.cwd(), 'src/main.js')],
        output: {
            path: path.join(__dirname, '../dist/'),
            publicPath: '/',
            filename: '[name].[hash].js',
            chunkFilename: '[id].[hash].js'
        },
        resolve: {
            extensions: ['.js', '.jsx'],
            modules: [
                path.join(__dirname, '../src'),
                path.join(__dirname, '../node_modules')
            ],
            alias: {
                '@constants': path.join(__dirname, '../src/constants'),
                '@c': path.join(__dirname, '../src/components'),
                '@C': path.join(__dirname, '../src/containers')
            }
        },
        plugins: options.plugins.concat([
            new Dotenv({
                path: path.join(process.cwd(), envPath)
            }),
            new HtmlWebPackPlugin({
                inject: true,
                template: path.join(__dirname, '../src/static/index.html'),
                favicon: path.join(__dirname, '../src/static/favicon.ico')
            })
        ]),
        module: {
            rules: options.module.rules.concat([
                // {
                //  enforce: 'pre',
                //  test: /.jsx?$/,
                //  exclude: /node_modules/,
                //  use: [
                //      {
                //          loader: 'eslint-loader',
                //          options: {
                //              quiet: true
                //          }
                //      }
                //  ]
                // },
                {
                    test: /.(woff|woff2|eot|ttf|otf)$/,
                    exclude: [ /.scss$/ ],
                    use: [
                        {
                            loader: 'file-loader',
                            options: {
                                name: '[hash].[ext]',
                                outputPath: 'fonts'
                            }
                        }
                    ]
                },
                {
                    test: /.svg$/,
                    loader: 'svg-react-loader'
                },
                {
                    test: /.(gif|png|jpe?g)$/i,
                    use: [
                        {
                            loader: 'url-loader',
                            options: {
                                limit: 10 * 1024,
                                name: '[hash].[ext]',
                                outputPath: 'assets'
                            }
                        },
                        {
                            loader: 'image-webpack-loader',
                            options: {
                                disable: options.mode === 'development'
                            }
                        }
                    ]
                }
            ])
        }
    }
}

webpack.dev.js

const webpack = require('webpack')
const BrowserSyncPlugin = require('browser-sync-webpack-plugin')

module.exports = require('./webpack.base')({
    mode: 'development',
    devServer: {
        hot: true,
        port: 3000,
        historyApiFallback: true
    },
    plugins: [
        new webpack.HotModuleReplacementPlugin(),
        new BrowserSyncPlugin(
            { proxy: 'http://localhost:3000/', open: false },
            { reload: false }
        )
    ],
    module: {
        rules: [
            {
                test: /.jsx?$/,
                exclude: /node_modules/,
                use: {
                    loader: 'babel-loader',
                    options: {
                        plugins: [
                            [
                                'react-css-modules',
                                {
                                    "filetypes": {
                                        ".scss": { "syntax": "postcss-scss" }
                                    },
                                    "generateScopedName": '[name]_[local]_[hash:base64:5]'
                                }
                            ],
                        ],
                    },
                },
                resolve: {
                        extensions: ['.js', '.jsx']
                }
            },
            {
                test: /.(sa|sc)ss$/,
                use: [
                    { loader: 'style-loader' },
                    {
                        loader: 'css-loader',
                        options: {
                            modules: true,
                            sourceMap: true,
                            localIdentName: '[name]_[local]_[hash:base64:5]'
                        }
                    },
                    {
                        loader: 'sass-loader'
                    }
                ]
            },
            {
                test: /.css$/,
                use: ['style-loader', 'css-loader', 'postcss-loader']
            },
        ]
    }
})

webpack.prod.js

const path = require('path');
const TerserPlugin = require('terser-webpack-plugin');
const CleanWebpackPlugin = require('clean-webpack-plugin');
const MiniCssExtractPlugin = require('mini-css-extract-plugin');
const CompressionPlugin = require('compression-webpack-plugin');
const OptimizeCSSAssetsPlugin = require('optimize-css-assets-webpack-plugin');

module.exports = require('./webpack.base')({
    mode: 'production',
    devServer: {
        port: 3000,
        contentBase: path.join(process.cwd(), 'dist/')
    },
    optimization: {
        minimize: true,
        minimizer: [
            new TerserPlugin({
                cache: true,
                parallel: true
            }),
            new OptimizeCSSAssetsPlugin()
        ]
    },
    module: {
        rules: [
            {
                test: /.jsx?$/,
                exclude: /node_modules/@babel/,
                use: {
                    loader: 'babel-loader',
                    options: {
                        presets: [
                            [
                            '@babel/preset-env',
                                {
                                    'targets': {
                                        'ie': '11'
                                    },
                                    'loose': true,
                                    'forceAllTransforms': true
                                }
                            ],
                            '@babel/preset-react'
                        ],
                        sourceType: 'unambiguous',
                        plugins: [
                            [
                                '@babel/plugin-proposal-decorators',
                                {
                                    'legacy': true
                                }
                            ],
                            '@babel/plugin-transform-runtime',
                            '@babel/plugin-syntax-dynamic-import',
                            '@babel/plugin-proposal-function-bind',
                            '@babel/plugin-proposal-class-properties',
                            '@babel/plugin-proposal-export-default-from',
                            '@babel/plugin-proposal-export-namespace-from'
                        ]
                    }
                },
                resolve: {
                    extensions: ['.js', '.jsx']
                }
            },
            {
                test: /.(sc|sa)ss$/,
                use: [
                    { loader: MiniCssExtractPlugin.loader },
                    {
                    loader: "css-loader",
                    options: {
                        modules: true,
                        sourceMap: true,
                        localIdentName: "[name]_[local]_[hash:base64:5]"
                    }
                    },
                    { loader: "postcss-loader" },
                    {  loader: "sass-loader" }
                ]
            },
            {
                test: /.css$/,
                use: [
                    MiniCssExtractPlugin.loader,
                    'css-loader',
                    'postcss-loader'
                ]
            }
        ]
    },
    plugins: [
        new CleanWebpackPlugin([path.join(process.cwd(), '/dist')], {
            allowExternal: true
        }),
        new MiniCssExtractPlugin({
            filename: '[name].[hash].css',
            chunkFilename: '[id].[hash].css'
        }),
        new CompressionPlugin({
            test: /.(js|css)$/,
            filename: asset => asset.file
        })
    ]
})
See Q

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
thumb_up_alt 0 like thumb_down_alt 0 dislike
127 views
Welcome To Ask or Share your Answers For Others

1 Answer

For this line of code

test: /.(sc|sa|c)ss$/,
                use: [
                    { loader: MiniCssExtractPlugin.loader },
                        {
                        loader: "css-loader",

I'm pretty sure you cant do that because scss and sass need to have sass or scss loader so it cant process sass or scss if you using css-loader

Here is how I config

module: {
        rules: [{
                test: /.scss$/,
                use: [
                    'style-loader',
                    MiniCssExtractPlugin.loader,
                    {
                        loader: "css-loader",
                        options: {
                            minimize: true,
                            sourceMap: true
                        }
                    },
                    {
                        loader: "sass-loader"
                    }
                ]
            }
        ]
    }

You can view my full config here


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
thumb_up_alt 0 like thumb_down_alt 0 dislike
Welcome to ShenZhenJia Knowledge Sharing Community for programmer and developer-Open, Learning and Share
...