mkdir webpack
and cd webpack
and npm init -y
npm i webpack webpack-cli --save-dev
所谓 loader 只是一个导出为函数的 JavaScript 模块。loader runner 会调用这个函数,而后把上一个 loader 产生的结果或者资源文件(resource file)传入进去。函数的 this 上下文将由 webpack 填充,而且 loader runner 具备一些有用方法,可使 loader 改变为异步调用方式,或者获取 query 参数。
第一个 loader 的传入参数只有一个:资源文件(resource file)的内容。compiler 须要获得最后一个 loader 产生的处理结果。这个处理结果应该是 String 或者 Buffer(被转换为一个 string),表明了模块的 JavaScript 源码。另外还能够传递一个可选的 SourceMap 结果(格式为 JSON 对象)。
若是是单个处理结果,能够在同步模式中直接返回。若是有多个处理结果,则必须调用 this.callback()。在异步模式中,必须调用 this.async(),来指示 loader runner 等待异步结果,它会返回 this.callback() 回调函数,随后 loader 必须返回 undefined 而且调用该回调函数。
webpack loader对js代码、样式、图片等资源从新编译返回一个理想的结果,本质上说,loader是一些特殊的webpack插件,固然webpack自己有plugin的概念。默认状况下,资源文件会被转化为 UTF-8 字符串,而后传给 loader。经过设置 raw,loader 能够接收原始的 Buffer。每个 loader 均可以用 String 或者 Buffer 的形式传递它的处理结果。Complier 将会把它们在 loader 之间相互转换。loader 老是从右到左地被调用。css
接下来咱们以css-loader为例看看它的输出
建立文件以下:html
-- a.css -- index.html -- index.js -- webpack.config.js
a.css
#app { background-color: #f5f5f5; color: blue; } #app p { color: gray; }
index.html
<div id="app"> <h4>hello webpack!</h4> <p>hello loader!</p> </div> <script src="./main.js"></script>
index.js
const a = require('./a.css'); console.log(a);
webpack.config.js
module.exports = { entry: { main: './index.js' }, output: { filename: '[name].js', }, module: { rules: [ { test: /\.css$/, use: 'css-loader' } ] } }
上面的代码很常见,webpack帮助咱们加载.css文件。当weback在构建的过程当中会根据已有配置首先将a.css做为参数交给css-loader, css-loader将会进行一系列处理输出特定的数据。实际上a.css
会做为raw resource string
类型的参数,有一些loader只能接受raw做为参数,例如css-loader、handlebars-loader...
执行npx webpack
能够看到,css-loader将样式代码处理成了js数组,而且咱们的样式代码被处理成了字符串
修改webpack.config.js
node
... module: { rules: [ { test: /\.css$/, use: [ 'style-loader', 'css-loader' ] } ] } ...
加上style-loader
,再看看输出的啥:webpack
如你所见,style-loader将css-loader返回的样式数组一顿操做插入到html head中去了,而后他本身返回了一个空对象git
loader特性之一就是:利用参数完成某个任务,不是必定有所输出,就像一个返回值为空的函数。
显然style-loader就是符合这种特性的loader之一,它与css-loader搭配起来实现了咱们须要的功能。而且他们各自独立,保持小而精的运行,方便与其余loader搭配合做,好比当我想把样式代码输出为js字符串时我就会选择to-string-loader
,首先安装这个新的partner,npm i to-string-loader
,而后按照顺序引用它,切记顺序很重要,github
... module: { rules: [ { test: /\.css$/, use: [ 'to-string-loader', 'css-loader' ] } ] } ...
从新构建后结果以下:web
css-loader使用频率比较高,它有一些配置能够帮助咱们实现特定需求。npm
... module: { rules: [ { test: /\.css$/, use: [ 'to-string-loader', { loader: 'css-loader', options: { url: true, // 是否启用url(), 相似于 url(image.png)` => `require('./image.png') import: true, // 是否启用@import()加载样式 modules: false, // 是否启用CSS Modules localIdentName: [hash:base64], // Configure the generated ident sourceMap: false, // Enable/Disable Sourcemaps camelCase: false, // Export Classnames in CamelCase importLoaders: 0 // Number of loaders applied before CSS loader } } ] } ] } ...