React Native開發的一種代碼規範:Eslint + FlowType

【這篇隨筆記錄的很簡單,沒有涉及具體的Eslint規則解釋以及FlowType的類型說明和使用等,只是連接了所需的若干文檔】

js開發很舒服,可是代碼一多起來就良莠不齊,難以閱讀了。因此加上一些代碼規範以及檢測報錯會保證項目代碼的健康程度,我這裏使用的是Eslint + FlowType來進行代碼規範的(我還不會TypeScript,因此就沒有和TS的對比了)。node

達到的目標:

  • Eslint
    • 對代碼的縮進、格式等有規定
    • ...諸多Eslint的規定,具體參見Eslint文檔。
  • FlowType
    • 全部的方法參數都有明確的類型聲明和返回類型聲明

具體的環境配置方法:

  • Eslint
    • 參考 Eslint Getting Started進行環境配置(我使用的是airbnb的,而且有所修改)。
    • 配置.eslintrc文件,指定屬於你本身的規則。
    • (可選)設置git提交,在eslint檢測經過後才能夠。修改git的<project-dir>/.git/hooks/pre-commit文件(沒有的話,新建一個),修改成以下所示。(這裏能夠用ln -s將.git/hooks連接到git倉庫裏的本身建立的gitHooks目錄,可使用git管理這些文件,默認的.git/目錄是被git忽視的,沒法直接管理。)
#! /usr/bin/env python

import sys
import os

# in "<project_dir>/gitHooks"
os.chdir(os.path.dirname(__file__))
# in "<project_dir>"
os.chdir('..')


def runCommand(command):
    return os.popen(command).read().strip('\n')


cachedFiles = runCommand('git diff --name-only --cached --diff-filter=ACMR')

if not cachedFiles:
    sys.exit(0)

files = cachedFiles.split('\n')
filePaths = ''

folderPath = os.getcwd()
for file in files:
    if file.endswith('.js'):
        filePaths += os.path.join(file) + ' '

if not filePaths.strip():
    sys.exit(0)

checkStylePath = ''
checkStyleCommand = './node_modules/.bin/eslint {files}'.format(files=filePaths)
if os.system(checkStyleCommand) == 0:
    sys.exit(0)
else:
    sys.exit(1)
  • FlowType
    • 參考FlowType的eslint引導,將其中的規則copy到eslintrc文件裏。能夠根據本身的要求修改。
    • FlowType的具體type定義使用參考FlowType

項目報錯,可是想修改這個eslint rule的步驟(針對WebStorm)

  • 查看錯誤緣由(指針指着紅線就能夠了),copy裏面的緣由,此處爲"spaced-comment"
  • 在node_module目錄下全局搜索錯誤緣由,從搜索結果裏挨個找,能夠找到air-bnb的文件,叫做eslint-config-airbnb-base...,從裏面能夠查看具體的規則說明,能夠經過註釋的連接跳轉到詳細的網頁。
  • 在網頁上查看具體規則說明,並修改本身的eslintrc文件的rule。

個人.eslintrc.js

module.exports = {
    env: {
        es6: true,
        node: true,
    },
    extends: 'airbnb',
    globals: {
        Atomics: 'readonly',
        SharedArrayBuffer: 'readonly',
    },
    // let babel-eslint parse, because type definition will be error with eslint parser.
    parser: "babel-eslint",
    parserOptions: {
        ecmaFeatures: {
            jsx: true,
        },
        ecmaVersion: 2018,
        sourceType: 'module',
    },
    plugins: [
        'react',
        "flowtype",
    ],
    rules: {
        // 0 for 'off', 1 for 'warning',2 for 'error',
        // indent by 4
        "indent": ["error", 4, {
            "SwitchCase": 1,
            "FunctionDeclaration": {
                "parameters": "first"
            },
            "FunctionExpression": {
                "parameters": "first"
            }
        }],
        // Enforce JSX indentation
        // https://github.com/yannickcr/eslint-plugin-react/blob/master/docs/rules/jsx-indent.md
        'react/jsx-indent': ['error', 4],
        // Validate props indentation in JSX
        // https://github.com/yannickcr/eslint-plugin-react/blob/master/docs/rules/jsx-indent-props.md
        'react/jsx-indent-props': ['error', 4],
        // max length of one line
        "max-len": ["error", 130],
        // should have space after "{" and before "}"
        "object-curly-spacing": ["error", "never"],
        // When there is only a single export from a module, prefer using default export over named export.
        'import/prefer-default-export': 'off',
        // http://eslint.org/docs/rules/quotes
        "quotes": ["off"],
        // https://eslint.org/docs/rules/object-curly-newline
        'object-curly-newline': ['error', {
            ObjectExpression: {minProperties: 4, multiline: true, consistent: true},
            ObjectPattern: {minProperties: 4, multiline: true, consistent: true},
            // it is not necessary to do with import and export( WebStorm does not supprt quick format to this )
            // ImportDeclaration: {minProperties: 4, multiline: true, consistent: true},
            // ExportDeclaration: {minProperties: 4, multiline: true, consistent: true},
        }],
        // http://eslint.org/docs/rules/no-underscore-dangle
        "no-underscore-dangle": [0],
        // allow
        "no-unused-expressions": 0,
        // allow use of variables before they are defined
        "no-use-before-define": 0,
        // only .js and .jsx files may have JSX,
        // https://github.com/yannickcr/eslint-plugin-react/blob/master/docs/rules/jsx-filename-extension.md
        'react/jsx-filename-extension': [
            2,
            {
                extensions: ['.js', '.jsx'],
            },
        ],
        // Validate whitespace in and around the JSX opening and closing brackets
        // https://github.com/yannickcr/eslint-plugin-react/blob/843d71a432baf0f01f598d7cf1eea75ad6896e4b/docs/rules/jsx-tag-spacing.md
        'react/jsx-tag-spacing': ['error', {
            closingSlash: 'never',
            beforeSelfClosing: 'never',
            afterOpening: 'never',
            beforeClosing: 'never',
        }],
        // do not require all requires be top-level to allow static require for <Image/>
        // https://eslint.org/docs/rules/global-require
        'global-require': 0,
        // enforces no braces where they can be omitted
        // https://eslint.org/docs/rules/arrow-body-style
        'arrow-body-style': [1, 'as-needed', {
            requireReturnForObjectLiteral: false,
        }],


        // below is flowType lint
        // https://github.com/gajus/eslint-plugin-flowtype
        "flowtype/boolean-style": [
            2,
            "boolean"
        ],
        "flowtype/define-flow-type": 1,
        "flowtype/delimiter-dangle": [
            2,
            "never"
        ],
        "flowtype/generic-spacing": [
            2,
            "never"
        ],
        "flowtype/no-mixed": 2,
        "flowtype/no-primitive-constructor-types": 2,
        "flowtype/no-types-missing-file-annotation": 2,
        "flowtype/no-weak-types": 2,
        "flowtype/object-type-delimiter": [
            2,
            "comma"
        ],
        "flowtype/require-parameter-type": 2,
        "flowtype/require-return-type": [
            2,
            "always",
            {
                "annotateUndefined": "never"
            }
        ],
        "flowtype/require-valid-file-annotation": 2,
        "flowtype/semi": [
            2,
            "always"
        ],
        "flowtype/space-after-type-colon": [
            2,
            "always"
        ],
        "flowtype/space-before-generic-bracket": [
            2,
            "never"
        ],
        "flowtype/space-before-type-colon": [
            2,
            "never"
        ],
        "flowtype/type-id-match": [
            2,
            "^([A-Z][a-z0-9]+)+Type$"
        ],
        "flowtype/union-intersection-spacing": [
            2,
            "always"
        ],
        "flowtype/use-flow-type": 1,
        "flowtype/valid-syntax": 1
    },
};
相關文章
相關標籤/搜索