【翻譯】Webpack 4 教程:從0配置到生產模式

Skandar-Ln發表於2018-05-15

原文連結:Webpack 4 Tutorial: from 0 Conf to Production Mode

webpack 4 問世了!

這個流行的模組打包工具進行了大規模的升級。

webpack4,有什麼更新?大幅度的效能優化,零配置和明智的預設配置

【翻譯】Webpack 4 教程:從0配置到生產模式

webpack 4 ,零配置的模組打包工具

webpack是一個強力和有著很多獨特功能的工具,但是他的一大痛點在於他的配置檔案

給中大型專案提供一個配置檔案不是什麼大問題。你甚至無法離開它。然而,對於一些較小型應用來說就有點麻煩了,尤其是你在心血來潮想開始做一些好玩的app的時候。

這也是Parcel吸引人的原因

現在的好訊息是webpack 4 預設再也不需要一個配置檔案了!

webpack 4:零配置開始

建立一個目錄然後進入

mkdir webpack-4-quickstart && cd $_
複製程式碼

初始化package.json:

npm init -y
複製程式碼

安裝webpack4:

npm i webpack --save-dev
複製程式碼

我們也需要安裝另外一個包:webpack-cli

npm i webpack-cli --save-dev
複製程式碼

然後開啟package.json新增構建指令碼:

"scripts": {
  "build": "webpack"
}
複製程式碼

關閉儲存

試著執行

npm run build
複製程式碼

然後我們看到

ERROR in Entry module not found: Error: Can't resolve './src' in '~/webpack-4-quickstart'
複製程式碼

webpack 4 需要在./src目錄下找一個入口檔案!如果你不知道這是什麼意思,請參考我之前的文章

簡要來說:webpack需要這個入口檔案來開始js程式碼的打包。

在以前的版本里webpack的入口檔案需要在配置檔案webpack.config.js裡指定。

但是現在不用指定了,它會預設選擇./src/index.js這個檔案。

測試這個新特性很容易,建立一個./src/index.js:

console.log(`I'm a silly entry point`);
複製程式碼

重新構建:

npm run build
複製程式碼

你會在~/webpack-4-quickstart/dist/main.js得到你打包後的檔案。

什麼?等一下。都不需要指定輸出檔案嗎?是的。

在webpack 4 中不需要指定入口和出口檔案

webpack的真正本領是程式碼拆分。但是相信我,有一個零配置的工具可以加速你的程式。

所以這就是第一個新特性:他會把./src/index.js預設為入口檔案,把打包後的檔案放在./dist/main.js。

下一章後我們能看到另一個有用的特性:生產和開發模式

Webpack 4:生產和開發模式

在webpack中擁有兩份配置檔案是常事。

一個典型的專案應該有:

  • 一個開發用的配置檔案,用來定義webpack的dev server和其他東西
  • 一個生產環境用的配置檔案,用來定義UglifyJSPlugin,sourcemap和其他東西。

在webpack4中你能夠不寫一行配置。

怎麼做到的?

webpack 4介紹了生產和開發模式。

實際上如果你關注過npm run build的輸出資訊你會看到這個警告:

【翻譯】Webpack 4 教程:從0配置到生產模式

The ‘mode’ option has not been set. Set ‘mode’ option to ‘development’ or ‘production’ to enable defaults for this environment.

這代表什麼?我們看看。

開啟package.json檔案新增如下指令碼

"scripts": {
  "dev": "webpack --mode development",
  "build": "webpack --mode production"
}
複製程式碼

現在執行:

npm run dev
複製程式碼

檢視./dis/main.js檔案。你看到了什麼?嗯,我知道,他沒有被壓縮!

現在這樣:

npm run build
複製程式碼

現在再看,你看到什麼?一個壓縮後的檔案!

是的!

生產模式開啟了一系列額外的優化。包括minification, scope hoisting, tree-shaking等。

另一邊開發模式為速度做了優化,除了提供一個沒有壓縮的包以外沒有做額外的事。

所以這是第二個新特性:生產和開發模式。

在webpack4你不需要一行配置,只需要一個--mode選項。

webpack 4:覆蓋預設的入口/出口檔案

我喜歡webpack4的零配置,但是,如果我要覆蓋預設的入口或者出口配置要怎麼做呢?

package.json裡配置他們。

這是一個例子

"scripts": {
  "dev": "webpack --mode development ./foo/src/js/index.js --output ./foo/main.js",
  "build": "webpack --mode production ./foo/src/js/index.js --output ./foo/main.js"
}
複製程式碼

webpack 4:用Babel轉換ES6的js程式碼

【翻譯】Webpack 4 教程:從0配置到生產模式

現代JavaScript大多是用ES6寫的。

但是不是所有瀏覽器都知道怎麼處理ES6。我們需要做一些轉換。

這個轉換的步驟叫做transpiling。transpiling是指把ES6轉換成瀏覽器能夠識別的程式碼。

webpack本身並不知道如何去轉換,但是它有loaders。把他們想象成轉換器。

babel-loader是webpack的一個loader,可以轉換ES6以上的程式碼到ES5。

為了使用這個loader我們需要去安裝一系列的依賴。特別是:

  • babel-core
  • babel-loader
  • babel-preset-env (for compiling Javascript ES6 code down to ES5)

來安裝吧:

npm i babel-core babel-loader babel-preset-env --save-dev
複製程式碼

下一步我們在專案目錄下建立一個.babelrc檔案用來配置Babel。

{
    "presets": [
        "env"
    ]
}
複製程式碼

在這裡我們有兩個途徑去配置babel-loader:

  • 用webpack的配置檔案
  • 在npm指令碼里使用--module-bind

哦,我知道你在想什麼了。webpack4把自己定位為一個零配置的工具。為什麼我們又要寫配置檔案了呢。

webpack 4的零配置適用於:

  • 入口檔案。預設是./src/index.js
  • 出口檔案。預設是./dist/main.js
  • 生產和開發模式(無需建立兩套配置檔案)

這就夠了。對於loaders我們仍然需要使用配置檔案。

我曾關於這件事問過Sean。在webpack4中loaders是否和webpack3中沒有區別?有計劃對這些通用的loaders比如babel-loader提供零配置嗎?

他的回答是:

在未來的版本(v4之後,可能是4.x或者5.0),我們已經開始探索預設或附加系統如何幫助我們定義這一點。我們不想要的是:把一堆東西塞到核心程式碼裡去。我們需要的是:能夠支援擴充套件。

對於現在來說你仍必須依賴webpack.config.js

webpack 4:通過配置檔案使用babel-loader

建立一個名叫webpack.config.js的檔案然後配置loader:

module.exports = {
  module: {
    rules: [
      {
        test: /\.js$/,
        exclude: /node_modules/,
        use: {
          loader: "babel-loader"
        }
      }
    ]
  }
};
複製程式碼

沒有必要去指定入口檔案除非你想指定。

下一步開啟./src/index.js然後寫一些ES6程式碼:

const arr = [1, 2, 3];
const iAmJavascriptES6 = () => console.log(...arr);
window.iAmJavascriptES6 = iAmJavascriptES6;
複製程式碼

最後打包:

npm run build
複製程式碼

然後去./dist/main.js看看轉換後的程式碼。

webpack 4:不通過配置檔案使用babel-loader

還有一種使用webpack loaders的方法。

--module-bind選項讓你從命令列指定loaders。謝謝Cezar指出了這一點。

這個選項並不是webpack 4獨有的。3開始就有了。

你可以這樣在package.json中使用:

"scripts": {
    "dev": "webpack --mode development --module-bind js=babel-loader",
    "build": "webpack --mode production --module-bind js=babel-loader"
}
複製程式碼

然後你就可以開始構建了。

然後我並不是很喜歡這種方法(不喜歡太長的npm指令碼),儘管如此它很有趣。

webpack 4:在webpack 4中配置React

【翻譯】Webpack 4 教程:從0配置到生產模式

如果你已經安裝配置好了babel這會很簡單。

安裝React:

npm i react react-dom --save-dev
複製程式碼

新增babel-preset-react

npm i babel-preset-react --save-dev
複製程式碼

在.babelrc裡配置preset

{
  "presets": ["env", "react"]
}
複製程式碼

這樣就可以了。

Conner Aiken建議的你可以配置babel-loader也去載入**.jsx**檔案。這在你使用jsx副檔名的時候很有用。

開啟webpack.config.js然後這樣配置:

module.exports = {
  module: {
    rules: [
      {
        test: /\.(js|jsx)$/,
        exclude: /node_modules/,
        use: {
          loader: "babel-loader"
        }
      }
    ]
  }
};
複製程式碼

測試是否搭好你可以在./src/App.js裡建立一個React元件。

import React from "react";
import ReactDOM from "react-dom";
const App = () => {
  return (
    <div>
      <p>React here!</p>
    </div>
  );
};
export default App;
ReactDOM.render(<App />, document.getElementById("app"));
複製程式碼

然後在./src/idnex.js中引入:

import App from "./App";
複製程式碼

重新構建

webpack 4:HTML外掛

webpack需要兩個額外的元件去處理HTML:html-webpack-plugin和html-loader。

新增這兩個依賴:

npm i html-webpack-plugin html-loader --save-dev
複製程式碼

然後更新webpack的配置

const HtmlWebPackPlugin = require("html-webpack-plugin");
module.exports = {
  module: {
    rules: [
      {
        test: /\.js$/,
        exclude: /node_modules/,
        use: {
          loader: "babel-loader"
        }
      },
      {
        test: /\.html$/,
        use: [
          {
            loader: "html-loader",
            options: { minimize: true }
          }
        ]
      }
    ]
  },
  plugins: [
    new HtmlWebPackPlugin({
      template: "./src/index.html",
      filename: "./index.html"
    })
  ]
};
複製程式碼

./src/index.html新建一個HTML檔案:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="utf-8">
    <title>webpack 4 quickstart</title>
</head>
<body>
    <div id="app">
    </div>
</body>
</html>
複製程式碼

執行:

npm run build
複製程式碼

檢視./dist目錄。你會看到執行的結果。

沒有必要再你的HTML檔案中引入你的JavaScript:它會自動地注入進去。

在瀏覽器開啟./dist/index.html:你可以看到React元件執行起來了!

如你所見在處理HTML上沒有什麼變化。

webpack 4仍然是一個主要目標是js的模組打包工具。

但有個將HTML作為模組的方法(HTML作為入口)。

提取CSS到檔案中

webpack不知道怎麼去提取CSS到檔案中。

在之前這是extract-text-webpack-plugin的工作。

不幸的是這個外掛在webpack 4表現並不好。

Michael Ciniawsky說:

維護extract-text-webpack-plugin是一個很大的負擔,而且這不是第一次因為這個問題使得升級webpack的主要版本變得困難。

mini-css-extract-plugin是來解決這些問題的。

提示:你需要把webpack升級到4.2.0.0,不然這個外掛無法執行!

安裝它:

npm i mini-css-extract-plugin css-loader --save-dev
複製程式碼

然後建立一個CSS檔案用來測試

/* */
/* CREATE THIS FILE IN ./src/main.css */
/* */
body {
    line-height: 2;
}
複製程式碼

配置plugin和loader:

const HtmlWebPackPlugin = require("html-webpack-plugin");
const MiniCssExtractPlugin = require("mini-css-extract-plugin");
module.exports = {
  module: {
    rules: [
      {
        test: /\.js$/,
        exclude: /node_modules/,
        use: {
          loader: "babel-loader"
        }
      },
      {
        test: /\.html$/,
        use: [
          {
            loader: "html-loader",
            options: { minimize: true }
          }
        ]
      },
      {
        test: /\.css$/,
        use: [MiniCssExtractPlugin.loader, "css-loader"]
      }
    ]
  },
  plugins: [
    new HtmlWebPackPlugin({
      template: "./src/index.html",
      filename: "./index.html"
    }),
    new MiniCssExtractPlugin({
      filename: "[name].css",
      chunkFilename: "[id].css"
    })
  ]
};
複製程式碼

最後在入口檔案中引入CSS:

//
// PATH OF THIS FILE: ./src/index.js
//
import style from "./main.css";
複製程式碼

構建:

npm run build
複製程式碼

檢視./dist目錄,你應該能看到CSS的結果!

結論:extract-text-webpack-plugin在webpack 4中不能用了。請使用mini-css-extract-plugin。

webpack 4:webpack dev server

在你改變程式碼後執行npm run dev?這不是個理想的做法。花幾分鐘去配置下webpack的開發服務。一旦配置了webpack dev server 它會在瀏覽器中載入你的app。

只要你改變了檔案,它會自動地重新整理瀏覽器的頁面。

安裝下面的包來搭建webpack dev server:

npm i webpack-dev-server --save-dev
複製程式碼

然後開啟package.json調整指令碼:

"scripts": {
  "start": "webpack-dev-server --mode development --open",
  "build": "webpack --mode production"
}
複製程式碼

儲存關閉。

現在執行:

npm run start
複製程式碼

你就能看到webpack dev server在瀏覽器中載入你的應用了。

webpack dev server非常適合用來開發。(而且它能使得的React Dev Tools在瀏覽器中正常的工作)

webpack 4:資源

本教程在Github上的連結 => webpack-4-quickstart

我知道早就有很多webpack的列表但是這裡是我的:一系列優秀的webpack4資源 => awesome-webpack-4

這裡一定還要提一下Juho Vepsäläinen的SurviveJS webpack 4

相關文章