2017-06-21 8 views
0

Webpackバンドルのサイズを小さくしようとしています。今は、初めてWebサイトをロードするのに約25秒かかります。 app.bundle.jsは11,989KB、vendor.bundle.jsは1,842KBです 私自身のコードはわずか数KBです。 私はapp.bundle.jsの内容をチェックすると、ほとんどのスペースが外部ライブラリ(react-dom、moment、react-bootstrap ...)によって取られます。webpack minify bundleを作成できません

私はそれらを小さくしようとしましたが私が試している何らかの理由が働いていない。

私はwebpackの専門家ではないので、知識の豊富な人からの助けを歓迎します。

注:使用しているWebpackファイルは、私が使用した別のプロジェクトのものです。サンプルがあります。だから完全に構成されていないかもしれません。ここで

は私のpackage.jsonです:

{ 
    "name": "myproject", 
    "version": "0.1.0", 
    "description": "a description.", 
    "private": true, 
    "devDependencies": { 
    "babel-plugin-react-html-attrs": "^2.0.0", 
    "babel-plugin-transform-runtime": "^6.15.0", 
    "babel-polyfill": "^6.16.0", 
    "babel-preset-stage-2": "^6.18.0", 
    "babili-webpack-plugin": "^0.1.1", 
    "compression-webpack-plugin": "^0.4.0", 
    "react-hot-loader": "^1.3.1", 
    "react-scripts": "0.9.2", 
    "serve-favicon": "^2.3.2", 
    "webpack-dev-server": "^2.4.1", 
    "webpack-hot-middleware": "^2.13.2" 
    }, 
    "dependencies": { 
    "axios": "^0.15.2", 
    "babel-core": "^6.2.1", 
    "babel-loader": "^6.2.0", 
    "babel-plugin-transform-class-properties": "^6.18.0", 
    "babel-plugin-transform-decorators-legacy": "^1.3.4", 
    "babel-plugin-transform-runtime": "^6.15.0", 
    "babel-polyfill": "^6.16.0", 
    "babel-preset-es2015": "^6.1.18", 
    "babel-preset-react": "^6.1.18", 
    "babel-preset-stage-0": "^6.3.13", 
    "babel-preset-stage-2": "^6.3.13", 
    "circular-dependency-plugin": "^2.0.0", 
    "classnames": "^2.2.1", 
    "clean-webpack-plugin": "^0.1.9", 
    "copy-webpack-plugin": "^4.0.1", 
    "css-loader": "^0.26.2", 
    "dotenv": "^4.0.0", 
    "es6-promise": "^4.0.5", 
    "file-loader": "^0.10.1", 
    "firebase": "^3.6.0", 
    "history": "^4.5.1", 
    "immutable": "^3.8.1", 
    "invariant": "^2.2.0", 
    "isomorphic-fetch": "^2.2.1", 
    "jsonwebtoken": "^7.2.1", 
    "less-loader": "^2.2.0", 
    "moment": "^2.11.1", 
    "react": "^15.4.2", 
    "react-addons-css-transition-group": "^15.4.2", 
    "react-async-script": "^0.7.0", 
    "react-bootstrap": "^0.30.7", 
    "react-dnd": "^2.0.2", 
    "react-dnd-html5-backend": "^2.0.2", 
    "react-dom": "^15.4.2", 
    "react-fontawesome": "^1.5.0", 
    "react-google-recaptcha": "^0.6.0", 
    "react-gravatar": "^2.2.2", 
    "react-helmet": "^4.0.0", 
    "react-input-range": "^1.0.2", 
    "react-modal": "^1.5.2", 
    "react-page-click": "^3.0.0", 
    "react-recaptcha": "^2.2.6", 
    "react-redux": "^5.0.3", 
    "react-router": "^3.0.2", 
    "react-router-redux": "^4.0.0", 
    "redux": "^3.0.4", 
    "redux-form": "^6.2.0", 
    "redux-logger": "^2.3.2", 
    "redux-thunk": "^2.2.0", 
    "rimraf": "^2.5.4", 
    "single-module-instance-webpack-plugin": "0.0.4", 
    "style-loader": "^0.13.2", 
    "superagent": "^3.5.0", 
    "webpack": "^2.2.1", 
    "xml2js": "^0.4.17", 
    "xmldom": "^0.1.27", 
    "xpath": "0.0.23" 
    }, 
    "scripts": { 
    "start": "node devServer.js --progress --verbose", 
    "clean": "rimraf ./dist", 
    "dev": "webpack -d --watch --progress --display-error-details --display-reasons", 
    "start1": "webpack-dev-server --config ./webpack.config.comphotdeploy -d --progress --colors --host localhost --port 28080 --hot --inline --content-base src", 
    "builddev": "webpack -d --progress --display-error-details --display-reasons", 
    "build": "webpack -p --progress --verbose", 
    "dist": "rimraf ./dist&&webpack -d --display-error-details --display-reasons", 
    "start-react": "SET PORT=9999&&SET DEVTOOL=source-map&&react-scripts start", 
    "build-react": "react-scripts build", 
    "test": "react-scripts test --env=jsdom", 
    "eject": "react-scripts eject" 
    }, 
    "eslintConfig": { 
    "extends": "./node_modules/react-scripts/config/eslint.js" 
    } 
} 

そして、私のWebPACK:

var BundleAnalyzerPlugin = require('webpack-bundle-analyzer').BundleAnalyzerPlugin; 

var webpack = require('webpack'); 
var path = require('path'); 

var ProvidePlugin = require("webpack/lib/ProvidePlugin"); 
var CommonsChunkPlugin = require("webpack/lib/optimize/CommonsChunkPlugin"); 
var LimitChunkCountPlugin = require("webpack/lib/optimize/LimitChunkCountPlugin"); 
var DedupePlugin = require("webpack/lib/optimize/DedupePlugin"); 
var SingleModuleInstancePlugin = require('single-module-instance-webpack-plugin'); 
var CleanWebpackPlugin = require('clean-webpack-plugin'); 
var CopyWebpackPlugin = require('copy-webpack-plugin'); 
var CircularDependencyPlugin = require('circular-dependency-plugin'); 

var BUILD_DIR = path.resolve(__dirname,'dist'); 

var APP_DIR = path.resolve(__dirname, 'src'); 

const BabiliPlugin = require('babili-webpack-plugin'); 

// http://dev.topheman.com/make-your-react-production-minified-version-with-webpack/ 
// https://medium.com/@rajaraodv/two-quick-ways-to-reduce-react-apps-size-in-production-82226605771a 
// https://hackernoon.com/tricks-to-minimize-react-js-build-file-size-a35e355b8c64 
var CompressionPlugin = require('compression-webpack-plugin'); 

// Load environment variables from .env file. Suppress warnings using silent 
// if this file is missing. dotenv will never modify any environment variables 
// that have already been set. 
// https://github.com/motdotla/dotenv 
require('dotenv').config({silent: true}); 

var PrintChunksPlugin = function() {}; 
PrintChunksPlugin.prototype.apply = function(compiler) { 
    compiler.plugin('compilation', function(compilation, params) { 
     compilation.plugin('after-optimize-chunk-assets', function(chunks) { 
      console.log(chunks.map(function(c) { 
       return { 
        id: c.id, 
        name: c.name 
/*, 
        includes: c.modules.map(function(m) { 
         return m.request; 
        }) 
*/ 
       }; 
      })); 
     }); 
    }); 
}; 

var config = { 
    devtool: 'cheap-module-source-map', 
    entry: { 
     app: APP_DIR + '/index.js', 
     vendor: [ 
      'react', 
      'react-dom' 
     ] 
    }, 

    output: { 
     path:BUILD_DIR, 
     filename: "[name].bundle.js", 
     chunkFilename: "[name]-chunk.js", 
     publicPath: BUILD_DIR 
    }, 

    watch: false, 
    watchOptions: { 
    poll: true, 
    aggregateTimeout: 300, 
    number: 1000 
    }, 
    module : { 
     loaders : [ 
      { 
       test : /\.jsx?/, 
       include : APP_DIR, 
       exclude: /node_modules/, 
       loaders: ['react-hot-loader', 'babel-loader?' + JSON.stringify({ 
       cacheDirectory: true, 
       plugins: [ 
        'transform-runtime', 
        'react-html-attrs', 
        'transform-class-properties', 
        'transform-decorators-legacy' 
       ], 
       presets: [ 
        [ 
         "es2015", 
         { 
          "modules": false 
         } 
        ], 
        'react', 
        'stage-2'] 
       })] 
      }, 

      // CSS 
      // "css" loader resolves paths in CSS and adds assets as dependencies. 
      // "style" loader turns CSS into JS modules that inject <style> tags. 
      // In production, we use a plugin to extract that CSS to a file, but 
      // in development "style" loader enables hot editing of CSS. 
      { 
       test: /\.css$/, 
       include: path.join(__dirname, 'src/style'), 
       loader: 'style-loader!css-loader' 
      }, 
      // "file" loader makes sure those assets get served by WebpackDevServer. 
      // When you `import` an asset, you get its (virtual) filename. 
      // In production, they would get copied to the `build` folder. 
      { 
       test: /\.(ico|jpg|png|gif|eot|otf|webp|svg|ttf|woff|woff2)(\?.*)?$/, 
       exclude: /\/favicon.ico$/, 
       loader: 'file-loader', 
       query: { 
       name: '[path][name][hash].[ext]', 
       publicPath: '/' 
       } 
      }, 
      { 
       test: /\.(ico)(\?.*)?$/, 
       exclude: /node_modules/, 
       loader: 'file-loader', 
       query: { 
        name: './images/[name].[ext]' 
       } 
      } 
     ] 
    }, 

    // use EnableCircularDependencyPlugin=true|false to check the option 
    plugins: [ 
     new webpack.DefinePlugin({ 
      // A common mistake is not stringifying the "production" string. 
      'process.env': { 'NODE_ENV': JSON.stringify('production') }, 

      // DISABLE redux-devtools HERE 
      __DEVTOOLS__: false 
     }), 

     // minify everything 
     new webpack.optimize.UglifyJsPlugin({ 
      compressor: { 
       warnings: false 
      } 
     }), 

     // Merge chunks 
     new webpack.optimize.AggressiveMergingPlugin(), 

     /* 
     new CompressionPlugin({ 
      asset: "[path].gz[query]", 
      algorithm: "gzip", 
      test: /\.js$|\.css$|\.html$/, 
      threshold: 10240, 
      minRatio: 0.8 
     }), 
     */ 

     // new BabiliPlugin(), 

     new CopyWebpackPlugin([ 
      { from: APP_DIR + '/index.html', to: BUILD_DIR + '/index.html' }, 
      { from: APP_DIR + '/images/favicon.ico', to: BUILD_DIR + '/images/favicon.ico' }, 
      { from: APP_DIR + '/images/favicon.png', to: BUILD_DIR + '/images/favicon.png' }, 
      { from: APP_DIR + '/images/favicon-16x16.png', to: BUILD_DIR + '/images/favicon-16x16.png' }, 
      { from: APP_DIR + '/images/favicon-32x32.png', to: BUILD_DIR + '/images/favicon-32x32.png' }, 
      { from: APP_DIR + '/images/favicon-48x48.png', to: BUILD_DIR + '/images/favicon-48x48.png' }, 
      { from: APP_DIR + '/images/favicon-57x57.png', to: BUILD_DIR + '/images/favicon-57x57.png' }, 
      { from: APP_DIR + '/images/favicon-60x60.png', to: BUILD_DIR + '/images/favicon-60x60.png' }, 
      { from: APP_DIR + '/images/favicon-72x72.png', to: BUILD_DIR + '/images/favicon-72x72.png' }, 
      { from: APP_DIR + '/images/favicon-76x76.png', to: BUILD_DIR + '/images/favicon-76x76.png' }, 
      { from: APP_DIR + '/images/favicon-96x96.png', to: BUILD_DIR + '/images/favicon-96x96.png' }, 
      { from: APP_DIR + '/images/favicon-114x114.png', to: BUILD_DIR + '/images/favicon-114x114.png' }, 
      { from: APP_DIR + '/images/favicon-120x120.png', to: BUILD_DIR + '/images/favicon-120x120.png' }, 
      { from: APP_DIR + '/images/favicon-144x144.png', to: BUILD_DIR + '/images/favicon-144x144.png' }, 
      { from: APP_DIR + '/images/favicon-152x152.png', to: BUILD_DIR + '/images/favicon-152x152.png' }, 
      { from: APP_DIR + '/images/favicon-160x160.png', to: BUILD_DIR + '/images/favicon-160x160.png' }, 
      { from: APP_DIR + '/images/favicon-180x180.png', to: BUILD_DIR + '/images/favicon-180x180.png' }, 
      { from: APP_DIR + '/images/favicon-192x192.png', to: BUILD_DIR + '/images/favicon-192x192.png' } 
      ]), 

     //new BundleAnalyzerPlugin({analyzerMode: 'static'}), 
     //new PrintChunksPlugin() 
    ], 

     /* 
      new webpack.HotModuleReplacementPlugin(), 

      new webpack.NoEmitOnErrorsPlugin(), 

      new webpack.optimize.CommonsChunkPlugin({ 
       name: 'permateam-core', 
       minChunks(module, count) { 
        var context = module.context; 
        return context && context.indexOf('src\\') >= 0; 
       }, 
      }), 

      new webpack.optimize.CommonsChunkPlugin({ 
       name: 'react-build', 
       minChunks(module, count) { 
        var context = module.context; 
        return context && (context.indexOf('node_modules\\react\\') >= 0 || context.indexOf('node_modules\\react-dom\\') >= 0); 
       }, 
      }), 

      new webpack.optimize.CommonsChunkPlugin({ 
       name: 'manifest' 
      }), 

      // uglfy/minify js 
      new webpack.optimize.OccurrenceOrderPlugin(), 
      new webpack.optimize.UglifyJsPlugin({ 
       mangle: true, 
       compress: { 
        warnings: false, // Suppress uglification warnings 
        pure_getters: true, 
        unsafe: true, 
        unsafe_comps: true, 
        screw_ie8: true 
       }, 
       output: { 
        comments: false, 
       }, 
       exclude: [/\.min\.js$/gi] // skip pre-minified libs 
      }), 

      new BundleAnalyzerPlugin({analyzerMode: 'static'}), 
      //new PrintChunksPlugin(), 

     //*********************************** async chunks************************* 

     //catch all - anything used in more than one place 
     new webpack.optimize.CommonsChunkPlugin({ 
      async: 'used-twice', 
      minChunks(module, count) { 
       return count >= 2; 
      }, 
     }), 

     //specifically bundle these large things 
     new webpack.optimize.CommonsChunkPlugin({ 
      async: 'react-dnd', 
      minChunks(module, count) { 
       var context = module.context; 
       var targets = ['react-dnd', 'react-dnd-html5-backend', 'react-dnd-touch-backend', 'dnd-core'] 
       return context && context.indexOf('node_modules') >= 0 && targets.find(t => new RegExp('\\\\' + t + '\\\\', 'i').test(context)); 
      }, 
     }), 

     return plugins; 
    })(), 
    */ 

    node: { 
     net: 'empty', 
     dns: 'empty' 
    } 
}; 

module.exports = config; 
+0

bundle.jsファイルを開き、すでにファイルが圧縮されているかどうかを確認しましたか? 'new webpack.DefinePlugin({ 'process.env':{ NODE_ENV:JSON.stringify( 'production') } })'それを小さくする必要があります – Hoyen

+0

はい。 これはapp.bundle.js内のサンプルです 'function translate(number、withoutSuffix、key){\ n var result = number + ''; \ n switch(key){\ n case 'm' :\ n返さずに返す? 'minuta': 'minut'; \ n大文字小文字の 'mm':\ n大文字小文字の 'h' \ nケース 'MM':\ n結果を返す+(複数の(複数))\ nケース 'hh':\ nリターン結果+(複数(数値)? 'godzin': 'ゴジン'番号)? 'miesiące': 'miesię' –

答えて

0

私は問題が起こる理由を私は理解していない場合でも、問題を解決する方法を見つけました。

私は今、私は

NPMの実行が

を構築やって

NPMの実行distの

をしていた

今app.bundle.jsが1765でありますKBとvendor.bundle.jsは151KB

です

私はまだapp.bundle.jsをさらに縮小するためにいくつかの最適化を行っていますが、それは既に良いスタートです。

誰かがアイデアを持っていれば、なぜminifyがdistで動作しないのか、私はまだ知りたいです。

関連する問題