前端必学的技术,实践教你从零构建前端
前端必学的技术,实践教你从零构建前端npm install --save-dev @typescript-eslint/eslint-plugin3、修改配置文件npm install --save-dev typescript @typescript-eslint/parser2、接下来需要安装对应的插件 @typescript-eslint/eslint-plugin 它作为 eslint 默认规则的补充,提供了一些额外的适用于 ts 语法的规则。var myName = 'Tom'; console.log(`My name is ${myNane}`);5、在命令行输入npx eslint index.js// eslint 报错信息: ✖ 2 problems (2 errors 0 warnings) error Unexpected var use let or const instead
作者:周振超
转发链接:https://segmentfault.com/a/1190000022881634
前言- 新手建议从头开始,都是手把手,按步骤配置一遍
- 有 ESLint 使用经验的,直接上 AlloyTeam 配置
- 让 ESLint 检查 TypeScript
- VSCode 集成 ESLint 检查 => 自动提示/修复错误
- 结合 Prettier => 格式化文件
- 继续集成 Stylelint => 检查样式
- 本地 Lint 已构建,缺少 Git 提交代码预检
- 代码检查主要是用来发现代码错误、统一代码风格。
- 在 JavaScript 项目中,我们一般使用 ESLint 来进行代码检查,它通过插件化的特性极大的丰富了适用范围,搭配 typescript-eslint 之后,甚至可以用来检查 TypeScript 代码。
1、新建一个文件夹,打开命令行,npm init -y创建package.json2、安装依赖npm install --save-dev eslint babel-eslint eslint-config-alloy3、在项目根目录下创建一个.eslintrc.js 或 .eslintrc.json的配置文件:
// .eslintrc.js
module.exports = {
extends: [
'alloy'
]
};
4、在项目根目录下创建一个index.js,复制下面内容:
var myName = 'Tom';
console.log(`My name is ${myNane}`);
5、在命令行输入npx eslint index.js
// eslint 报错信息:
✖ 2 problems (2 errors 0 warnings)
error Unexpected var use let or const instead no-var
error 'myNane' is not defined no-undef
6、使用npx eslint index.js --fix自动修复某些规则
// 这时 var 变成了 let
// 还剩下一个无法自动修复的错误
✖ 1 problem (1 error 0 warnings)
error 'myNane' is not defined no-undef
配合 TypeScript
1、由于 ESLint 默认使用 Espree 进行语法解析,无法识别 TypeScript 的一些语法,故我们需要安装 @typescript-eslint/parser,替代掉默认的解析器,别忘了同时安装 typescript:
npm install --save-dev typescript @typescript-eslint/parser
2、接下来需要安装对应的插件 @typescript-eslint/eslint-plugin 它作为 eslint 默认规则的补充,提供了一些额外的适用于 ts 语法的规则。
npm install --save-dev @typescript-eslint/eslint-plugin
3、修改配置文件
module.exports = {
extends: [
'alloy'
]
parser: '@typescript-eslint/parser'
plugins: ['@typescript-eslint']
rules: {
// 禁止使用 var
'no-var': "error"
// 优先使用 interface 而不是 type
'@typescript-eslint/consistent-type-definitions': [
"error"
"interface"
]
}
}
- 以上配置中,我们自定义了两个规则,其中 no-var是 ESLint 原生的规则(我们刚刚已经用到了这个规则,它被包含在alloy中,此处会覆盖),@typescript-eslint/consistent-type-definitions 是 @typescript-eslint/eslint-plugin 新增的规则
- 规则的取值一般是一个数组(上例中的 @typescript-eslint/consistent-type-definitions),其中第一项是 off、warn 或 error 中的一个,表示关闭、警告和报错。后面的项都是该规则的其他配置。
- 如果没有其他配置的话,则可以将规则的取值简写为数组中的第一项(上例中的 no-var)。
关闭、警告和报错的含义如下:
- 关闭:禁用此规则
- 警告:代码检查时输出错误信息,但是不会影响到 exit code
- 报错:发现错误时,不仅会输出错误信息,而且 exit code 将被设为 1(一般 exit code 不为 0 则表示执行出现错误)
4、新建index.ts文件:
var myName = 'Tom';
console.log(`My name is ${myNane}`);
console.log(`My name is ${myName.toStrng()}`);
type Foo = {};
5、在命令行输入npx eslint index.ts,如下可以看到报错信息以及可修复项
1:1 error Unexpected var use let or const instead no-var
2:27 error 'myNane' is not defined no-undef
4:6 error Use an `interface` instead of a `type` @typescript-eslint/consistent-type-definitions
✖ 3 problems (3 errors 0 warnings)
2 errors and 0 warnings potentially fixable with the `--fix` option.
脚本命令检查整个项目
1、根目录新建一个src文件夹,将我们的index.js和index.ts放进去2、在package.json中的scripts新增:
{
"scripts": {
// 因为eslint不是全局安装的,所以要使用npx
"lint": "npx eslint src --ext .js .ts tsx"
// eslint 默认不会检查 .ts 后缀的文件,所以需要加上参数 --ext .ts
}
}
3、然后npm run lint就可以看到src下所有指定后缀文件的报错信息
推荐使用 AlloyTeam 的配置- 上面手把手完成了ESLint的配置过程
- 有一定经验的推荐直接使用AlloyTeam实现可自定义拓展的ESLint规则
- AlloyTeam/eslint-config-alloy已经帮我们集成了各种技术栈
1、安装技术栈相关依赖
// Eslint
npm install --save-dev eslint babel-eslint eslint-config-alloy
// React
npm install --save-dev eslint babel-eslint eslint-plugin-react eslint-config-alloy
// Vue
npm install --save-dev eslint babel-eslint vue-eslint-parser eslint-plugin-vue eslint-config-alloy
// TypeScript
npm install --save-dev eslint typescript @typescript-eslint/parser @typescript-eslint/eslint-plugin eslint-config-alloy
// TypeScript React
npm install --save-dev eslint typescript @typescript-eslint/parser @typescript-eslint/eslint-plugin eslint-plugin-react eslint-config-alloy
2、配置.eslintrc.js文件
/* .eslintrc.js */
module.exports = {
extends: [
'alloy' // 都需要
'alloy/vue' //vue项目需要
'alloy/react' //react项目需要
'alloy/typescript' //ts项目需要
]
env: {
// 你的环境变量(包含多个预定义的全局变量)
//
// browser: true
// node: true
// mocha: true
// jest: true
// Jquery: true
}
globals: {
// 你的全局变量(设置为 false 表示它不允许被重新赋值)
//
// myGlobal: false
}
rules: {
// 自定义你的规则
}
};
3、接下来就可以直接用eslint命令检查文件了4、这样就引入了alloy团队的lint规则了,然后可以用rules覆盖你不爽的规则,直接采用开源规则是为了避免重复造轮子,你也可以选择别的团队,或者自己定义一套
VSCode 集成 ESLint 检查在编辑器中集成 ESLint 检查,可以在开发过程中就发现错误,甚至可以在保存时自动修复错误,极大的增加了开发效率
1、先安装 ESLint 插件,打开 VSCode 点击「扩展」按钮,搜索 ESLint,然后安装即可2、在「文件 => 首选项 => 设置 => 工作区」中(也可以在项目根目录下创建一个配置文件 .vscode/settings.json),添加以下配置:
{
// VSCode 中的 ESLint 插件默认是不会检查 `.vue`、`.ts` 或 `.tsx` 后缀的
"eslint.validate": [
"javascript"
"javascriptreact"
"vue"
"typescript"
"typescriptreact"
]
// 开启保存时自动修复
"editor.codeActionsOnSave": {
"source.fixAll.eslint": true
}
// 指定VSCode用于IntelliSense(智能感知)的ts版本,将内置版本更换为工作区版本
"typescript.tsdk": "node_modules/typescript/lib"
}
结合 Prettier 使用
Prettier 是一个代码格式化工具,相比于 ESLint 中的代码格式规则,它提供了更少的选项,但是却更加专业。
AlloyTeam 推荐用 Prettier 管理格式化相关的规则,用 ESLint 来检查它更擅长的逻辑错误。
1、安装 Prettier
npm install --save-dev prettier
2、配置 .prettierrc.js 仅供参考:
// .prettierrc.js
module.exports = {
// 一行最多 100 字符
printWidth: 100
// 使用 4 个空格缩进
tabWidth: 4
// 不使用缩进符,而使用空格
useTabs: false
// 行尾需要有分号
semi: true
// 使用单引号
singleQuote: true
// 对象的 key 仅在必要时用引号
quoteProps: 'as-needed'
// jsx 不使用单引号,而使用双引号
jsxSingleQuote: false
// 末尾不需要逗号
trailingComma: 'none'
// 大括号内的首尾需要空格
bracketSpacing: true
// jsx 标签的反尖括号需要换行
jsxBracketSameLine: false
// 箭头函数,只有一个参数的时候,也需要括号
arrowParens: 'always'
// 每个文件格式化的范围是文件的全部内容
rangeStart: 0
rangeEnd: Infinity
// 不需要写文件开头的 @prettier
requirePragma: false
// 不需要自动在文件开头插入 @prettier
insertPragma: false
// 使用默认的折行标准
proseWrap: 'preserve'
// 根据显示样式决定 html 要不要折行
htmlWhitespaceSensitivity: 'css'
// 换行符使用 lf
endOfLine: 'lf'
};
VSCode 集成 Prettier
1、在.vscode/settings.json中添加配置:
{
// 保存时自动格式化所有支持文件 javascript/javascriptreact/typescript/typescriptreact/json/graphql
"editor.formatOnSave": true
"editor.defaultFormatter": "esbenp.prettier-vscode"
}
2、这时我们保存文件的时候,已经可以自动格式化了3、也可以指定格式化文件类型:
{
// Set the default
"editor.formatOnSave": false
// Enable per-language
"[javascript]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
"editor.formatOnSave": true
}
}
继续集成 Stylelint
顾名思义,Stylelint帮我们解决类css文件样式问题
Stylelint 规则分为三个类别- Possible errors: 可以使用stylelint-config-recommended启用这些规则
- Stylistic issues: stylelint-config-standard拓展了Possible errors,并启用此类的规则
- Limit language features: 其他规则,如果有需要,可以在rules里面配置
- 详尽的配置规则
1、安装依赖
npm install --save-dev stylelint stylelint-config-standard stylelint-order
2、在项目根目录中创建一个.stylelintrc.js配置文件:
module.exports = {
extends: [
'stylelint-config-standard'
]
plugins: ['stylelint-order']
rules: {
// ...
}
};
- stylelint-config-standard是stylelint的推荐配置
- stylelint-order是 css 属性排序插件
3、npx stylelint "**/*.css" 尝试检查 css 文件
支持 SCSS1、安装依赖
npm install --save-dev stylelint-config-sass-guidelines stylelint-scss
2、调整.stylelintrc.js配置文件:
module.exports = {
extends: [
'stylelint-config-standard'
'stylelint-config-sass-guidelines'
]
plugins: ['stylelint-order' 'stylelint-scss']
rules: {
// ...
}
};
3、更多配置及插件
VSCode 集成 Stylelint1、在.vscode/settings.json中添加配置:
{
"editor.codeActionsOnSave": {
// 开启保存自动修复所有stylelint可修复的选项
"source.fixAll.stylelint": true
}
}
2、这时我们保存文件的时候,Stylelint已经可以自动修复,但是我们上面让Prettier负责了所有文件的格式化,因此可能会导致冲突,倒腾了好久VSCode配置项,效果并不好,比如去除了 css 等文件的格式化,到.vue内联<style>依然有问题:
{
// 去除其他插件
"css.validate": false
"less.validate": false
"scss.validate": false
// 编辑器格式化全部交给 Prettiern 配置
"editor.formatOnSave": true
"editor.defaultFormatter": "esbenp.prettier-vscode"
// 针对某种语言,配置替代编辑器设置,取消自动保存格式化
"[css]": {
"editor.formatOnSave": false
}
"[less]": {
"editor.formatOnSave": false
}
"[scss]": {
"editor.formatOnSave": false
}
}
3、如上还是会有问题,换个思路,让Stylelint禁用所有与Prettiern有关的规则,很符合我们整篇文章「各司其职」的思想4、安装依赖npm install --save-dev stylelint-config-prettier5、调整.stylelintrc.js配置文件:
module.exports = {
extends: [
'stylelint-config-standard'
'stylelint-config-sass-guidelines'
'stylelint-config-prettier'
]
plugins: ['stylelint-order' 'stylelint-scss']
rules: {
// ...
}
};
6、至此,我们让Prettiern负责格式化,让Stylelint检查样式,让ESLint检查语法逻辑,完成了整个前端 Lint 工作流
Git 代码预检- 上面我们配置了ESLint、Prettier、Stylelint集成了VSCode插件,实现了错误提示和保存自动修复
- 然而自动修复的只是小部分,如果团队成员不按规范,依然可以将不规范的代码推送至远程代码库
- 我们通过Git 代码预检,一定程度防止不规范的代码被提交
- 待提交的代码
- git add 添加到暂存区
- 执行 git commit(这时进行代码预检)
- husky注册在git pre-commit的钩子调起 lint-staged
- lint-staged 取得所有被提交的文件依次执行写好的任务
- 如果有错误(没通过ESlint检查)则停止任务,等待下次commit,同时打印错误信息
- 成功提交后,git push推送到远程库
- git hook就是.git文件夹的hooks下的一些钩子函数,特定时机他们将被调用
- 查看所有 git 钩子函数:
cd .git/hooks
ls -l
// 打印如下:
total 96
-rwxr-xr-x 1 zzc staff 478 10 21 2019 applypatch-msg.sample
-rwxr-xr-x 1 zzc staff 896 10 21 2019 commit-msg.sample
-rwxr-xr-x 1 zzc staff 3327 10 21 2019 fsmonitor-watchman.sample
-rwxr-xr-x 1 zzc staff 189 10 21 2019 post-update.sample
-rwxr-xr-x 1 zzc staff 424 10 21 2019 pre-applypatch.sample
-rwxr-xr-x 1 zzc staff 1638 10 21 2019 pre-commit.sample
-rwxr-xr-x 1 zzc staff 1348 10 21 2019 pre-push.sample
-rwxr-xr-x 1 zzc staff 4898 10 21 2019 pre-rebase.sample
-rwxr-xr-x 1 zzc staff 544 10 21 2019 pre-receive.sample
-rwxr-xr-x 1 zzc staff 1492 10 21 2019 prepare-commit-msg.sample
-rwxr-xr-x 1 zzc staff 3610 10 21 2019 update.sample
- .sample为各个钩子的案例脚本,可以把sample去掉,直接编写shell脚本来执行。
- 而前端可以用插件husky与pre-commit,来使钩子生效。
Requires Node >= 10 and Git >= 2.13.0.
- husky新老版本的配置方式和使用变化较大,老版本请自行升级,详见 husky
1、安装 husky
npm install husky --save-dev
2、编辑 package.json 文件:
{
"husky": {
"hooks": {
"pre-commit": "eslint src/**/*.js"
}
}
}
3、尝试 git commit 提交,就会先执行eslint src/**/*.js,代码没有问题才会被真正提交4、这样每次提交代码,eslint都会检查所有文件,如果报错过多,一定会崩溃
lint-staged 只 Lint 改动代码lint-staged requires Node.js version 10.13.0 or later.
- v10.0.0 以后对原始暂存文件的任何新修改都将自动添加到提交中。如果您的任务以前包含一个git add步骤,请删除此步骤,同时运行多个git操作通常会导致错误,详见 lint-staged
1、安装 lint-staged
npm install lint-staged --save-dev
2、新增 package.json 配置:
{
"lint-staged": {
"src/**/*.js": "eslint"
}
}
3、如此husky只负责注册git hook,后续操作交给lint-staged,只对改动的文件执行任务,而且可以很方便地配置多条命令:
{
"husky": {
"hooks": {
"pre-commit": "lint-staged"
}
}
"lint-staged": {
"src/**/*.js": ["eslint --fix" "prettier --write"]
}
}
4、如上,我们提交代码之前,程序会自动修复eslint配置,格式化prettier配置
几点建议- 建议代码提交只做检查和测试,拦截问题代码比较好,还是在保存时,自动修复eslint、prettier配置,而且大部分还需要手动修复才行
- 实在紧急,也可通过git commit -m -n "跳过代码代码预检"跳过检查,慎用
- 和构建有关的包建议使用--save-dev安装在项目内部
- 使用VSCode打开项目,path不要嵌套过深,可能导致Lint工具失效
- 老版本husky lint-staged配置都放在package.json中,现在eslint prettier husky lint-staged都支持多种后缀配置文件,建议采用.js统一格式,也方便拓展:
// .eslintrc.js
module.exports = {
extends: [
'alloy'
]
};
// .prettierrc.js
module.exports = {
// 一行最多 100 字符
printWidth: 100
// 使用 4 个空格缩进
tabWidth: 4
// ...
};
// .huskyrc.js
module.exports = {
'hooks': {
'pre-commit': "lint-staged"
}
}
// .lintstagedrc.js
module.exports = {
"src/**/*.{js ts}": "eslint"
}
// .stylelintrc.js
module.exports = {
extends: [
'stylelint-config-standard'
'stylelint-config-sass-guidelines'
'stylelint-config-prettier'
]
plugins: ['stylelint-order' 'stylelint-scss']
rules: {
// ...
}
};
拓展示例
- .huskyrc.js
// 数组方式配置多条命令
const tasks = arr => arr.join(' && ')
module.exports = {
'hooks': {
'pre-commit': tasks([
'npm run lint'
'npm test'
])
}
}
- .lintstagedrc.js
module.exports = {
// 如果超过10个暂存文件,则在整个存储库上运行eslint
'**/*.js?(x)': (filenames) =>
filenames.length > 10 ? 'eslint .' : `eslint ${filenames.join(' ')}`
"*.css": "stylelint"
"*.scss": "stylelint --syntax=scss"
// 对ts文件运行tsc,但不传递任何参数
'**/*.ts?(x)': () => 'tsc -p tsconfig.json --noEmit'
}
推荐JavaScript经典实例学习资料文章
《高性能多级多选级联组件开发「JS篇」》
《深入浅出讲解Node.js CLI 工具最佳实战》
《延迟加载图像以提高Web网站性能的五种方法「实践」》
《比较 JavaScript 对象的四种方式「实践」》
《使用Service Worker让你的 Web 应用如虎添翼(上)「干货」》
《使用Service Worker让你的 Web 应用如虎添翼(中)「干货」》
《使用Service Worker让你的 Web 应用如虎添翼(下)「干货」》
《前端如何一次性处理10万条数据「进阶篇」》
《推荐三款正则可视化工具「JS篇」》
《如何让用户选择是否离开当前页面?「JS篇」》
《JavaScript开发人员更喜欢Deno的五大原因》
《仅用18行JavaScript实现一个倒数计时器》
《图文细说JavaScript 的运行机制》
《一个轻量级 JavaScript 全文搜索库,轻松实现站内离线搜索》
《推荐Web程序员常用的15个源代码编辑器》
《10个实用的JS技巧「值得收藏」》
《细品269个JavaScript小函数,让你少加班熬夜(一)「值得收藏」》
《细品269个JavaScript小函数,让你少加班熬夜(二)「值得收藏」》
《细品269个JavaScript小函数,让你少加班熬夜(三)「值得收藏」》
《细品269个JavaScript小函数,让你少加班熬夜(四)「值得收藏」》
《细品269个JavaScript小函数,让你少加班熬夜(五)「值得收藏」》
《细品269个JavaScript小函数,让你少加班熬夜(六)「值得收藏」》
《深入JavaScript教你内存泄漏如何防范》
《手把手教你7个有趣的JavaScript 项目-上「附源码」》
《手把手教你7个有趣的JavaScript 项目-下「附源码」》
《JavaScript 使用 mediaDevices API 访问摄像头自拍》
《手把手教你前端代码如何做错误上报「JS篇」》
《一文让你彻底搞懂移动前端和Web 前端区别在哪里》
《63个JavaScript 正则大礼包「值得收藏」》
《提高你的 JavaScript 技能10 个问答题》
《JavaScript图表库的5个首选》
《一文彻底搞懂JavaScript 中Object.freeze与Object.seal的用法》
《可视化的 JS:动态图演示 - 事件循环 Event Loop的过程》
《教你如何用动态规划和贪心算法实现前端瀑布流布局「实践」》
《可视化的 js:动态图演示 Promises & Async/Await 的过程》
《原生JS封装拖动验证滑块你会吗?「实践」》
《如何实现高性能的在线 PDF 预览》
《细说使用字体库加密数据-仿58同城》
《Node.js要完了吗?》
《Pug 3.0.0正式发布,不再支持 Node.js 6/8》
《纯JS手写轮播图(代码逻辑清晰,通俗易懂)》
《JavaScript 20 年 中文版之创立标准》
《值得收藏的前端常用60余种工具方法「JS篇」》
《箭头函数和常规函数之间的 5 个区别》
《通过发布/订阅的设计模式搞懂 Node.js 核心模块 Events》
《「前端篇」不再为正则烦恼》
《「速围」Node.js V14.3.0 发布支持顶级 Await 和 REPL 增强功能》
《深入细品浏览器原理「流程图」》
《JavaScript 已进入第三个时代,未来将何去何从?》
《前端上传前预览文件 image、text、json、video、audio「实践」》
《深入细品 EventLoop 和浏览器渲染、帧动画、空闲回调的关系》
《推荐13个有用的JavaScript数组技巧「值得收藏」》
《前端必备基础知识:window.location 详解》
《不要再依赖CommonJS了》
《犀牛书作者:最该忘记的JavaScript特性》
《36个工作中常用的JavaScript函数片段「值得收藏」》
《Node H5 实现大文件分片上传、断点续传》
《一文了解文件上传全过程(1.8w字深度解析)「前端进阶必备」》
《【实践总结】关于小程序挣脱枷锁实现批量上传》
《手把手教你前端的各种文件上传攻略和大文件断点续传》
《字节跳动面试官:请你实现一个大文件上传和断点续传》
《谈谈前端关于文件上传下载那些事【实践】》
《手把手教你如何编写一个前端图片压缩、方向纠正、预览、上传插件》
《最全的 JavaScript 模块化方案和工具》
《「前端进阶」JS中的内存管理》
《JavaScript正则深入以及10个非常有意思的正则实战》
《前端面试者经常忽视的一道JavaScript 面试题》
《一行JS代码实现一个简单的模板字符串替换「实践」》
《JS代码是如何被压缩的「前端高级进阶」》
《前端开发规范:命名规范、html规范、css规范、js规范》
《【规范篇】前端团队代码规范最佳实践》
《100个原生JavaScript代码片段知识点详细汇总【实践】》
《关于前端174道 JavaScript知识点汇总(一)》
《关于前端174道 JavaScript知识点汇总(二)》
《关于前端174道 JavaScript知识点汇总(三)》
《几个非常有意思的javascript知识点总结【实践】》
《都2020年了,你还不会JavaScript 装饰器?》
《JavaScript实现图片合成下载》
《70个JavaScript知识点详细总结(上)【实践】》
《70个JavaScript知识点详细总结(下)【实践】》
《开源了一个 JavaScript 版敏感词过滤库》
《送你 43 道 JavaScript 面试题》
《3个很棒的小众JavaScript库,你值得拥有》
《手把手教你深入巩固JavaScript知识体系【思维导图】》
《推荐7个很棒的JavaScript产品步骤引导库》
《Echa哥教你彻底弄懂 JavaScript 执行机制》
《一个合格的中级前端工程师需要掌握的 28 个 JavaScript 技巧》
《深入解析高频项目中运用到的知识点汇总【JS篇】》
《JavaScript 工具函数大全【新】》
《从JavaScript中看设计模式(总结)》
《身份证号码的正则表达式及验证详解(JavaScript,Regex)》
《浏览器中实现JavaScript计时器的4种创新方式》
《Three.js 动效方案》
《手把手教你常用的59个JS类方法》
《127个常用的JS代码片段,每段代码花30秒就能看懂-【上】》
《深入浅出讲解 js 深拷贝 vs 浅拷贝》
《手把手教你JS开发H5游戏【消灭星星】》
《深入浅出讲解JS中this/apply/call/bind巧妙用法【实践】》
《手把手教你全方位解读JS中this真正含义【实践】》
《书到用时方恨少,一大波JS开发工具函数来了》
《干货满满!如何优雅简洁地实现时钟翻牌器(支持JS/Vue/React)》
《手把手教你JS 异步编程六种方案【实践】》
《让你减少加班的15条高效JS技巧知识点汇总【实践】》
《手把手教你JS开发H5游戏【黄金矿工】》
《手把手教你JS实现监控浏览器上下左右滚动》
《JS 经典实例知识点整理汇总【实践】》
《2.6万字JS干货分享,带你领略前端魅力【基础篇】》
《2.6万字JS干货分享,带你领略前端魅力【实践篇】》
《简单几步让你的 JS 写得更漂亮》
《恭喜你获得治疗JS this的详细药方》
《谈谈前端关于文件上传下载那些事【实践】》
《面试中教你绕过关于 JavaScript 作用域的 5 个坑》
《Jquery插件(常用的插件库)》
《【JS】如何防止重复发送ajax请求》
《JavaScript Canvas实现自定义画板》
《Continuation 在 JS 中的应用「前端篇」》
作者:周振超
转发链接:https://segmentfault.com/a/1190000022881634