zoukankan      html  css  js  c++  java
  • webpack的学习感悟

    https://github.com/webpack/webpack    webpack gethub地址。

    http://webpack.github.io/   webpack 官网

    前言

    webpack作为现在比较火的前端框架,可以打包js、css、html、less、jade等文件,并且应用比较广泛。甚至一些比较火的前端框架都在使用webpack打包工具,例如vue,react等等。本着互联网的分享精神,我就将我自己的理解和想法分享给大家。

    安装

    安装之前如果会用cnpm的尽量用cnpm这样会快一点,本案例默认电脑上没有安装cnpm镜像。

    1、设置全局webpack

    npm install -g webpack

    2、进入目标文件夹,本人使用文件目录(E:webpack-test)

    cd  E:webpack-test

    3、在项目中引导创建一个package.json文件 

    npm init  (初始化过程就默认按回车就行了)

    4、安装webpack

    npm install webpack --save-dev   ( --save-dev 安装包信息将加入到devDependencies(开发阶段的依赖),所以开发阶段一般使用它) 安装完成后会在项目目录下出现node_module文件夹就证明安装成功了

     跟我一起使用

    案例1

    1、在项目目录下新建一个test1.js文件 ,随便写一个函数。然后进行打包

    function test(){
        console.log('1')
    }

    2、开始打包

    在命令行内输入webpack test1.js(文件入口)   test-pack.js(打包完成名字)

    3、打包完成

      打包完成后命令行会返回几个参数,1、Hash - 哈希值2、Version - webpack的版本、 Time:打包耗费时长。

      另外还返回一个列表Asset - 这次生成的文件、Size - 打包后的大小、Chunks - 这次打包的分块、Chunk Name  - 这次打包的块名称。

    4、打开test-pack.js文件

    我们发现,文件好像比没有打包之前大了,因为webpack打包之前会生成一些需要的内置函数,在页面的最下方可以看见我们打包的代码。

    webpack打包css文件 

    注意webpack中在js文件内是可以引用css文件的。

    1、新建一个css文件名称叫做style.css

      在里面随便写一些css代码。

    2、在test.js文件中引用css

      test.js全部代码

    require('./style.css')
    function test() {
        console.log('1')
    }

    3、打包css 但是打包之前需要安装css-loader、 和style-loader否则会报错。

      npm install css-loader style-loader  --save-dev    style-loader 是让css生效,生效后的效果就是在html页面的head标签里自动新建style标签并插入代码(这个以后的案例会讲)、css-loader是让打包软件识别css并处理css文件。

    4、运行打包命令

      webpack test1.js test-pack.js  - 但是还会报错提示- You may need an appropriate loader to handle this file type 明明已经安装了loader怎么还报错呢。

      解决错误,根目录也就是webpack-test 下新建webpack.config.js文件写入如下代码。即可解决。错误原因是没有指定loader。

    var Webpack = require("webpack");
    module.exports = {
        module: {
            loaders: [
                {
                    test: /.css$/,
                    loader: "style-loader!css-loader"
                }
            ]
        }
    }

      或者引入css时候增加css-loader!,前缀即可

    require('css-loader!./style.css');
    

    5、打包完成

    打包完成后我们看test-pack文件中又多出了好多webpack引入的一些代码,在代码的中间部分可以看见我们刚才写的css,这说明我们的css已经引入成功了。

     如何实现多文件打包

      在一些单页面应用中一般都会打包成一个文件,那例如像官网(举例)那种也可以打包成为多页应用。但是要如何配置呢。很简单只需要配置webpack.config.js文件即可。

      代码如下,配置完成后 在命令行内输入 webpack 就可以了,因为已经配置了webpack.config.js。就不用像上面案例那样输入很长一段语句了。

    var path = require('path') //这里是引入了node.js的path模块,
    module.exports = {
        entry: {
            main1:'./src/script/main.js',    //如果这的value指定的是一个数组,那么就相当于将两个文件打包成一个文件。
            main2:'./src/script/main2.js',
        }, //多文件入口文件配置  如果是单文件只需要写一个.string路径即可。
        output: {
            path: path.resolve(__dirname, './dist/js'), //打包后的文件的绝对路径地址
            filename: '[name].js' //打包后的文件名称[name]就像当月entry下的key(main1)还有hash、chunkhash等选项,但一般不怎么用所以呢,就不只拿name举例了。如果这里不写[]变量占位符而是一个普通的字符串的话打包文件会被覆盖,最后只会留下最后打包那个文件。
        },
    };

    chunkhash使用后文件生成动态名称,那么script要怎么引用呢。html-webpack-plugin

      在一些大型项目中需要上传到服务器远程仓库,这时候chunkhash就非常有效,因为chunkhash是当文件修改后他才会发生改变,对代码的控制性比较强。但是chunkhash改变后 script 的引用名称也需要进行更改,这样做是不是很麻烦呢,但是有一种方法可以解决。请看代码。

      1、安装 npm install html-webpack-plugin --save-dev

    var path = require('path');
    var htmlWebpackPlugin = require('html-webpack-plugin');
    
    module.exports = {
        entry: {
            main1: './src/script/main.js',
            main2: './src/script/main2.js',
        }, //多文件入口文件配置  如果是单文件只需要写一个.string路径即可。
        output: {
            path: path.resolve(__dirname, './dist/js'), //打包后的文件地址
            filename: '[name]-[chunkhash].js' //打包后的文件名称[name]就像当月entry下的key(main1)
        },
        plugins: [
            new htmlWebpackPlugin({
                template: 'index.html',  //指定模板文件,如果不指定的话会自动生成一个新建的index.html文件一起打包到path指定的打包地址。如果指定了的话,会将指定的模板打包后放入path指定的打包地址,然后自动使用script的 src引入entry下的所有文件
                minify:{ //代码压缩
                    removeComments:true,  //删除代码内的注释
                    collapseWhitespace:true,//删除代码内的空格
                }
            })
        ]
    };

     使用html-webpack-plugin打包多html文件

    使用html-webpack-plugin打包多文件其实很简单,因为plugins接收的是一个数组。所以只要多new htmlwebpackPlugin即可。

      请看代码

    var path = require('path');
    var htmlWebpackPlugin = require('html-webpack-plugin');
    
    module.exports = {
        entry: {
            main1: './src/script/main.js',
            a: './src/script/a.js',
            b: './src/script/b.js',
            c: './src/script/c.js',
        }, //多文件入口文件配置  如果是单文件只需要写一个.string路径即可。
        output: {
            path: path.resolve(__dirname, './dist/js'), //打包后的文件地址
            filename: '[name]-[chunkhash].js' //打包后的文件名称[name]就像当月entry下的key(main1)
        },
        plugins: [
            new htmlWebpackPlugin({
                filename: "a.html",  //打包后的html文件名称 
                template: 'index.html',   //理解为要打包那个文件,其实这里专业解释是使用那个模板。
                inject: 'body',    // 将JavaScript模块放在那个标签下,
                chunks: ['a', 'main1']//要使用那个JavaScript模块   也可是使用excludeChunks,excludeChunks和chunks相反,excludeChunks是排除entey下的那个模块的使用,例如 excludeChunks: ['a']  那么就是除了a意外entry下的模块都使用。
            }),
            new htmlWebpackPlugin({
                filename: "b.html",
                template: 'index.html',
                inject: 'body',
                chunks: ['b']
            }),
            new htmlWebpackPlugin({
                filename: "c.html",
                template: 'index.html',
                inject: 'body',
                chunks: ['c']
            })
        ]
    };

     使用babel-loader将要es6语法转换为es5语法

    安装

    npm  install  babel-loader babel-core  babel-preset-latest --save-dev

    设置 webpack.config.js文件。 打包完成后就将es6语法转换为es语法了。

    var htmlWebpackPlugin = require('html-webpack-plugin');
    var path = require('path');
    module.exports = {
        entry: './src/app.js',
        output: {
            path: path.resolve(__dirname, './dist/js'),
            filename: 'js/[name].bundle.js'
        },
        module: {
            loaders: [
                {
                    test: /.js$/,
                    loader: 'babel-loader',
                    exclude:  path.resolve(__dirname, './node_modules'), //排除那些文件不打包 include 制定打包那些
                    query: {
                        presets: ['latest']   //这里可以指定想转换为什么语法。例如2015 
                    }
                },
                {
                    test: /.css$/,
                    loader: "style-loader!css-loader"
                }
            ]
        },
        plugins: [
            new htmlWebpackPlugin({
                filename: 'index.html',
                template: 'index.html',
                inject: 'body'     //将js文件插入body文件内
            })
        ]
    }

     也可以将配置信息写在package中

    注意: 直接写在对象中就可以

     "babel": {
        "presets": [
          "latest"
        ]
      },

     使用postcss-loader 实现webpack对css语法打包,并对浏览器兼容性样式进行处理。

    安装:

    npm install postcss-loader postcss-import  autoprefixer  cssnano --save -dev 

    注意:如果没有安装css-loader 和style-loader 的同学记得安装,上述案例已经进行讲解。

    var htmlWebpackPlugin = require('html-webpack-plugin');
    var path = require('path');
    module.exports = {
        entry: './src/app.js',
        output: {
            path: path.resolve(__dirname, './dist/js'),
            filename: 'js/[name].bundle.js'
        },
        module: {
            loaders: [
                {
                    test: /.css$/,
                    use: [
                        'style-loader',
                        {
                            loader: 'css-loader',
                            options: {importLoaders: 1} //这里可以简单理解为,如果css文件中有import 进来的文件也进行处理
                        },
                        {
                            loader: 'postcss-loader',
                            options: {           // 如果没有options这个选项将会报错 No PostCSS Config found
                                plugins: (loader) => [
                                    require('postcss-import')({root: loader.resourcePath}),
                                    require('autoprefixer')(), //CSS浏览器兼容
                                    require('cssnano')()  //压缩css
                                ]
                            }
                        }
                    ]
                }
            ]
        },
    
        plugins: [
            new htmlWebpackPlugin({
                filename: 'index.html',
                template: 'index.html',
                inject: 'body'     //将js文件插入body文件内
            }),
        ]
    };

    webpack怎么实现打包less,sass

    安装

      npm install  less-loader  css-loader postcss-loader less-loader less --save-dev

    webpack.config.js 代码

    var htmlWebpackPlugin = require('html-webpack-plugin');
    var path = require('path');
    module.exports = {
        entry: './src/app.js',
        output: {
            path: path.resolve(__dirname, './dist/js'),
            filename: 'js/[name].bundle.js'
        },
        module: {
            loaders: [
                {
                    test: /.less$/,     //如果使用sass的话就把less换成sass即可,但记得安装sass-loader
                    use: [
                        'style-loader',
                        {
                            loader: 'css-loader',
                            options: {
                                importLoaders: 1
                            }
                        },
                        {
                            loader: 'postcss-loader',
                            options: {
                                plugins: (loader) => [
                                    require('postcss-import')({root: loader.resourcePath}),
                                    require('autoprefixer')(), //CSS浏览器兼容
                                    require('cssnano')()  //压缩css
                                ]
                            }
                        },
                        {
                            loader: 'less-loader'    //如果使用sass的话就把less换成sass即可,但记得安装sass-loader
                        }
                    ]
                },
            ]
        },
        plugins: [
            new htmlWebpackPlugin({   //配置html打包参数
                filename: 'index.html', //打包后的名字
                template: 'index.html',// 打包所使用的模板,理解为使用的html。
                inject: 'body'     //将js文件插入body文件内
            }),
        ]
    };

    入口文件app.js代码

    import  './conponents/layer/layer.less'

     使用html-loader、实现对html引用的打包。

     安装

    npm install html-loader --save-dev

    由于此案例稍有些繁琐 我将源码发送给大家。  http://pan.baidu.com/s/1nv4Zf7r

    webpack.config.js

    var htmlWebpackPlugin = require('html-webpack-plugin');
    var path = require('path');
    module.exports = {
        entry: './src/app.js',
        output: {
            path: path.resolve(__dirname, './dist/js'),
            filename: 'js/[name].bundle.js'
        },
        module: {
            loaders: [
                {
                    test: /.html/,
                    loader: 'html-loader'
    
                },
            ]
        },
        plugins: [
            new htmlWebpackPlugin({
                filename: 'index.html',
                template: 'index.html',
                inject: 'body'     //将js文件插入body文件内
            }),
        ]
    };

    入口文件app.js代码

    import layer from './conponents/layer/layer.js'
    const App = function () {
        var dom = document.getElementById('app');
        var lay = new layer();
        dom.innerHTML = lay.tpl;
    
    };
    new App();

    被引入文件layer代码

    import tpl from './layer.html';
    import  './layer.less'
    function layer() {
        return {
            name: 'layer',
            tpl: tpl
        }
    }
    
    export  default layer;

     主文件index.html代码

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
    </head>
    <body>
    <div id="app"></div>
    </body>
    </html>

     怎么对html模板进行传参—ejs-loader

     安装:cnpm install ejs-loader --save-dev

    webpack.config.js

    var htmlWebpackPlugin = require('html-webpack-plugin');
    var path = require('path');
    module.exports = {
        entry: './src/app.js',
        output: {
            path: path.resolve(__dirname, './dist'),
            filename: 'js/[name].bundle.js'
        },
        module: {
            loaders: [
    
                {
                    test: /.tpl$/,
                    loader: 'ejs-loader'
                },
                {
                    test: /.html/,
                    loader: 'html-loader'
    
                },
                {
                    test: /.less$/,
                    use: [
                        'style-loader',
                        {
                            loader: 'css-loader',
                            options: {
                                importLoaders: 1
                            }
                        },
                        {
                            loader: 'postcss-loader',
                            options: {
                                plugins: (loader) => [
                                    require('postcss-import')({root: loader.resourcePath}),
                                    require('autoprefixer')(), //CSS浏览器兼容
                                    require('cssnano')()  //压缩css
                                ]
                            }
                        },
                        {
                            loader: 'less-loader'
                        }
                    ]
                },
                {
                    test: '/.js$',
                    loader: 'babel-loader',
                    exclude: path.resolve(__dirname, './node_modules'), //排除那些文件不打包 include 制定打包那些
                    query: {
                        presets: ['latest']
                    }
                },
                {
                    test: /.css$/,
                    use: [
                        'style-loader',
                        {
                            loader: 'css-loader',
                            options: {importLoaders: 1} //这里可以简单理解为,如果css文件中有import 进来的文件也进行处理
                        },
                        {
                            loader: 'postcss-loader',
                            options: {           // 如果没有options这个选项将会报错 No PostCSS Config found
                                plugins: (loader) => [
                                    require('postcss-import')({root: loader.resourcePath}),
                                    require('autoprefixer')(), //CSS浏览器兼容
                                    require('cssnano')()  //压缩css
                                ]
                            }
                        }
                    ]
                },
                {
                    test: /.(png|jpg|gif|svg)$/i,
                    loaders: [
                        'url-loader?limit=20&name=assets/[name]-[hash:5].[ext]',
                        'image-webpack-loader'
                    ]
                    // loader: 'url-loader', //file-loader
                    // query: {
                    //     limit: 20000,
                    //     name: 'assets/[name]-[hash:5].[ext]'
                    // }
                }
            ]
        },
    
        plugins: [
            new htmlWebpackPlugin({
                filename: 'index.html',
                template: 'index.html',
                inject: 'body'     //将js文件插入body文件内
            }),
        ]
    };

    layer.tpl 源码

        <div class="layer">
            <img src="${require('../../essets/bg.jpg')}" alt="">
            <div>this is<%= name %></div>
                <% for (var i = 0; i < arr.length; i++){ %>
                <%= arr[i] %>
                <% } %>
        </div>

    layer.js 源码

    import tpl from './layer.tpl';
    import  './layer.less'
    function layer() {
        return {
            name: 'layer',
            tpl: tpl
        }
    }
    export  default layer;

    入口文件 app.js源码

    import layer from './conponents/layer/layer.js'
    const App = function () {
        var dom = document.getElementById('app');
        var lay = new layer();
        dom.innerHTML = lay.tpl({
            name: 'john',
            arr: ['a', 'b', 'c']
        });
    };
    new App();

    如果对图片进行压缩或者转换为bese64

    安装 npm install image-webpack-loader url-loader--save-dev

    当然也可以容file-loader 代替 url-loader

    limit=20000的意思是当图片小于20000k的时候压缩为bese64 编码 name=img/[name] 就是讲图片存储到什么位置,{name}是个占位符,代表的事图片原来的名字,[ext]是文件原本的后缀名。
                {
                    test: /.(png|jpg|gif|svg)$/i,
                    loaders: [
                        'url-loader?limit=20000&name=img/[name].[ext]',
                        'image-webpack-loader'
                    ]
                }
  • 相关阅读:
    Android OpenGL ES和OpenGL一起学(二)------理解Viewport(视口)和坐标系Android OpenGL ES篇(转帖)
    CSOM中如何取到managed metadata类型字段的类型信息
    "Value does not fall within the expected range" with managed metadata fields
    GLFW_KEY_KP_ADD和GLFW_KEY_KP_SUBTRACT
    OPENGL: WHY IS YOUR CODE PRODUCING A BLACK WINDOW?
    (转)真正的中国天气api接口xml,json(求加精) ...
    Mongo如何在多个字段中查询某个关键字?
    VS2010整合NUnit进行单元测试
    ASP.NET MVC3 学习心得------路由机制
    MVC3中 ViewBag、ViewData和TempData的使用和区别
  • 原文地址:https://www.cnblogs.com/waitforyou/p/6842623.html
Copyright © 2011-2022 走看看