目錄css
上節: css代碼分割html
目錄:node
先改一下src/index.js:webpack
import _ from 'lodash'; const root = document.getElementById('root'); root.innerText = _.join(['hello', 'webpack'], '-');
如今寫一個簡單的loader,將全部的webpack替換成其它內容,內容可經過options配置。
在根目錄新建loaders/replace-loader.js。web
loaders/replace-loader.js:npm
const { getOptions } = require('loader-utils'); module.exports = function(source) { /* this指向webpack source:打包後的文件內容 this.query options參數 */ const options = getOptions(this) || {}; // 返回處理後的結果,至關因而打包攔截器 return source.replace('webpack', options.name || 'Madao'); }
source是打包後生成的文件,options能夠拿到配置參數,這個loader會將全部webpack替換成options.name的內容,若是沒指定options.name, 就替換成Madao.segmentfault
而後引用這個loader, 修改webpack/webpack.base.js:api
const HtmlWebpackPlugin = require('html-webpack-plugin'); const { resolve } = require('path'); module.exports = { entry: './src/index.js', output: { path: resolve(__dirname, '../bundles') }, // 註冊loader resolveLoader: { // loader查找順序,從左到右 modules: ['node_modules', './loaders/'] }, module: { rules: [{ test: /\.js$/, exclude: /node_modules/, // 先不傳options use: ['replace-loader', 'babel-loader'] }, { test: /\.(gif|jpg|jpeg|png|svg)$/, use: ['url-loader'] }] }, plugins: [ new HtmlWebpackPlugin({ template: './index.html' }) ] };
安裝loader工具庫:npm i loader-utils -D
而後npm run build, 打開bundles下的main.[contenthash].js文件,應該能夠搜索到Madao:babel
而後咱們本身傳一個配置參數,修改webpack/webpack.base.js:異步
// 省略 module: { rules: [{ test: /\.js$/, exclude: /node_modules/, use: [{ loader: 'replace-loader', options: { name: '史珍香' } }, 'babel-loader'] }, { test: /\.(gif|jpg|jpeg|png|svg)$/, use: ['url-loader'] }] }, // 省略
再次npm run build,能夠看到webpack就換成了'史珍香':
一個簡單的loader就實現了。如今這個replace-loader只返回了替換後的內容,若是還想返回點其它內容,就得再改寫下。
loaders/replace-loader.js:
const { getOptions } = require('loader-utils'); module.exports = function(source) { /* this指向webpack source:打包後的文件內容 this.query options參數 */ const options = getOptions(this) || {}; // 返回處理後的結果,至關因而打包攔截器 // return source.replace('webpack', options.name || 'Madao'); const result = source.replace('webpack', options.name || 'Madao'); /* this.callback( err: Error | null, // error信息 content: string | Buffer, // 要返回的內容 sourceMap?: SourceMap, // source-map meta?: any // 會被 webpack 忽略,能夠是任何東西(例如一些元數據)。 ); */ // 若是隻傳這兩個參數,效果同上 this.callback(null, result); }
若是轉換過程當中有什麼異步操做,還能夠返回異步loader,這裏用定時器模擬下異步
loaders/replace-loader.js:
module.exports = function(source) { const callback = this.async(); setTimeout(() => { // 直接影響打包時間 const options = getOptions(this); const result = source.replace('webpack', options.name || 'Madao'); callback(null, result); // 這裏實際仍是調用了this.callback() }, 3000); }
this對象上還掛了不少屬性,具體參考:https://webpack.js.org/api/lo...
下節:編寫一個plugin