• uniapp项目,使用HbuilderX建立eslint规范


    好久没写博客了。最近要开始小程序的项目,我们是用uniapp写的小程序。原来是用HbuilderX + 微信开发者工具来搞的。
    在权衡了一下其他开发工具后,还是决定继续使用官方推荐的HbuilderX。
    语法提示是有不少支持,但是编辑器做的确实不尽人意。平时用惯了Vscode,之前的web项目是装了eslint一系列插件来做项目的规范。那么,在HbuiderX的前提下,怎么去使用eslint呢。

    社区说明:https://ask.dcloud.net.cn/article/37070

    安装插件

    目前HbuilderX的插件市场,要做eslint校验,只有这种方法。安装 eslint-js和eslint-plugin-vue插件
    在这里插入图片描述

    配置插件

    默认是不打开实时校验的,我这里勾上了
    注意:实时校验毛病挺多,很容易卡死~
    在这里插入图片描述

    配置规则

    在安装完插件后,已经内置了一个比较基础的配置文件。但是太过简单,像我们需要团队协作的,还是要自行配置,做好规范。而且内置的eslintrc.js文件是在本地目录的。我们通常是放在项目根目录下的。

    1.在项目根目录,新建 .eslintrc.js 文件。这样eslint插件会优先读取项目下的配置文件。
    2.修改配置文件

    下面奉上我整理的规则,每一行都有写注释哦~,可以让你少踩很多坑。你可以根据自己项目的实际情况来调整。

    // 更详细的配置文档请参考:https://github.com/vuejs/eslint-plugin-vue#gear-configs
    module.exports = {
      'root': true,
      'env': {
        'node': true,
        'es6': true
      },
      'extends': ['plugin:vue/recommended', 'eslint:recommended'],
      'parserOptions': {
        'ecmaVersion': 'latest',
        'sourceType': 'module'
      },
      'settings': {
        'html/html-extensions': [
          '.erb',
          '.handlebars',
          '.hbs',
          '.htm',
          '.html',
          '.mustache',
          '.nunjucks',
          '.php',
          '.tag',
          '.twig',
          '.wxml',
          '.we'
        ]
      },
      'globals': {
        /** 避免uni报错 */
        'uni': true,
        'UniApp': true
      },
      'rules': {
        // 末尾不添加分号
        'semi': [2, 'never'],
        'semi-spacing': [2, {
          'before': false,
          'after': true
        }],
        // 缩进
        'indent': [2, 2, {
          'SwitchCase': 1
        }],
        // 使用单引号
        'quotes': [2, 'single', {
          'avoidEscape': true,
          'allowTemplateLiterals': true
        }],
        // 禁止修改const声明的变量
        'no-const-assign': 2,
        // 在创建对象字面量时不允许键重复 {a:1,a:1}
        'no-dupe-keys': 2,
        // 函数参数不能重复
        'no-dupe-args': 2,
        // switch中的case标签不能重复
        'no-duplicate-case': 2,
        // 正则表达式中的[]内容不能为空
        'no-empty-character-class': 2,
        'no-empty-pattern': 2,
        // 禁止使用未申明的变量
        'no-undef': 2,
        // 禁止将变量初始化为 undefined
        'no-undef-init': 2,
        // 禁止多余的空格
        'no-multi-spaces': 2,
        // 字符串不能用\换行
        'no-multi-str': 2,
        // 禁止多余的空行
        'no-multiple-empty-lines': [2, {
          'max': 1
        }],
        // 禁止未使用过的变量
        'no-unused-vars': [2, {
          'vars': 'all',
          'args': 'none'
        }],
        // 禁止在 return、throw、continue 和 break 语句之后出现不可达代码
        'no-unreachable': 2,
        // 禁止在 finally 语句块中出现控制流语句
        'no-unsafe-finally': 2,
        // 强制在块之前使用一致的空格
        'space-before-blocks': [2, 'always'],
        // 强制在 function的左括号之前使用一致的空格
        'space-before-function-paren': [2, 'never'],
        // 强制在圆括号内使用一致的空格
        'space-in-parens': [2, 'never'],
        // 要求操作符周围有空格
        'space-infix-ops': 2,
        // 强制在一元操作符前后使用一致的空格
        'space-unary-ops': [2, {
          'words': true,
          'nonwords': false
        }],
        // 强制在注释中 // 或 /* 使用一致的空格
        'spaced-comment': [2, 'always', {
          'markers': ['global', 'globals', 'eslint', 'eslint-disable', '*package', '!', ',']
        }],
        // 禁止在模板字符串和它们的字面量之间有空格
        'template-curly-spacing': [2, 'never'],
        // 强制在大括号中使用一致的空格
        'object-curly-spacing': [2, 'always', {
          objectsInObjects: false
        }],
        // 强制数组方括号中使用一致的空格
        'array-bracket-spacing': [2, 'never'],
        // 禁止块语句和类的开始或末尾有空行
        'padded-blocks': [2, 'never'],
        // 强制函数中的变量要么一起声明要么分开声明
        'one-var': [2, {
          'initialized': 'never'
        }],
        // 强制操作符使用一致的换行符
        'operator-linebreak': [2, 'after', {
          'overrides': {
            '?': 'before',
            ':': 'before'
          }
        }],
        // 禁止属性前有空白
        'no-whitespace-before-property': 2,
        // 强制 getter 和 setter 在对象中成对出现
        'accessor-pairs': 2,
        // 强制箭头函数的箭头前后使用一致的空格
        'arrow-spacing': [2, {
          'before': true,
          'after': true
        }],
        // 强制在代码块中开括号前和闭括号后有空格
        'block-spacing': [2, 'always'],
        // 强制在代码块中使用一致的大括号风格
        'brace-style': [2, '1tbs', {
          'allowSingleLine': true
        }],
        // 驼峰命名
        'camelcase': [0, {
          'properties': 'always'
        }],
        // 禁止使用拖尾逗号
        'comma-dangle': [2, 'never'],
        // 强制在逗号前后使用一致的空格
        'comma-spacing': [2, {
          'before': false,
          'after': true
        }],
        // 强制使用一致的逗号风格
        'comma-style': [2, 'last'],
        // 要求或禁止文件末尾存在空行
        'eol-last': 2,
        // 强制在点号之前和之后一致的换行
        'dot-location': [2, 'property'],
        // 要求使用 === 和 !==
        'eqeqeq': [2, 'allow-null'],
        // 强制在对象字面量的属性中键和值之间使用一致的间距
        'key-spacing': [2, {
          'beforeColon': false,
          'afterColon': true
        }],
        // 强制在关键字前后使用一致的空格
        'keyword-spacing': [2, {
          'before': true,
          'after': true
        }],
        // 强制第一个属性的位置(属性换行)
        'vue/first-attribute-linebreak': [2, {
          // 单行时,第一属性前不允许使用换行符
          singleline: 'beside',
          // 多行时,第一属性前必须使用换行符
          multiline: 'below'
        }],
        // 强制每行的最大属性数
        'vue/max-attributes-per-line': [2, {
          // 单行时可以接收最大数量
          singleline: 6,
          // 多行时可以接收最大数量
          multiline: {
            max: 1
          }
        }],
        // 在单行元素的内容之前和之后不需要换行符
        'vue/singleline-html-element-content-newline': 0,
        // 关闭组件命名规则校验
        'vue/multi-word-component-names': 0,
        // 在computed properties中禁用异步actions
        'vue/no-async-in-computed-properties': 'error',
        // 不允许重复的keys
        'vue/no-dupe-keys': 'error',
        // 不允许重复的attributes
        'vue/no-duplicate-attributes': 'warn',
        // 在 <template> 标签下不允许解析错误
        'vue/no-parsing-error': ['error', {
          'x-invalid-end-tag': false
        }],
        // 不允许覆盖保留关键字
        'vue/no-reserved-keys': 'error',
        // 强制data必须是一个带返回值的函数
        // 'vue/no-shared-component-data': 'error',
        // 不允许在computed properties中出现副作用。
        'vue/no-side-effects-in-computed-properties': 'error',
        // <template>不允许key属性
        'vue/no-template-key': 'warn',
        // 在 <textarea> 中不允许mustaches
        'vue/no-textarea-mustache': 'error',
        // 不允许在v-for或者范围内的属性出现未使用的变量定义
        'vue/no-unused-vars': 'warn',
        // <component>标签需要v-bind:is属性
        'vue/require-component-is': 'error',
        // render 函数必须有一个返回值
        'vue/require-render-return': 'error',
        // 保证 v-bind:key 和 v-for 指令成对出现
        'vue/require-v-for-key': 'error',
        // 检查默认的prop值是否有效
        'vue/require-valid-default-prop': 'error',
        // 保证computed属性中有return语句 
        'vue/return-in-computed-property': 'error',
        // 强制校验 template 根节点
        'vue/valid-template-root': 'error',
        // 强制校验 v-bind 指令
        'vue/valid-v-bind': 'error',
        // 强制校验 v-cloak 指令
        'vue/valid-v-cloak': 'error',
        // 强制校验 v-else-if 指令
        'vue/valid-v-else-if': 'error',
        // 强制校验 v-else 指令 
        'vue/valid-v-else': 'error',
        // 强制校验 v-for 指令
        'vue/valid-v-for': 'error',
        // 强制校验 v-html 指令
        'vue/valid-v-html': 'error',
        // 强制校验 v-if 指令
        'vue/valid-v-if': 'error',
        // 强制校验 v-model 指令
        'vue/valid-v-model': 'error',
        // 强制校验 v-on 指令
        'vue/valid-v-on': 'error',
        // 强制校验 v-once 指令
        'vue/valid-v-once': 'error',
        // 强制校验 v-pre 指令
        'vue/valid-v-pre': 'error',
        // 强制校验 v-show 指令
        'vue/valid-v-show': 'error',
        // 强制校验 v-text 指令
        'vue/valid-v-text': 'error',
        'vue/comment-directive': 0
      }
    }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68
    • 69
    • 70
    • 71
    • 72
    • 73
    • 74
    • 75
    • 76
    • 77
    • 78
    • 79
    • 80
    • 81
    • 82
    • 83
    • 84
    • 85
    • 86
    • 87
    • 88
    • 89
    • 90
    • 91
    • 92
    • 93
    • 94
    • 95
    • 96
    • 97
    • 98
    • 99
    • 100
    • 101
    • 102
    • 103
    • 104
    • 105
    • 106
    • 107
    • 108
    • 109
    • 110
    • 111
    • 112
    • 113
    • 114
    • 115
    • 116
    • 117
    • 118
    • 119
    • 120
    • 121
    • 122
    • 123
    • 124
    • 125
    • 126
    • 127
    • 128
    • 129
    • 130
    • 131
    • 132
    • 133
    • 134
    • 135
    • 136
    • 137
    • 138
    • 139
    • 140
    • 141
    • 142
    • 143
    • 144
    • 145
    • 146
    • 147
    • 148
    • 149
    • 150
    • 151
    • 152
    • 153
    • 154
    • 155
    • 156
    • 157
    • 158
    • 159
    • 160
    • 161
    • 162
    • 163
    • 164
    • 165
    • 166
    • 167
    • 168
    • 169
    • 170
    • 171
    • 172
    • 173
    • 174
    • 175
    • 176
    • 177
    • 178
    • 179
    • 180
    • 181
    • 182
    • 183
    • 184
    • 185
    • 186
    • 187
    • 188
    • 189
    • 190
    • 191
    • 192
    • 193
    • 194
    • 195
    • 196
    • 197
    • 198
    • 199
    • 200
    • 201
    • 202
    • 203
    • 204
    • 205
    • 206
    • 207
    • 208
    • 209
    • 210
    • 211
    • 212
    • 213
    • 214
    • 215
    • 216
    • 217
    • 218
    • 219
    • 220
    • 221
    • 222
    • 223
    • 224
    • 225
    • 226
    • 227
    • 228
    • 229
    • 230
    • 231
    • 232
    • 233
    • 234
    • 235
    • 236
    • 237
    • 238
    • 239
    • 240
    • 241
    • 242
    • 243
    • 244
    • 245
    • 246
    • 247

    修改tab缩进

    看你的项目风格,因为我都是用两个空格缩进,编辑器默认是4个,所以需要修改一下。
    HbuilderX需要修改tab的缩进为两个空格。 编辑-》缩进-》tab宽度:2个空格

    注意事项

    一开始我配置完规则后,还是遇到了不少问题

    module is not defined

    这个报错要注意在配置文件里,加上env环境,设置node为true。因为module,require等这些变量是属于node环境下的。
    ‘env’: {
    ‘node’: true
    }

    uni is not defined
    因为我们是uniapp项目,uni其实是个全局的变量,但是eslint没有识别。
    需要在配置文件加入
    ‘globals’: {
    /** 避免uni报错 */
    ‘uni’: true
    }
    假如你使用到了其他全局变量,也是同样道理。

    保存后,没有格式化代码
    其实这是正常的,因为装的这两个eslint插件,其实并不像vscode那样装插件好用,不怎么灵。
    你可以试一下,随便改一下代码,再去保存,可能就好了。
    还是不行,就重启一下HbuilderX
    再不行就只能卸载eslint插件重装咯~

    使用的规则不生效
    要注意查一下,你extends的是什么规则,比如我这里是[‘plugin:vue/recommended’, ‘eslint:recommended’]
    然后再去官方eslint文档看下,你用的那个rules,是不是包含在里面。

    xxx rule is not valid
    我照搬以前项目的规则,也踩了个坑。
    比如以下这个规则, "allowFirstLine"其实在新的eslint版本,已经被废除了。

    "vue/max-attributes-per-line": [2, {
      "singleline": 10,
      "multiline": {
        "max": 1,
        "allowFirstLine": false
      }
    }],
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7

    换成以下的

    // 强制第一个属性的位置(属性换行)
    'vue/first-attribute-linebreak': [2, {
      // 单行时,第一属性前不允许使用换行符
      singleline: 'beside',
      // 多行时,第一属性前必须使用换行符
      multiline: 'below'
    }],
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7

    总结

    这两个eslint插件很多地方还不完善,希望作者后续更新好点吧。
    eslint的规则,多去查官方的文档看看,可能格式化后,有些地方不是你想要的,就需要自己去做出调整。

  • 相关阅读:
    解决服务器中的mysql连接不上Navicat的问题脚本
    spring03-SpringJdbcTemplate模板技术和事务处理
    CoaXPress 线缆和接插件的设计要求
    B2C在线教育商城--前后端分离部署
    要精通Java,先研究它的执行原理
    格式化前做好备份,内存卡数据安全无忧
    收下我的膝盖 阿里架构师编写的668页Java虚拟机笔记真强
    JavaScript或其他编程语言中关于函数的各种高级特性和设计模式
    java的网络编程
    Web安全——穷举爆破上篇(仅供学习)
  • 原文地址:https://blog.csdn.net/weixin_42190844/article/details/125403951