webpack学习笔记

webpack是什么?

webpack简单来说是一个模块打包机:分析你的项目结构,找到JavaScript模块、图片以及其它的一些浏览器不能直接运行的拓展语(Scss,TypeScript等,并将其打包为合适的格式以供浏览器使用。

webpack学习笔记_第1张图片
webpack打包.png

为什么我们要使用webpack?

随着前端开发项目功能越来越丰富的需求,前端所写的JavaScript也越来越复杂还有得安装一大堆依赖,给我们前端开发带来越来越多的复杂度,所以在这个时候webpack就可以帮助我们将开发复杂度化简提高开发效率,同时他还具备以下优点
① 模块化开发(import,require),让我们可以把复杂的程序细化为小的文件;
② 预处理(Less,Sass,ES6,TypeScript……)
③ 主流框架脚手架支持(Vue,React,Angular)

安装webpack

安装webpack之前我们得先提前安装好node.js,因为我们得需要通过使用npm安装webpack

npm install webpack -g   (这是全局安装)
npm install webpack --save-dev  (这是安装到自己本地的项目)
或者下面这种带有版本号的安装
npm install --save-dev webpack@

(这里提示最好是安装到本地项目里面,因为当你同时开着多个项目的时候可能会出现不同项目需要不同版本的webpack)

-如果你使用 webpack 4+ 版本,你还需要安装 CLI

npm install --save-dev webpack-cli

设置webpack-dev-server

在开发时,每次更改文件后要运行npm run build 来重新编译、打包文件,无聊又麻烦。我们可以设置 webpack-dev-server来让他自动运行。webpack-dev-server 主要是启动了一个使用 express 的 Http服务器 ,它的作用主要是用来伺服资源文件 。此外这个 Http服务器 和 client 使用了 websocket 通讯协议,原始文件作出改动后, webpack-dev-server 会实时的编译,但是最后的编译的文件并没有输出到目标文件夹。在webpack.config.js配置文件中增加入口命令可以使文件变化时浏览器自动刷新。
首先要安装它 npm install webpack-dev-server --save-dev。然后在package.json文件的scripts部分增加快捷指令:

"scripts": {
    "dev": "webpack-dev-server --open --history-api-fallback",
    "build": "webpack"
  },

webpack的使用

entry与output

//基本结构
module.exports = {
var path = require('path');
  context: path.join(__dirname),  //这是entry配置项的根目录(绝对路径)
    entry: "./src/root.js",//打包入口文件,就是打包谁
    output: {
        path: __dirname + "/dist/",//打包后文件放置的目录路径
        // publicPath: "发布项目时在相对路径前面添加的绝对路径"
        filename: "bundle.js"//打包后文件的名字
    }
}

entry:

写法一:字符串 ----------打包一个入口文件,如上

写法二: 数组 ------------['./a.js', './b.js'] 打包两个不相依赖的文件,打包在一起

写法三:对象----------在多页面应用中,针对不同的页面填写不同的入口文件

entry: {
    page1:  './a.js',-----可以是一个
    page2: ['./as.js', './b.js']-------可以是多个
}

此时如果还像上面那样子写output则只会生成一个输出文件,且后面的打包文件会把前面输出文件覆盖,解决方法是在filename中添加一个占位符,区分不同输出文件,方法有三种:
1 [name] 就是entry对象的key值,page1, page2
output: {
filename: '[name]'.js,
path: __dirname + 'src'
}
2 [hash] 每次打包生成的一个hash值,假设为“123asd”,可以和[name]一起使用
output: {
filename: '[name]-[hash]'.js,
path: __dirname + 'src'
}
多个打包生成文件hash相同,都是“123asd”

loader

module.exports = {

    module: {
        rules: [
            {//js、jsx
19                 test: /\.jsx?$/,
20                 exclude:/node_modules/,//排除node_modules中的库文件,加快编译速度
21                 loader: 'babel',
22                 query:{
23                     presets:['es2015', 'react']
24                 }
25             },            
26             {//css
27                 test: /\.css$/,
28                 loader: ExtractTextPlugin.extract("style", "css")//多个加载器通过!链接,可忽略加载器后缀“-loader”
29             },            
30             {//sass,还需要安装node-sass
31                 test: /\.scss$/,
32                 loader: 'style!css!sass'
33             },
34             
35             {//less,还需要安装less
36                 test: /\.less$/,
37                 loader: 'style!css!less'
38             },
39             {//url-loader:图片、字体图标加载器,是对file-loader的上层封装,支持base64编码。传入的size(也有的写limit) 参数是告诉它图片如果不大于 25KB 的话要自动在它从属的 css 文件中转成 BASE64 字符串.
40                 test: /\.(png|jpg|jpeg|gif|svg|woff|woff2|ttf|eot)$/,
41                 loader: 'url?limit=25000&name=[name].[ext]'
42             }
        ]
    },
}

webpack 本身只能处理 JavaScript 模块,如果要处理其他类型的文件,就需要使用 loader 进行转换。Loader 可以理解为模块和资源的转换器,它本身是一个函数,接受源文件作为参数,返回转换的结果。这样,我们就可以通过 require 来加载任何类型的模块或文件,比如 CoffeeScript、 JSX、 LESS 或图片。Loader 本身也是运行在 node.js 环境中的 JavaScript 模块,它通常会返回一个函数。大多数情况下,我们通过 npm 来管理 loader,但是你也可以在项目中自己写 loader 模块。

一般loader 一般以xxx-loader的方式命名,xxx代表了这个 loader 要做的转换功能,比如css-loader。Loader 可以在require()引用模块的时候添加,也可以在 webpack 全局配置中进行绑定,还可以通过命令行的方式使用。例如页面中要引入样式文件main.css,我们可以将main.css看成一个模块,然后css-loader会遍历 CSS 文件,然后找到 url() 处理他们,style-loader 会把原来的 CSS 代码插入页面中的一个 style 标签中。

插件plugins

插件可以完成更多loader不能完成的任务。在webpack.config.js中增加config.plugins:
列如webpack插件 html-webpack-plugin,就是可以帮你在打包的时候自动给你生成index.html并且帮你往里面引入你的js文件,你就省的自己去手动引入创建了

 1 var webpack = require("webpack");
 2 var path = require('path');
 3 var ExtractTextPlugin = require('extract-text-webpack-plugin');
 4 var HtmlWebpackPlugin = require('html-webpack-plugin');
 5 
 6 var config = {
 7         //省略entry、output等
 8      plugins:[//给打包输出的文件加banner
 9         new webpack.BannerPlugin("The file is creted by yangmin.--" + new Date()),
10         new webpack.ProvidePlugin({
11           $: "webpack-zepto",             
12       }),
13       /*插件:单独使用style标签加载css文件*/
14       new ExtractTextPlugin("css/[name].css"),//设置其路径(路径相对于path)
15       /*插件:动态生成html,在webpack完成前端资源打包以后,自动将打包后的资源路径和版本号写入HTML中,达到自动化的效果。*/
16       new HtmlWebpackPlugin({
17           filename:'view/index-build.html',    //生成的html存放路径,相对于 path
18             template:'src/view/index.html',    //html模板路径
19             inject:true,    //允许插件修改哪些内容,包括head与body
20             hash:false,    //为静态资源生成hash值
21             minify:{    //压缩HTML文件
22                 removeComments:false,    //移除HTML中的注释
23                 collapseWhitespace:false    //删除空白符与换行符
24            }
25        })
26     ]
27 };
28    module.export = config;   

babel的实现

安装 npm i -D @babel-preset-env @babel-core babel-loader

@babel-preset-env:可以让我们灵活设置代码目标执行环境
@babel-core: babel核心库
babel-loader: webpack的babel插件,让我们可以在webpack中运行babel

配置.babelrc

{
    "presets": ['@babel/preset-env']
}

配置webpack.config.js

module.exports = {
    entry: './src/index.js',
    output: {
        path: path.resolve(__dirname, 'dist'),
        filename: 'bundle.js'
    },
    module: {
        rules: [{
            test: /\.js$/,
            exclude: /node_modules/,
            use: {loader: 'babel-loader'}
        }]
    }
}

在webpack中如何做到长缓存优化?

webpack中可以在output中指定chunkhash,并且分离经常更新的代码和框架代码。通过NameModulesPlugin或HashedModuleIdsPlugin使再次打包文件名不变。

你可能感兴趣的:(webpack学习笔记)