今天整理下跟 Weex 不那么相关但是对于保证软件质量特别重要的一环,那就是静态代码检查,工具当然是 ESLint

为什么要用 ESLint? Why not ?

About

下面摘一段 ESLint 官网的介绍。

ESLint 是一个开源的 JavaScript 代码检查工具,由 Nicholas C. Zakas 于2013年6月创建。代码检查是一种静态的分析,常用于寻找有问题的模式或者代码,并且不依赖于具体的编码风格。对大多数编程语言来说都会有代码检查,一般来说编译程序会内置检查工具。

JavaScript 是一个动态的弱类型语言,在开发中比较容易出错。因为没有编译程序,为了寻找 JavaScript 代码错误通常需要在执行过程中不断调适。像 ESLint 这样的可以让程序员在编码的过程中发现问题而不是在执行的过程中。

OK,总结一下,本质上 ESLint 将程序的问题暴露在开发阶段而非测试或者上线,如何做到的呢,静态代码分析,实现机制这里不展开。

到底有多少人在用?几乎每一个对代码质量有追求的团队都会用 ESLint 统一团队成员的编码编码规范,发现问题。像一些稍微大一点的厂(当然小厂也有,只不过是大厂的会更受关注,比如 Airbnb, Google),都会有自己的 Code Style 并且有对应的扩展规则。

How to Integrate With Weex

一开始在用 weex-toolkit 创建项目的时候, 并没有关于 ESLint 相关的配置。当时我手动在项目里集成 ESLint。

而我们的第一个项目 使用的 weex-toolkit 版本是 1.0.5, 工程里已经默认有 ESLint 相关的配置。

比如非常关键的 .eslintrc配置文件,以及 webpack.conf.js 中的注释都是提示你应该用一下 ESLint。

下面我们把它完善一下。

Install

两种选择,Local 或者 Global 安装。

我以 Global 为例。
npm install -g eslint

因为项目中已经有 .eslintrc配置文件, 所以这里不用再重复创建,但让也可以手动创建,而且,配置文件格式可以使 Js Module,JSON 或者YML 任意一种。

详细的安装教程参考这里

接下来就是如何配置 Lint 选项了。

Config ESLint

最全的配置教程当然还是官方文档了。

weex-toolkit@1.0.5 默认生成的 .eslintrc 内容如下:

1
{
  "root": true,
  "parser": "babel-eslint",
  "parserOptions": {
    "sourceType": "module"
  },
  "globals": {
    "Vue": false,
  },
  "extends": "standard",
  "plugins": [
    "html"
  ],
  "rules": {
    "arrow-parens": 0,
    "generator-star-spacing": 0,
  }
}

解释一下这里的配置选项:

  • root
    默认情况下,ESLint 会在所有父级目录里寻找配置文件,一直到根目录。如果你想要你所有项目都遵循一个特定的约定时,这将会很有用,但有时候会导致意想不到的结果。为了将 ESLint 限制到一个特定的项目,在你项目根目录下的 package.json 文件或者 .eslintrc.* 文件里的 eslintConfig 字段下设置 “root”: true。ESLint 一旦发现配置文件中有 “root”: true,它就会停止在父级目录中寻找。
  • parser
    ESLint 默认使用Espree作为其解析器, 也可以指定不懂的解析器,但是需要满足一下几点:
    • 它必须是本地安装的一个 npm 模块。
    • 它必须有兼容 Esprima 的接口(它必须输出一个 parse() 方法)
    • 它必须产出兼容 Esprima 的 AST 和 token 对象
      这里指定的 Babel-ESLint 对 Babel 解析器的包装使其与 ESLint 兼容。

:当使用自定义解析器时,为了使 ESLint 在非 ECMAScript 5 特性下正常工作,配置属性 parserOptions 仍然是必须的。解析器被传入 parserOptions,可能会也可能不会使用它们来决定开启哪个特征。

  • parserOptions
    指定你想要支持的 JavaScript 语言选项。
    例如:
  • globals
    当访问未定义的变量时,no-undef 规则将发出警告。如果你想在一个文件里使用全局变量,推荐你定义这些全局变量,这样 ESLint 就不会发出警告了。你可以使用注释或在配置文件中定义全局变量。
  • extends
    一个配置文件可以被基础配置中的已启用的规则继承。
    extends 属性值可以是:、
    • 在配置中指定的一个字符串
    • 字符串数组:每个配置继承它前面的配置
  • plugins
    一个 npm 包,通常输出规则。一些插件也可以输出一个或多个命名的 配置。要确保这个包安装在 ESLint 能请求到的目录下。plugins 属性值 可以省略包名的前缀 eslint-plugin-。
  • rules
    规则。由于规则太多。不一一介绍,请参考官方文档

修改一下默认生成的 eslintrc 文件,最终我们的第一个项目 的 ESLint 配置下:

1
{
  "root": true,
  "parser": "babel-eslint",
  "parserOptions": {
    "sourceType": "module",
    "ecmaVersion": 6,
    "ecmaFeatures": {
      "experimentalObjectRestSpread": true
    }
  },
  "globals": {
    "Vue": false,
  },
  "extends": "",
  "plugins": [ ],
  "rules": {
    "no-unused-vars": 1,
    "eqeqeq": [2, "allow-null"],
    "no-console": 0,
    "no-alert": 0,
    "linebreak-style": [
      "error",
      "unix"
    ],
    "quotes": [
      "error",
      "single"
    ],
    "semi": [
      "warn", //行末没有 ; 视为警告
      "always"
    ],
    "no-multi-spaces": 1,//不能用多余的空格
    "curly": [2, "all"],//必须使用 if(){} 中的{},
    "prefer-const": 0//首选const
  }
}

这里主要是增强了一下 rules 的配置。

此时,就可以使用 ESLint 提供的 CLI 执行 ESLint 的配置了。但是不够优雅。

下面讲如何与 Webpack 优雅的集成在一起。

Integrate With Webpack

这里的优雅是这样定义的:每次改动文件不需要手动执行 Lint,应该实时的贯彻到开发过程中,只要出现不符合规则写法,需要及时给出提示。

因此,集成到 Webpack 里是不错的选择。
现在我们的 webpack.conf.js 内容如下:

1
function getBaseConfig () {
  return {
    ...
    module: {
      preLoaders: [
        {
          test: /\.js$/,
          loader: 'eslint',
          exclude: /node_modules/
        }
      ],
      loaders: [
       ...
      ]
    },
    vue: {
      //检测.vue文件中的JS代码
      loaders:{
        js: 'babel!eslint'
      }
    },
    plugins: [bannerPlugin]
  }
}
...

可以看到我们加了 preLoaders 先进行 eslint , 然后再做 babel 转换。对于 Vue 中的 JavaScript 代码也加了 'babel!eslint' 这种loader 的链式调用,要注意的是 loader 顺序,从右至左执行,也就是要在发生 babel 转换前进行 eslint 。

现在,命令行输入 npm run dev,

可以看到,不符合 rules 中定义的规则的项,文件,行列号,不规范的原因都给出。

检验一下,我们对 app.js 做如下修改,加一个未引用的变量声明:

控制台会给出如下的提示:

当然 ESLint 的 rules 远不止这些,ESLint 也有对应的拓展规则和插件,请参考官网。

这样,通过一份 .eslintrc 文件,就可以保证代码的 Style 和 Quality。

What Next ?

也许有人对此不以为然,但 ESLint 对于团队和成员都是有好处的。虽然不能避免写出垃圾代码,是至少关于 Style 的问题再也不需要在 Review 代码的时候争吵半天了。我建议你在其他的项目中也试用一下 ESLint, 你会爱上他的。


以上。

本文仍按照上一篇的预告来走,接下来估计会探索一下 Weex 中使用图标的姿势问题。