模块化开发
模块化概述
项目越来越复杂,需要大量的时间维护,模块化是通过把复杂代码,按照功能的不同,划分为不同的模块,单独维护的一种方式,去提高我们的开发效率,降低维护成本。
【模块化】只是思想,并不包含具体的实现
模块化演变过程
- 文件划分方式:文件即模块,会污染全局作用域,完全依靠约定
- 命名空间方式
- IIFE:立即执行函数,实现了私有成员
模块化规范的出现
commonJS规范:以同步方式加载模块
- 一个文件就是一个模板
- 每个模板都有单独的作用域
- 通过module.exports导出成员
- 通过require函数载入模块
AMD:异步
ES Modules 特性
- 自动采用严格模式,忽略
use strict - 每个ES Modules都是运行在单独的私有作用域中
- 在ES Modules当中,外部JS文件是通过CORS的方式去请求的
- 在ES Modules的script标签会延迟执行脚本
ES Module 导入导出的注意事项
- 导出成员并不是一个自变量对象,导出的对象并不是成员里的值,导出的是地址存储的值
- 导入并非解构,导入成员是只读的
- 导入导出有固定的语法
ES Module 导入用法
导入时不能是扩展名,可以是相对路径的点斜线文件,或者是绝对路径,再或者是完整的URL
ES Module 导出导入成员
导入的结果直接作为当前文件的导出成员
ES Modules in Node.js - 与 CommonJS
- ES Modules中可以导入CommonJS模块
- CommonJS中不能导入ES Modules模块
- CommonJS始终只会导出一个默认成员
- 注意import不是解构导出对象
ES Modules in Node.js - 新版本进一步支持
// package.json{"type": "module"}
ES Modules in Node.js - Babel 兼容方案

{// "presets": [ "@babel/preset-env" ],"plugins": ["@babel/plugin-transform-modules-commonjs"]}
Webpack 打包
模块化打包工具的由来
模块化存在的问题:
- ES Modules 存在环境兼容问题
- 模块文件过多,网络请求频繁
- 所有的前端资源都需要模块化
- 毋庸置疑,所有文件都需要模块化
需要:
- 新特性代码编译
- 模块化JavaScript打包
- 支持不同类型的资源模块
模块打包工具概要
webpack
- 模块打包器(Module Builder)
- 代码拆分(Code Splitting)
- 资源模块(Asset Module)
模块化工具的作用:打包工具解决的是前端整体的模块化,并不单指JavaScript模块化
Webpack:大而全,适合开发应用程序
概念:
本质上,webpack 是一个现代 JavaScript 应用程序的静态模块打包器(module bundler)。当 webpack 处理应用程序时,它会递归地构建一个依赖关系图(dependency graph),其中包含应用程序需要的每个模块,然后将所有这些模块打包成一个或多个 bundle,
配置文件的核心概念:
- 入口(entry):告诉webpack 应该使用哪个模块,来作为构建其内部依赖图的开始。
- 输出(output):告诉 webpack 在哪里输出它所创建的 bundles,以及如何命名这些文件。
- filename:设置输出文件的文件名
- path: 指定filename所在的目录
- loader:让 webpack 能够去处理其他类型的文件,并将它们转换为有效模块,以供应用程序使用,以及被添加到依赖图中。
- test 属性,识别出哪些文件会被转换。
- use 属性,定义出在进行转换时,应该使用哪个 loader。
- 插件(plugins):打包优化,资源管理,注入环境变量。
- 模式(mode):通过选择 development, production 或 none 之中的一个,来设置 mode 参数,你可以启用 webpack 内置在相应环境下的优化。其默认值为 production。
- 浏览器兼容性(browser compatibility):webpack 支持所有符合 ES5 标准 的浏览器(不支持 IE8 及以下版本)。webpack 的 import() 和 require.ensure() 需要 Promise。不支持旧版本浏览器
JavaScript驱动了整个前端应用
- 逻辑合理,JS确实需要这些资源文件
- 确保上线资源不缺失,都是必要的
webpack模块加载方式
- 遵循ES Modules标准的import声明
- 遵循CommonJS标准的require函数
- 遵循AMD标准的define函数和require函数
其他文件触发加载**
- 样式代码中的@import指令和url函数
- HTML代码中图片标签的src属性
其他打包工具
Rollup:小而美,适合开发库/框架
更为小巧,仅仅是一款ES Module打包器,充分利用ESM各项特性的高效打包器,插件是rollup唯一的扩展途径
优点:
- 输出结果更加扁平,执行效率更高
- 自动移除未引用代码
- 打包结果依然完全可读
缺点:
- 加载费ESM的第三方模块比较复杂
- 模块最终都被打包倒一个函数中,无法实现HMR
- 浏览器环境中,代码拆分功能依赖AMD库
// rollup.config.jsimport json from 'rollup-plugin-json'import resolve from 'rollup-plugin-node-resolve'import commonjs from 'rollup-plugin-commonjs'export default {input: {index: 'src/index.js'},// output: {// file: 'dist/bundle.js',// format: 'iife'// },output: {dir: 'dist',format: 'amd'},plugins: [ json(), resolve(), commonjs() ]}
规范化标准
规范化介绍
规范化介绍
- 为什么要有规范标准
- 哪里需要规范化标准
- 实施规范化的方法
为什么要有规范化标准
- 软件开发需要多人协同
- 不同开发者具有不同的编码习惯和喜好
- 不同的喜好增加项目维护成本
- 每个项目或者团队需要明确统一的标准
哪里需要规范化标准
- 代码、文档、甚至是提交日志
- 开发过程中人为编写的成果物
- 代码标准化规范最为重要
实施规范化的方法
- 编码前人为的标准约定
- 通过工具实现Lint
常见的规范化实现方式
- ESLint工具使用
- 定制ESLint校验规则
- ESLint对TypeScript的支持
- ESLint结合自动化工具或者Webpack
- 基于ESLint的衍生工具
- Stylelint工具的使用
Eslint介绍
- 最为主流的JavaScript Lint工具监测JS代码质量
- ESLint很容易统一开发者的编码风格
- ESLint可以帮助开发者提升编码能力
ESLint 快速上手
ESLint检查步骤
- 编写“问题”代码
- 使用eslint执行检测
- 完成eslint使用配置
eslint --init
.eslintrc.js 中 env 运行环境:环境不互斥
- browser - 浏览器环境中的全局变量。
- node - Node.js全局变量和Node . js作用域。
- commonjs - CommonJS全局变量和CommonJS 作用域(用于Browserify/WebPack 打包的只在浏览器中运行的代码)。
- shared-node browser - Node. js和Browser 通用全局变量。
- es6 - 启用除了modules 以外的所有ECMAScript 6特性(该选项会自动设置ecmaVersion 解析器选项为6) 。
- worker - Web Workers全局变量。
- amd -将require() 和define() 定义为像amd -样的全局变量。
- mocha -添加所有的Mocha 测试全局变量。
- jasmine -添加所有的Jasmine 版本1.3和2.0的测试全局变量。
- jest -Jest全局变量。
- phantomjs - PhantomJS 全局变量。
- protractor - Protractor 全局变量。
- qunit - QUnit全局变量。
- jquery - jQuery 全局变量。
- prototypejs - Prototype.js 全局变量。
- shelljs - ShelLJS全局变量。
- meteor - Meteor全局变量。
- mongo - MongoDB 全局变量。
- applescript - AppLeScript 全局变量。
- nashorn - Java 8 Nashorn 全局变量。
- servic eworker
- Service Worker 全局变量。
- atomtest - Atom测试全局变量。
- embertest - Ember 测试全局变量。
- webextensions - WebExtensions 全局变量。
- greasemonkey - GreaseMonkey 全局变量
eslint结合自动化工具的好处:
- 集成之后,ESLint-定会工作
- 与项目统一 ,管理更加方便
使用eslint-loader:在babel-loader 之前使用,需要在设置内添加
enforce:'pre'
Git Hooks介绍
- Git Hook也称之为git钩子,每个钩子都对应一个任务
- 通过shell脚本可以编写钩子任务触发时要具体执行的操作
作业
一、简答题
1、Webpack 的构建流程主要有哪些环境?如果可以请尽可能详尽的描述 Webpack 打包的整个过程。
mode:
- development:默认值,启用 NamedChunksPlugin 和 NamedModulesPlugin
- production:启用 FlagDependencyUsagePlugin , FlagIncludedChunksPlugin , ModuleConcatenationPlugin , NoEmitOnErrorsPlugin , OccurrenceOrderPlugin , SideEffectsFlagPlugin 和 TerserPlugin
- none:不做任何优化
以下来自Webpak官网:
概念:
本质上,webpack 是一个现代 JavaScript 应用程序的静态模块打包器(module bundler)。当 webpack 处理应用程序时,它会递归地构建一个依赖关系图(dependency graph),其中包含应用程序需要的每个模块,然后将所有这些模块打包成一个或多个 bundle,
配置文件的核心概念:
- 入口(entry):告诉webpack 应该使用哪个模块,来作为构建其内部依赖图的开始。
- 输出(output):告诉 webpack 在哪里输出它所创建的 bundles,以及如何命名这些文件。
- filename:设置输出文件的文件名
- path: 指定filename所在的目录
- loader:让 webpack 能够去处理其他类型的文件,并将它们转换为有效模块,以供应用程序使用,以及被添加到依赖图中。
- test 属性,识别出哪些文件会被转换。
- use 属性,定义出在进行转换时,应该使用哪个 loader。
- 插件(plugins):打包优化,资源管理,注入环境变量。
- 模式(mode):通过选择 development, production 或 none 之中的一个,来设置 mode 参数,你可以启用 webpack 内置在相应环境下的优化。其默认值为 production。
- 浏览器兼容性(browser compatibility):webpack 支持所有符合 ES5 标准 的浏览器(不支持 IE8 及以下版本)。webpack 的 import() 和 require.ensure() 需要 Promise。不支持旧版本浏览器。
2、Loader 和 Plugin 有哪些不同?请描述一下开发 Loader 和 Plugin 的思路。
答:loader负责资源文件从输入到输出的转换,并且对于同一个资源可以一次进行使用多个loader,plugin目的在于解决 loader无法实现的其他事,如:打包优化,资源管理,注入环境变量等。
开发思路:**
- loader:根据需求对source进行转换,并返回相应的JavaScript代码
- plugin:通过钩子机制实现,类似于事件,根据所需要实现的功能使用生命周期中的钩子,挂载函数实现扩展。
二、编程题
1、使用 Webpack 实现 Vue 项目打包任务
具体任务及说明:
先下载任务的基础代码:https://github.com/lagoufed/fed-e-001/raw/master/tasks/02-02-base-code.zip
这是一个使用 Vue CLI 创建出来的 Vue 项目基础结构
有所不同的是这里我移除掉了 vue-cli-service(包含 webpack 等工具的黑盒工具)
这里的要求就是直接使用 webpack 以及你所了解的周边工具、Loader、Plugin 还原这个项目的打包任务
尽可能的使用上所有你了解到的功能和特性
作业要求
本次作业的中的编程题要求大家完成相应代码过后,录制一个小视频简单介绍一下实现思路,演示一下相应功能。最终将录制的视频和代码统一提交至作业仓库。
