写在前面之前看过一篇不错的文章,很适合入门,传送门
本篇文章是基于我看了一些文章后动手写的一些结合平时业务的demo
完整代码在master分支上
####业务场景:
我现在想写一个插件,这个插件在编写完成后打包只生成一个js,别人用这个插件的时候只需要将这个js引入即可,相应的布局和样式会自动渲染到页面上(简单的一个插件实现)
demo目录结构如下:
从根目录开始看起,index.html是整个项目的容器模板(测试用),index.js是入口文件,同时也是插件的核心处理文件,其他就不用多说。然后template下面,是插件的核心模板和样式,loader目录下面放的就是自己写的loader了
下面是webpack的配置:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 var path = require ('path' ), webpack = require ('webpack' ), ROOT_PATH = path.resolve(__dirname), BUILD_DIR = path.resolve(ROOT_PATH, 'build' ); var HtmlWebpackPlugin = require ('html-webpack-plugin' );module .exports = { entry: { 'index' : path.resolve(ROOT_PATH, './index.js' ) }, output: { path: BUILD_DIR, publicPath: './' , filename: '[name]/index.js' }, module : { rules: [{ test: /\.html$/ , use: ['html-loader' ] },{ test: /\.html$/ , use: [{ loader: path.resolve('loader/test-html-loader.js' ) }], include: [path.resolve('template/' )] }] }, plugins: [ new HtmlWebpackPlugin({ title: '' , template: path.resolve('index.html' ), filename: 'index.html' , chunks: ['index' ], inject: 'body' }) ] }
其中核心的部分是:
1 2 3 4 5 6 7 { test: /\.html$/, use: [{ loader: path.resolve('loader/test-html-loader.js') }], include: [path.resolve('template/')] }
这个是我自己写的loader,处理的是以html结尾同时是在template目录下的文件,然后就是test-html-loader的具体代码:
1 2 3 4 5 6 7 8 9 var loaderUtils = require('loader-utils' );var fs = require('fs' );module .exports = function (source) { var basePath = this .context; var cssPath = /(\_include\()+('|")+(.+)+(' |")+\)/.exec(source)[3]; var content = fs.readFileSync(basePath +'/'+ cssPath); var all = source.replace(/(\_include\()+('|")+(.+)+('|")+\)/, '<style>'+content+'</style>'); return all; }
解释一下,这个loader主要做的就是匹配_include(PATH),然后拿到文件路径,读取对应文件之后替换掉_include(PATH),最后返回处理后的文件,为什么要这么做,是因为我的center.html里是这样写的:
1 2 3 4 5 6 <div > _include("center.css") <h2 > test</h2 > <h3 > xixi</h3 > <button > click</button > </div >
目的就是将css打到html中,然后index.js再去以模板的形式引入:
1 2 3 4 5 6 7 var tpl = require ('./template/center.html' );var parentEl = document .createElement('div' );parentEl.innerHTML = tpl; parentEl.querySelector('button' ).onclick = function ( ) { console .log(111 ); } document .body.appendChild(parentEl);
这样,当我打包完成以后,打开index.html就可以看到