parcel 最大的特色就是簡單,內置常見依賴,默認支持模塊熱替換和引用 CSS 文件。css
webpack 4.0 在優化構建性能的同時,也添加了許多默認配置。(重大變化:點我)html
特性 | webpack | parcel |
---|---|---|
文件名添加 hash | 支持 | 不支持 |
構建時處理 css | 需配置 | 易 |
tree-shaking | production 下支持 | 不支持 |
構建時預編譯 | production 下支持 | 不支持 |
生成 html 文件並引用資源 | 需配置,且默認 CSS 在 JS 文件中 | 自動生成,CSS 是獨立的文件 |
熱模塊更新(HMR) | 需配置 | 開發模式下默認開啓 |
如下針對構建工具經常使用功能,對 webpack
和 parcel
進行對比node
const path = require('path'); module.exports = { mode: 'development', // development / production entry: './src/index.js', output: { filename: 'bundle-[hash].js', path: path.resolve(__dirname, 'dist') } };
兩個模式(主要區別就是前一個開發模式不壓縮,生產模式壓縮)react
NamedModulesPlugin
UglifyJsPlugin
, ModuleConcatenationPlugin(預編譯)
and NoEmitOnErrorsPlugin
開發模式(支持熱更新,並開啓服務):webpack
parcel index.html --out-dir ../dist/
生產模式(代碼壓縮):es6
parcel build index.js --out-dir ../dist
webpack 只構建 JS 文件,因此 CSS 文件都會以字符串形式保存在 JS 文件中(固然必要時也能夠單獨配置,拆分 css 文件),並需手動引用到 index.html 文件中。web
對 CSS 預處理,都須要配置 webpack.config.js 文件,添加 loadertypescript
module: { rules: [{ test: /\.css$/, use: [ 'style-loader', 'css-loader' ] }] }
在 js 文件中引入的 CSS 會自動構建並引用到 html 裏,還支持預處理器如:less sass stylusnpm
這裏舉 sass 爲例json
npm install node-sass
import './index.sass'
執行 parcel,sass 文件將會被構建成 css 文件名引用到 index.html 中
babel
安裝依賴包
npm install babel-loader babel-core babel-preset-env webpack
配置 webpack.config.js
文件
module: { rules: [{ test: /\.js$/, exclude: /(node_modules|bower_components)/, use: { loader: 'babel-loader', options: { presets: ['babel-preset-env'] } } }] }
postcss
安裝
npm i -D postcss-loader
配置 postcss.config.js
文件
module.exports = { parser: false, plugins: { 'postcss-import': {}, 'postcss-cssnext': {}, 'cssnano': {}, 'autoprefixer': true } }
typescript
安裝依賴包
npm install --save-dev typescript ts-loader
建立 tsconfig.json
文件
{ "compileOptions": { "outDir": "./dist/", "noImplicitAny": true, "module": "es6", "target": "es5", "jsx": "react", "allowJs": true } }
建立 index.ts
文件
function greeter(person: string) { return "Hello, " + person; } let user = "Jane User"; document.body.innerHTML = greeter(user);
配置 webpack.config.js
const path = require('path'); module.exports = { mode: 'development', entry: './src/index.ts', module: { rules: [{ test: /\.css$/, use: [ 'style-loader', 'css-loader' ] }, { test: /.tsx?$/, use: 'ts-loader', exclude: /node_modules/ }] }, resolve: { extensions: [ '.tsx', '.ts', '.js' ] }, output: { filename: 'bundle.js', path: path.resolve(__dirname, 'dist') }, };
babel
npm i babel-preset-env // create a .babelrc: { "presets": ["env"] }
PostCSS
npm i postcss-modules autoprefixer { "plugins": { "autoprefixer": { "grid": true } } }
typescript
只需安裝 typescript 便能使用
npm i typescript
有三種方法來實現
在 webpack.config.js
中配置 entry point
const path = require('path'); const HTMLWebpackPlugin = require('html-webpack-plugin'); module.exports = { mode: 'development',//'production', entry: { index: './src/index.js', another: './src/util.js' }, plugins: [ new HTMLWebpackPlugin({ // 生成 html 文件,並引入入口文件 title: 'Code Splitting' }) ], output: { filename: '[name].bundle.js', path: path.resolve(__dirname, 'dist') }, };
使用 splitChunks
提取公共組件
webpack 4
中,CommonChunkPlugin
將被配置項 optimization.splitChunks
const path = require('path'); const HTMLWebpackPlugin = require('html-webpack-plugin'); module.exports = { mode: 'development', entry: { index: './src/index.js', another: './src/another.js' }, plugins: [ new HTMLWebpackPlugin({ // 生成 html 文件,並引入入口文件 title: 'Code Splitting' }) ], optimization: { splitChunks: { chunks: "all", name: 'common', } }, output: { filename: '[name].bundle.js', path: path.resolve(__dirname, 'dist') }, };
動態引用,import
異步加載
異步加載文件,並返回 promise
,若是多個異步import
的 chunkname
一致,則構建時會合並這個文件
配置 webpack.config.js
const path = require('path'); const HTMLWebpackPlugin = require('html-webpack-plugin'); module.exports = { mode: 'development',//'production', entry: { index: './src/index.js', another: './src/another.js' }, output: { filename: '[name].bundle.js', chunkFilename: '[name].bundle.js', path: path.resolve(__dirname, 'dist') }, };
引用方法
function getComponent() { return import(/* webpackChunkName: "lodash" */ 'lodash').then(_ => { // todo }) } getComponent().then(component => {})
async
寫法
async function getComponent() { const _ = await import(/* webpackChunkName: "lodash" */ 'lodash'); // todo } getComponent().then(component => {});
util.js
文件
export function a() { console.log('a'); } export function b() { console.log('b'); }
index.js
文件
import('./util').then(function (util) { util.a(); });
安裝依賴
npm install --save-dev webpack-dev-server
配置 webpack.config.js
const path = require('path'); const HTMLWebpackPlugin = require('html-webpack-plugin'); const webpack = require('webpack'); module.exports = { mode: 'development',//'production', entry: { index: './src/index.js', another: './src/another.js' }, devServer: { contentBase: './dist', hot: true }, plugins: [ // new CleanWebpackPlugin(['dist']), new HTMLWebpackPlugin({ title: 'Hot Module Replacement' }), new webpack.NamedModulesPlugin(), new webpack.HotModuleReplacementPlugin() ], output: { filename: '[name].bundle.js', chunkFilename: '[name].bundle.js', path: path.resolve(__dirname, 'dist') }, };
配置 package.json
"scripts": { "start": "webpack-dev-server --open" }
執行運行代碼
npm start
開發模式下自動默認支持