Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

生产环境 webpack 最基础的配置 #3

Open
shirleyMHao opened this issue Feb 23, 2018 · 0 comments
Open

生产环境 webpack 最基础的配置 #3

shirleyMHao opened this issue Feb 23, 2018 · 0 comments
Labels

Comments

@shirleyMHao
Copy link
Owner

本文只讨论webpack做为打包工具,生成生产环境所必须的js、css的基本配置

具体实现如下几项:

  1. 静态处理: 包括css和js 压缩打包,以及css的抽取,es6语法支持
  2. 图片处理:小图改为data uri
  3. 静态文件注入html

目录结构如下:

image
下面我们一条一条的说如何达成目标:

首先是 webpack基本配置(entry & output)

    const path = require('path');
    var assetsPath = function (_path) {
        var assetsSubDirectory = 'static'
        return path.posix.join(assetsSubDirectory, _path)
    }
    module.exports = {
       entry: './SRC/main.js',  //指定入口文件
       output: {
            filename: assetsPath('src/main.[hash:7].js'), // 生成文件名
            path: path.resolve(__dirname, 'dist')  // 生成文件根目录
        }
    }

静态文件处理:

- 处理css:

  1. 基础:

    一般来说需要css-loader 和 style-loader。由于webpack的入口文件必须是js,我们一般需要在js中通
    过import 引入css源文件,css-loader用于解析css文件,style-loader用于将解析后的css代码嵌入到js
    中。

module: {
    rules: [
     {
        test: /\.css$/,
        use: [ 'style-loader', 'css-loader' ]
      }
    ]
}
  1. 将css抽取为独立文件

    经过css-loader和style-loader的处理之后,css文件被成功插入到js中。这种做法存在的问题是,如果css过大,会导致js单文件过大,因此我们需要将css文件单独抽取出来生成独立文件。
    我们采用extract-text-webpack-plugin 插件。它会将所有的入口 chunk(entry chunks)中引用的 *.css,移动到独立分离的 CSS 文件。因此,你的样式将不再内嵌到 JS bundle 中,而是会放到一个单独的 CSS 文件(即 styles.css)当中。 如果你的样式文件大小较大,这会做更快提前加载,因为 CSS bundle 会跟 JS bundle 并行加载来实现css文件的抽取。
    下图是官方提供优缺点对比
    image

    使用该插件,我们需要在已有的loader,创建一个提取loader
    处理css的rules变更为:

const ExtractTextPlugin = require("extract-text-webpack-plugin");
module: {
    rules: [
     {
        test: /\.css$/,
        use:  ExtractTextPlugin ({
            fallback: 'style-loader',
            use: 'css-loader'
        })
      }
    ]
}

之后在plugin中指定抽取文件的生成目录和文件名了:

plugins: {
    new ExtractTextPlugin({
      filename: assetsPath('css/[name].[contenthash].css')
    })
}
 至此我们完成了css静态文件的打包和抽取。

处理js:

  1. 解析js

:支持es6语法,引入了babel-loader

module:{
    rules:[
      {
        test: /\.js$/,
        exclude: /(node_modules)/,
        use: {
          loader: 'babel-loader'
        }
      }
}
  1. 压缩js :

webpack 自带uglifyjs插件:

plugins: [
new webpack.optimize.UglifyJsPlugin({
      compress: { //压缩
        warnings: false
      },
      sourceMap: true //生成sourceMap
    })
]

处理图片

原则上使用url-loader和file-loader都可以。url-loader可以将低于limit的图片编译为data uri插入css,但url-loader是基于file-loader的,所以我们把两者结合起来一起使用。

module:{
    rules:[
    {
        test: /\.(png|jpe?g|gif|svg)(\?.*)?$/,
        loader: 'url-loader',
        options: {
          limit: 10000, //低于10000的图片编译为data uri
          name: assetsPath('img/[name].[hash:7].[ext]')
        }
      }
  ]
}

html处理

html-webpack-plugin插件根据模板生成编译后的html文件,并将编译后的静态资源注入html

plugins:[
new HtmlWebpackPlugin({
      filename: 'index.html',
      template: 'SRC/index.html',
      inject: true,
      minify: {
        removeComments: true,
        collapseWhitespace: true,
        removeAttributeQuotes: true
      }
    })
]

总结

package.json

"scripts": {
    "build": "webpack"
  },
"devDependencies": {
    "babel-cli": "^6.26.0",
    "babel-loader": "^7.1.2",
    "babel-preset-env": "^1.6.1",
    "css-loader": "^0.28.9",
    "extract-text-webpack-plugin": "^3.0.2",
    "file-loader": "^1.1.6",
    "html-webpack-plugin": "^2.30.1",
    "style-loader": "^0.20.1",
    "url-loader": "^0.6.2",
    "webpack": "^3.10.0"
  }

webpack.config.js

const path = require('path');
var webpack = require('webpack')
var HtmlWebpackPlugin = require('html-webpack-plugin');
const ExtractTextPlugin = require("extract-text-webpack-plugin");
assetsPath = function (_path) {
  var assetsSubDirectory = 'static'
  return path.posix.join(assetsSubDirectory, _path)
}
module.exports = {
  entry: './SRC/main.js',
  output: {
    filename: assetsPath('src/main.[hash:7].js'),
    path: path.resolve(__dirname, 'dist')
  },
  module:{
    rules:[
      {
        test: /\.js$/,
        exclude: /(node_modules)/,
        use: {
          loader: 'babel-loader'
        }
      },
      {
        test: /\.css$/,
        use: ExtractTextPlugin.extract({
          fallback: "style-loader",
          use: "css-loader"
        })
      },
      {
        test: /\.(png|jpe?g|gif|svg)(\?.*)?$/,
        loader: 'url-loader',
        options: {
          limit: 10000,
          name: assetsPath('img/[name].[hash:7].[ext]')
        }
      },
    ]
  },
  plugins: [
    new HtmlWebpackPlugin({
      filename: 'index.html',
      template: 'SRC/index.html',
      inject: true,
      minify: {
        removeComments: true,
        collapseWhitespace: true,
        removeAttributeQuotes: true
      }
    }),
    new ExtractTextPlugin({
      filename: assetsPath('css/[name].[contenthash].css')
    }),
    new webpack.optimize.UglifyJsPlugin({
      compress: {
        warnings: false
      },
      sourceMap: true
    })
  ]
};
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

1 participant