webpack.config.js 3.3 KB
Newer Older
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
/* eslint-disable no-console */
const path = require('path');
const fs = require('fs');
const webpack = require('webpack');
const Terser = require('terser');
const HtmlWebpackPlugin = require('html-webpack-plugin');
const MiniCssExtractPlugin = require('mini-css-extract-plugin');
const CopyWebpackPlugin = require('copy-webpack-plugin');

const netron = path.dirname(require.resolve('netron/src'));
const output = path.resolve(__dirname, 'dist');

const excludes = ['index.js', 'view.js', 'view-sidebar.js', 'view-grapher.js', 'app.js', 'base.js', 'electron.js'];
const src = fs.readdirSync(netron, {encoding: 'utf-8'}).filter(file => fs.statSync(path.join(netron, file)).isFile());
const commons = src.filter(file => path.extname(file) === '.js' && !excludes.includes(file));
const metadata = src.filter(file => path.extname(file) === '.json');

module.exports = {
    mode: 'production',
    context: __dirname,
    entry: {
        index: './src/index.js',
        shim: './src/shim.js',
        style: './src/style.scss'
    },
    output: {
        path: output,
        filename: '[name].[hash].js',
        publicPath: './'
    },
    optimization: {
        splitChunks: {
            cacheGroups: {
                vendors: {
                    name: 'vendors',
                    test: /[\\/]node_modules[\\/](?!netron)/,
                    chunks: 'all'
                },
                styles: {
                    name: 'styles',
                    test: /\.scss$/,
                    chunks: 'all',
                    enforce: true
                }
            }
        }
    },
    module: {
        rules: [
            {
                test: /\.scss/,
                use: [MiniCssExtractPlugin.loader, 'css-loader', 'postcss-loader', 'sass-loader']
            }
        ]
    },
    plugins: [
        new webpack.ProvidePlugin({
            pako: 'pako'
        }),
        new MiniCssExtractPlugin({
            filename: '[name].[contenthash].css',
            chunkFilename: '[id].[contenthash].css'
        }),
        new HtmlWebpackPlugin({
            filename: 'index.html',
            template: './src/index.html',
            inject: 'body',
            scriptLoading: 'blocking'
        }),
        new CopyWebpackPlugin({
            patterns: commons.map(file => ({
                from: path.join(netron, file),
                to: file,
                transform: content => {
                    try {
                        const result = Terser.minify(content.toString());
                        if (result.error) {
                            throw result.error;
                        }
                        return result.code;
                    } catch (e) {
                        console.error(e);
                        return content;
                    }
                }
            }))
        }),
        new CopyWebpackPlugin({
            patterns: metadata.map(file => ({
                from: path.join(netron, file),
                to: file,
                transform: content => {
                    try {
                        return JSON.stringify(JSON.parse(content.toString()));
                    } catch (e) {
                        console.error(e);
                        return content;
                    }
                }
            }))
        })
    ]
};