直接使用script管理插件存在以下问题
- 污染全局变量
- 缺少依赖关系,如果依赖不存在,或者引入顺序错误,应用程序将无法正常运行。 如果依赖被引入但是并没有使用,浏览器将被迫下载无用代码。
当前几种常见的模块化规范
CommonJS
CommonJS是适用于Node服务器端的语法规范(node自带)。
加载模块使用require方法,该方法同步读取一个文件并执行(会阻塞后续代码),最后返回文件内部的exports对象。
var math = require('math');
math.add(2, 3);
AMD
Asynchronous Module Definition(异步模块定义)是 RequireJS 在推广过程中对模块定义的规范化产出,通过define定义模块的同时需要指定待引入的其他模块,无法按需加载模块。
//通过数组引入依赖 ,回调函数通过形参传入依赖
define(['Module1', ‘Module2’], function (Module1, Module2) {
function foo () {
/// someing
Module1.test();
}
return {foo: foo}
});
CMD
Common Module Definition是SeaJS 在推广过程中对模块定义的规范化产出,异步加载且按需加载
define(function(require, exports, module) {
var clock = require('clock');
clock.start();
});
import/export
ES6标准发布后,module成为标准,标准使用是以export指令导出接口,以import引入模块,且通过webpack可以转译为兼容于较低版本浏览器的语法。
但是在node模块中,我们依然采用的是CommonJS规范,使用require引入模块,使用module.exports导出接口。
webpack
webpack 是一个现代 JavaScript 应用程序的静态模块打包工具。
安装webpack
mkdir webpack-demo && cd webpack-demo
npm init -y
npm install --save-dev webpack webpack-cli
hello world
执行npx webpack
会默认将src/index.js
作为入口文件,打包到dist/main.js
对于src/index.js
中涉及文件的 import/export 已通过webpack自带的兼容转译进行打包,但其他代码如未使用Babel等转译工具则只会压缩混淆而不会转译。
webpack-demo
|- package.json
|- /dist
|- index.html
+|- main.js
|- /src
|- index.js
使用配置文件
- package.json
{
"name": "webpack",
"scripts": {
"build": "webpack --config webpack.config.js",
"start": "webpack-dev-server --open"
},
"devDependencies": {
"clean-webpack-plugin": "^3.0.0",
"css-loader": "^3.5.3",
"file-loader": "^6.0.0",
"html-loader": "^1.1.0",
"html-webpack-plugin": "^4.3.0",
"resolve-cwd": "^3.0.0",
"style-loader": "^1.2.1",
"uglifyjs-webpack-plugin": "^2.2.0",
"webpack": "^4.43.0",
"webpack-cli": "^3.3.11",
"webpack-dev-server": "^3.11.0"
}
}
- webpack.config.js
const path = require("path");
const uglify = require("uglifyjs-webpack-plugin");
const HtmlWebpackPlugin = require("html-webpack-plugin");
const { CleanWebpackPlugin } = require("clean-webpack-plugin");
module.exports = {
//监听入口文件变化后自动打包
// watch: true,
entry: {
index: "./src/index.js",
},
output: {
filename: "[name].min.js",
path: path.resolve(__dirname, "dist"),
},
module: {
rules: [
//允许在js中impot导入CSS,并直接作用在页面上
//配合file-loader让css中背景图指向的图片自动打包并改变对应指向
{
test: /\.css$/,
use: ["style-loader", "css-loader"],
},
//允许在js中import引入图片,并在js中将其赋值给img的src
{
test: /\.(png|svg|jpg|gif)$/,
use: ["file-loader"],
},
//配合file-loader让html中img.src指向的图片自动打包并改变对应指向
{
test: /\.html$/,
use: ["html-loader"],
},
// {
// test: /\.(woff|woff2|eot|ttf|otf)$/,
// use: ["file-loader"],
// },
],
},
plugins: [
//每次打包前清除dist原本内容
new CleanWebpackPlugin(),
//使用该插件才会将html页面也输出到dist,并自动在页面中插入entry中的js
new HtmlWebpackPlugin({ title: "titleee", template: "./src/index.html" }),
//js压缩
new uglify(),
],
//配合package.json中"start": "webpack-dev-server --open",
//可替代watch并启动一个具有 live reloading(实时重新加载)的web server
devServer: {
contentBase: "./dist",
},
mode: "development",
devtool: "inline-source-map", //可以找到报错的原本文件位置
};
- entry 指定入口起点
当仅有一个入口时也可以简写为entry:"XXX"
- output 输出文件的位置和名称
[name]
即为此处entry的key,简写时为main
- module.rules
webpack 只能理解 JavaScript 和 JSON 文件。loader 让 webpack 能够去处理其他类型的文件
rules数组中的loader会从后往前依次执行。 - plugins 插件
想要使用一个插件,你只需要 require() 它,然后把它添加到 plugins 数组中。多数插件可以通过选项(option)自定义。你也可以在一个配置文件中因为不同目的而多次使用同一个插件,这时需要通过使用 new 操作符来创建它的一个实例。 - mode 模式
通过选择 development, production(默认) 或 none 之中的一个,来设置 mode 参数,会影响一些webpack的默认行为。也可以在cmd中输入webpack --mode=production
。
网友评论