uniapp配置eslint + prettier +editorconfig + lint-staged

目標:給新建的uniapp項目增加語法規(guī)范和保存自動格式化代碼,有不對的歡迎指正

2020-11-4日新增

今日看到各種黃色波浪線都來自一個eslint-plugin-vue這個插件,只用eslint + eslint-plugin-vue這兩個插件就足夠用了,簡單明了三步走

1.第一步

npm i eslint  eslint-plugin-vue -D
npm i babel-eslint eslint-plugin-node -D // 這兩個在配置中可用可不用

2.第二步: 新建.eslintrc.js 文件,極簡配置即可。

新建的.eslintrc.js 文件中
module.exports = {
  extends: [
    'plugin:vue/recommended',
    'eslint:recommended'
  ],
  globals: { uni: true, wx: true },
  rules: {
    "no-mixed-spaces-and-tabs": ["error", "smart-tabs"]
// 還有很多js規(guī)則去github上找項目vue-element-admin上搞一份
  },
  env: {
    es6: true,
    browser: true,
    node: true
  },
  parserOptions: {
    parser: 'babel-eslint'
  }
}

或者可以直接放在packag.json中都行,參考腳手架生成的vue項目

packag.json 文件中
 "eslintConfig": {
    "root": true,
    "env": {
      "node": true
    },
    "extends": [
       'plugin:vue/recommended',
    'eslint:recommended'
    ],
    "parserOptions": {
      "parser": "babel-eslint"
    },
    "rules": {}
  },

3.第三步:.vscode文件settings.json用下面的配置即可

{
  // "vetur.validation.template": false, // 把 vetur 擴展的 template 格式化去掉
  "editor.formatOnSave": false,
  "eslint.enable": true, // eslint 格式化的配置
  "eslint.run": "onType",
  "editor.tabSize": 2,
  "editor.autoClosingQuotes": "always",
  "javascript.preferences.quoteStyle": "single",
  "workbench.iconTheme": "vscode-icons",
  "editor.codeActionsOnSave": {
    // For ESLint
    "source.fixAll.eslint": true,
    // For TSLint
    "source.fixAll.tslint": true,
    // For Stylelint
    "source.fixAll.stylelint": true
  },
  "eslint.options": {
    "extensions": [".js", ".vue"]
  }
}

以下內(nèi)容選擇性瀏覽

2020-11-1新建

問:為什么是eslint + prettier
答: 這兩者都有規(guī)范代碼的作用,ESLint 主要解決的是代碼質(zhì)量問題,例如使用cost或者let替代var;Prettier 認為格式很重要,比如規(guī)定用單引號和或雙引號。想要雙劍合璧,去掉兩者使用中的沖突,使用起來就完美了

問:editorconfig, lint-staged是什么
答:1. 不同的編輯器和系統(tǒng)在編碼上一些操作會有不同,比如:縮進是tab還是space,結(jié)尾end_of_line是lf還是crlf(editorconfig的能力 —— 用于覆蓋編輯器的默認配置)

  1. lint-staged 用于對 Git 暫存區(qū)中的文件執(zhí)行代碼檢測,結(jié)合husky 用到 pre-commit這個 hook,在執(zhí)行 commit 之前,可以運行一些自定義操作

1.在插件市場安裝要用到的插件,注意:再加個vetur 如下圖

企業(yè)微信截圖_16042994154716.png

2.新建下圖中需要用到的文件

[圖片上傳中...(企業(yè)微信截圖_16042994154716.png-992558-1604299420862-0)]

editorconfig 大致配置,不建議深究,能用就行

# http://editorconfig.org
root = true

[*]
indent_style = space
indent_size = 2
end_of_line = crlf
charset = utf-8
trim_trailing_whitespace = true
insert_final_newline = true

[*.md]
trim_trailing_whitespace = false

[Makefile]
indent_style = tab

# editorconfig-tools is unable to ignore longs strings or urls
max_line_length = null

問: 怎么生成.vscode文件
答:編輯器左下角設(shè)置按鈕,隨便改個設(shè)置就會在項目生成該文件夾

3. 下載要用到的包

npm i eslint prettier eslint-plugin-prettier eslint-config-prettier  -D

eslint-config-prettier :關(guān)掉 (disable) 所有和 Prettier 沖突的 ESLint 的配置
eslint-plugin-prettier : 把 Prettier 推薦的格式問題的配置以 ESLint rules 的方式寫入,這樣相當于可以統(tǒng)一代碼問題的來源

問:怎么關(guān)掉沖突呢
答:在 .eslintrc.js 里面將 prettier 設(shè)為最后一個 extends

// .eslintrc    
{      
    "extends": ["eslint:recommended", "prettier"] // prettier 一定要是最后一個,才能確保覆蓋   eslint:recommended 的規(guī)則 
}

問:怎么導(dǎo)入eslint-plugin-prettier

// .eslintrc    
{      
    "plugins": ["prettier"],      
    "rules": {        
        "prettier/prettier": "error"      
    }    
}

以上兩者可以簡寫為

// .eslintrc    
{      
    "extends": ["eslint:recommended", "plugin:prettier/recommended"] // 這個plugin也放在extends數(shù)組最后才能覆蓋
}

4. vue文件檢測并設(shè)置保存就自動格式化代碼

npm i eslint-plugin-vue eslint-plugin-prettier-vue  -D
// .eslintrc    
// eslint-plugin-vue現(xiàn)在已經(jīng)廢棄,改為eslint-plugin-vue-libs,有興趣的朋友可以嘗試
{      
    "extends": ["plugin:vue/essential"] 
}
// .vscode文件夾 的setting.json文件
{
"vetur.validation.template": false ,   // 把 vetur 擴展的 template 格式化去掉
"editor.formatOnSave": false,        
// 去掉 vscode 自帶的自動保存 ,vscode 默認也是 false的,如果要用 eslint 格式化,默認的格式化就不能開啟
//不關(guān)閉會和plugin:vue/recommended的規(guī)則相沖突
"eslint.enable": true,              // eslint 格式化的配置
"eslint.run": "onType",
  "editor.tabSize": 2,
  "editor.autoClosingQuotes": "always",
  "javascript.preferences.quoteStyle": "single",
  "workbench.iconTheme": "vscode-icons",
  // eslint自動格式化代碼詳細配置說明:https://www.worldlink.com.cn/en/osdir/vscode-eslint.html
  "editor.codeActionsOnSave": {
    // For ESLint
    "source.fixAll.eslint": true,
    // For TSLint
    "source.fixAll.tslint": true,
    // For Stylelint
    "source.fixAll.stylelint": true
  },
// 以下是舊寫法,不必理會
 // "eslint.validate": [
 //   "javascript", // 用eslint的規(guī)則檢測js文件
//    {
//      "language": "js",
//      "autoFix": true
//    },
//    {
//      "language": "vue",
//      "autoFix": true
//    }
  ],
  "eslint.options": {
    "extensions": [".js", ".vue"]
  }
}

5.代碼提交前校驗

npm i husky lint-staged  -D
// package.json文件中增加
"lint-staged": {
    "**/**.{js,json,pcss,md,vue}": [
      "prettier --write",
      "eslint",
      "git add"
    ]
  },
  "husky": {
    "hooks": {
      "pre-commit": "lint-staged"
    }
  }

最后:下面是eslintrc.js配置全文,另外有一些插件需要下載,可以根據(jù)自己的需要或者eslint報錯提示進行安裝

npm i babel-eslint eslint-plugin-import eslint-plugin-node eslint-plugin-promise  "eslint-plugin-html -D

下圖可以看到項目中eslint或其他插件運行的情況,有報錯根據(jù)提示解決即可


企業(yè)微信截圖_16043040494958.png

至于相關(guān)配置可以參考:點我https://my.oschina.net/lsjcoder/blog/1611755
如果項目crl + s保存后還有一些波浪號,沒關(guān)系。鼠標放上去看提示的什么,點擊進入到具體的規(guī)則去配置即可,如下圖

企業(yè)微信截圖_16043850131799.png

直接看代碼備注了解,選擇需要下載的插件下載即可

//eslintrc.js文件內(nèi)容
/** 
 * rules
 * https://eslint.org/docs/rules/
 * https://github.com/benmosher/eslint-plugin-import
 */
module.exports = {
  extends: [
    'plugin:vue/essential',
    // "plugin:vue/essential" 僅包含Base Rules和Priority A:Essential,這里用前兩種,少些規(guī)則html上僅有:src 和@tap不用換行
    // "plugin:vue/recommended" 包含Base Rules、Priority A:Essential、Priority B: Strongly Recommended、Priority C: Recommended
    'eslint:recommended',
    'plugin:prettier/recommended' // 放在最后面,用prettier的代碼規(guī)范
  ],
  globals: { uni: true, wx: true }, //全局變量要在這里添加,避免出現(xiàn)提示
  plugins: [ 'import'], // eslint-plugin-import需要下載,因為下面rules需要用到該插件所以在這里導(dǎo)入
  env: {
    es6: true,
    browser: true,
    node: true    // eslint-plugin-node這個插件要安裝
  },
  /**
   * "off"    0
   * "warn"   1
   * "error"  2
   */
  rules: {
    curly: [2, 'all'], // 必須使用 if(){} 中的{}

    'space-before-function-paren': [0],
    eqeqeq: [0],
    'vars-on-top': [2],
    'no-var': [2],
    'object-property-newline': [
      'error',
      { allowMultiplePropertiesPerLine: true }
    ],  // Map要么多行。要么單行
    'object-shorthand': [
      'error',
      'always',
      {
        ignoreConstructors: false,
        avoidQuotes: true
      }
    ],
    'padding-line-between-statements': [
      'error',
      { blankLine: 'always', prev: ['const', 'let', 'var'], next: '*' },
      {
        blankLine: 'any',
        prev: ['const', 'let', 'var'],
        next: ['const', 'let', 'var']
      },
      {
        blankLine: 'always',
        prev: ['import', 'cjs-import'],
        next: 'expression'
      },
      { blankLine: 'always', prev: '*', next: 'block-like' },
      { blankLine: 'always', prev: 'block-like', next: '*' },
      { blankLine: 'always', prev: '*', next: 'return' }
    ],
    'prefer-destructuring': [
      'warn',
      {
        VariableDeclarator: {
          array: false,
          object: true
        },
        AssignmentExpression: {
          array: false,
          object: true
        }
      },
      {
        enforceForRenamedProperties: false
      }
    ],
    'prefer-rest-params': 'error',
    'prefer-spread': 'error',
    'prefer-template': 'error',
    'prefer-arrow-callback': [
      'error',
      {
        allowNamedFunctions: false,
        allowUnboundThis: true
      }
    ],
    'no-use-before-define': [
      'error',
      {
        classes: true,
        functions: false,
        variables: true
      }
    ],
    'no-unused-expressions': [
      'error',
      {
        allowShortCircuit: true,
        allowTernary: true
      }
    ]
  },
  parserOptions: {
    parser: 'babel-eslint',   // babel-eslint這個插件要安裝
    ecmaVersion: 7,
    sourceType: 'module',
    ecmaFeatures: {
      jsx: true,
      experimentalObjectRestSpread: true
    }
  }
}

prettierrc.js文件內(nèi)容

module.exports = {
  /**
   * 保留現(xiàn)有的結(jié)尾行
   */
  endOfLine: 'auto',

  /**
   * 代碼行的長度
   */
  printWidth: 80,

  /**
   * 縮進方式
   * true  = tab縮進
   * false = 空格縮進
   */
  useTabs: false,

  /**
   * 縮進長度
   */
  tabWidth: 2,

  /**
   * 語句是否有";"
   *
   * true  - const a = 1;
   * false - const b = 2
   */
  semi: false,

  /**
   * 字符串是否使用單引號包裹
   *
   * true  - 'hello'
   * false - "a"
   */
  singleQuote: true,

  /**
   * 數(shù)組&&對象&&參數(shù)列表 多行顯示時,結(jié)尾處是否有","
   *
   * "none" - NO
   * "es5"  - Array,Object YES
   * "all"  - Array,Object,Parameter List YES
   */
  trailingComma: 'none',

  /**
   * 字面對象的大括號之間是否使用空格
   *
   * true  - { a: 1 }
   * false - {a: 1}
   */
  bracketSpacing: true,

  /**
   * 控制單個參數(shù)箭頭函數(shù)的括號:
   * "avoid"  - 無括號 x => x
   * "always" - 有括號 (x) => x
   */
  arrowParens: 'avoid'
}

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。