eslint 4.12.1 → 4.15.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +49 -0
- package/README.md +3 -3
- package/lib/cli-engine.js +4 -0
- package/lib/linter.js +78 -35
- package/lib/options.js +47 -41
- package/lib/report-translator.js +34 -13
- package/lib/rules/.eslintrc.yml +1 -0
- package/lib/rules/accessor-pairs.js +2 -1
- package/lib/rules/array-bracket-newline.js +2 -1
- package/lib/rules/array-bracket-spacing.js +2 -1
- package/lib/rules/array-callback-return.js +18 -3
- package/lib/rules/array-element-newline.js +2 -1
- package/lib/rules/arrow-body-style.js +15 -2
- package/lib/rules/arrow-parens.js +2 -1
- package/lib/rules/arrow-spacing.js +2 -1
- package/lib/rules/block-scoped-var.js +2 -1
- package/lib/rules/block-spacing.js +2 -1
- package/lib/rules/brace-style.js +2 -1
- package/lib/rules/callback-return.js +2 -1
- package/lib/rules/camelcase.js +29 -17
- package/lib/rules/capitalized-comments.js +2 -1
- package/lib/rules/class-methods-use-this.js +2 -1
- package/lib/rules/comma-dangle.js +2 -1
- package/lib/rules/comma-spacing.js +2 -1
- package/lib/rules/comma-style.js +2 -1
- package/lib/rules/complexity.js +3 -16
- package/lib/rules/computed-property-spacing.js +2 -1
- package/lib/rules/consistent-return.js +2 -1
- package/lib/rules/consistent-this.js +2 -1
- package/lib/rules/constructor-super.js +2 -1
- package/lib/rules/curly.js +2 -1
- package/lib/rules/default-case.js +2 -1
- package/lib/rules/dot-location.js +2 -1
- package/lib/rules/dot-notation.js +2 -1
- package/lib/rules/eol-last.js +10 -1
- package/lib/rules/eqeqeq.js +2 -1
- package/lib/rules/for-direction.js +2 -1
- package/lib/rules/func-call-spacing.js +2 -1
- package/lib/rules/func-name-matching.js +2 -1
- package/lib/rules/func-names.js +2 -1
- package/lib/rules/func-style.js +2 -1
- package/lib/rules/function-paren-newline.js +2 -1
- package/lib/rules/generator-star-spacing.js +2 -1
- package/lib/rules/getter-return.js +2 -1
- package/lib/rules/global-require.js +2 -1
- package/lib/rules/guard-for-in.js +2 -1
- package/lib/rules/handle-callback-err.js +2 -1
- package/lib/rules/id-blacklist.js +2 -1
- package/lib/rules/id-length.js +2 -1
- package/lib/rules/id-match.js +2 -1
- package/lib/rules/implicit-arrow-linebreak.js +2 -1
- package/lib/rules/indent-legacy.js +2 -1
- package/lib/rules/indent.js +13 -2
- package/lib/rules/init-declarations.js +2 -1
- package/lib/rules/jsx-quotes.js +2 -1
- package/lib/rules/key-spacing.js +2 -1
- package/lib/rules/keyword-spacing.js +2 -1
- package/lib/rules/line-comment-position.js +2 -1
- package/lib/rules/linebreak-style.js +2 -1
- package/lib/rules/lines-around-comment.js +2 -1
- package/lib/rules/lines-around-directive.js +2 -1
- package/lib/rules/lines-between-class-members.js +53 -4
- package/lib/rules/max-depth.js +2 -1
- package/lib/rules/max-len.js +2 -1
- package/lib/rules/max-lines.js +2 -1
- package/lib/rules/max-nested-callbacks.js +2 -1
- package/lib/rules/max-params.js +2 -1
- package/lib/rules/max-statements-per-line.js +2 -1
- package/lib/rules/max-statements.js +2 -1
- package/lib/rules/multiline-comment-style.js +2 -1
- package/lib/rules/multiline-ternary.js +2 -1
- package/lib/rules/new-cap.js +2 -1
- package/lib/rules/new-parens.js +2 -1
- package/lib/rules/newline-after-var.js +2 -1
- package/lib/rules/newline-before-return.js +2 -1
- package/lib/rules/newline-per-chained-call.js +2 -1
- package/lib/rules/no-alert.js +2 -1
- package/lib/rules/no-array-constructor.js +2 -1
- package/lib/rules/no-await-in-loop.js +2 -1
- package/lib/rules/no-bitwise.js +2 -1
- package/lib/rules/no-buffer-constructor.js +2 -1
- package/lib/rules/no-caller.js +2 -1
- package/lib/rules/no-case-declarations.js +2 -1
- package/lib/rules/no-catch-shadow.js +2 -1
- package/lib/rules/no-class-assign.js +2 -1
- package/lib/rules/no-compare-neg-zero.js +2 -1
- package/lib/rules/no-cond-assign.js +2 -1
- package/lib/rules/no-confusing-arrow.js +2 -1
- package/lib/rules/no-console.js +2 -1
- package/lib/rules/no-const-assign.js +2 -1
- package/lib/rules/no-constant-condition.js +2 -1
- package/lib/rules/no-continue.js +2 -1
- package/lib/rules/no-control-regex.js +2 -1
- package/lib/rules/no-debugger.js +2 -1
- package/lib/rules/no-delete-var.js +2 -1
- package/lib/rules/no-div-regex.js +2 -1
- package/lib/rules/no-dupe-args.js +2 -1
- package/lib/rules/no-dupe-class-members.js +2 -1
- package/lib/rules/no-dupe-keys.js +2 -1
- package/lib/rules/no-duplicate-case.js +2 -1
- package/lib/rules/no-duplicate-imports.js +2 -1
- package/lib/rules/no-else-return.js +2 -1
- package/lib/rules/no-empty-character-class.js +2 -1
- package/lib/rules/no-empty-function.js +2 -1
- package/lib/rules/no-empty-pattern.js +2 -1
- package/lib/rules/no-empty.js +2 -1
- package/lib/rules/no-eq-null.js +2 -1
- package/lib/rules/no-eval.js +2 -1
- package/lib/rules/no-ex-assign.js +2 -1
- package/lib/rules/no-extend-native.js +2 -1
- package/lib/rules/no-extra-bind.js +2 -1
- package/lib/rules/no-extra-boolean-cast.js +2 -1
- package/lib/rules/no-extra-label.js +2 -1
- package/lib/rules/no-extra-parens.js +3 -2
- package/lib/rules/no-extra-semi.js +2 -1
- package/lib/rules/no-fallthrough.js +2 -1
- package/lib/rules/no-floating-decimal.js +2 -1
- package/lib/rules/no-func-assign.js +2 -1
- package/lib/rules/no-global-assign.js +2 -1
- package/lib/rules/no-implicit-coercion.js +2 -1
- package/lib/rules/no-implicit-globals.js +2 -1
- package/lib/rules/no-implied-eval.js +2 -1
- package/lib/rules/no-inline-comments.js +2 -1
- package/lib/rules/no-inner-declarations.js +2 -1
- package/lib/rules/no-invalid-regexp.js +2 -1
- package/lib/rules/no-invalid-this.js +2 -1
- package/lib/rules/no-irregular-whitespace.js +2 -1
- package/lib/rules/no-iterator.js +2 -1
- package/lib/rules/no-label-var.js +2 -1
- package/lib/rules/no-labels.js +2 -1
- package/lib/rules/no-lone-blocks.js +2 -1
- package/lib/rules/no-lonely-if.js +2 -1
- package/lib/rules/no-loop-func.js +2 -1
- package/lib/rules/no-magic-numbers.js +2 -1
- package/lib/rules/no-mixed-operators.js +2 -1
- package/lib/rules/no-mixed-requires.js +2 -1
- package/lib/rules/no-mixed-spaces-and-tabs.js +2 -1
- package/lib/rules/no-multi-assign.js +2 -1
- package/lib/rules/no-multi-spaces.js +2 -1
- package/lib/rules/no-multi-str.js +2 -1
- package/lib/rules/no-multiple-empty-lines.js +2 -1
- package/lib/rules/no-native-reassign.js +2 -1
- package/lib/rules/no-negated-condition.js +2 -1
- package/lib/rules/no-negated-in-lhs.js +2 -1
- package/lib/rules/no-nested-ternary.js +2 -1
- package/lib/rules/no-new-func.js +2 -1
- package/lib/rules/no-new-object.js +2 -1
- package/lib/rules/no-new-require.js +2 -1
- package/lib/rules/no-new-symbol.js +2 -1
- package/lib/rules/no-new-wrappers.js +2 -1
- package/lib/rules/no-new.js +2 -1
- package/lib/rules/no-obj-calls.js +2 -1
- package/lib/rules/no-octal-escape.js +2 -1
- package/lib/rules/no-octal.js +2 -1
- package/lib/rules/no-param-reassign.js +2 -1
- package/lib/rules/no-path-concat.js +2 -1
- package/lib/rules/no-plusplus.js +2 -1
- package/lib/rules/no-process-env.js +2 -1
- package/lib/rules/no-process-exit.js +2 -1
- package/lib/rules/no-proto.js +2 -1
- package/lib/rules/no-prototype-builtins.js +2 -1
- package/lib/rules/no-redeclare.js +2 -1
- package/lib/rules/no-regex-spaces.js +2 -1
- package/lib/rules/no-restricted-globals.js +2 -1
- package/lib/rules/no-restricted-imports.js +2 -1
- package/lib/rules/no-restricted-modules.js +2 -1
- package/lib/rules/no-restricted-properties.js +2 -1
- package/lib/rules/no-restricted-syntax.js +2 -1
- package/lib/rules/no-return-assign.js +2 -1
- package/lib/rules/no-return-await.js +5 -1
- package/lib/rules/no-script-url.js +2 -1
- package/lib/rules/no-self-assign.js +2 -1
- package/lib/rules/no-self-compare.js +2 -1
- package/lib/rules/no-sequences.js +2 -1
- package/lib/rules/no-shadow-restricted-names.js +2 -1
- package/lib/rules/no-shadow.js +2 -1
- package/lib/rules/no-spaced-func.js +2 -1
- package/lib/rules/no-sparse-arrays.js +2 -1
- package/lib/rules/no-sync.js +2 -1
- package/lib/rules/no-tabs.js +2 -1
- package/lib/rules/no-template-curly-in-string.js +2 -1
- package/lib/rules/no-ternary.js +2 -1
- package/lib/rules/no-this-before-super.js +2 -1
- package/lib/rules/no-throw-literal.js +2 -1
- package/lib/rules/no-trailing-spaces.js +2 -1
- package/lib/rules/no-undef-init.js +2 -1
- package/lib/rules/no-undef.js +2 -1
- package/lib/rules/no-undefined.js +2 -1
- package/lib/rules/no-underscore-dangle.js +2 -1
- package/lib/rules/no-unexpected-multiline.js +2 -1
- package/lib/rules/no-unmodified-loop-condition.js +81 -79
- package/lib/rules/no-unneeded-ternary.js +2 -1
- package/lib/rules/no-unreachable.js +2 -1
- package/lib/rules/no-unsafe-finally.js +2 -1
- package/lib/rules/no-unsafe-negation.js +2 -1
- package/lib/rules/no-unused-expressions.js +2 -1
- package/lib/rules/no-unused-labels.js +2 -1
- package/lib/rules/no-unused-vars.js +10 -14
- package/lib/rules/no-use-before-define.js +2 -1
- package/lib/rules/no-useless-call.js +2 -1
- package/lib/rules/no-useless-computed-key.js +2 -1
- package/lib/rules/no-useless-concat.js +2 -1
- package/lib/rules/no-useless-constructor.js +2 -1
- package/lib/rules/no-useless-escape.js +2 -1
- package/lib/rules/no-useless-rename.js +2 -1
- package/lib/rules/no-useless-return.js +2 -1
- package/lib/rules/no-var.js +2 -1
- package/lib/rules/no-void.js +2 -1
- package/lib/rules/no-warning-comments.js +2 -1
- package/lib/rules/no-whitespace-before-property.js +2 -1
- package/lib/rules/no-with.js +2 -1
- package/lib/rules/nonblock-statement-body-position.js +2 -1
- package/lib/rules/object-curly-newline.js +2 -1
- package/lib/rules/object-curly-spacing.js +2 -1
- package/lib/rules/object-property-newline.js +2 -1
- package/lib/rules/object-shorthand.js +2 -1
- package/lib/rules/one-var-declaration-per-line.js +2 -1
- package/lib/rules/one-var.js +42 -8
- package/lib/rules/operator-assignment.js +2 -1
- package/lib/rules/operator-linebreak.js +2 -1
- package/lib/rules/padded-blocks.js +2 -1
- package/lib/rules/padding-line-between-statements.js +2 -1
- package/lib/rules/prefer-arrow-callback.js +2 -1
- package/lib/rules/prefer-const.js +2 -1
- package/lib/rules/prefer-destructuring.js +2 -1
- package/lib/rules/prefer-numeric-literals.js +2 -1
- package/lib/rules/prefer-promise-reject-errors.js +2 -1
- package/lib/rules/prefer-reflect.js +2 -1
- package/lib/rules/prefer-rest-params.js +2 -1
- package/lib/rules/prefer-spread.js +2 -1
- package/lib/rules/prefer-template.js +2 -1
- package/lib/rules/quote-props.js +2 -1
- package/lib/rules/quotes.js +2 -1
- package/lib/rules/radix.js +2 -1
- package/lib/rules/require-await.js +2 -1
- package/lib/rules/require-jsdoc.js +2 -1
- package/lib/rules/require-yield.js +2 -1
- package/lib/rules/rest-spread-spacing.js +2 -1
- package/lib/rules/semi-spacing.js +2 -1
- package/lib/rules/semi-style.js +2 -1
- package/lib/rules/semi.js +2 -1
- package/lib/rules/sort-imports.js +2 -1
- package/lib/rules/sort-keys.js +2 -1
- package/lib/rules/sort-vars.js +2 -1
- package/lib/rules/space-before-blocks.js +2 -1
- package/lib/rules/space-before-function-paren.js +2 -1
- package/lib/rules/space-in-parens.js +2 -1
- package/lib/rules/space-infix-ops.js +2 -1
- package/lib/rules/space-unary-ops.js +2 -1
- package/lib/rules/spaced-comment.js +2 -1
- package/lib/rules/strict.js +2 -1
- package/lib/rules/switch-colon-spacing.js +2 -1
- package/lib/rules/symbol-description.js +2 -1
- package/lib/rules/template-curly-spacing.js +2 -1
- package/lib/rules/template-tag-spacing.js +2 -1
- package/lib/rules/unicode-bom.js +2 -1
- package/lib/rules/use-isnan.js +2 -1
- package/lib/rules/valid-jsdoc.js +2 -1
- package/lib/rules/valid-typeof.js +2 -1
- package/lib/rules/vars-on-top.js +2 -1
- package/lib/rules/wrap-iife.js +2 -1
- package/lib/rules/wrap-regex.js +2 -1
- package/lib/rules/yield-star-spacing.js +2 -1
- package/lib/rules/yoda.js +2 -1
- package/lib/testers/rule-tester.js +63 -30
- package/lib/util/interpolate.js +24 -0
- package/lib/util/source-code.js +41 -6
- package/lib/util/traverser.js +163 -15
- package/package.json +3 -3
package/CHANGELOG.md
CHANGED
@@ -1,3 +1,52 @@
|
|
1
|
+
v4.15.0 - January 6, 2018
|
2
|
+
|
3
|
+
* 6ab04b5 New: Add context.report({ messageId }) (fixes #6740) (#9165) (Jed Fox)
|
4
|
+
* fc7f404 Docs: add url to each of the rules (refs #6582) (#9788) (Patrick McElhaney)
|
5
|
+
* fc44da9 Docs: fix sort-imports rule block language (#9805) (ferhat elmas)
|
6
|
+
* 65f0176 New: CLIEngine#getRules() (refs #6582) (#9782) (Patrick McElhaney)
|
7
|
+
* c64195f Update: More detailed assert message for rule-tester (#9769) (Weijia Wang)
|
8
|
+
* 9fcfabf Fix: no-extra-parens false positive (fixes: #9755) (#9795) (Erin)
|
9
|
+
* 61e5fa0 Docs: Add table of contents to Node.js API docs (#9785) (Patrick McElhaney)
|
10
|
+
* 4c87f42 Fix: incorrect error messages of no-unused-vars (fixes #9774) (#9791) (akouryy)
|
11
|
+
* bbabf34 Update: add `ignoreComments` option to `indent` rule (fixes #9018) (#9752) (Kevin Partington)
|
12
|
+
* db431cb Docs: HTTP -> HTTPS (fixes #9768) (#9768) (Ronald Eddy Jr)
|
13
|
+
* cbf0fb9 Docs: describe how to feature-detect scopeManager/visitorKeys support (#9764) (Teddy Katz)
|
14
|
+
* f7dcb70 Docs: Add note about "patch release pending" label to maintainer guide (#9763) (Teddy Katz)
|
15
|
+
|
16
|
+
v4.14.0 - December 23, 2017
|
17
|
+
|
18
|
+
* be2f57e Update: support separate requires in one-var. (fixes #6175) (#9441) (薛定谔的猫)
|
19
|
+
* 370d614 Docs: Fix typos (#9751) (Jed Fox)
|
20
|
+
* 8196c45 Chore: Reorganize CLI options and associated docs (#9758) (Kevin Partington)
|
21
|
+
* 75c7419 Update: Logical-and is counted in `complexity` rule (fixes #8535) (#9754) (Kevin Partington)
|
22
|
+
* eb4b1e0 Docs: reintroduce misspelling in `valid-typeof` example (#9753) (Teddy Katz)
|
23
|
+
* ae51eb2 New: Add allowImplicit option to array-callback-return (fixes #8539) (#9344) (James C. Davis)
|
24
|
+
* e9d5dfd Docs: improve no-extra-parens formatting (#9747) (Rich Trott)
|
25
|
+
* 37d066c Chore: Add unit tests for overrides glob matching. (#9744) (Robert Jackson)
|
26
|
+
* 805a94e Chore: Fix typo in CLIEngine test name (#9741) (@scriptdaemon)
|
27
|
+
* 1c2aafd Update: Improve parser integrations (fixes #8392) (#8755) (Toru Nagashima)
|
28
|
+
* 4ddc131 Upgrade: debug@^3.1.0 (#9731) (Kevin Partington)
|
29
|
+
* f252c19 Docs: Make the lint message `source` property a little more subtle (#9735) (Jed Fox)
|
30
|
+
* 5a5c23c Docs: fix the link to contributing page (#9727) (Victor Hom)
|
31
|
+
* f44ce11 Docs: change beginner to good first issue label text (#9726) (Victor Hom)
|
32
|
+
* 14baa2e Chore: improve arrow-body-style error message (refs #5498) (#9718) (Teddy Katz)
|
33
|
+
* f819920 Docs: fix typos (#9723) (Thomas Broadley)
|
34
|
+
* 43d4ba8 Fix: false positive on rule`lines-between-class-members` (fixes #9665) (#9680) (sakabar)
|
35
|
+
|
36
|
+
v4.13.1 - December 11, 2017
|
37
|
+
|
38
|
+
* b72dc83 Fix: eol-last allow empty-string to always pass (refs #9534) (#9696) (Kevin Partington)
|
39
|
+
* d80aa7c Fix: camelcase destructure leading/trailing underscore (fixes #9700) (#9701) (Kevin Partington)
|
40
|
+
* d49d9d0 Docs: Add missing period to the README (#9702) (Kevin Partington)
|
41
|
+
* 4564fe0 Chore: no-invalid-meta crash if no export assignment (refs #9534) (#9698) (Kevin Partington)
|
42
|
+
|
43
|
+
v4.13.0 - December 8, 2017
|
44
|
+
|
45
|
+
* 256481b Update: update handling of destructuring in camelcase (fixes #8511) (#9468) (Erin)
|
46
|
+
* d067ae1 Docs: Don’t use undocumented array-style configuration for max-len (#9690) (Jed Fox)
|
47
|
+
* 1ad3091 Chore: fix test-suite to work with node master (#9688) (Myles Borins)
|
48
|
+
* cdb1488 Docs: Adds an example with try/catch. (#9672) (Jaap Taal)
|
49
|
+
|
1
50
|
v4.12.1 - November 30, 2017
|
2
51
|
|
3
52
|
* 1e362a0 Revert "Fix: Use XML 1.1 on XML formatters (fixes #9607) (#9608)" (#9667) (Kevin Partington)
|
package/README.md
CHANGED
@@ -156,7 +156,7 @@ Before filing an issue, please be sure to read the guidelines for what you're re
|
|
156
156
|
|
157
157
|
## Semantic Versioning Policy
|
158
158
|
|
159
|
-
ESLint follows [semantic versioning](
|
159
|
+
ESLint follows [semantic versioning](https://semver.org). However, due to the nature of ESLint as a code quality tool, it's not always clear when a minor or major version bump occurs. To help clarify this for everyone, we've defined the following semantic versioning policy for ESLint:
|
160
160
|
|
161
161
|
* Patch release (intended to not break your lint build)
|
162
162
|
* A bug fix in a rule that results in ESLint reporting fewer errors.
|
@@ -188,7 +188,7 @@ According to our policy, any minor update may report more errors than the previo
|
|
188
188
|
|
189
189
|
### How is ESLint different from JSHint?
|
190
190
|
|
191
|
-
The most significant difference is that
|
191
|
+
The most significant difference is that ESLint has pluggable linting rules. That means you can use the rules it comes with, or you can extend it with rules created by others or by yourself!
|
192
192
|
|
193
193
|
### How does ESLint performance compare to JSHint?
|
194
194
|
|
@@ -239,7 +239,7 @@ Once a language feature has been adopted into the ECMAScript standard (stage 4 a
|
|
239
239
|
|
240
240
|
### Where to ask for help?
|
241
241
|
|
242
|
-
Join our [Mailing List](https://groups.google.com/group/eslint) or [Chatroom](https://gitter.im/eslint/eslint)
|
242
|
+
Join our [Mailing List](https://groups.google.com/group/eslint) or [Chatroom](https://gitter.im/eslint/eslint).
|
243
243
|
|
244
244
|
|
245
245
|
[npm-image]: https://img.shields.io/npm/v/eslint.svg?style=flat-square
|
package/lib/cli-engine.js
CHANGED
@@ -420,6 +420,10 @@ class CLIEngine {
|
|
420
420
|
this.config = new Config(this.options, this.linter);
|
421
421
|
}
|
422
422
|
|
423
|
+
getRules() {
|
424
|
+
return this.linter.getRules();
|
425
|
+
}
|
426
|
+
|
423
427
|
/**
|
424
428
|
* Returns results that only contains errors.
|
425
429
|
* @param {LintResult[]} results The results to filter.
|
package/lib/linter.js
CHANGED
@@ -10,6 +10,7 @@
|
|
10
10
|
//------------------------------------------------------------------------------
|
11
11
|
|
12
12
|
const eslintScope = require("eslint-scope"),
|
13
|
+
evk = require("eslint-visitor-keys"),
|
13
14
|
levn = require("levn"),
|
14
15
|
lodash = require("lodash"),
|
15
16
|
blankScriptAST = require("../conf/blank-script.json"),
|
@@ -43,6 +44,8 @@ const MAX_AUTOFIX_PASSES = 10;
|
|
43
44
|
* @property {ASTNode} ast The ESTree AST Program node.
|
44
45
|
* @property {Object} services An object containing additional services related
|
45
46
|
* to the parser.
|
47
|
+
* @property {ScopeManager|null} scopeManager The scope manager object of this AST.
|
48
|
+
* @property {Object|null} visitorKeys The visitor keys to traverse this AST.
|
46
49
|
*/
|
47
50
|
|
48
51
|
//------------------------------------------------------------------------------
|
@@ -501,6 +504,28 @@ function getRuleOptions(ruleConfig) {
|
|
501
504
|
|
502
505
|
}
|
503
506
|
|
507
|
+
/**
|
508
|
+
* Analyze scope of the given AST.
|
509
|
+
* @param {ASTNode} ast The `Program` node to analyze.
|
510
|
+
* @param {Object} parserOptions The parser options.
|
511
|
+
* @param {Object} visitorKeys The visitor keys.
|
512
|
+
* @returns {ScopeManager} The analysis result.
|
513
|
+
*/
|
514
|
+
function analyzeScope(ast, parserOptions, visitorKeys) {
|
515
|
+
const ecmaFeatures = parserOptions.ecmaFeatures || {};
|
516
|
+
const ecmaVersion = parserOptions.ecmaVersion || 5;
|
517
|
+
|
518
|
+
return eslintScope.analyze(ast, {
|
519
|
+
ignoreEval: true,
|
520
|
+
nodejsScope: ecmaFeatures.globalReturn,
|
521
|
+
impliedStrict: ecmaFeatures.impliedStrict,
|
522
|
+
ecmaVersion,
|
523
|
+
sourceType: parserOptions.sourceType || "script",
|
524
|
+
childVisitorKeys: visitorKeys || evk.KEYS,
|
525
|
+
fallback: Traverser.getKeys
|
526
|
+
});
|
527
|
+
}
|
528
|
+
|
504
529
|
/**
|
505
530
|
* Parses text into an AST. Moved out here because the try-catch prevents
|
506
531
|
* optimization of functions, so it's best to keep the try-catch as isolated
|
@@ -509,18 +534,20 @@ function getRuleOptions(ruleConfig) {
|
|
509
534
|
* @param {Object} providedParserOptions Options to pass to the parser
|
510
535
|
* @param {Object} parser The parser module
|
511
536
|
* @param {string} filePath The path to the file being parsed.
|
512
|
-
* @returns {{success: false, error: Problem}|{success: true,
|
537
|
+
* @returns {{success: false, error: Problem}|{success: true, sourceCode: SourceCode}}
|
513
538
|
* An object containing the AST and parser services if parsing was successful, or the error if parsing failed
|
514
539
|
* @private
|
515
540
|
*/
|
516
541
|
function parse(text, providedParserOptions, parser, filePath) {
|
517
|
-
|
542
|
+
const textToParse = stripUnicodeBOM(text).replace(astUtils.SHEBANG_MATCHER, (match, captured) => `//${captured}`);
|
518
543
|
const parserOptions = Object.assign({}, providedParserOptions, {
|
519
544
|
loc: true,
|
520
545
|
range: true,
|
521
546
|
raw: true,
|
522
547
|
tokens: true,
|
523
548
|
comment: true,
|
549
|
+
eslintVisitorKeys: true,
|
550
|
+
eslintScopeManager: true,
|
524
551
|
filePath
|
525
552
|
});
|
526
553
|
|
@@ -531,20 +558,30 @@ function parse(text, providedParserOptions, parser, filePath) {
|
|
531
558
|
* problem that ESLint identified just like any other.
|
532
559
|
*/
|
533
560
|
try {
|
534
|
-
|
535
|
-
|
536
|
-
|
537
|
-
|
538
|
-
|
539
|
-
|
540
|
-
|
541
|
-
};
|
542
|
-
}
|
561
|
+
const parseResult = (typeof parser.parseForESLint === "function")
|
562
|
+
? parser.parseForESLint(textToParse, parserOptions)
|
563
|
+
: { ast: parser.parse(textToParse, parserOptions) };
|
564
|
+
const ast = parseResult.ast;
|
565
|
+
const parserServices = parseResult.services || {};
|
566
|
+
const visitorKeys = parseResult.visitorKeys || evk.KEYS;
|
567
|
+
const scopeManager = parseResult.scopeManager || analyzeScope(ast, parserOptions, visitorKeys);
|
543
568
|
|
544
569
|
return {
|
545
570
|
success: true,
|
546
|
-
|
547
|
-
|
571
|
+
|
572
|
+
/*
|
573
|
+
* Save all values that `parseForESLint()` returned.
|
574
|
+
* If a `SourceCode` object is given as the first parameter instead of source code text,
|
575
|
+
* linter skips the parsing process and reuses the source code object.
|
576
|
+
* In that case, linter needs all the values that `parseForESLint()` returned.
|
577
|
+
*/
|
578
|
+
sourceCode: new SourceCode({
|
579
|
+
text,
|
580
|
+
ast,
|
581
|
+
parserServices,
|
582
|
+
scopeManager,
|
583
|
+
visitorKeys
|
584
|
+
})
|
548
585
|
};
|
549
586
|
} catch (ex) {
|
550
587
|
|
@@ -717,7 +754,6 @@ module.exports = class Linter {
|
|
717
754
|
*/
|
718
755
|
_verifyWithoutProcessors(textOrSourceCode, config, filenameOrOptions) {
|
719
756
|
let text,
|
720
|
-
parserServices,
|
721
757
|
allowInlineConfig,
|
722
758
|
providedFilename,
|
723
759
|
reportUnusedDisableDirectives;
|
@@ -731,8 +767,6 @@ module.exports = class Linter {
|
|
731
767
|
providedFilename = filenameOrOptions;
|
732
768
|
}
|
733
769
|
|
734
|
-
const filename = typeof providedFilename === "string" ? providedFilename : "<input>";
|
735
|
-
|
736
770
|
if (typeof textOrSourceCode === "string") {
|
737
771
|
lastSourceCodes.set(this, null);
|
738
772
|
text = textOrSourceCode;
|
@@ -741,6 +775,8 @@ module.exports = class Linter {
|
|
741
775
|
text = textOrSourceCode.text;
|
742
776
|
}
|
743
777
|
|
778
|
+
const filename = typeof providedFilename === "string" ? providedFilename : "<input>";
|
779
|
+
|
744
780
|
// search and apply "eslint-env *".
|
745
781
|
const envInFile = findEslintEnv(text);
|
746
782
|
|
@@ -757,9 +793,7 @@ module.exports = class Linter {
|
|
757
793
|
// process initial config to make it safe to extend
|
758
794
|
config = prepareConfig(config, this.environments);
|
759
795
|
|
760
|
-
if (lastSourceCodes.get(this)) {
|
761
|
-
parserServices = {};
|
762
|
-
} else {
|
796
|
+
if (!lastSourceCodes.get(this)) {
|
763
797
|
|
764
798
|
// there's no input, just exit here
|
765
799
|
if (text.trim().length === 0) {
|
@@ -783,7 +817,7 @@ module.exports = class Linter {
|
|
783
817
|
}];
|
784
818
|
}
|
785
819
|
const parseResult = parse(
|
786
|
-
|
820
|
+
text,
|
787
821
|
config.parserOptions,
|
788
822
|
parser,
|
789
823
|
filename
|
@@ -793,8 +827,24 @@ module.exports = class Linter {
|
|
793
827
|
return [parseResult.error];
|
794
828
|
}
|
795
829
|
|
796
|
-
|
797
|
-
|
830
|
+
lastSourceCodes.set(this, parseResult.sourceCode);
|
831
|
+
} else {
|
832
|
+
|
833
|
+
/*
|
834
|
+
* If the given source code object as the first argument does not have scopeManager, analyze the scope.
|
835
|
+
* This is for backward compatibility (SourceCode is frozen so it cannot rebind).
|
836
|
+
*/
|
837
|
+
const lastSourceCode = lastSourceCodes.get(this);
|
838
|
+
|
839
|
+
if (!lastSourceCode.scopeManager) {
|
840
|
+
lastSourceCodes.set(this, new SourceCode({
|
841
|
+
text: lastSourceCode.text,
|
842
|
+
ast: lastSourceCode.ast,
|
843
|
+
parserServices: lastSourceCode.parserServices,
|
844
|
+
visitorKeys: lastSourceCode.visitorKeys,
|
845
|
+
scopeManager: analyzeScope(lastSourceCode.ast, config.parserOptions)
|
846
|
+
}));
|
847
|
+
}
|
798
848
|
}
|
799
849
|
|
800
850
|
const problems = [];
|
@@ -814,16 +864,7 @@ module.exports = class Linter {
|
|
814
864
|
|
815
865
|
const emitter = createEmitter();
|
816
866
|
const traverser = new Traverser();
|
817
|
-
const
|
818
|
-
const ecmaVersion = config.parserOptions.ecmaVersion || 5;
|
819
|
-
const scopeManager = eslintScope.analyze(sourceCode.ast, {
|
820
|
-
ignoreEval: true,
|
821
|
-
nodejsScope: ecmaFeatures.globalReturn,
|
822
|
-
impliedStrict: ecmaFeatures.impliedStrict,
|
823
|
-
ecmaVersion,
|
824
|
-
sourceType: config.parserOptions.sourceType || "script",
|
825
|
-
fallback: Traverser.getKeys
|
826
|
-
});
|
867
|
+
const scopeManager = sourceCode.scopeManager;
|
827
868
|
|
828
869
|
/*
|
829
870
|
* Create a frozen object with the ruleContext properties and methods that are shared by all rules.
|
@@ -842,7 +883,7 @@ module.exports = class Linter {
|
|
842
883
|
markVariableAsUsed: name => markVariableAsUsed(scopeManager, traverser.current(), config.parserOptions, name),
|
843
884
|
parserOptions: config.parserOptions,
|
844
885
|
parserPath: config.parser,
|
845
|
-
parserServices,
|
886
|
+
parserServices: sourceCode.parserServices,
|
846
887
|
settings: config.settings,
|
847
888
|
|
848
889
|
/**
|
@@ -870,6 +911,7 @@ module.exports = class Linter {
|
|
870
911
|
}
|
871
912
|
|
872
913
|
const rule = this.rules.get(ruleId);
|
914
|
+
const messageIds = rule && rule.meta && rule.meta.messages;
|
873
915
|
let reportTranslator = null;
|
874
916
|
const ruleContext = Object.freeze(
|
875
917
|
Object.assign(
|
@@ -890,7 +932,7 @@ module.exports = class Linter {
|
|
890
932
|
* with Node 8.4.0.
|
891
933
|
*/
|
892
934
|
if (reportTranslator === null) {
|
893
|
-
reportTranslator = createReportTranslator({ ruleId, severity, sourceCode });
|
935
|
+
reportTranslator = createReportTranslator({ ruleId, severity, sourceCode, messageIds });
|
894
936
|
}
|
895
937
|
const problem = reportTranslator.apply(null, arguments);
|
896
938
|
|
@@ -957,7 +999,8 @@ module.exports = class Linter {
|
|
957
999
|
},
|
958
1000
|
leave(node) {
|
959
1001
|
eventGenerator.leaveNode(node);
|
960
|
-
}
|
1002
|
+
},
|
1003
|
+
visitorKeys: sourceCode.visitorKeys
|
961
1004
|
});
|
962
1005
|
|
963
1006
|
return applyDisableDirectives({
|
package/lib/options.js
CHANGED
@@ -64,26 +64,6 @@ module.exports = optionator({
|
|
64
64
|
type: "Object",
|
65
65
|
description: "Specify parser options"
|
66
66
|
},
|
67
|
-
{
|
68
|
-
heading: "Caching"
|
69
|
-
},
|
70
|
-
{
|
71
|
-
option: "cache",
|
72
|
-
type: "Boolean",
|
73
|
-
default: "false",
|
74
|
-
description: "Only check changed files"
|
75
|
-
},
|
76
|
-
{
|
77
|
-
option: "cache-file",
|
78
|
-
type: "path::String",
|
79
|
-
default: ".eslintcache",
|
80
|
-
description: "Path to the cache file. Deprecated: use --cache-location"
|
81
|
-
},
|
82
|
-
{
|
83
|
-
option: "cache-location",
|
84
|
-
type: "path::String",
|
85
|
-
description: "Path to the cache file or directory"
|
86
|
-
},
|
87
67
|
{
|
88
68
|
heading: "Specifying rules and plugins"
|
89
69
|
},
|
@@ -102,6 +82,21 @@ module.exports = optionator({
|
|
102
82
|
type: "Object",
|
103
83
|
description: "Specify rules"
|
104
84
|
},
|
85
|
+
{
|
86
|
+
heading: "Fixing problems"
|
87
|
+
},
|
88
|
+
{
|
89
|
+
option: "fix",
|
90
|
+
type: "Boolean",
|
91
|
+
default: false,
|
92
|
+
description: "Automatically fix problems"
|
93
|
+
},
|
94
|
+
{
|
95
|
+
option: "fix-dry-run",
|
96
|
+
type: "Boolean",
|
97
|
+
default: false,
|
98
|
+
description: "Automatically fix problems without saving the changes to the file system"
|
99
|
+
},
|
105
100
|
{
|
106
101
|
heading: "Ignoring files"
|
107
102
|
},
|
@@ -176,25 +171,48 @@ module.exports = optionator({
|
|
176
171
|
description: "Force enabling/disabling of color"
|
177
172
|
},
|
178
173
|
{
|
179
|
-
heading: "
|
174
|
+
heading: "Inline configuration comments"
|
180
175
|
},
|
181
176
|
{
|
182
|
-
option: "
|
177
|
+
option: "inline-config",
|
183
178
|
type: "Boolean",
|
184
|
-
default: "
|
185
|
-
description: "
|
179
|
+
default: "true",
|
180
|
+
description: "Prevent comments from changing config or rules"
|
186
181
|
},
|
187
182
|
{
|
188
|
-
option: "
|
183
|
+
option: "report-unused-disable-directives",
|
189
184
|
type: "Boolean",
|
190
185
|
default: false,
|
191
|
-
description: "
|
186
|
+
description: "Adds reported errors for unused eslint-disable directives"
|
192
187
|
},
|
193
188
|
{
|
194
|
-
|
189
|
+
heading: "Caching"
|
190
|
+
},
|
191
|
+
{
|
192
|
+
option: "cache",
|
195
193
|
type: "Boolean",
|
196
|
-
default: false,
|
197
|
-
description: "
|
194
|
+
default: "false",
|
195
|
+
description: "Only check changed files"
|
196
|
+
},
|
197
|
+
{
|
198
|
+
option: "cache-file",
|
199
|
+
type: "path::String",
|
200
|
+
default: ".eslintcache",
|
201
|
+
description: "Path to the cache file. Deprecated: use --cache-location"
|
202
|
+
},
|
203
|
+
{
|
204
|
+
option: "cache-location",
|
205
|
+
type: "path::String",
|
206
|
+
description: "Path to the cache file or directory"
|
207
|
+
},
|
208
|
+
{
|
209
|
+
heading: "Miscellaneous"
|
210
|
+
},
|
211
|
+
{
|
212
|
+
option: "init",
|
213
|
+
type: "Boolean",
|
214
|
+
default: "false",
|
215
|
+
description: "Run config initialization wizard"
|
198
216
|
},
|
199
217
|
{
|
200
218
|
option: "debug",
|
@@ -214,18 +232,6 @@ module.exports = optionator({
|
|
214
232
|
type: "Boolean",
|
215
233
|
description: "Output the version number"
|
216
234
|
},
|
217
|
-
{
|
218
|
-
option: "inline-config",
|
219
|
-
type: "Boolean",
|
220
|
-
default: "true",
|
221
|
-
description: "Prevent comments from changing config or rules"
|
222
|
-
},
|
223
|
-
{
|
224
|
-
option: "report-unused-disable-directives",
|
225
|
-
type: "Boolean",
|
226
|
-
default: false,
|
227
|
-
description: "Adds reported errors for unused eslint-disable directives"
|
228
|
-
},
|
229
235
|
{
|
230
236
|
option: "print-config",
|
231
237
|
type: "path::String",
|
package/lib/report-translator.js
CHANGED
@@ -11,6 +11,7 @@
|
|
11
11
|
|
12
12
|
const assert = require("assert");
|
13
13
|
const ruleFixer = require("./util/rule-fixer");
|
14
|
+
const interpolate = require("./util/interpolate");
|
14
15
|
|
15
16
|
//------------------------------------------------------------------------------
|
16
17
|
// Typedefs
|
@@ -41,7 +42,9 @@ function normalizeMultiArgReportCall() {
|
|
41
42
|
|
42
43
|
// If there is one argument, it is considered to be a new-style call already.
|
43
44
|
if (arguments.length === 1) {
|
44
|
-
|
45
|
+
|
46
|
+
// Shallow clone the object to avoid surprises if reusing the descriptor
|
47
|
+
return Object.assign({}, arguments[0]);
|
45
48
|
}
|
46
49
|
|
47
50
|
// If the second argument is a string, the arguments are interpreted as [node, message, data, fix].
|
@@ -100,16 +103,7 @@ function normalizeReportLoc(descriptor) {
|
|
100
103
|
* @returns {string} The interpolated message for the descriptor
|
101
104
|
*/
|
102
105
|
function normalizeMessagePlaceholders(descriptor) {
|
103
|
-
|
104
|
-
return descriptor.message;
|
105
|
-
}
|
106
|
-
return descriptor.message.replace(/\{\{\s*([^{}]+?)\s*\}\}/g, (fullMatch, term) => {
|
107
|
-
if (term in descriptor.data) {
|
108
|
-
return descriptor.data[term];
|
109
|
-
}
|
110
|
-
|
111
|
-
return fullMatch;
|
112
|
-
});
|
106
|
+
return interpolate(descriptor.message, descriptor.data);
|
113
107
|
}
|
114
108
|
|
115
109
|
/**
|
@@ -216,6 +210,14 @@ function createProblem(options) {
|
|
216
210
|
source: options.sourceLines[options.loc.start.line - 1] || ""
|
217
211
|
};
|
218
212
|
|
213
|
+
/*
|
214
|
+
* If this isn’t in the conditional, some of the tests fail
|
215
|
+
* because `messageId` is present in the problem object
|
216
|
+
*/
|
217
|
+
if (options.messageId) {
|
218
|
+
problem.messageId = options.messageId;
|
219
|
+
}
|
220
|
+
|
219
221
|
if (options.loc.end) {
|
220
222
|
problem.endLine = options.loc.end.line;
|
221
223
|
problem.endColumn = options.loc.end.column + 1;
|
@@ -231,12 +233,13 @@ function createProblem(options) {
|
|
231
233
|
/**
|
232
234
|
* Returns a function that converts the arguments of a `context.report` call from a rule into a reported
|
233
235
|
* problem for the Node.js API.
|
234
|
-
* @param {{ruleId: string, severity: number, sourceCode: SourceCode}} metadata Metadata for the reported problem
|
236
|
+
* @param {{ruleId: string, severity: number, sourceCode: SourceCode, messageIds: Object}} metadata Metadata for the reported problem
|
235
237
|
* @param {SourceCode} sourceCode The `SourceCode` instance for the text being linted
|
236
238
|
* @returns {function(...args): {
|
237
239
|
* ruleId: string,
|
238
240
|
* severity: (0|1|2),
|
239
|
-
* message: string,
|
241
|
+
* message: (string|undefined),
|
242
|
+
* messageId: (string|undefined),
|
240
243
|
* line: number,
|
241
244
|
* column: number,
|
242
245
|
* endLine: (number|undefined),
|
@@ -261,11 +264,29 @@ module.exports = function createReportTranslator(metadata) {
|
|
261
264
|
|
262
265
|
assertValidNodeInfo(descriptor);
|
263
266
|
|
267
|
+
if (descriptor.messageId) {
|
268
|
+
if (!metadata.messageIds) {
|
269
|
+
throw new TypeError("context.report() called with a messageId, but no messages were present in the rule metadata.");
|
270
|
+
}
|
271
|
+
const id = descriptor.messageId;
|
272
|
+
const messages = metadata.messageIds;
|
273
|
+
|
274
|
+
if (descriptor.message) {
|
275
|
+
throw new TypeError("context.report() called with a message and a messageId. Please only pass one.");
|
276
|
+
}
|
277
|
+
if (!messages || !Object.prototype.hasOwnProperty.call(messages, id)) {
|
278
|
+
throw new TypeError(`context.report() called with a messageId of '${id}' which is not present in the 'messages' config: ${JSON.stringify(messages, null, 2)}`);
|
279
|
+
}
|
280
|
+
descriptor.message = messages[id];
|
281
|
+
}
|
282
|
+
|
283
|
+
|
264
284
|
return createProblem({
|
265
285
|
ruleId: metadata.ruleId,
|
266
286
|
severity: metadata.severity,
|
267
287
|
node: descriptor.node,
|
268
288
|
message: normalizeMessagePlaceholders(descriptor),
|
289
|
+
messageId: descriptor.messageId,
|
269
290
|
loc: normalizeReportLoc(descriptor),
|
270
291
|
fix: normalizeFixes(descriptor, metadata.sourceCode),
|
271
292
|
sourceLines: metadata.sourceCode.lines
|
package/lib/rules/.eslintrc.yml
CHANGED
@@ -75,7 +75,8 @@ module.exports = {
|
|
75
75
|
docs: {
|
76
76
|
description: "enforce getter and setter pairs in objects",
|
77
77
|
category: "Best Practices",
|
78
|
-
recommended: false
|
78
|
+
recommended: false,
|
79
|
+
url: "https://eslint.org/docs/rules/accessor-pairs"
|
79
80
|
},
|
80
81
|
schema: [{
|
81
82
|
type: "object",
|
@@ -16,7 +16,8 @@ module.exports = {
|
|
16
16
|
docs: {
|
17
17
|
description: "enforce linebreaks after opening and before closing array brackets",
|
18
18
|
category: "Stylistic Issues",
|
19
|
-
recommended: false
|
19
|
+
recommended: false,
|
20
|
+
url: "https://eslint.org/docs/rules/array-bracket-newline"
|
20
21
|
},
|
21
22
|
fixable: "whitespace",
|
22
23
|
schema: [
|
@@ -15,7 +15,8 @@ module.exports = {
|
|
15
15
|
docs: {
|
16
16
|
description: "enforce consistent spacing inside array brackets",
|
17
17
|
category: "Stylistic Issues",
|
18
|
-
recommended: false
|
18
|
+
recommended: false,
|
19
|
+
url: "https://eslint.org/docs/rules/array-bracket-spacing"
|
19
20
|
},
|
20
21
|
fixable: "whitespace",
|
21
22
|
schema: [
|
@@ -142,13 +142,27 @@ module.exports = {
|
|
142
142
|
docs: {
|
143
143
|
description: "enforce `return` statements in callbacks of array methods",
|
144
144
|
category: "Best Practices",
|
145
|
-
recommended: false
|
145
|
+
recommended: false,
|
146
|
+
url: "https://eslint.org/docs/rules/array-callback-return"
|
146
147
|
},
|
147
148
|
|
148
|
-
schema: [
|
149
|
+
schema: [
|
150
|
+
{
|
151
|
+
type: "object",
|
152
|
+
properties: {
|
153
|
+
allowImplicit: {
|
154
|
+
type: "boolean"
|
155
|
+
}
|
156
|
+
},
|
157
|
+
additionalProperties: false
|
158
|
+
}
|
159
|
+
]
|
149
160
|
},
|
150
161
|
|
151
162
|
create(context) {
|
163
|
+
|
164
|
+
const options = context.options[0] || { allowImplicit: false };
|
165
|
+
|
152
166
|
let funcInfo = {
|
153
167
|
upper: null,
|
154
168
|
codePath: null,
|
@@ -212,7 +226,8 @@ module.exports = {
|
|
212
226
|
if (funcInfo.shouldCheck) {
|
213
227
|
funcInfo.hasReturn = true;
|
214
228
|
|
215
|
-
if
|
229
|
+
// if allowImplicit: false, should also check node.argument
|
230
|
+
if (!options.allowImplicit && !node.argument) {
|
216
231
|
context.report({
|
217
232
|
node,
|
218
233
|
message: "{{name}} expected a return value.",
|
@@ -16,7 +16,8 @@ module.exports = {
|
|
16
16
|
docs: {
|
17
17
|
description: "enforce line breaks after each array element",
|
18
18
|
category: "Stylistic Issues",
|
19
|
-
recommended: false
|
19
|
+
recommended: false,
|
20
|
+
url: "https://eslint.org/docs/rules/array-element-newline"
|
20
21
|
},
|
21
22
|
fixable: "whitespace",
|
22
23
|
schema: [
|
@@ -19,7 +19,8 @@ module.exports = {
|
|
19
19
|
docs: {
|
20
20
|
description: "require braces around arrow function bodies",
|
21
21
|
category: "ECMAScript 6",
|
22
|
-
recommended: false
|
22
|
+
recommended: false,
|
23
|
+
url: "https://eslint.org/docs/rules/arrow-body-style"
|
23
24
|
},
|
24
25
|
|
25
26
|
schema: {
|
@@ -109,10 +110,22 @@ module.exports = {
|
|
109
110
|
}
|
110
111
|
|
111
112
|
if (never || asNeeded && blockBody[0].type === "ReturnStatement") {
|
113
|
+
let message;
|
114
|
+
|
115
|
+
if (blockBody.length === 0) {
|
116
|
+
message = "Unexpected block statement surrounding arrow body; put a value of `undefined` immediately after the `=>`.";
|
117
|
+
} else if (blockBody.length > 1) {
|
118
|
+
message = "Unexpected block statement surrounding arrow body.";
|
119
|
+
} else if (astUtils.isOpeningBraceToken(sourceCode.getFirstToken(blockBody[0], { skip: 1 }))) {
|
120
|
+
message = "Unexpected block statement surrounding arrow body; parenthesize the returned value and move it immediately after the `=>`.";
|
121
|
+
} else {
|
122
|
+
message = "Unexpected block statement surrounding arrow body; move the returned value immediately after the `=>`.";
|
123
|
+
}
|
124
|
+
|
112
125
|
context.report({
|
113
126
|
node,
|
114
127
|
loc: arrowBody.loc.start,
|
115
|
-
message
|
128
|
+
message,
|
116
129
|
fix(fixer) {
|
117
130
|
const fixes = [];
|
118
131
|
|