1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129
| const path = require('path'); const HtmlWebpackPlugin = require('html-webpack-plugin'); const MiniCssExtractPlugin = require('mini-css-extract-plugin'); const TerserPlugin = require('terser-webpack-plugin'); const CssMinimizerPlugin = require('css-minimizer-webpack-plugin'); const BundleAnalyzerPlugin = require('webpack-bundle-analyzer').BundleAnalyzerPlugin;
module.exports = { mode: 'production', entry: { app: './src/index.js' }, output: { path: path.resolve(__dirname, 'dist'), filename: 'js/[name].[contenthash:8].js', chunkFilename: 'js/[name].[contenthash:8].chunk.js', clean: true }, optimization: { minimizer: [ new TerserPlugin({ terserOptions: { compress: { drop_console: true, drop_debugger: true, pure_funcs: ['console.log'] } } }), new CssMinimizerPlugin() ], splitChunks: { chunks: 'all', cacheGroups: { vendor: { test: /[\\/]node_modules[\\/]/, name: 'vendors', priority: 10, chunks: 'all' }, common: { name: 'common', minChunks: 2, chunks: 'all', priority: 5, reuseExistingChunk: true } } }, runtimeChunk: { name: 'runtime' } }, module: { rules: [ { test: /\.js$/, exclude: /node_modules/, use: { loader: 'babel-loader', options: { presets: [ ['@babel/preset-env', { targets: '> 0.25%, not dead' }], ['@babel/preset-react', { runtime: 'automatic' }] ], plugins: [ '@babel/plugin-syntax-import-assertions', ['@babel/plugin-proposal-decorators', { legacy: true }] ] } } }, { test: /\.css$/, use: [ process.env.NODE_ENV === 'production' ? MiniCssExtractPlugin.loader : 'style-loader', 'css-loader', 'postcss-loader' ] }, { test: /\.(png|jpg|jpeg|gif|svg)$/, type: 'asset/resource', generator: { filename: 'images/[name].[hash:8][ext]' } } ] }, plugins: [ new HtmlWebpackPlugin({ template: './public/index.html', minify: { removeComments: true, collapseWhitespace: true, removeRedundantAttributes: true, useShortDoctype: true, removeEmptyAttributes: true, removeStyleLinkTypeAttributes: true, keepClosingSlash: true, minifyJS: true, minifyCSS: true, minifyURLs: true } }), new MiniCssExtractPlugin({ filename: 'css/[name].[contenthash:8].css', chunkFilename: 'css/[name].[contenthash:8].chunk.css' }), ...(process.env.ANALYZE ? [new BundleAnalyzerPlugin()] : []) ], resolve: { extensions: ['.js', '.jsx', '.ts', '.tsx'], alias: { '@': path.resolve(__dirname, 'src'), '@components': path.resolve(__dirname, 'src/components'), '@utils': path.resolve(__dirname, 'src/utils'), '@services': path.resolve(__dirname, 'src/services'), '@hooks': path.resolve(__dirname, 'src/hooks') } } };
|