From 48c6b76402ba4431297ce8715ac1336266d7995c Mon Sep 17 00:00:00 2001 From: Yosuke Ota Date: Mon, 25 May 2020 13:27:43 +0900 Subject: [PATCH 1/4] Introduce Prettier and update eslint config --- .eslintrc.js | 88 ++- .prettierrc | 4 + docs/.vuepress/config.js | 74 +- .../consistent-docs-description.js | 42 +- .../no-invalid-meta-docs-categories.js | 62 +- eslint-internal-rules/no-invalid-meta.js | 50 +- .../require-meta-docs-url.js | 142 ++-- lib/configs/base.js | 4 +- lib/index.js | 10 +- lib/processor.js | 6 +- lib/rules/attribute-hyphenation.js | 39 +- lib/rules/attributes-order.js | 6 +- lib/rules/block-spacing.js | 7 +- lib/rules/brace-style.js | 8 +- lib/rules/comma-spacing.js | 8 +- lib/rules/comma-style.js | 15 +- lib/rules/comment-directive.js | 63 +- lib/rules/component-definition-name-casing.js | 40 +- .../component-name-in-template-casing.js | 128 +-- lib/rules/component-tags-order.js | 22 +- lib/rules/html-closing-bracket-newline.js | 72 +- lib/rules/html-closing-bracket-spacing.js | 81 +- lib/rules/html-comment-content-newline.js | 93 ++- lib/rules/html-comment-content-spacing.js | 47 +- lib/rules/html-comment-indent.js | 86 ++- lib/rules/html-end-tags.js | 52 +- lib/rules/html-indent.js | 27 +- lib/rules/html-quotes.js | 91 ++- lib/rules/html-self-closing.js | 165 ++-- lib/rules/jsx-uses-vars.js | 4 +- lib/rules/key-spacing.js | 7 +- lib/rules/keyword-spacing.js | 7 +- lib/rules/match-component-file-name.js | 42 +- lib/rules/max-attributes-per-line.js | 30 +- lib/rules/max-len.js | 167 ++-- .../multiline-html-element-content-newline.js | 119 +-- lib/rules/mustache-interpolation-spacing.js | 18 +- lib/rules/name-property-casing.js | 22 +- lib/rules/no-arrow-functions-in-watch.js | 11 +- lib/rules/no-async-in-computed-properties.js | 110 +-- lib/rules/no-boolean-default.js | 24 +- lib/rules/no-confusing-v-for-v-if.js | 14 +- lib/rules/no-custom-modifiers-on-v-model.js | 7 +- .../no-deprecated-data-object-declaration.js | 36 +- .../no-deprecated-dollar-listeners-api.js | 41 +- lib/rules/no-deprecated-events-api.js | 43 +- lib/rules/no-deprecated-filter.js | 7 +- .../no-deprecated-functional-template.js | 10 +- lib/rules/no-deprecated-html-element-is.js | 9 +- lib/rules/no-deprecated-inline-template.js | 9 +- lib/rules/no-deprecated-scope-attribute.js | 6 +- lib/rules/no-deprecated-slot-attribute.js | 2 +- .../no-deprecated-slot-scope-attribute.js | 13 +- lib/rules/no-deprecated-v-bind-sync.js | 16 +- .../no-deprecated-v-on-native-modifier.js | 12 +- .../no-deprecated-v-on-number-modifiers.js | 21 +- .../no-deprecated-vue-config-keycodes.js | 18 +- lib/rules/no-dupe-keys.js | 2 +- lib/rules/no-duplicate-attr-inheritance.js | 17 +- lib/rules/no-duplicate-attributes.js | 15 +- lib/rules/no-extra-parens.js | 63 +- lib/rules/no-irregular-whitespace.js | 71 +- lib/rules/no-lifecycle-after-await.js | 92 ++- lib/rules/no-multi-spaces.js | 49 +- lib/rules/no-multiple-template-root.js | 4 +- lib/rules/no-mutating-props.js | 171 ++-- lib/rules/no-parsing-error.js | 82 +- .../no-potential-component-option-typo.js | 27 +- lib/rules/no-ref-as-operand.js | 48 +- lib/rules/no-reserved-component-names.js | 80 +- lib/rules/no-reserved-keys.js | 5 +- lib/rules/no-setup-props-destructure.js | 41 +- lib/rules/no-shared-component-data.js | 27 +- .../no-side-effects-in-computed-properties.js | 37 +- ...-spaces-around-equal-signs-in-attribute.js | 9 +- lib/rules/no-static-inline-styles.js | 10 +- lib/rules/no-template-key.js | 14 +- lib/rules/no-template-shadow.js | 75 +- lib/rules/no-template-target-blank.js | 77 +- lib/rules/no-textarea-mustache.js | 4 +- lib/rules/no-unregistered-components.js | 189 +++-- lib/rules/no-unsupported-features.js | 26 +- lib/rules/no-unused-components.js | 165 ++-- lib/rules/no-unused-properties.js | 99 ++- lib/rules/no-unused-vars.js | 47 +- lib/rules/no-use-v-if-with-v-for.js | 45 +- lib/rules/no-v-html.js | 4 +- lib/rules/no-v-model-argument.js | 7 +- lib/rules/no-watch-after-await.js | 74 +- lib/rules/one-component-per-file.js | 9 +- lib/rules/padding-line-between-blocks.js | 38 +- lib/rules/prefer-template.js | 4 +- lib/rules/prop-name-casing.js | 25 +- lib/rules/require-component-is.js | 7 +- lib/rules/require-default-prop.js | 101 ++- lib/rules/require-explicit-emits.js | 177 +++-- lib/rules/require-name-property.js | 10 +- lib/rules/require-prop-type-constructor.js | 47 +- lib/rules/require-prop-types.js | 33 +- lib/rules/require-render-return.js | 30 +- lib/rules/require-toggle-inside-transition.js | 22 +- lib/rules/require-v-for-key.js | 14 +- lib/rules/require-valid-default-prop.js | 217 +++--- lib/rules/return-in-computed-property.js | 52 +- lib/rules/return-in-emits-validator.js | 106 +-- lib/rules/script-indent.js | 17 +- ...singleline-html-element-content-newline.js | 103 ++- lib/rules/sort-keys.js | 69 +- lib/rules/space-in-parens.js | 8 +- lib/rules/space-infix-ops.js | 7 +- lib/rules/space-unary-ops.js | 7 +- lib/rules/static-class-names-order.js | 22 +- .../syntaxes/dynamic-directive-arguments.js | 4 +- lib/rules/syntaxes/scope-attribute.js | 6 +- lib/rules/syntaxes/slot-attribute.js | 49 +- lib/rules/syntaxes/slot-scope-attribute.js | 41 +- .../v-bind-prop-modifier-shorthand.js | 10 +- lib/rules/syntaxes/v-slot.js | 19 +- lib/rules/this-in-template.js | 117 +-- lib/rules/use-v-on-exact.js | 67 +- lib/rules/v-bind-style.js | 24 +- lib/rules/v-on-function-call.js | 49 +- lib/rules/v-on-style.js | 17 +- lib/rules/v-slot-style.js | 20 +- lib/rules/valid-template-root.js | 7 +- lib/rules/valid-v-bind-sync.js | 25 +- lib/rules/valid-v-bind.js | 7 +- lib/rules/valid-v-cloak.js | 4 +- lib/rules/valid-v-else-if.js | 13 +- lib/rules/valid-v-else.js | 13 +- lib/rules/valid-v-for.js | 32 +- lib/rules/valid-v-html.js | 4 +- lib/rules/valid-v-if.js | 10 +- lib/rules/valid-v-model.js | 36 +- lib/rules/valid-v-on.js | 50 +- lib/rules/valid-v-once.js | 4 +- lib/rules/valid-v-pre.js | 4 +- lib/rules/valid-v-show.js | 4 +- lib/rules/valid-v-slot.js | 135 ++-- lib/rules/valid-v-text.js | 4 +- lib/utils/casing.js | 64 +- lib/utils/html-comments.js | 49 +- lib/utils/indent-common.js | 4 +- lib/utils/index.js | 6 +- lib/utils/regexp.js | 6 +- package.json | 3 + tests/integrations/eslint-plugin-import.js | 10 +- tests/lib/autofix.js | 72 +- tests/lib/rules/attribute-hyphenation.js | 214 ++--- tests/lib/rules/attributes-order.js | 6 +- tests/lib/rules/block-spacing.js | 12 +- tests/lib/rules/brace-style.js | 17 +- tests/lib/rules/camelcase.js | 4 +- tests/lib/rules/comma-dangle.js | 24 +- tests/lib/rules/comma-spacing.js | 44 +- tests/lib/rules/comma-style.js | 10 +- tests/lib/rules/comment-directive.js | 73 +- .../rules/component-definition-name-casing.js | 181 +++-- .../component-name-in-template-casing.js | 114 ++- tests/lib/rules/component-tags-order.js | 6 +- tests/lib/rules/eqeqeq.js | 4 +- .../lib/rules/html-closing-bracket-newline.js | 120 +-- .../lib/rules/html-closing-bracket-spacing.js | 87 ++- .../lib/rules/html-comment-content-newline.js | 104 ++- .../lib/rules/html-comment-content-spacing.js | 58 +- tests/lib/rules/html-comment-indent.js | 571 +++++++------- tests/lib/rules/html-quotes.js | 20 +- tests/lib/rules/html-self-closing.js | 81 +- tests/lib/rules/jsx-uses-vars.js | 38 +- tests/lib/rules/key-spacing.js | 4 +- tests/lib/rules/keyword-spacing.js | 24 +- tests/lib/rules/match-component-file-name.js | 126 ++- tests/lib/rules/max-attributes-per-line.js | 162 ++-- tests/lib/rules/max-len.js | 44 +- .../multiline-html-element-content-newline.js | 46 +- .../rules/mustache-interpolation-spacing.js | 7 +- tests/lib/rules/name-property-casing.js | 85 +- .../lib/rules/no-arrow-functions-in-watch.js | 30 +- .../rules/no-async-in-computed-properties.js | 206 +++-- tests/lib/rules/no-boolean-default.js | 49 +- tests/lib/rules/no-confusing-v-for-v-if.js | 18 +- .../rules/no-custom-modifiers-on-v-model.js | 1 - .../no-deprecated-data-object-declaration.js | 67 +- .../no-deprecated-dollar-listeners-api.js | 1 - tests/lib/rules/no-deprecated-events-api.js | 45 +- tests/lib/rules/no-deprecated-filter.js | 6 +- .../rules/no-deprecated-inline-template.js | 15 +- tests/lib/rules/no-deprecated-v-bind-sync.js | 148 ++-- .../no-deprecated-v-on-native-modifier.js | 1 - .../no-deprecated-v-on-number-modifiers.js | 104 ++- .../no-deprecated-vue-config-keycodes.js | 21 +- tests/lib/rules/no-dupe-keys.js | 207 +++-- .../rules/no-duplicate-attr-inheritance.js | 7 +- tests/lib/rules/no-duplicate-attributes.js | 3 +- tests/lib/rules/no-empty-pattern.js | 1 - tests/lib/rules/no-extra-parens.js | 12 +- tests/lib/rules/no-irregular-whitespace.js | 281 ++++--- tests/lib/rules/no-lifecycle-after-await.js | 3 +- tests/lib/rules/no-multi-spaces.js | 59 +- tests/lib/rules/no-multiple-template-root.js | 13 +- tests/lib/rules/no-mutating-props.js | 9 +- tests/lib/rules/no-parsing-error.js | 41 +- tests/lib/rules/no-ref-as-operand.js | 9 +- .../lib/rules/no-reserved-component-names.js | 731 ++++++++++++------ tests/lib/rules/no-reserved-keys.js | 60 +- tests/lib/rules/no-restricted-syntax.js | 41 +- tests/lib/rules/no-shared-component-data.js | 41 +- .../no-side-effects-in-computed-properties.js | 100 ++- ...-spaces-around-equal-signs-in-attribute.js | 12 +- tests/lib/rules/no-template-key.js | 15 +- tests/lib/rules/no-template-shadow.js | 152 ++-- tests/lib/rules/no-template-target-blank.js | 59 +- tests/lib/rules/no-textarea-mustache.js | 6 +- tests/lib/rules/no-unregistered-components.js | 137 ++-- tests/lib/rules/no-unsupported-features.js | 1 - .../dynamic-directive-arguments.js | 6 +- .../slot-scope-attribute.js | 5 +- .../rules/no-unsupported-features/utils.js | 4 +- .../v-bind-prop-modifier-shorthand.js | 12 +- .../rules/no-unsupported-features/v-slot.js | 1 - tests/lib/rules/no-unused-components.js | 101 ++- tests/lib/rules/no-unused-properties.js | 27 +- tests/lib/rules/no-unused-vars.js | 58 +- tests/lib/rules/no-use-v-if-with-v-for.js | 148 ++-- tests/lib/rules/no-v-model-argument.js | 7 +- tests/lib/rules/prop-name-casing.js | 134 ++-- tests/lib/rules/require-default-prop.js | 125 +-- tests/lib/rules/require-explicit-emits.js | 96 ++- tests/lib/rules/require-name-property.js | 40 +- .../rules/require-prop-type-constructor.js | 97 ++- tests/lib/rules/require-prop-types.js | 115 +-- tests/lib/rules/require-render-return.js | 72 +- .../rules/require-toggle-inside-transition.js | 30 +- tests/lib/rules/require-v-for-key.js | 27 +- tests/lib/rules/require-valid-default-prop.js | 68 +- .../lib/rules/return-in-computed-property.js | 82 +- tests/lib/rules/return-in-emits-validator.js | 82 +- ...singleline-html-element-content-newline.js | 30 +- tests/lib/rules/sort-keys.js | 625 +++++++++++---- tests/lib/rules/space-in-parens.js | 14 +- tests/lib/rules/space-infix-ops.js | 2 +- tests/lib/rules/space-unary-ops.js | 8 +- tests/lib/rules/static-class-names-order.js | 23 +- tests/lib/rules/this-in-template.js | 55 +- tests/lib/rules/use-v-on-exact.js | 37 +- tests/lib/rules/v-on-function-call.js | 16 +- tests/lib/rules/v-slot-style.js | 112 ++- tests/lib/rules/valid-template-root.js | 17 +- tests/lib/rules/valid-v-bind-sync.js | 190 +++-- tests/lib/rules/valid-v-else-if.js | 65 +- tests/lib/rules/valid-v-else.js | 59 +- tests/lib/rules/valid-v-for.js | 126 ++- tests/lib/rules/valid-v-if.js | 11 +- tests/lib/rules/valid-v-model.js | 80 +- tests/lib/rules/valid-v-on.js | 8 +- tests/lib/rules/valid-v-slot.js | 10 +- tests/lib/utils/html-comments.js | 38 +- tests/lib/utils/index.js | 53 +- tools/lib/categories.js | 68 +- tools/lib/configs.js | 8 +- tools/lib/rules.js | 34 +- tools/update-docs-rules-index.js | 24 +- tools/update-docs.js | 51 +- tools/update-lib-configs.js | 14 +- tools/update-lib-index.js | 8 +- tools/update-no-layout-rules-config.js | 4 +- 266 files changed, 8717 insertions(+), 5555 deletions(-) create mode 100644 .prettierrc diff --git a/.eslintrc.js b/.eslintrc.js index e89fc7ff3..f45e3ef28 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -1,8 +1,7 @@ 'use strict' module.exports = { - // https://github.com/eslint/eslint/issues/11888 - root: false, + root: true, parserOptions: { ecmaVersion: 6 }, @@ -12,28 +11,79 @@ module.exports = { }, extends: [ 'plugin:eslint-plugin/recommended', - 'plugin:vue-libs/recommended' - ], - plugins: [ - 'eslint-plugin' + 'plugin:vue-libs/recommended', + 'prettier' ], + plugins: ['eslint-plugin', 'prettier'], rules: { - 'eslint-plugin/report-message-format': ['error', '^[A-Z`\'{].*\\.$'], + 'prettier/prettier': 'error', + 'eslint-plugin/report-message-format': ['error', "^[A-Z`'{].*\\.$"], 'eslint-plugin/prefer-placeholders': 'error', 'eslint-plugin/consistent-output': 'error', - 'no-mixed-operators': 'error' + + 'no-debugger': 'error', + 'no-console': 'error', + 'no-alert': 'error', + 'no-void': 'error', + + 'no-warning-comments': 'warn', + 'no-var': 'error', + 'prefer-template': 'error', + 'object-shorthand': 'error', + 'prefer-rest-params': 'error', + 'prefer-arrow-callback': 'error', + 'prefer-spread': 'error', + + 'dot-notation': 'error' }, + overrides: [ + // Introduce prettier. but ignore files to avoid conflicts with PR. + { + files: [ + // https://github.com/vuejs/eslint-plugin-vue/pull/1107 + 'lib/rules/order-in-components.js', + 'tests/lib/rules/order-in-components.js', + // https://github.com/vuejs/eslint-plugin-vue/pull/1090 + 'lib/rules/require-direct-export.js', + 'tests/lib/rules/require-direct-export.js', + 'lib/utils/index.js', + 'tests/lib/utils/vue-component.js', + // https://github.com/vuejs/eslint-plugin-vue/pull/1017 + 'lib/utils/indent-common.js', + 'tests/lib/rules/html-indent.js', + 'tests/lib/rules/script-indent.js', + // https://github.com/vuejs/eslint-plugin-vue/pull/982 + 'lib/rules/attributes-order.js', + 'tests/lib/rules/attributes-order.js', + // https://github.com/vuejs/eslint-plugin-vue/pull/819 + 'lib/rules/attributes-order.js', + 'tests/lib/rules/attributes-order.js' + ], + extends: [ + 'plugin:eslint-plugin/recommended', + 'plugin:vue-libs/recommended' + ], + rules: { + 'prettier/prettier': 'off', - overrides: [{ - files: ['lib/rules/*.js'], - rules: { - 'consistent-docs-description': 'error', - 'no-invalid-meta': 'error', - 'no-invalid-meta-docs-categories': 'error', - 'eslint-plugin/require-meta-type': 'error', - 'require-meta-docs-url': ['error', { - 'pattern': `https://eslint.vuejs.org/rules/{{name}}.html` - }] + 'rest-spread-spacing': 'error', + 'no-mixed-operators': 'error' + } + }, + { + files: ['lib/rules/*.js'], + rules: { + 'consistent-docs-description': 'error', + 'no-invalid-meta': 'error', + 'no-invalid-meta-docs-categories': 'error', + 'eslint-plugin/require-meta-type': 'error', + 'require-meta-docs-url': [ + 'error', + { + pattern: `https://eslint.vuejs.org/rules/{{name}}.html` + } + ] + } } - }] + ] } diff --git a/.prettierrc b/.prettierrc new file mode 100644 index 000000000..38d9aa9aa --- /dev/null +++ b/.prettierrc @@ -0,0 +1,4 @@ +semi: false +singleQuote: true +printWidth: 80 +trailingComma: none diff --git a/docs/.vuepress/config.js b/docs/.vuepress/config.js index 1bc13cdac..143b203d9 100644 --- a/docs/.vuepress/config.js +++ b/docs/.vuepress/config.js @@ -6,32 +6,62 @@ const rules = require('../../tools/lib/rules') -const uncategorizedRules = rules.filter(rule => !rule.meta.docs.categories && !rule.meta.deprecated) -const deprecatedRules = rules.filter(rule => rule.meta.deprecated) +const uncategorizedRules = rules.filter( + (rule) => !rule.meta.docs.categories && !rule.meta.deprecated +) +const deprecatedRules = rules.filter((rule) => rule.meta.deprecated) const sidebarCategories = [ { title: 'Base Rules', categoryIds: ['base'] }, - { title: 'Priority A: Essential', categoryIds: ['vue3-essential', 'essential'] }, - { title: 'Priority A: Essential for Vue.js 3.x', categoryIds: ['vue3-essential'] }, + { + title: 'Priority A: Essential', + categoryIds: ['vue3-essential', 'essential'] + }, + { + title: 'Priority A: Essential for Vue.js 3.x', + categoryIds: ['vue3-essential'] + }, { title: 'Priority A: Essential for Vue.js 2.x', categoryIds: ['essential'] }, - { title: 'Priority B: Strongly Recommended', categoryIds: ['vue3-strongly-recommended', 'strongly-recommended'] }, - { title: 'Priority B: Strongly Recommended for Vue.js 3.x', categoryIds: ['vue3-strongly-recommended'] }, - { title: 'Priority B: Strongly Recommended for Vue.js 2.x', categoryIds: ['strongly-recommended'] }, - { title: 'Priority C: Recommended', categoryIds: ['vue3-recommended', 'recommended'] }, - { title: 'Priority C: Recommended for Vue.js 3.x', categoryIds: ['vue3-recommended'] }, - { title: 'Priority C: Recommended for Vue.js 2.x', categoryIds: ['recommended'] } + { + title: 'Priority B: Strongly Recommended', + categoryIds: ['vue3-strongly-recommended', 'strongly-recommended'] + }, + { + title: 'Priority B: Strongly Recommended for Vue.js 3.x', + categoryIds: ['vue3-strongly-recommended'] + }, + { + title: 'Priority B: Strongly Recommended for Vue.js 2.x', + categoryIds: ['strongly-recommended'] + }, + { + title: 'Priority C: Recommended', + categoryIds: ['vue3-recommended', 'recommended'] + }, + { + title: 'Priority C: Recommended for Vue.js 3.x', + categoryIds: ['vue3-recommended'] + }, + { + title: 'Priority C: Recommended for Vue.js 2.x', + categoryIds: ['recommended'] + } ] const categorizedRules = [] for (const { title, categoryIds } of sidebarCategories) { const categoryRules = rules - .filter(rule => rule.meta.docs.categories && !rule.meta.deprecated) - .filter(rule => categoryIds - .every(categoryId => rule.meta.docs.categories.includes(categoryId)) + .filter((rule) => rule.meta.docs.categories && !rule.meta.deprecated) + .filter((rule) => + categoryIds.every((categoryId) => + rule.meta.docs.categories.includes(categoryId) + ) ) const children = categoryRules .filter(({ ruleId }) => { - const exists = categorizedRules.some(({ children }) => children.some(([, alreadyRuleId]) => alreadyRuleId === ruleId)) + const exists = categorizedRules.some(({ children }) => + children.some(([, alreadyRuleId]) => alreadyRuleId === ruleId) + ) return !exists }) .map(({ ruleId, name }) => [`/rules/${name}`, ruleId]) @@ -51,19 +81,25 @@ if (uncategorizedRules.length > 0) { extraCategories.push({ title: 'Uncategorized', collapsable: false, - children: uncategorizedRules.map(({ ruleId, name }) => [`/rules/${name}`, ruleId]) + children: uncategorizedRules.map(({ ruleId, name }) => [ + `/rules/${name}`, + ruleId + ]) }) } if (deprecatedRules.length > 0) { extraCategories.push({ title: 'Deprecated', collapsable: false, - children: deprecatedRules.map(({ ruleId, name }) => [`/rules/${name}`, ruleId]) + children: deprecatedRules.map(({ ruleId, name }) => [ + `/rules/${name}`, + ruleId + ]) }) } module.exports = { - configureWebpack (_config, _isServer) { + configureWebpack(_config, _isServer) { return { resolve: { alias: { @@ -77,9 +113,7 @@ module.exports = { title: 'eslint-plugin-vue', description: 'Official ESLint plugin for Vue.js', evergreen: true, - head: [ - ['link', { rel: 'icon', href: '/favicon.png' }] - ], + head: [['link', { rel: 'icon', href: '/favicon.png' }]], plugins: { '@vuepress/pwa': { diff --git a/eslint-internal-rules/consistent-docs-description.js b/eslint-internal-rules/consistent-docs-description.js index 6a6e4b9c4..6ff7f8673 100644 --- a/eslint-internal-rules/consistent-docs-description.js +++ b/eslint-internal-rules/consistent-docs-description.js @@ -5,11 +5,7 @@ 'use strict' -const ALLOWED_FIRST_WORDS = [ - 'enforce', - 'require', - 'disallow' -] +const ALLOWED_FIRST_WORDS = ['enforce', 'require', 'disallow'] // ------------------------------------------------------------------------------ // Helpers @@ -22,7 +18,7 @@ const ALLOWED_FIRST_WORDS = [ * @param {ASTNode} node The ObjectExpression node. * @returns {ASTNode} The Property node or null if not found. */ -function getPropertyFromObject (property, node) { +function getPropertyFromObject(property, node) { if (node && node.type === 'ObjectExpression') { const properties = node.properties @@ -42,15 +38,17 @@ function getPropertyFromObject (property, node) { * @param {ASTNode} exportsNode ObjectExpression node that the rule exports. * @returns {void} */ -function checkMetaDocsDescription (context, exportsNode) { +function checkMetaDocsDescription(context, exportsNode) { if (exportsNode.type !== 'ObjectExpression') { // if the exported node is not the correct format, "internal-no-invalid-meta" will already report this. return } const metaProperty = getPropertyFromObject('meta', exportsNode) - const metaDocs = metaProperty && getPropertyFromObject('docs', metaProperty.value) - const metaDocsDescription = metaDocs && getPropertyFromObject('description', metaDocs.value) + const metaDocs = + metaProperty && getPropertyFromObject('docs', metaProperty.value) + const metaDocsDescription = + metaDocs && getPropertyFromObject('description', metaDocs.value) if (!metaDocsDescription) { // if there is no `meta.docs.description` property, "internal-no-invalid-meta" will already report this. @@ -88,7 +86,8 @@ function checkMetaDocsDescription (context, exportsNode) { if (ALLOWED_FIRST_WORDS.indexOf(firstWord) === -1) { context.report({ node: metaDocsDescription.value, - message: '`meta.docs.description` should start with one of the following words: {{ allowedWords }}. Started with "{{ firstWord }}" instead.', + message: + '`meta.docs.description` should start with one of the following words: {{ allowedWords }}. Started with "{{ firstWord }}" instead.', data: { allowedWords: ALLOWED_FIRST_WORDS.join(', '), firstWord @@ -100,7 +99,7 @@ function checkMetaDocsDescription (context, exportsNode) { context.report({ node: metaDocsDescription.value, message: '`meta.docs.description` should not end with `.`.', - fix (fixer) { + fix(fixer) { const pos = metaDocsDescription.range[1] - 2 return fixer.removeRange([pos, pos + 1]) } @@ -115,22 +114,25 @@ function checkMetaDocsDescription (context, exportsNode) { module.exports = { meta: { docs: { - description: 'enforce correct conventions of `meta.docs.description` property in core rules', + description: + 'enforce correct conventions of `meta.docs.description` property in core rules', categories: ['Internal'] }, fixable: 'code', schema: [] }, - create (context) { + create(context) { return { - AssignmentExpression (node) { - if (node.left && - node.right && - node.left.type === 'MemberExpression' && - node.left.object.name === 'module' && - node.left.property.name === 'exports' && - node.right.type === 'ObjectExpression') { + AssignmentExpression(node) { + if ( + node.left && + node.right && + node.left.type === 'MemberExpression' && + node.left.object.name === 'module' && + node.left.property.name === 'exports' && + node.right.type === 'ObjectExpression' + ) { checkMetaDocsDescription(context, node.right) } } diff --git a/eslint-internal-rules/no-invalid-meta-docs-categories.js b/eslint-internal-rules/no-invalid-meta-docs-categories.js index 5332cfe56..74cfff1cd 100644 --- a/eslint-internal-rules/no-invalid-meta-docs-categories.js +++ b/eslint-internal-rules/no-invalid-meta-docs-categories.js @@ -16,7 +16,7 @@ * @param {ASTNode} node The ObjectExpression node. * @returns {ASTNode} The Property node or null if not found. */ -function getPropertyFromObject (property, node) { +function getPropertyFromObject(property, node) { if (node && node.type === 'ObjectExpression') { const properties = node.properties @@ -35,7 +35,7 @@ function getPropertyFromObject (property, node) { * @param {ASTNode} exportsNode ObjectExpression node that the rule exports. * @returns {ASTNode} The `meta` Property node or null if not found. */ -function getMetaPropertyFromExportsNode (exportsNode) { +function getMetaPropertyFromExportsNode(exportsNode) { return getPropertyFromObject('meta', exportsNode) } @@ -47,7 +47,7 @@ function getMetaPropertyFromExportsNode (exportsNode) { * @param {boolean} ruleIsFixable whether the rule is fixable or not. * @returns {void} */ -function checkMetaValidity (context, exportsNode) { +function checkMetaValidity(context, exportsNode) { const metaProperty = getMetaPropertyFromExportsNode(exportsNode) if (!metaProperty) { return @@ -63,18 +63,27 @@ function checkMetaValidity (context, exportsNode) { context.report({ node: metaDocs, message: 'Rule is missing a meta.docs.categories property.', - fix (fixer) { + fix(fixer) { const category = getPropertyFromObject('category', metaDocs.value) if (!category) { return null } const fixes = [fixer.replaceText(category.key, 'categories')] - if (category.value && category.value.type === 'Literal' && typeof category.value.value === 'string') { + if ( + category.value && + category.value.type === 'Literal' && + typeof category.value.value === 'string' + ) { // fixes.push(fixer.insertTextBefore(category.value, '['), fixer.insertTextAfter(category.value, ']')) // for vue3 migration if (category.value.value !== 'base') { - fixes.push(fixer.insertTextBefore(category.value, `['vue3-${category.value.value}', `)) + fixes.push( + fixer.insertTextBefore( + category.value, + `['vue3-${category.value.value}', ` + ) + ) } else { fixes.push(fixer.insertTextBefore(category.value, '[')) } @@ -86,12 +95,15 @@ function checkMetaValidity (context, exportsNode) { return } - if (categories.value && - ( - categories.value.type !== 'ArrayExpression' && - !(categories.value.type === 'Literal' && categories.value.value == null) && - !(categories.value.type === 'Identifier' && categories.value.name === 'undefined') - )) { + if ( + categories.value && + categories.value.type !== 'ArrayExpression' && + !(categories.value.type === 'Literal' && categories.value.value == null) && + !( + categories.value.type === 'Identifier' && + categories.value.name === 'undefined' + ) + ) { context.report(categories.value, 'meta.docs.categories must be an array.') } } @@ -102,7 +114,7 @@ function checkMetaValidity (context, exportsNode) { * @param {ASTNode} node node that the rule exports. * @returns {boolean} `true` if the exported node is the correct format for a rule definition */ -function isCorrectExportsFormat (node) { +function isCorrectExportsFormat(node) { return node != null && node.type === 'ObjectExpression' } @@ -120,23 +132,29 @@ module.exports = { schema: [] }, - create (context) { + create(context) { let exportsNode return { - AssignmentExpression (node) { - if (node.left && - node.right && - node.left.type === 'MemberExpression' && - node.left.object.name === 'module' && - node.left.property.name === 'exports') { + AssignmentExpression(node) { + if ( + node.left && + node.right && + node.left.type === 'MemberExpression' && + node.left.object.name === 'module' && + node.left.property.name === 'exports' + ) { exportsNode = node.right } }, - 'Program:exit' (programNode) { + 'Program:exit'(programNode) { if (!isCorrectExportsFormat(exportsNode)) { - context.report({ node: exportsNode || programNode, message: 'Rule does not export an Object. Make sure the rule follows the new rule format.' }) + context.report({ + node: exportsNode || programNode, + message: + 'Rule does not export an Object. Make sure the rule follows the new rule format.' + }) return } diff --git a/eslint-internal-rules/no-invalid-meta.js b/eslint-internal-rules/no-invalid-meta.js index 8d3818984..a032023f9 100644 --- a/eslint-internal-rules/no-invalid-meta.js +++ b/eslint-internal-rules/no-invalid-meta.js @@ -16,7 +16,7 @@ * @param {ASTNode} node The ObjectExpression node. * @returns {ASTNode} The Property node or null if not found. */ -function getPropertyFromObject (property, node) { +function getPropertyFromObject(property, node) { if (node && node.type === 'ObjectExpression') { const properties = node.properties @@ -35,7 +35,7 @@ function getPropertyFromObject (property, node) { * @param {ASTNode} exportsNode ObjectExpression node that the rule exports. * @returns {ASTNode} The `meta` Property node or null if not found. */ -function getMetaPropertyFromExportsNode (exportsNode) { +function getMetaPropertyFromExportsNode(exportsNode) { return getPropertyFromObject('meta', exportsNode) } @@ -45,7 +45,7 @@ function getMetaPropertyFromExportsNode (exportsNode) { * @param {ASTNode} metaPropertyNode The `meta` ObjectExpression for this rule. * @returns {boolean} `true` if a `docs` property exists. */ -function hasMetaDocs (metaPropertyNode) { +function hasMetaDocs(metaPropertyNode) { return Boolean(getPropertyFromObject('docs', metaPropertyNode.value)) } @@ -55,7 +55,7 @@ function hasMetaDocs (metaPropertyNode) { * @param {ASTNode} metaPropertyNode The `meta` ObjectExpression for this rule. * @returns {boolean} `true` if a `docs.description` property exists. */ -function hasMetaDocsDescription (metaPropertyNode) { +function hasMetaDocsDescription(metaPropertyNode) { const metaDocs = getPropertyFromObject('docs', metaPropertyNode.value) return metaDocs && getPropertyFromObject('description', metaDocs.value) @@ -67,7 +67,7 @@ function hasMetaDocsDescription (metaPropertyNode) { * @param {ASTNode} metaPropertyNode The `meta` ObjectExpression for this rule. * @returns {boolean} `true` if a `docs.category` property exists. */ -function hasMetaDocsCategories (metaPropertyNode) { +function hasMetaDocsCategories(metaPropertyNode) { const metaDocs = getPropertyFromObject('docs', metaPropertyNode.value) return metaDocs && getPropertyFromObject('categories', metaDocs.value) @@ -79,7 +79,7 @@ function hasMetaDocsCategories (metaPropertyNode) { * @param {ASTNode} metaPropertyNode The `meta` ObjectExpression for this rule. * @returns {boolean} `true` if a `schema` property exists. */ -function hasMetaSchema (metaPropertyNode) { +function hasMetaSchema(metaPropertyNode) { return getPropertyFromObject('schema', metaPropertyNode.value) } @@ -91,7 +91,7 @@ function hasMetaSchema (metaPropertyNode) { * @param {boolean} ruleIsFixable whether the rule is fixable or not. * @returns {void} */ -function checkMetaValidity (context, exportsNode) { +function checkMetaValidity(context, exportsNode) { const metaProperty = getMetaPropertyFromExportsNode(exportsNode) if (!metaProperty) { @@ -105,12 +105,18 @@ function checkMetaValidity (context, exportsNode) { } if (!hasMetaDocsDescription(metaProperty)) { - context.report(metaProperty, 'Rule is missing a meta.docs.description property.') + context.report( + metaProperty, + 'Rule is missing a meta.docs.description property.' + ) return } if (!hasMetaDocsCategories(metaProperty)) { - context.report(metaProperty, 'Rule is missing a meta.docs.categories property.') + context.report( + metaProperty, + 'Rule is missing a meta.docs.categories property.' + ) return } @@ -125,7 +131,7 @@ function checkMetaValidity (context, exportsNode) { * @param {ASTNode} node node that the rule exports. * @returns {boolean} `true` if the exported node is the correct format for a rule definition */ -function isCorrectExportsFormat (node) { +function isCorrectExportsFormat(node) { return node != null && node.type === 'ObjectExpression' } @@ -143,23 +149,29 @@ module.exports = { schema: [] }, - create (context) { + create(context) { let exportsNode return { - AssignmentExpression (node) { - if (node.left && - node.right && - node.left.type === 'MemberExpression' && - node.left.object.name === 'module' && - node.left.property.name === 'exports') { + AssignmentExpression(node) { + if ( + node.left && + node.right && + node.left.type === 'MemberExpression' && + node.left.object.name === 'module' && + node.left.property.name === 'exports' + ) { exportsNode = node.right } }, - 'Program:exit' (programNode) { + 'Program:exit'(programNode) { if (!isCorrectExportsFormat(exportsNode)) { - context.report({ node: exportsNode || programNode, message: 'Rule does not export an Object. Make sure the rule follows the new rule format.' }) + context.report({ + node: exportsNode || programNode, + message: + 'Rule does not export an Object. Make sure the rule follows the new rule format.' + }) return } diff --git a/eslint-internal-rules/require-meta-docs-url.js b/eslint-internal-rules/require-meta-docs-url.js index 87385b01e..88cd9de0f 100644 --- a/eslint-internal-rules/require-meta-docs-url.js +++ b/eslint-internal-rules/require-meta-docs-url.js @@ -21,12 +21,17 @@ const path = require('path') // ----------------------------------------------------------------------------- /** -* Determines whether a node is a 'normal' (i.e. non-async, non-generator) function expression. -* @param {ASTNode} node The node in question -* @returns {boolean} `true` if the node is a normal function expression -*/ -function isNormalFunctionExpression (node) { - return (node.type === 'FunctionExpression' || node.type === 'ArrowFunctionExpression') && !node.generator && !node.async + * Determines whether a node is a 'normal' (i.e. non-async, non-generator) function expression. + * @param {ASTNode} node The node in question + * @returns {boolean} `true` if the node is a normal function expression + */ +function isNormalFunctionExpression(node) { + return ( + (node.type === 'FunctionExpression' || + node.type === 'ArrowFunctionExpression') && + !node.generator && + !node.async + ) } /** @@ -34,14 +39,17 @@ function isNormalFunctionExpression (node) { * @param {ASTNode} node The `Property` node * @returns {string|null} The key name, or `null` if the name cannot be determined statically. */ -function getKeyName (property) { +function getKeyName(property) { if (!property.computed && property.key.type === 'Identifier') { return property.key.name } if (property.key.type === 'Literal') { - return '' + property.key.value + return `${property.key.value}` } - if (property.key.type === 'TemplateLiteral' && property.key.quasis.length === 1) { + if ( + property.key.type === 'TemplateLiteral' && + property.key.quasis.length === 1 + ) { return property.key.quasis[0].value.cooked } return null @@ -55,20 +63,22 @@ for the final values of `module.exports.meta` and `module.exports.create`. `isNe is an object, and `false` if module.exports is just the `create` function. If no valid ESLint rule info can be extracted from the file, the return value will be `null`. */ -function getRuleInfo (ast) { +function getRuleInfo(ast) { const INTERESTING_KEYS = new Set(['create', 'meta']) let exportsVarOverridden = false let exportsIsFunction = false const exportNodes = ast.body - .filter(statement => statement.type === 'ExpressionStatement') - .map(statement => statement.expression) - .filter(expression => expression.type === 'AssignmentExpression') - .filter(expression => expression.left.type === 'MemberExpression') + .filter((statement) => statement.type === 'ExpressionStatement') + .map((statement) => statement.expression) + .filter((expression) => expression.type === 'AssignmentExpression') + .filter((expression) => expression.left.type === 'MemberExpression') .reduce((currentExports, node) => { if ( - node.left.object.type === 'Identifier' && node.left.object.name === 'module' && - node.left.property.type === 'Identifier' && node.left.property.name === 'exports' + node.left.object.type === 'Identifier' && + node.left.object.name === 'module' && + node.left.property.type === 'Identifier' && + node.left.property.name === 'exports' ) { exportsVarOverridden = true @@ -93,17 +103,22 @@ function getRuleInfo (ast) { } else if ( !exportsIsFunction && node.left.object.type === 'MemberExpression' && - node.left.object.object.type === 'Identifier' && node.left.object.object.name === 'module' && - node.left.object.property.type === 'Identifier' && node.left.object.property.name === 'exports' && - node.left.property.type === 'Identifier' && INTERESTING_KEYS.has(node.left.property.name) + node.left.object.object.type === 'Identifier' && + node.left.object.object.name === 'module' && + node.left.object.property.type === 'Identifier' && + node.left.object.property.name === 'exports' && + node.left.property.type === 'Identifier' && + INTERESTING_KEYS.has(node.left.property.name) ) { // Check `module.exports.create = () => {}` currentExports[node.left.property.name] = node.right } else if ( !exportsVarOverridden && - node.left.object.type === 'Identifier' && node.left.object.name === 'exports' && - node.left.property.type === 'Identifier' && INTERESTING_KEYS.has(node.left.property.name) + node.left.object.type === 'Identifier' && + node.left.object.name === 'exports' && + node.left.property.type === 'Identifier' && + INTERESTING_KEYS.has(node.left.property.name) ) { // Check `exports.create = () => {}` @@ -129,13 +144,15 @@ module.exports = { recommended: false }, fixable: 'code', - schema: [{ - type: 'object', - properties: { - pattern: { type: 'string' } - }, - additionalProperties: false - }] + schema: [ + { + type: 'object', + properties: { + pattern: { type: 'string' } + }, + additionalProperties: false + } + ] }, /** @@ -143,29 +160,28 @@ module.exports = { * @param {RuleContext} context - The rule context. * @returns {Object} AST event handlers. */ - create (context) { + create(context) { const options = context.options[0] || {} const sourceCode = context.getSourceCode() const filename = context.getFilename() - const ruleName = filename === '' ? undefined : path.basename(filename, '.js') - const expectedUrl = !options.pattern || !ruleName - ? undefined - : options.pattern.replace(/{{\s*name\s*}}/g, ruleName) + const ruleName = + filename === '' ? undefined : path.basename(filename, '.js') + const expectedUrl = + !options.pattern || !ruleName + ? undefined + : options.pattern.replace(/{{\s*name\s*}}/g, ruleName) /** * Check whether a given node is the expected URL. * @param {Node} node The node of property value to check. * @returns {boolean} `true` if the node is the expected URL. */ - function isExpectedUrl (node) { + function isExpectedUrl(node) { return Boolean( node && - node.type === 'Literal' && - typeof node.value === 'string' && - ( - expectedUrl === undefined || - node.value === expectedUrl - ) + node.type === 'Literal' && + typeof node.value === 'string' && + (expectedUrl === undefined || node.value === expectedUrl) ) } @@ -176,7 +192,7 @@ module.exports = { * @param {string} propertyText The property code to insert. * @returns {void} */ - function insertProperty (fixer, node, propertyText) { + function insertProperty(fixer, node, propertyText) { if (node.properties.length === 0) { return fixer.replaceText(node, `{\n${propertyText}\n}`) } @@ -187,7 +203,7 @@ module.exports = { } return { - Program (node) { + Program(node) { const info = getRuleInfo(node) if (!info) { return @@ -196,11 +212,15 @@ module.exports = { const docsPropNode = metaNode && metaNode.properties && - metaNode.properties.find(p => p.type === 'Property' && getKeyName(p) === 'docs') + metaNode.properties.find( + (p) => p.type === 'Property' && getKeyName(p) === 'docs' + ) const urlPropNode = docsPropNode && docsPropNode.value.properties && - docsPropNode.value.properties.find(p => p.type === 'Property' && getKeyName(p) === 'url') + docsPropNode.value.properties.find( + (p) => p.type === 'Property' && getKeyName(p) === 'url' + ) if (isExpectedUrl(urlPropNode && urlPropNode.value)) { return @@ -213,26 +233,42 @@ module.exports = { (metaNode && metaNode.loc) || node.loc.start, - message: - !urlPropNode ? 'Rules should export a `meta.docs.url` property.' - : !expectedUrl ? '`meta.docs.url` property must be a string.' - /* otherwise */ : '`meta.docs.url` property must be `{{expectedUrl}}`.', + message: !urlPropNode + ? 'Rules should export a `meta.docs.url` property.' + : !expectedUrl + ? '`meta.docs.url` property must be a string.' + : /* otherwise */ '`meta.docs.url` property must be `{{expectedUrl}}`.', data: { expectedUrl }, - fix (fixer) { + fix(fixer) { if (expectedUrl) { const urlString = JSON.stringify(expectedUrl) if (urlPropNode) { return fixer.replaceText(urlPropNode.value, urlString) } - if (docsPropNode && docsPropNode.value.type === 'ObjectExpression') { - return insertProperty(fixer, docsPropNode.value, `url: ${urlString}`) + if ( + docsPropNode && + docsPropNode.value.type === 'ObjectExpression' + ) { + return insertProperty( + fixer, + docsPropNode.value, + `url: ${urlString}` + ) } - if (!docsPropNode && metaNode && metaNode.type === 'ObjectExpression') { - return insertProperty(fixer, metaNode, `docs: {\nurl: ${urlString}\n}`) + if ( + !docsPropNode && + metaNode && + metaNode.type === 'ObjectExpression' + ) { + return insertProperty( + fixer, + metaNode, + `docs: {\nurl: ${urlString}\n}` + ) } } return null diff --git a/lib/configs/base.js b/lib/configs/base.js index 81789e991..747f2e65c 100644 --- a/lib/configs/base.js +++ b/lib/configs/base.js @@ -16,9 +16,7 @@ module.exports = { browser: true, es6: true }, - plugins: [ - 'vue' - ], + plugins: ['vue'], rules: { 'vue/comment-directive': 'error', 'vue/jsx-uses-vars': 'error' diff --git a/lib/index.js b/lib/index.js index d73a7f83a..6b5ea2011 100644 --- a/lib/index.js +++ b/lib/index.js @@ -13,7 +13,7 @@ module.exports = { 'attributes-order': require('./rules/attributes-order'), 'block-spacing': require('./rules/block-spacing'), 'brace-style': require('./rules/brace-style'), - 'camelcase': require('./rules/camelcase'), + camelcase: require('./rules/camelcase'), 'comma-dangle': require('./rules/comma-dangle'), 'comma-spacing': require('./rules/comma-spacing'), 'comma-style': require('./rules/comma-style'), @@ -22,7 +22,7 @@ module.exports = { 'component-name-in-template-casing': require('./rules/component-name-in-template-casing'), 'component-tags-order': require('./rules/component-tags-order'), 'dot-location': require('./rules/dot-location'), - 'eqeqeq': require('./rules/eqeqeq'), + eqeqeq: require('./rules/eqeqeq'), 'html-closing-bracket-newline': require('./rules/html-closing-bracket-newline'), 'html-closing-bracket-spacing': require('./rules/html-closing-bracket-spacing'), 'html-comment-content-newline': require('./rules/html-comment-content-newline'), @@ -145,10 +145,10 @@ module.exports = { 'valid-v-text': require('./rules/valid-v-text') }, configs: { - 'base': require('./configs/base'), - 'essential': require('./configs/essential'), + base: require('./configs/base'), + essential: require('./configs/essential'), 'no-layout-rules': require('./configs/no-layout-rules'), - 'recommended': require('./configs/recommended'), + recommended: require('./configs/recommended'), 'strongly-recommended': require('./configs/strongly-recommended'), 'vue3-essential': require('./configs/vue3-essential'), 'vue3-recommended': require('./configs/vue3-recommended'), diff --git a/lib/processor.js b/lib/processor.js index fcd8aaf67..a45827632 100644 --- a/lib/processor.js +++ b/lib/processor.js @@ -4,11 +4,11 @@ 'use strict' module.exports = { - preprocess (code) { + preprocess(code) { return [code] }, - postprocess (messages) { + postprocess(messages) { const state = { block: { disableAll: false, @@ -21,7 +21,7 @@ module.exports = { } // Filter messages which are in disabled area. - return messages[0].filter(message => { + return messages[0].filter((message) => { if (message.ruleId === 'vue/comment-directive') { const rules = message.message.split(' ') const type = rules.shift() diff --git a/lib/rules/attribute-hyphenation.js b/lib/rules/attribute-hyphenation.js index e52d321b8..ed5ab1904 100644 --- a/lib/rules/attribute-hyphenation.js +++ b/lib/rules/attribute-hyphenation.js @@ -15,7 +15,8 @@ module.exports = { meta: { type: 'suggestion', docs: { - description: 'enforce attribute naming style on custom components in template', + description: + 'enforce attribute naming style on custom components in template', categories: ['vue3-strongly-recommended', 'strongly-recommended'], url: 'https://eslint.vuejs.org/rules/attribute-hyphenation.html' }, @@ -27,13 +28,13 @@ module.exports = { { type: 'object', properties: { - 'ignore': { + ignore: { type: 'array', items: { allOf: [ { type: 'string' }, - { not: { type: 'string', pattern: ':exit$' }}, - { not: { type: 'string', pattern: '^\\s*$' }} + { not: { type: 'string', pattern: ':exit$' } }, + { not: { type: 'string', pattern: '^\\s*$' } } ] }, uniqueItems: true, @@ -45,7 +46,7 @@ module.exports = { ] }, - create (context) { + create(context) { const sourceCode = context.getSourceCode() const option = context.options[0] const optionsPayload = context.options[1] @@ -56,24 +57,29 @@ module.exports = { ignoredAttributes = ignoredAttributes.concat(optionsPayload.ignore) } - const caseConverter = casing.getExactConverter(useHyphenated ? 'kebab-case' : 'camelCase') + const caseConverter = casing.getExactConverter( + useHyphenated ? 'kebab-case' : 'camelCase' + ) - function reportIssue (node, name) { + function reportIssue(node, name) { const text = sourceCode.getText(node.key) context.report({ node: node.key, loc: node.loc, - message: useHyphenated ? "Attribute '{{text}}' must be hyphenated." : "Attribute '{{text}}' can't be hyphenated.", + message: useHyphenated + ? "Attribute '{{text}}' must be hyphenated." + : "Attribute '{{text}}' can't be hyphenated.", data: { text }, - fix: fixer => fixer.replaceText(node.key, text.replace(name, caseConverter(name))) + fix: (fixer) => + fixer.replaceText(node.key, text.replace(name, caseConverter(name))) }) } - function isIgnoredAttribute (value) { - const isIgnored = ignoredAttributes.some(function (attr) { + function isIgnoredAttribute(value) { + const isIgnored = ignoredAttributes.some((attr) => { return value.indexOf(attr) !== -1 }) @@ -89,13 +95,14 @@ module.exports = { // ---------------------------------------------------------------------- return utils.defineTemplateBodyVisitor(context, { - VAttribute (node) { + VAttribute(node) { if (!utils.isCustomComponent(node.parent.parent)) return - const name = - !node.directive ? node.key.rawName - : node.key.name.name === 'bind' ? node.key.argument && node.key.argument.rawName - : /* otherwise */ false + const name = !node.directive + ? node.key.rawName + : node.key.name.name === 'bind' + ? node.key.argument && node.key.argument.rawName + : /* otherwise */ false if (!name || isIgnoredAttribute(name)) return reportIssue(node, name) diff --git a/lib/rules/attributes-order.js b/lib/rules/attributes-order.js index 1641e9b7f..2f3d54f09 100644 --- a/lib/rules/attributes-order.js +++ b/lib/rules/attributes-order.js @@ -30,12 +30,12 @@ function getAttributeName (attribute, sourceCode) { } function getDirectiveKeyName (directiveKey, sourceCode) { - let text = 'v-' + directiveKey.name.name + let text = `v-${directiveKey.name.name}` if (directiveKey.argument) { - text += ':' + sourceCode.getText(directiveKey.argument) + text += `:${sourceCode.getText(directiveKey.argument)}` } for (const modifier of directiveKey.modifiers) { - text += '.' + modifier.name + text += `.${modifier.name}` } return text } diff --git a/lib/rules/block-spacing.js b/lib/rules/block-spacing.js index 32c22a26b..d12ad7da8 100644 --- a/lib/rules/block-spacing.js +++ b/lib/rules/block-spacing.js @@ -6,7 +6,6 @@ const { wrapCoreRule } = require('../utils') // eslint-disable-next-line no-invalid-meta, no-invalid-meta-docs-categories -module.exports = wrapCoreRule( - require('eslint/lib/rules/block-spacing'), - { skipDynamicArguments: true } -) +module.exports = wrapCoreRule(require('eslint/lib/rules/block-spacing'), { + skipDynamicArguments: true +}) diff --git a/lib/rules/brace-style.js b/lib/rules/brace-style.js index f74715629..66680948d 100644 --- a/lib/rules/brace-style.js +++ b/lib/rules/brace-style.js @@ -6,8 +6,6 @@ const { wrapCoreRule } = require('../utils') // eslint-disable-next-line no-invalid-meta, no-invalid-meta-docs-categories -module.exports = wrapCoreRule( - require('eslint/lib/rules/brace-style'), - { skipDynamicArguments: true } -) - +module.exports = wrapCoreRule(require('eslint/lib/rules/brace-style'), { + skipDynamicArguments: true +}) diff --git a/lib/rules/comma-spacing.js b/lib/rules/comma-spacing.js index f51bb7c6e..2a68be8f1 100644 --- a/lib/rules/comma-spacing.js +++ b/lib/rules/comma-spacing.js @@ -6,7 +6,7 @@ const { wrapCoreRule } = require('../utils') // eslint-disable-next-line no-invalid-meta, no-invalid-meta-docs-categories -module.exports = wrapCoreRule( - require('eslint/lib/rules/comma-spacing'), - { skipDynamicArguments: true, skipDynamicArgumentsReport: true } -) +module.exports = wrapCoreRule(require('eslint/lib/rules/comma-spacing'), { + skipDynamicArguments: true, + skipDynamicArgumentsReport: true +}) diff --git a/lib/rules/comma-style.js b/lib/rules/comma-style.js index 87ffaabc5..4f7f32b2d 100644 --- a/lib/rules/comma-style.js +++ b/lib/rules/comma-style.js @@ -6,15 +6,12 @@ const { wrapCoreRule } = require('../utils') // eslint-disable-next-line no-invalid-meta, no-invalid-meta-docs-categories -module.exports = wrapCoreRule( - require('eslint/lib/rules/comma-style'), - { - create (_context, { coreHandlers }) { - return { - VSlotScopeExpression (node) { - coreHandlers.FunctionExpression(node) - } +module.exports = wrapCoreRule(require('eslint/lib/rules/comma-style'), { + create(_context, { coreHandlers }) { + return { + VSlotScopeExpression(node) { + coreHandlers.FunctionExpression(node) } } } -) +}) diff --git a/lib/rules/comment-directive.js b/lib/rules/comment-directive.js index 2058190fc..9b3842ca9 100644 --- a/lib/rules/comment-directive.js +++ b/lib/rules/comment-directive.js @@ -17,7 +17,7 @@ const COMMENT_DIRECTIVE_L = /^\s*(eslint-disable(?:-next)?-line)(?:\s+(\S|\S[\s\ * @param {string} value The comment text to strip. * @returns {string} The stripped text. */ -function stripDirectiveComment (value) { +function stripDirectiveComment(value) { return value.split(/\s-{2,}\s/u)[0].trim() } @@ -27,7 +27,7 @@ function stripDirectiveComment (value) { * @param {string} comment The comment value to parse. * @returns {({type:string,rules:string[]})|null} The parsing result. */ -function parse (pattern, comment) { +function parse(pattern, comment) { const match = pattern.exec(stripDirectiveComment(comment)) if (match == null) { return null @@ -36,7 +36,7 @@ function parse (pattern, comment) { const type = match[1] const rules = (match[2] || '') .split(',') - .map(s => s.trim()) + .map((s) => s.trim()) .filter(Boolean) return { type, rules } @@ -50,11 +50,15 @@ function parse (pattern, comment) { * @param {string[]} rules The rule IDs to enable. * @returns {void} */ -function enable (context, loc, group, rules) { +function enable(context, loc, group, rules) { if (rules.length === 0) { - context.report({ loc, message: '++ {{group}}', data: { group }}) + context.report({ loc, message: '++ {{group}}', data: { group } }) } else { - context.report({ loc, message: '+ {{group}} {{rules}}', data: { group, rules: rules.join(' ') }}) + context.report({ + loc, + message: '+ {{group}} {{rules}}', + data: { group, rules: rules.join(' ') } + }) } } @@ -66,11 +70,15 @@ function enable (context, loc, group, rules) { * @param {string[]} rules The rule IDs to disable. * @returns {void} */ -function disable (context, loc, group, rules) { +function disable(context, loc, group, rules) { if (rules.length === 0) { - context.report({ loc, message: '-- {{group}}', data: { group }}) + context.report({ loc, message: '-- {{group}}', data: { group } }) } else { - context.report({ loc, message: '- {{group}} {{rules}}', data: { group, rules: rules.join(' ') }}) + context.report({ + loc, + message: '- {{group}} {{rules}}', + data: { group, rules: rules.join(' ') } + }) } } @@ -81,7 +89,7 @@ function disable (context, loc, group, rules) { * @param {Token} comment The comment token to process. * @returns {void} */ -function processBlock (context, comment) { +function processBlock(context, comment) { const parsed = parse(COMMENT_DIRECTIVE_B, comment.value) if (parsed != null) { if (parsed.type === 'eslint-disable') { @@ -99,10 +107,11 @@ function processBlock (context, comment) { * @param {Token} comment The comment token to process. * @returns {void} */ -function processLine (context, comment) { +function processLine(context, comment) { const parsed = parse(COMMENT_DIRECTIVE_L, comment.value) if (parsed != null && comment.loc.start.line === comment.loc.end.line) { - const line = comment.loc.start.line + (parsed.type === 'eslint-disable-line' ? 0 : 1) + const line = + comment.loc.start.line + (parsed.type === 'eslint-disable-line' ? 0 : 1) const column = -1 disable(context, { line, column }, 'line', parsed.rules) enable(context, { line: line + 1, column }, 'line', parsed.rules) @@ -114,21 +123,24 @@ function processLine (context, comment) { * @param {VDocumentFragment} documentFragment The document fragment. * @returns {VElement[]} The top-level elements */ -function extractTopLevelHTMLElements (documentFragment) { - return documentFragment.children.filter(e => e.type === 'VElement') +function extractTopLevelHTMLElements(documentFragment) { + return documentFragment.children.filter((e) => e.type === 'VElement') } /** * Extracts the top-level comments in document fragment. * @param {VDocumentFragment} documentFragment The document fragment. * @returns {Token[]} The top-level comments */ -function extractTopLevelDocumentFragmentComments (documentFragment) { +function extractTopLevelDocumentFragmentComments(documentFragment) { const elements = extractTopLevelHTMLElements(documentFragment) - return documentFragment.comments.filter(comment => - elements.every(element => - comment.range[1] <= element.range[0] || element.range[1] <= comment.range[0] - )) + return documentFragment.comments.filter((comment) => + elements.every( + (element) => + comment.range[1] <= element.range[0] || + element.range[1] <= comment.range[0] + ) + ) } // ----------------------------------------------------------------------------- @@ -146,11 +158,13 @@ module.exports = { schema: [] }, - create (context) { - const documentFragment = context.parserServices.getDocumentFragment && context.parserServices.getDocumentFragment() + create(context) { + const documentFragment = + context.parserServices.getDocumentFragment && + context.parserServices.getDocumentFragment() return { - Program (node) { + Program(node) { if (node.templateBody) { // Send directives to the post-process. for (const comment of node.templateBody.comments) { @@ -166,7 +180,9 @@ module.exports = { } if (documentFragment) { // Send directives to the post-process. - for (const comment of extractTopLevelDocumentFragmentComments(documentFragment)) { + for (const comment of extractTopLevelDocumentFragmentComments( + documentFragment + )) { processBlock(context, comment) processLine(context, comment) } @@ -183,4 +199,3 @@ module.exports = { } } } - diff --git a/lib/rules/component-definition-name-casing.js b/lib/rules/component-definition-name-casing.js index 9012873a4..453e3943e 100644 --- a/lib/rules/component-definition-name-casing.js +++ b/lib/rules/component-definition-name-casing.js @@ -18,7 +18,8 @@ module.exports = { docs: { description: 'enforce specific casing for component definition name', categories: ['vue3-strongly-recommended', 'strongly-recommended'], - url: 'https://eslint.vuejs.org/rules/component-definition-name-casing.html' + url: + 'https://eslint.vuejs.org/rules/component-definition-name-casing.html' }, fixable: 'code', // or "code" or "whitespace" schema: [ @@ -28,15 +29,16 @@ module.exports = { ] }, - create (context) { + create(context) { const options = context.options[0] - const caseType = allowedCaseOptions.indexOf(options) !== -1 ? options : 'PascalCase' + const caseType = + allowedCaseOptions.indexOf(options) !== -1 ? options : 'PascalCase' // ---------------------------------------------------------------------- // Public // ---------------------------------------------------------------------- - function convertName (node) { + function convertName(node) { let nodeValue let range if (node.type === 'TemplateLiteral') { @@ -50,26 +52,32 @@ module.exports = { if (!casing.getChecker(caseType)(nodeValue)) { context.report({ - node: node, + node, message: 'Property name "{{value}}" is not {{caseType}}.', data: { value: nodeValue, - caseType: caseType + caseType }, - fix: fixer => fixer.replaceTextRange([range[0] + 1, range[1] - 1], casing.getExactConverter(caseType)(nodeValue)) + fix: (fixer) => + fixer.replaceTextRange( + [range[0] + 1, range[1] - 1], + casing.getExactConverter(caseType)(nodeValue) + ) }) } } - function canConvert (node) { - return node.type === 'Literal' || ( - node.type === 'TemplateLiteral' && - node.expressions.length === 0 && - node.quasis.length === 1 + function canConvert(node) { + return ( + node.type === 'Literal' || + (node.type === 'TemplateLiteral' && + node.expressions.length === 0 && + node.quasis.length === 1) ) } - return Object.assign({}, + return Object.assign( + {}, utils.executeOnCallVueComponent(context, (node) => { if (node.arguments.length === 2) { const argument = node.arguments[0] @@ -80,12 +88,12 @@ module.exports = { } }), utils.executeOnVue(context, (obj) => { - const node = obj.properties - .find(item => ( + const node = obj.properties.find( + (item) => item.type === 'Property' && item.key.name === 'name' && canConvert(item.value) - )) + ) if (!node) return convertName(node.value) diff --git a/lib/rules/component-name-in-template-casing.js b/lib/rules/component-name-in-template-casing.js index 91481b0f4..90eb48d84 100644 --- a/lib/rules/component-name-in-template-casing.js +++ b/lib/rules/component-name-in-template-casing.js @@ -27,9 +27,11 @@ module.exports = { meta: { type: 'suggestion', docs: { - description: 'enforce specific casing for the component naming style in template', + description: + 'enforce specific casing for the component naming style in template', categories: undefined, - url: 'https://eslint.vuejs.org/rules/component-name-in-template-casing.html' + url: + 'https://eslint.vuejs.org/rules/component-name-in-template-casing.html' }, fixable: 'code', schema: [ @@ -54,13 +56,16 @@ module.exports = { ] }, - create (context) { + create(context) { const caseOption = context.options[0] const options = context.options[1] || {} - const caseType = allowedCaseOptions.indexOf(caseOption) !== -1 ? caseOption : defaultCase + const caseType = + allowedCaseOptions.indexOf(caseOption) !== -1 ? caseOption : defaultCase const ignores = (options.ignores || []).map(toRegExp) const registeredComponentsOnly = options.registeredComponentsOnly !== false - const tokens = context.parserServices.getTemplateBodyTokenStore && context.parserServices.getTemplateBodyTokenStore() + const tokens = + context.parserServices.getTemplateBodyTokenStore && + context.parserServices.getTemplateBodyTokenStore() const registeredComponents = [] @@ -69,15 +74,16 @@ module.exports = { * @param {VElement} node element node * @returns {boolean} `true` if the given node is the verification target node. */ - function isVerifyTarget (node) { - if (ignores.some(re => re.test(node.rawName))) { + function isVerifyTarget(node) { + if (ignores.some((re) => re.test(node.rawName))) { // ignore return false } if (!registeredComponentsOnly) { // If the user specifies registeredComponentsOnly as false, it checks all component tags. - if ((!utils.isHtmlElementNode(node) && !utils.isSvgElementNode(node)) || + if ( + (!utils.isHtmlElementNode(node) && !utils.isSvgElementNode(node)) || utils.isHtmlWellKnownElementName(node.rawName) || utils.isSvgWellKnownElementName(node.rawName) ) { @@ -86,9 +92,14 @@ module.exports = { return true } // We only verify the components registered in the component. - if (registeredComponents - .filter(name => casing.isPascalCase(name)) // When defining a component with PascalCase, you can use either case - .some(name => node.rawName === name || casing.pascalCase(node.rawName) === name)) { + if ( + registeredComponents + .filter((name) => casing.isPascalCase(name)) // When defining a component with PascalCase, you can use either case + .some( + (name) => + node.rawName === name || casing.pascalCase(node.rawName) === name + ) + ) { return true } @@ -97,55 +108,60 @@ module.exports = { let hasInvalidEOF = false - return utils.defineTemplateBodyVisitor(context, { - 'VElement' (node) { - if (hasInvalidEOF) { - return - } + return utils.defineTemplateBodyVisitor( + context, + { + VElement(node) { + if (hasInvalidEOF) { + return + } - if (!isVerifyTarget(node)) { - return - } + if (!isVerifyTarget(node)) { + return + } - const name = node.rawName - if (!casing.getChecker(caseType)(name)) { - const startTag = node.startTag - const open = tokens.getFirstToken(startTag) - const casingName = casing.getExactConverter(caseType)(name) - context.report({ - node: open, - loc: open.loc, - message: 'Component name "{{name}}" is not {{caseType}}.', - data: { - name, - caseType - }, - fix: fixer => { - const endTag = node.endTag - if (!endTag) { - return fixer.replaceText(open, `<${casingName}`) + const name = node.rawName + if (!casing.getChecker(caseType)(name)) { + const startTag = node.startTag + const open = tokens.getFirstToken(startTag) + const casingName = casing.getExactConverter(caseType)(name) + context.report({ + node: open, + loc: open.loc, + message: 'Component name "{{name}}" is not {{caseType}}.', + data: { + name, + caseType + }, + fix: (fixer) => { + const endTag = node.endTag + if (!endTag) { + return fixer.replaceText(open, `<${casingName}`) + } + const endTagOpen = tokens.getFirstToken(endTag) + return [ + fixer.replaceText(open, `<${casingName}`), + fixer.replaceText(endTagOpen, ` { - registeredComponents.push(...utils.getRegisteredComponents(obj).map(n => n.name)) - }) - : {} - )) + Object.assign( + { + Program(node) { + hasInvalidEOF = utils.hasInvalidEOF(node) + } + }, + registeredComponentsOnly + ? utils.executeOnVue(context, (obj) => { + registeredComponents.push( + ...utils.getRegisteredComponents(obj).map((n) => n.name) + ) + }) + : {} + ) + ) } } diff --git a/lib/rules/component-tags-order.js b/lib/rules/component-tags-order.js index 46dde00c8..c19429637 100644 --- a/lib/rules/component-tags-order.js +++ b/lib/rules/component-tags-order.js @@ -34,21 +34,25 @@ module.exports = { } }, messages: { - unexpected: 'The <{{name}}> should be above the <{{firstUnorderedName}}> on line {{line}}.' + unexpected: + 'The <{{name}}> should be above the <{{firstUnorderedName}}> on line {{line}}.' } }, - create (context) { - const order = (context.options[0] && context.options[0].order) || DEFAULT_ORDER - const documentFragment = context.parserServices.getDocumentFragment && context.parserServices.getDocumentFragment() + create(context) { + const order = + (context.options[0] && context.options[0].order) || DEFAULT_ORDER + const documentFragment = + context.parserServices.getDocumentFragment && + context.parserServices.getDocumentFragment() - function getTopLevelHTMLElements () { + function getTopLevelHTMLElements() { if (documentFragment) { - return documentFragment.children.filter(e => e.type === 'VElement') + return documentFragment.children.filter((e) => e.type === 'VElement') } return [] } - function report (element, firstUnorderedElement) { + function report(element, firstUnorderedElement) { context.report({ node: element, loc: element.loc, @@ -65,7 +69,7 @@ module.exports = { context, {}, { - Program (node) { + Program(node) { if (utils.hasInvalidEOF(node)) { return } @@ -78,7 +82,7 @@ module.exports = { } const firstUnordered = elements .slice(0, index) - .filter(e => expectedIndex < order.indexOf(e.name)) + .filter((e) => expectedIndex < order.indexOf(e.name)) .sort( (e1, e2) => order.indexOf(e1.name) - order.indexOf(e2.name) )[0] diff --git a/lib/rules/html-closing-bracket-newline.js b/lib/rules/html-closing-bracket-newline.js index 02ddeb445..20d7fbd20 100644 --- a/lib/rules/html-closing-bracket-newline.js +++ b/lib/rules/html-closing-bracket-newline.js @@ -15,11 +15,14 @@ const utils = require('../utils') // Helpers // ------------------------------------------------------------------------------ -function getPhrase (lineBreaks) { +function getPhrase(lineBreaks) { switch (lineBreaks) { - case 0: return 'no line breaks' - case 1: return '1 line break' - default: return `${lineBreaks} line breaks` + case 0: + return 'no line breaks' + case 1: + return '1 line break' + default: + return `${lineBreaks} line breaks` } } @@ -31,39 +34,55 @@ module.exports = { meta: { type: 'layout', docs: { - description: "require or disallow a line break before tag's closing brackets", + description: + "require or disallow a line break before tag's closing brackets", categories: ['vue3-strongly-recommended', 'strongly-recommended'], url: 'https://eslint.vuejs.org/rules/html-closing-bracket-newline.html' }, fixable: 'whitespace', - schema: [{ - type: 'object', - properties: { - 'singleline': { enum: ['always', 'never'] }, - 'multiline': { enum: ['always', 'never'] } - }, - additionalProperties: false - }] + schema: [ + { + type: 'object', + properties: { + singleline: { enum: ['always', 'never'] }, + multiline: { enum: ['always', 'never'] } + }, + additionalProperties: false + } + ] }, - create (context) { - const options = Object.assign({}, { - singleline: 'never', - multiline: 'always' - }, context.options[0] || {}) - const template = context.parserServices.getTemplateBodyTokenStore && context.parserServices.getTemplateBodyTokenStore() + create(context) { + const options = Object.assign( + {}, + { + singleline: 'never', + multiline: 'always' + }, + context.options[0] || {} + ) + const template = + context.parserServices.getTemplateBodyTokenStore && + context.parserServices.getTemplateBodyTokenStore() return utils.defineTemplateBodyVisitor(context, { - 'VStartTag, VEndTag' (node) { + 'VStartTag, VEndTag'(node) { const closingBracketToken = template.getLastToken(node) - if (closingBracketToken.type !== 'HTMLSelfClosingTagClose' && closingBracketToken.type !== 'HTMLTagClose') { + if ( + closingBracketToken.type !== 'HTMLSelfClosingTagClose' && + closingBracketToken.type !== 'HTMLTagClose' + ) { return } const prevToken = template.getTokenBefore(closingBracketToken) - const type = (node.loc.start.line === prevToken.loc.end.line) ? 'singleline' : 'multiline' - const expectedLineBreaks = (options[type] === 'always') ? 1 : 0 - const actualLineBreaks = (closingBracketToken.loc.start.line - prevToken.loc.end.line) + const type = + node.loc.start.line === prevToken.loc.end.line + ? 'singleline' + : 'multiline' + const expectedLineBreaks = options[type] === 'always' ? 1 : 0 + const actualLineBreaks = + closingBracketToken.loc.start.line - prevToken.loc.end.line if (actualLineBreaks !== expectedLineBreaks) { context.report({ @@ -72,12 +91,13 @@ module.exports = { start: prevToken.loc.end, end: closingBracketToken.loc.start }, - message: 'Expected {{expected}} before closing bracket, but {{actual}} found.', + message: + 'Expected {{expected}} before closing bracket, but {{actual}} found.', data: { expected: getPhrase(expectedLineBreaks), actual: getPhrase(actualLineBreaks) }, - fix (fixer) { + fix(fixer) { const range = [prevToken.range[1], closingBracketToken.range[0]] const text = '\n'.repeat(expectedLineBreaks) return fixer.replaceTextRange(range, text) diff --git a/lib/rules/html-closing-bracket-spacing.js b/lib/rules/html-closing-bracket-spacing.js index eaf885ba5..9b70dfb09 100644 --- a/lib/rules/html-closing-bracket-spacing.js +++ b/lib/rules/html-closing-bracket-spacing.js @@ -20,28 +20,34 @@ const utils = require('../utils') * @param {TokenStore} tokens The token store of template body. * @returns {{startTag:"always"|"never",endTag:"always"|"never",selfClosingTag:"always"|"never"}} The normalized options. */ -function parseOptions (options, tokens) { - return Object.assign({ - startTag: 'never', - endTag: 'never', - selfClosingTag: 'always', +function parseOptions(options, tokens) { + return Object.assign( + { + startTag: 'never', + endTag: 'never', + selfClosingTag: 'always', - detectType (node) { - const openType = tokens.getFirstToken(node).type - const closeType = tokens.getLastToken(node).type + detectType(node) { + const openType = tokens.getFirstToken(node).type + const closeType = tokens.getLastToken(node).type - if (openType === 'HTMLEndTagOpen' && closeType === 'HTMLTagClose') { - return this.endTag - } - if (openType === 'HTMLTagOpen' && closeType === 'HTMLTagClose') { - return this.startTag - } - if (openType === 'HTMLTagOpen' && closeType === 'HTMLSelfClosingTagClose') { - return this.selfClosingTag + if (openType === 'HTMLEndTagOpen' && closeType === 'HTMLTagClose') { + return this.endTag + } + if (openType === 'HTMLTagOpen' && closeType === 'HTMLTagClose') { + return this.startTag + } + if ( + openType === 'HTMLTagOpen' && + closeType === 'HTMLSelfClosingTagClose' + ) { + return this.selfClosingTag + } + return null } - return null - } - }, options) + }, + options + ) } // ----------------------------------------------------------------------------- @@ -52,23 +58,25 @@ module.exports = { meta: { type: 'layout', docs: { - description: 'require or disallow a space before tag\'s closing brackets', + description: "require or disallow a space before tag's closing brackets", categories: ['vue3-strongly-recommended', 'strongly-recommended'], url: 'https://eslint.vuejs.org/rules/html-closing-bracket-spacing.html' }, - schema: [{ - type: 'object', - properties: { - startTag: { enum: ['always', 'never'] }, - endTag: { enum: ['always', 'never'] }, - selfClosingTag: { enum: ['always', 'never'] } - }, - additionalProperties: false - }], + schema: [ + { + type: 'object', + properties: { + startTag: { enum: ['always', 'never'] }, + endTag: { enum: ['always', 'never'] }, + selfClosingTag: { enum: ['always', 'never'] } + }, + additionalProperties: false + } + ], fixable: 'whitespace' }, - create (context) { + create(context) { const sourceCode = context.getSourceCode() const tokens = context.parserServices.getTemplateBodyTokenStore && @@ -76,18 +84,22 @@ module.exports = { const options = parseOptions(context.options[0], tokens) return utils.defineTemplateBodyVisitor(context, { - 'VStartTag, VEndTag' (node) { + 'VStartTag, VEndTag'(node) { const type = options.detectType(node) const lastToken = tokens.getLastToken(node) const prevToken = tokens.getLastToken(node, 1) // Skip if EOF exists in the tag or linebreak exists before `>`. - if (type == null || prevToken == null || prevToken.loc.end.line !== lastToken.loc.start.line) { + if ( + type == null || + prevToken == null || + prevToken.loc.end.line !== lastToken.loc.start.line + ) { return } // Check and report. - const hasSpace = (prevToken.range[1] !== lastToken.range[0]) + const hasSpace = prevToken.range[1] !== lastToken.range[0] if (type === 'always' && !hasSpace) { context.report({ node, @@ -105,7 +117,8 @@ module.exports = { }, message: "Expected no space before '{{bracket}}', but found.", data: { bracket: sourceCode.getText(lastToken) }, - fix: (fixer) => fixer.removeRange([prevToken.range[1], lastToken.range[0]]) + fix: (fixer) => + fixer.removeRange([prevToken.range[1], lastToken.range[0]]) }) } } diff --git a/lib/rules/html-comment-content-newline.js b/lib/rules/html-comment-content-newline.js index a736f4885..e5e436490 100644 --- a/lib/rules/html-comment-content-newline.js +++ b/lib/rules/html-comment-content-newline.js @@ -18,17 +18,20 @@ const htmlComments = require('../utils/html-comments') // Helpers // ------------------------------------------------------------------------------ -function parseOption (param) { +function parseOption(param) { if (param && typeof param === 'string') { return { singleline: param, multiline: param } } - return Object.assign({ - singleline: 'never', - multiline: 'always' - }, param) + return Object.assign( + { + singleline: 'never', + multiline: 'always' + }, + param + ) } // ------------------------------------------------------------------------------ @@ -54,8 +57,8 @@ module.exports = { { type: 'object', properties: { - 'singleline': { enum: ['always', 'never', 'ignore'] }, - 'multiline': { enum: ['always', 'never', 'ignore'] } + singleline: { enum: ['always', 'never', 'ignore'] }, + multiline: { enum: ['always', 'never', 'ignore'] } }, additionalProperties: false } @@ -78,33 +81,37 @@ module.exports = { expectedAfterHTMLCommentOpen: "Expected line break after ''.", expectedAfterExceptionBlock: 'Expected line break after exception block.', - expectedBeforeExceptionBlock: 'Expected line break before exception block.', + expectedBeforeExceptionBlock: + 'Expected line break before exception block.', unexpectedAfterHTMLCommentOpen: "Unexpected line breaks after ''." } }, - create (context) { + create(context) { const option = parseOption(context.options[0]) - return htmlComments.defineVisitor(context, context.options[1], (comment) => { - if (!comment.value) { - return - } - const startLine = comment.openDecoration - ? comment.openDecoration.loc.end.line - : comment.value.loc.start.line - const endLine = comment.closeDecoration - ? comment.closeDecoration.loc.start.line - : comment.value.loc.end.line - const newlineType = startLine === endLine - ? option.singleline - : option.multiline - if (newlineType === 'ignore') { - return + return htmlComments.defineVisitor( + context, + context.options[1], + (comment) => { + if (!comment.value) { + return + } + const startLine = comment.openDecoration + ? comment.openDecoration.loc.end.line + : comment.value.loc.start.line + const endLine = comment.closeDecoration + ? comment.closeDecoration.loc.start.line + : comment.value.loc.end.line + const newlineType = + startLine === endLine ? option.singleline : option.multiline + if (newlineType === 'ignore') { + return + } + checkCommentOpen(comment, newlineType !== 'never') + checkCommentClose(comment, newlineType !== 'never') } - checkCommentOpen(comment, newlineType !== 'never') - checkCommentClose(comment, newlineType !== 'never') - }) + ) /** * Reports the newline before the contents of a given comment if it's invalid. @@ -112,7 +119,7 @@ module.exports = { * @param {boolean} requireNewline - `true` if line breaks are required. * @returns {void} */ - function checkCommentOpen (comment, requireNewline) { + function checkCommentOpen(comment, requireNewline) { const beforeToken = comment.openDecoration || comment.open if (requireNewline) { @@ -125,8 +132,12 @@ module.exports = { start: beforeToken.loc.end, end: comment.value.loc.start }, - messageId: comment.openDecoration ? 'expectedAfterExceptionBlock' : 'expectedAfterHTMLCommentOpen', - fix: comment.openDecoration ? undefined : (fixer) => fixer.insertTextAfter(beforeToken, '\n') + messageId: comment.openDecoration + ? 'expectedAfterExceptionBlock' + : 'expectedAfterHTMLCommentOpen', + fix: comment.openDecoration + ? undefined + : (fixer) => fixer.insertTextAfter(beforeToken, '\n') }) } else { if (beforeToken.loc.end.line === comment.value.loc.start.line) { @@ -139,7 +150,11 @@ module.exports = { end: comment.value.loc.start }, messageId: 'unexpectedAfterHTMLCommentOpen', - fix: (fixer) => fixer.replaceTextRange([beforeToken.range[1], comment.value.range[0]], ' ') + fix: (fixer) => + fixer.replaceTextRange( + [beforeToken.range[1], comment.value.range[0]], + ' ' + ) }) } } @@ -150,7 +165,7 @@ module.exports = { * @param {boolean} requireNewline - `true` if line breaks are required. * @returns {void} */ - function checkCommentClose (comment, requireNewline) { + function checkCommentClose(comment, requireNewline) { const afterToken = comment.closeDecoration || comment.close if (requireNewline) { @@ -163,8 +178,12 @@ module.exports = { start: comment.value.loc.end, end: afterToken.loc.start }, - messageId: comment.closeDecoration ? 'expectedBeforeExceptionBlock' : 'expectedBeforeHTMLCommentOpen', - fix: comment.closeDecoration ? undefined : (fixer) => fixer.insertTextBefore(afterToken, '\n') + messageId: comment.closeDecoration + ? 'expectedBeforeExceptionBlock' + : 'expectedBeforeHTMLCommentOpen', + fix: comment.closeDecoration + ? undefined + : (fixer) => fixer.insertTextBefore(afterToken, '\n') }) } else { if (comment.value.loc.end.line === afterToken.loc.start.line) { @@ -177,7 +196,11 @@ module.exports = { end: afterToken.loc.start }, messageId: 'unexpectedBeforeHTMLCommentOpen', - fix: (fixer) => fixer.replaceTextRange([comment.value.range[1], afterToken.range[0]], ' ') + fix: (fixer) => + fixer.replaceTextRange( + [comment.value.range[1], afterToken.range[0]], + ' ' + ) }) } } diff --git a/lib/rules/html-comment-content-spacing.js b/lib/rules/html-comment-content-spacing.js index 9f318cf77..250fd7ae9 100644 --- a/lib/rules/html-comment-content-spacing.js +++ b/lib/rules/html-comment-content-spacing.js @@ -55,23 +55,28 @@ module.exports = { } }, - create (context) { + create(context) { // Unless the first option is never, require a space const requireSpace = context.options[0] !== 'never' - return htmlComments.defineVisitor(context, context.options[1], (comment) => { - if (!comment.value) { - return - } - checkCommentOpen(comment) - checkCommentClose(comment) - }, { includeDirectives: true }) + return htmlComments.defineVisitor( + context, + context.options[1], + (comment) => { + if (!comment.value) { + return + } + checkCommentOpen(comment) + checkCommentClose(comment) + }, + { includeDirectives: true } + ) /** * Reports the space before the contents of a given comment if it's invalid. * @param {HTMLComment} comment - comment data. * @returns {void} */ - function checkCommentOpen (comment) { + function checkCommentOpen(comment) { const beforeToken = comment.openDecoration || comment.open if (beforeToken.loc.end.line !== comment.value.loc.start.line) { // Ignore newline @@ -88,8 +93,12 @@ module.exports = { start: beforeToken.loc.end, end: comment.value.loc.start }, - messageId: comment.openDecoration ? 'expectedAfterExceptionBlock' : 'expectedAfterHTMLCommentOpen', - fix: comment.openDecoration ? undefined : (fixer) => fixer.insertTextAfter(beforeToken, ' ') + messageId: comment.openDecoration + ? 'expectedAfterExceptionBlock' + : 'expectedAfterHTMLCommentOpen', + fix: comment.openDecoration + ? undefined + : (fixer) => fixer.insertTextAfter(beforeToken, ' ') }) } else { if (comment.openDecoration) { @@ -106,7 +115,8 @@ module.exports = { end: comment.value.loc.start }, messageId: 'unexpectedAfterHTMLCommentOpen', - fix: (fixer) => fixer.removeRange([beforeToken.range[1], comment.value.range[0]]) + fix: (fixer) => + fixer.removeRange([beforeToken.range[1], comment.value.range[0]]) }) } } @@ -116,7 +126,7 @@ module.exports = { * @param {HTMLComment} comment - comment data. * @returns {void} */ - function checkCommentClose (comment) { + function checkCommentClose(comment) { const afterToken = comment.closeDecoration || comment.close if (comment.value.loc.end.line !== afterToken.loc.start.line) { // Ignore newline @@ -133,8 +143,12 @@ module.exports = { start: comment.value.loc.end, end: afterToken.loc.start }, - messageId: comment.closeDecoration ? 'expectedBeforeExceptionBlock' : 'expectedBeforeHTMLCommentOpen', - fix: comment.closeDecoration ? undefined : (fixer) => fixer.insertTextBefore(afterToken, ' ') + messageId: comment.closeDecoration + ? 'expectedBeforeExceptionBlock' + : 'expectedBeforeHTMLCommentOpen', + fix: comment.closeDecoration + ? undefined + : (fixer) => fixer.insertTextBefore(afterToken, ' ') }) } else { if (comment.closeDecoration) { @@ -151,7 +165,8 @@ module.exports = { end: afterToken.loc.start }, messageId: 'unexpectedBeforeHTMLCommentOpen', - fix: (fixer) => fixer.removeRange([comment.value.range[1], afterToken.range[0]]) + fix: (fixer) => + fixer.removeRange([comment.value.range[1], afterToken.range[0]]) }) } } diff --git a/lib/rules/html-comment-indent.js b/lib/rules/html-comment-indent.js index bdc4ca0af..c3b60bfcc 100644 --- a/lib/rules/html-comment-indent.js +++ b/lib/rules/html-comment-indent.js @@ -23,7 +23,7 @@ const htmlComments = require('../utils/html-comments') * @param {number|"tab"|undefined} type The type of indentation. * @returns {Object} Normalized options. */ -function parseOptions (type) { +function parseOptions(type) { const ret = { indentChar: ' ', indentSize: 2 @@ -40,13 +40,13 @@ function parseOptions (type) { return ret } -function toDisplay (s, unitChar) { +function toDisplay(s, unitChar) { if (s.length === 0 && unitChar) { return `0 ${toUnit(unitChar)}s` } const char = s[0] if (char === ' ' || char === '\t') { - if (s.split('').every(c => c === char)) { + if (s.split('').every((c) => c === char)) { return `${s.length} ${toUnit(char)}${s.length === 1 ? '' : 's'}` } } @@ -54,7 +54,7 @@ function toDisplay (s, unitChar) { return JSON.stringify(s) } -function toUnit (char) { +function toUnit(char) { if (char === '\t') { return 'tab' } @@ -80,52 +80,60 @@ module.exports = { fixable: 'whitespace', schema: [ { - anyOf: [ - { type: 'integer', minimum: 0 }, - { enum: ['tab'] } - ] + anyOf: [{ type: 'integer', minimum: 0 }, { enum: ['tab'] }] } ], messages: { - unexpectedBaseIndentation: 'Expected base point indentation of {{expected}}, but found {{actual}}.', - missingBaseIndentation: 'Expected base point indentation of {{expected}}, but not found.', - unexpectedIndentationCharacter: 'Expected {{expected}} character, but found {{actual}} character.', - unexpectedIndentation: 'Expected indentation of {{expected}} but found {{actual}}.', - unexpectedRelativeIndentation: 'Expected relative indentation of {{expected}} but found {{actual}}.' + unexpectedBaseIndentation: + 'Expected base point indentation of {{expected}}, but found {{actual}}.', + missingBaseIndentation: + 'Expected base point indentation of {{expected}}, but not found.', + unexpectedIndentationCharacter: + 'Expected {{expected}} character, but found {{actual}} character.', + unexpectedIndentation: + 'Expected indentation of {{expected}} but found {{actual}}.', + unexpectedRelativeIndentation: + 'Expected relative indentation of {{expected}} but found {{actual}}.' } }, - create (context) { + create(context) { const options = parseOptions(context.options[0]) const sourceCode = context.getSourceCode() - return htmlComments.defineVisitor(context, null, (comment) => { - const baseIndentText = getLineIndentText(comment.open.loc.start.line) - let endLine - if (comment.value) { - const startLine = comment.value.loc.start.line - endLine = comment.value.loc.end.line + return htmlComments.defineVisitor( + context, + null, + (comment) => { + const baseIndentText = getLineIndentText(comment.open.loc.start.line) + let endLine + if (comment.value) { + const startLine = comment.value.loc.start.line + endLine = comment.value.loc.end.line - const checkStartLine = comment.open.loc.end.line === startLine ? startLine + 1 : startLine + const checkStartLine = + comment.open.loc.end.line === startLine ? startLine + 1 : startLine - for (let line = checkStartLine; line <= endLine; line++) { - validateIndentForLine(line, baseIndentText, 1) + for (let line = checkStartLine; line <= endLine; line++) { + validateIndentForLine(line, baseIndentText, 1) + } + } else { + endLine = comment.open.loc.end.line } - } else { - endLine = comment.open.loc.end.line - } - if (endLine < comment.close.loc.start.line) { - // `-->` - validateIndentForLine(comment.close.loc.start.line, baseIndentText, 0) - } - }, { includeDirectives: true }) + if (endLine < comment.close.loc.start.line) { + // `-->` + validateIndentForLine(comment.close.loc.start.line, baseIndentText, 0) + } + }, + { includeDirectives: true } + ) /** * Checks whether the given line is a blank line. * @param {number} line The number of line. Begins with 1. * @returns {boolean} `true` if the given line is a blank line */ - function isEmptyLine (line) { + function isEmptyLine(line) { const lineText = sourceCode.getLines()[line - 1] return !lineText.trim() } @@ -135,7 +143,7 @@ module.exports = { * @param {number} line The number of line. Begins with 1. * @returns {string} The actual indentation text */ - function getLineIndentText (line) { + function getLineIndentText(line) { const lineText = sourceCode.getLines()[line - 1] const charIndex = lineText.search(/\S/) // already checked @@ -152,8 +160,8 @@ module.exports = { * @param {string} expectedIndentText The expected indentation text. * @returns {function} The defined function. */ - function defineFix (line, actualIndentText, expectedIndentText) { - return fixer => { + function defineFix(line, actualIndentText, expectedIndentText) { + return (fixer) => { const start = sourceCode.getIndexFromLoc({ line, column: 0 @@ -171,7 +179,7 @@ module.exports = { * @param {string} baseIndentText The expected base indentation text. * @param {number} offset The number of the indentation offset. */ - function validateIndentForLine (line, baseIndentText, offset) { + function validateIndentForLine(line, baseIndentText, offset) { if (isEmptyLine(line)) { return } @@ -184,7 +192,7 @@ module.exports = { if ( baseIndentText && (actualIndentText.length < baseIndentText.length || - !actualIndentText.startsWith(baseIndentText)) + !actualIndentText.startsWith(baseIndentText)) ) { context.report({ loc: { @@ -203,7 +211,9 @@ module.exports = { return } - const actualOffsetIndentText = actualIndentText.slice(baseIndentText.length) + const actualOffsetIndentText = actualIndentText.slice( + baseIndentText.length + ) // validate indent charctor for (let i = 0; i < actualOffsetIndentText.length; ++i) { diff --git a/lib/rules/html-end-tags.js b/lib/rules/html-end-tags.js index cce52b721..b40a53ce0 100644 --- a/lib/rules/html-end-tags.js +++ b/lib/rules/html-end-tags.js @@ -27,34 +27,38 @@ module.exports = { schema: [] }, - create (context) { + create(context) { let hasInvalidEOF = false - return utils.defineTemplateBodyVisitor(context, { - VElement (node) { - if (hasInvalidEOF) { - return - } + return utils.defineTemplateBodyVisitor( + context, + { + VElement(node) { + if (hasInvalidEOF) { + return + } + + const name = node.name + const isVoid = utils.isHtmlVoidElementName(name) + const isSelfClosing = node.startTag.selfClosing + const hasEndTag = node.endTag != null - const name = node.name - const isVoid = utils.isHtmlVoidElementName(name) - const isSelfClosing = node.startTag.selfClosing - const hasEndTag = node.endTag != null - - if (!isVoid && !hasEndTag && !isSelfClosing) { - context.report({ - node: node.startTag, - loc: node.startTag.loc, - message: "'<{{name}}>' should have end tag.", - data: { name }, - fix: (fixer) => fixer.insertTextAfter(node, ``) - }) + if (!isVoid && !hasEndTag && !isSelfClosing) { + context.report({ + node: node.startTag, + loc: node.startTag.loc, + message: "'<{{name}}>' should have end tag.", + data: { name }, + fix: (fixer) => fixer.insertTextAfter(node, ``) + }) + } + } + }, + { + Program(node) { + hasInvalidEOF = utils.hasInvalidEOF(node) } } - }, { - Program (node) { - hasInvalidEOF = utils.hasInvalidEOF(node) - } - }) + ) } } diff --git a/lib/rules/html-indent.js b/lib/rules/html-indent.js index b8d6b2e7d..d62f6f3a5 100644 --- a/lib/rules/html-indent.js +++ b/lib/rules/html-indent.js @@ -17,11 +17,13 @@ const utils = require('../utils') // ------------------------------------------------------------------------------ module.exports = { - create (context) { + create(context) { const tokenStore = context.parserServices.getTemplateBodyTokenStore && context.parserServices.getTemplateBodyTokenStore() - const visitor = indentCommon.defineVisitor(context, tokenStore, { baseIndent: 1 }) + const visitor = indentCommon.defineVisitor(context, tokenStore, { + baseIndent: 1 + }) return utils.defineTemplateBodyVisitor(context, visitor) }, @@ -35,26 +37,23 @@ module.exports = { fixable: 'whitespace', schema: [ { - anyOf: [ - { type: 'integer', minimum: 1 }, - { enum: ['tab'] } - ] + anyOf: [{ type: 'integer', minimum: 1 }, { enum: ['tab'] }] }, { type: 'object', properties: { - 'attribute': { type: 'integer', minimum: 0 }, - 'baseIndent': { type: 'integer', minimum: 0 }, - 'closeBracket': { type: 'integer', minimum: 0 }, - 'switchCase': { type: 'integer', minimum: 0 }, - 'alignAttributesVertically': { type: 'boolean' }, - 'ignores': { + attribute: { type: 'integer', minimum: 0 }, + baseIndent: { type: 'integer', minimum: 0 }, + closeBracket: { type: 'integer', minimum: 0 }, + switchCase: { type: 'integer', minimum: 0 }, + alignAttributesVertically: { type: 'boolean' }, + ignores: { type: 'array', items: { allOf: [ { type: 'string' }, - { not: { type: 'string', pattern: ':exit$' }}, - { not: { type: 'string', pattern: '^\\s*$' }} + { not: { type: 'string', pattern: ':exit$' } }, + { not: { type: 'string', pattern: '^\\s*$' } } ] }, uniqueItems: true, diff --git a/lib/rules/html-quotes.js b/lib/rules/html-quotes.js index 6740a5590..05bb272d5 100644 --- a/lib/rules/html-quotes.js +++ b/lib/rules/html-quotes.js @@ -38,62 +38,69 @@ module.exports = { ] }, - create (context) { + create(context) { const sourceCode = context.getSourceCode() const double = context.options[0] !== 'single' - const avoidEscape = context.options[1] && context.options[1].avoidEscape === true + const avoidEscape = + context.options[1] && context.options[1].avoidEscape === true const quoteChar = double ? '"' : "'" const quoteName = double ? 'double quotes' : 'single quotes' let hasInvalidEOF - return utils.defineTemplateBodyVisitor(context, { - 'VAttribute[value!=null]' (node) { - if (hasInvalidEOF) { - return - } + return utils.defineTemplateBodyVisitor( + context, + { + 'VAttribute[value!=null]'(node) { + if (hasInvalidEOF) { + return + } - const text = sourceCode.getText(node.value) - const firstChar = text[0] + const text = sourceCode.getText(node.value) + const firstChar = text[0] - if (firstChar !== quoteChar) { - const quoted = (firstChar === "'" || firstChar === '"') - if (avoidEscape && quoted) { - const contentText = text.slice(1, -1) - if (contentText.includes(quoteChar)) { - return + if (firstChar !== quoteChar) { + const quoted = firstChar === "'" || firstChar === '"' + if (avoidEscape && quoted) { + const contentText = text.slice(1, -1) + if (contentText.includes(quoteChar)) { + return + } } - } - context.report({ - node: node.value, - loc: node.value.loc, - message: 'Expected to be enclosed by {{kind}}.', - data: { kind: quoteName }, - fix (fixer) { - const contentText = quoted ? text.slice(1, -1) : text + context.report({ + node: node.value, + loc: node.value.loc, + message: 'Expected to be enclosed by {{kind}}.', + data: { kind: quoteName }, + fix(fixer) { + const contentText = quoted ? text.slice(1, -1) : text - const fixToDouble = avoidEscape && !quoted && contentText.includes(quoteChar) - ? ( - double - ? contentText.includes("'") - : !contentText.includes('"') - ) - : double + const fixToDouble = + avoidEscape && !quoted && contentText.includes(quoteChar) + ? double + ? contentText.includes("'") + : !contentText.includes('"') + : double - const quotePattern = fixToDouble ? /"/g : /'/g - const quoteEscaped = fixToDouble ? '"' : ''' - const fixQuoteChar = fixToDouble ? '"' : "'" + const quotePattern = fixToDouble ? /"/g : /'/g + const quoteEscaped = fixToDouble ? '"' : ''' + const fixQuoteChar = fixToDouble ? '"' : "'" - const replacement = fixQuoteChar + contentText.replace(quotePattern, quoteEscaped) + fixQuoteChar - return fixer.replaceText(node.value, replacement) - } - }) + const replacement = + fixQuoteChar + + contentText.replace(quotePattern, quoteEscaped) + + fixQuoteChar + return fixer.replaceText(node.value, replacement) + } + }) + } + } + }, + { + Program(node) { + hasInvalidEOF = utils.hasInvalidEOF(node) } } - }, { - Program (node) { - hasInvalidEOF = utils.hasInvalidEOF(node) - } - }) + ) } } diff --git a/lib/rules/html-self-closing.js b/lib/rules/html-self-closing.js index b64c86ca1..f2fa0b277 100644 --- a/lib/rules/html-self-closing.js +++ b/lib/rules/html-self-closing.js @@ -31,11 +31,14 @@ const ELEMENT_TYPE = Object.freeze({ * @param {Object|undefined} options The raw options object. * @returns {Object} Normalized options. */ -function parseOptions (options) { +function parseOptions(options) { return { - [ELEMENT_TYPE.NORMAL]: (options && options.html && options.html.normal) || 'always', - [ELEMENT_TYPE.VOID]: (options && options.html && options.html.void) || 'never', - [ELEMENT_TYPE.COMPONENT]: (options && options.html && options.html.component) || 'always', + [ELEMENT_TYPE.NORMAL]: + (options && options.html && options.html.normal) || 'always', + [ELEMENT_TYPE.VOID]: + (options && options.html && options.html.void) || 'never', + [ELEMENT_TYPE.COMPONENT]: + (options && options.html && options.html.component) || 'always', [ELEMENT_TYPE.SVG]: (options && options.svg) || 'always', [ELEMENT_TYPE.MATH]: (options && options.math) || 'always' } @@ -46,7 +49,7 @@ function parseOptions (options) { * @param {VElement} node The element node to get. * @returns {string} The elementType of the element. */ -function getElementType (node) { +function getElementType(node) { if (utils.isCustomComponent(node)) { return ELEMENT_TYPE.COMPONENT } @@ -72,9 +75,9 @@ function getElementType (node) { * @param {SourceCode} sourceCode The source code object of the current context. * @returns {boolean} `true` if the element is empty. */ -function isEmpty (node, sourceCode) { +function isEmpty(node, sourceCode) { const start = node.startTag.range[1] - const end = (node.endTag != null) ? node.endTag.range[0] : node.range[1] + const end = node.endTag != null ? node.endTag.range[0] : node.range[1] return sourceCode.text.slice(start, end).trim() === '' } @@ -99,86 +102,106 @@ module.exports = { } }, type: 'array', - items: [{ - type: 'object', - properties: { - html: { - type: 'object', - properties: { - normal: { $ref: '#/definitions/optionValue' }, - void: { $ref: '#/definitions/optionValue' }, - component: { $ref: '#/definitions/optionValue' } + items: [ + { + type: 'object', + properties: { + html: { + type: 'object', + properties: { + normal: { $ref: '#/definitions/optionValue' }, + void: { $ref: '#/definitions/optionValue' }, + component: { $ref: '#/definitions/optionValue' } + }, + additionalProperties: false }, - additionalProperties: false + svg: { $ref: '#/definitions/optionValue' }, + math: { $ref: '#/definitions/optionValue' } }, - svg: { $ref: '#/definitions/optionValue' }, - math: { $ref: '#/definitions/optionValue' } - }, - additionalProperties: false - }], + additionalProperties: false + } + ], maxItems: 1 } }, - create (context) { + create(context) { const sourceCode = context.getSourceCode() const options = parseOptions(context.options[0]) let hasInvalidEOF = false - return utils.defineTemplateBodyVisitor(context, { - 'VElement' (node) { - if (hasInvalidEOF) { - return - } + return utils.defineTemplateBodyVisitor( + context, + { + VElement(node) { + if (hasInvalidEOF) { + return + } - const elementType = getElementType(node) - const mode = options[elementType] + const elementType = getElementType(node) + const mode = options[elementType] - if (mode === 'always' && !node.startTag.selfClosing && isEmpty(node, sourceCode)) { - context.report({ - node, - loc: node.loc, - message: 'Require self-closing on {{elementType}} (<{{name}}>).', - data: { elementType, name: node.rawName }, - fix: (fixer) => { - const tokens = context.parserServices.getTemplateBodyTokenStore() - const close = tokens.getLastToken(node.startTag) - if (close.type !== 'HTMLTagClose') { - return null + if ( + mode === 'always' && + !node.startTag.selfClosing && + isEmpty(node, sourceCode) + ) { + context.report({ + node, + loc: node.loc, + message: 'Require self-closing on {{elementType}} (<{{name}}>).', + data: { elementType, name: node.rawName }, + fix: (fixer) => { + const tokens = context.parserServices.getTemplateBodyTokenStore() + const close = tokens.getLastToken(node.startTag) + if (close.type !== 'HTMLTagClose') { + return null + } + return fixer.replaceTextRange( + [close.range[0], node.range[1]], + '/>' + ) } - return fixer.replaceTextRange([close.range[0], node.range[1]], '/>') - } - }) - } + }) + } - if (mode === 'never' && node.startTag.selfClosing) { - context.report({ - node, - loc: node.loc, - message: 'Disallow self-closing on {{elementType}} (<{{name}}/>).', - data: { elementType, name: node.rawName }, - fix: (fixer) => { - const tokens = context.parserServices.getTemplateBodyTokenStore() - const close = tokens.getLastToken(node.startTag) - if (close.type !== 'HTMLSelfClosingTagClose') { - return null - } - if (elementType === ELEMENT_TYPE.VOID) { - return fixer.replaceText(close, '>') + if (mode === 'never' && node.startTag.selfClosing) { + context.report({ + node, + loc: node.loc, + message: + 'Disallow self-closing on {{elementType}} (<{{name}}/>).', + data: { elementType, name: node.rawName }, + fix: (fixer) => { + const tokens = context.parserServices.getTemplateBodyTokenStore() + const close = tokens.getLastToken(node.startTag) + if (close.type !== 'HTMLSelfClosingTagClose') { + return null + } + if (elementType === ELEMENT_TYPE.VOID) { + return fixer.replaceText(close, '>') + } + // If only `close` is targeted for replacement, it conflicts with `component-name-in-template-casing`, + // so replace the entire element. + // return fixer.replaceText(close, `>`) + const elementPart = sourceCode.text.slice( + node.range[0], + close.range[0] + ) + return fixer.replaceText( + node, + `${elementPart}>` + ) } - // If only `close` is targeted for replacement, it conflicts with `component-name-in-template-casing`, - // so replace the entire element. - // return fixer.replaceText(close, `>`) - const elementPart = sourceCode.text.slice(node.range[0], close.range[0]) - return fixer.replaceText(node, elementPart + `>`) - } - }) + }) + } + } + }, + { + Program(node) { + hasInvalidEOF = utils.hasInvalidEOF(node) } } - }, { - Program (node) { - hasInvalidEOF = utils.hasInvalidEOF(node) - } - }) + ) } } diff --git a/lib/rules/jsx-uses-vars.js b/lib/rules/jsx-uses-vars.js index b5abaf702..2d335dde1 100644 --- a/lib/rules/jsx-uses-vars.js +++ b/lib/rules/jsx-uses-vars.js @@ -45,9 +45,9 @@ module.exports = { schema: [] }, - create (context) { + create(context) { return { - JSXOpeningElement (node) { + JSXOpeningElement(node) { let name if (node.name.name) { // diff --git a/lib/rules/key-spacing.js b/lib/rules/key-spacing.js index f594086a9..27e624517 100644 --- a/lib/rules/key-spacing.js +++ b/lib/rules/key-spacing.js @@ -6,7 +6,6 @@ const { wrapCoreRule } = require('../utils') // eslint-disable-next-line no-invalid-meta, no-invalid-meta-docs-categories -module.exports = wrapCoreRule( - require('eslint/lib/rules/key-spacing'), - { skipDynamicArguments: true } -) +module.exports = wrapCoreRule(require('eslint/lib/rules/key-spacing'), { + skipDynamicArguments: true +}) diff --git a/lib/rules/keyword-spacing.js b/lib/rules/keyword-spacing.js index 6a340bb2a..0b0da6277 100644 --- a/lib/rules/keyword-spacing.js +++ b/lib/rules/keyword-spacing.js @@ -6,7 +6,6 @@ const { wrapCoreRule } = require('../utils') // eslint-disable-next-line no-invalid-meta, no-invalid-meta-docs-categories -module.exports = wrapCoreRule( - require('eslint/lib/rules/keyword-spacing'), - { skipDynamicArguments: true } -) +module.exports = wrapCoreRule(require('eslint/lib/rules/keyword-spacing'), { + skipDynamicArguments: true +}) diff --git a/lib/rules/match-component-file-name.js b/lib/rules/match-component-file-name.js index b5261825e..45d603727 100644 --- a/lib/rules/match-component-file-name.js +++ b/lib/rules/match-component-file-name.js @@ -46,11 +46,13 @@ module.exports = { ] }, - create (context) { + create(context) { const options = context.options[0] const shouldMatchCase = (options && options.shouldMatchCase) || false const extensionsArray = options && options.extensions - const allowedExtensions = Array.isArray(extensionsArray) ? extensionsArray : ['jsx'] + const allowedExtensions = Array.isArray(extensionsArray) + ? extensionsArray + : ['jsx'] const extension = path.extname(context.getFilename()) const filename = path.basename(context.getFilename(), extension) @@ -66,15 +68,18 @@ module.exports = { // Private // ---------------------------------------------------------------------- - function compareNames (name, filename) { + function compareNames(name, filename) { if (shouldMatchCase) { return name === filename } - return casing.pascalCase(name) === filename || casing.kebabCase(name) === filename + return ( + casing.pascalCase(name) === filename || + casing.kebabCase(name) === filename + ) } - function verifyName (node) { + function verifyName(node) { let name if (node.type === 'TemplateLiteral') { const quasis = node.quasis[0] @@ -85,22 +90,25 @@ module.exports = { if (!compareNames(name, filename)) { errors.push({ - node: node, - message: 'Component name `{{name}}` should match file name `{{filename}}`.', + node, + message: + 'Component name `{{name}}` should match file name `{{filename}}`.', data: { filename, name } }) } } - function canVerify (node) { - return node.type === 'Literal' || ( - node.type === 'TemplateLiteral' && - node.expressions.length === 0 && - node.quasis.length === 1 + function canVerify(node) { + return ( + node.type === 'Literal' || + (node.type === 'TemplateLiteral' && + node.expressions.length === 0 && + node.quasis.length === 1) ) } - return Object.assign({}, + return Object.assign( + {}, utils.executeOnCallVueComponent(context, (node) => { if (node.arguments.length === 2) { const argument = node.arguments[0] @@ -111,12 +119,12 @@ module.exports = { } }), utils.executeOnVue(context, (object) => { - const node = object.properties - .find(item => ( + const node = object.properties.find( + (item) => item.type === 'Property' && item.key.name === 'name' && canVerify(item.value) - )) + ) componentCount++ @@ -124,7 +132,7 @@ module.exports = { verifyName(node.value) }), { - 'Program:exit' () { + 'Program:exit'() { if (componentCount > 1) return errors.forEach((error) => context.report(error)) diff --git a/lib/rules/max-attributes-per-line.js b/lib/rules/max-attributes-per-line.js index 2b15523aa..29b6a4e6b 100644 --- a/lib/rules/max-attributes-per-line.js +++ b/lib/rules/max-attributes-per-line.js @@ -66,32 +66,40 @@ module.exports = { ] }, - create: function (context) { + create(context) { const sourceCode = context.getSourceCode() const configuration = parseOptions(context.options[0]) const multilineMaximum = configuration.multiline const singlelinemMaximum = configuration.singleline const canHaveFirstLine = configuration.allowFirstLine - const template = context.parserServices.getTemplateBodyTokenStore && context.parserServices.getTemplateBodyTokenStore() + const template = + context.parserServices.getTemplateBodyTokenStore && + context.parserServices.getTemplateBodyTokenStore() return utils.defineTemplateBodyVisitor(context, { - 'VStartTag' (node) { + VStartTag(node) { const numberOfAttributes = node.attributes.length if (!numberOfAttributes) return - if (utils.isSingleLine(node) && numberOfAttributes > singlelinemMaximum) { + if ( + utils.isSingleLine(node) && + numberOfAttributes > singlelinemMaximum + ) { showErrors(node.attributes.slice(singlelinemMaximum)) } if (!utils.isSingleLine(node)) { - if (!canHaveFirstLine && node.attributes[0].loc.start.line === node.loc.start.line) { + if ( + !canHaveFirstLine && + node.attributes[0].loc.start.line === node.loc.start.line + ) { showErrors([node.attributes[0]]) } groupAttrsByLine(node.attributes) - .filter(attrs => attrs.length > multilineMaximum) - .forEach(attrs => showErrors(attrs.splice(multilineMaximum))) + .filter((attrs) => attrs.length > multilineMaximum) + .forEach((attrs) => showErrors(attrs.splice(multilineMaximum))) } } }) @@ -99,7 +107,7 @@ module.exports = { // ---------------------------------------------------------------------- // Helpers // ---------------------------------------------------------------------- - function parseOptions (options) { + function parseOptions(options) { const defaults = { singleline: 1, multiline: 1, @@ -131,7 +139,7 @@ module.exports = { return defaults } - function showErrors (attributes) { + function showErrors(attributes) { attributes.forEach((prop, i) => { const fix = (fixer) => { if (i !== 0) return null @@ -150,14 +158,14 @@ module.exports = { context.report({ node: prop, loc: prop.loc, - message: '\'{{name}}\' should be on a new line.', + message: "'{{name}}' should be on a new line.", data: { name: sourceCode.getText(prop.key) }, fix }) }) } - function groupAttrsByLine (attributes) { + function groupAttrsByLine(attributes) { const propsPerLine = [[attributes[0]]] attributes.reduce((previous, current) => { diff --git a/lib/rules/max-len.js b/lib/rules/max-len.js index 83bb80910..5e8998233 100644 --- a/lib/rules/max-len.js +++ b/lib/rules/max-len.js @@ -86,7 +86,7 @@ const OPTIONS_OR_INTEGER_SCHEMA = { * @returns {int} The computed line length. * @private */ -function computeLineLength (line, tabWidth) { +function computeLineLength(line, tabWidth) { let extraCharacterCount = 0 line.replace(/\t/gu, (match, offset) => { @@ -107,10 +107,14 @@ function computeLineLength (line, tabWidth) { * @param {ASTNode} comment The comment to inspect * @returns {boolean} If the comment is trailing on the given line */ -function isTrailingComment (line, lineNumber, comment) { - return comment && - (comment.loc.start.line === lineNumber && lineNumber <= comment.loc.end.line) && - (comment.loc.end.line > lineNumber || comment.loc.end.column === line.length) +function isTrailingComment(line, lineNumber, comment) { + return ( + comment && + comment.loc.start.line === lineNumber && + lineNumber <= comment.loc.end.line && + (comment.loc.end.line > lineNumber || + comment.loc.end.column === line.length) + ) } /** @@ -120,14 +124,18 @@ function isTrailingComment (line, lineNumber, comment) { * @param {ASTNode} comment The comment to remove * @returns {boolean} If the comment covers the entire line */ -function isFullLineComment (line, lineNumber, comment) { +function isFullLineComment(line, lineNumber, comment) { const start = comment.loc.start const end = comment.loc.end const isFirstTokenOnLine = !line.slice(0, comment.loc.start.column).trim() - return comment && - (start.line < lineNumber || (start.line === lineNumber && isFirstTokenOnLine)) && - (end.line > lineNumber || (end.line === lineNumber && end.column === line.length)) + return ( + comment && + (start.line < lineNumber || + (start.line === lineNumber && isFirstTokenOnLine)) && + (end.line > lineNumber || + (end.line === lineNumber && end.column === line.length)) + ) } /** @@ -137,7 +145,7 @@ function isFullLineComment (line, lineNumber, comment) { * @param {ASTNode} comment The comment to remove * @returns {string} Line without comment and trailing whitepace */ -function stripTrailingComment (line, comment) { +function stripTrailingComment(line, comment) { // loc.column is zero-indexed return line.slice(0, comment.loc.start.column).replace(/\s+$/u, '') } @@ -151,7 +159,7 @@ function stripTrailingComment (line, comment) { * @returns {void} * @private */ -function ensureArrayAndPush (object, key, value) { +function ensureArrayAndPush(object, key, value) { if (!Array.isArray(object[key])) { object[key] = [] } @@ -166,7 +174,7 @@ function ensureArrayAndPush (object, key, value) { * @returns {Object} the modified accumulator * @private */ -function groupByLineNumber (acc, node) { +function groupByLineNumber(acc, node) { for (let i = node.loc.start.line; i <= node.loc.end.line; ++i) { ensureArrayAndPush(acc, i, node) } @@ -193,12 +201,14 @@ module.exports = { OPTIONS_SCHEMA ], messages: { - max: 'This line has a length of {{lineLength}}. Maximum allowed is {{maxLength}}.', - maxComment: 'This line has a comment length of {{lineLength}}. Maximum allowed is {{maxCommentLength}}.' + max: + 'This line has a length of {{lineLength}}. Maximum allowed is {{maxLength}}.', + maxComment: + 'This line has a comment length of {{lineLength}}. Maximum allowed is {{maxCommentLength}}.' } }, - create (context) { + create(context) { /* * Inspired by http://tools.ietf.org/html/rfc3986#appendix-B, however: * - They're matching an entire string that we know is a URI @@ -215,7 +225,10 @@ module.exports = { const htmlAttributeValues = [] // The options object must be the last option specified… - const options = Object.assign({}, context.options[context.options.length - 1]) + const options = Object.assign( + {}, + context.options[context.options.length - 1] + ) // …but max code length… if (typeof context.options[0] === 'number') { @@ -228,13 +241,15 @@ module.exports = { } const scriptMaxLength = typeof options.code === 'number' ? options.code : 80 - const tabWidth = typeof options.tabWidth === 'number' ? options.tabWidth : 2// default value of `vue/html-indent` - const templateMaxLength = typeof options.template === 'number' ? options.template : scriptMaxLength + const tabWidth = typeof options.tabWidth === 'number' ? options.tabWidth : 2 // default value of `vue/html-indent` + const templateMaxLength = + typeof options.template === 'number' ? options.template : scriptMaxLength const ignoreComments = !!options.ignoreComments const ignoreStrings = !!options.ignoreStrings const ignoreTemplateLiterals = !!options.ignoreTemplateLiterals const ignoreRegExpLiterals = !!options.ignoreRegExpLiterals - const ignoreTrailingComments = !!options.ignoreTrailingComments || !!options.ignoreComments + const ignoreTrailingComments = + !!options.ignoreTrailingComments || !!options.ignoreComments const ignoreUrls = !!options.ignoreUrls const ignoreHTMLAttributeValues = !!options.ignoreHTMLAttributeValues const ignoreHTMLTextContents = !!options.ignoreHTMLTextContents @@ -254,9 +269,14 @@ module.exports = { * * @returns {ASTNode[]} An array of string nodes. */ - function getAllStrings () { - return tokens.filter(token => (token.type === 'String' || - (token.type === 'JSXText' && sourceCode.getNodeByRangeIndex(token.range[0] - 1).type === 'JSXAttribute'))) + function getAllStrings() { + return tokens.filter( + (token) => + token.type === 'String' || + (token.type === 'JSXText' && + sourceCode.getNodeByRangeIndex(token.range[0] - 1).type === + 'JSXAttribute') + ) } /** @@ -264,8 +284,8 @@ module.exports = { * * @returns {ASTNode[]} An array of template literal nodes. */ - function getAllTemplateLiterals () { - return tokens.filter(token => token.type === 'Template') + function getAllTemplateLiterals() { + return tokens.filter((token) => token.type === 'Template') } /** @@ -273,8 +293,8 @@ module.exports = { * * @returns {ASTNode[]} An array of RegExp literal nodes. */ - function getAllRegExpLiterals () { - return tokens.filter(token => token.type === 'RegularExpression') + function getAllRegExpLiterals() { + return tokens.filter((token) => token.type === 'RegularExpression') } /** @@ -282,8 +302,8 @@ module.exports = { * * @returns {ASTNode[]} An array of HTML text nodes. */ - function getAllHTMLTextContents () { - return tokens.filter(token => token.type === 'HTMLText') + function getAllHTMLTextContents() { + return tokens.filter((token) => token.type === 'HTMLText') } /** @@ -292,7 +312,7 @@ module.exports = { * @returns {void} * @private */ - function checkProgramForMaxLength (node) { + function checkProgramForMaxLength(node) { const programNode = node const templateBody = node.templateBody @@ -303,7 +323,9 @@ module.exports = { if (context.parserServices.getTemplateBodyTokenStore && templateBody) { const tokenStore = context.parserServices.getTemplateBodyTokenStore() - const templateTokens = tokenStore.getTokens(templateBody, { includeComments: true }) + const templateTokens = tokenStore.getTokens(templateBody, { + includeComments: true + }) if (templateBody.range[0] < programNode.range[0]) { tokens.push(...templateTokens, ...scriptTokens) @@ -331,8 +353,14 @@ module.exports = { if (scriptTokens.length) { if (scriptComments.length) { scriptLinesRange = [ - Math.min(scriptTokens[0].loc.start.line, scriptComments[0].loc.start.line), - Math.max(scriptTokens[scriptTokens.length - 1].loc.end.line, scriptComments[scriptComments.length - 1].loc.end.line) + Math.min( + scriptTokens[0].loc.start.line, + scriptComments[0].loc.start.line + ), + Math.max( + scriptTokens[scriptTokens.length - 1].loc.end.line, + scriptComments[scriptComments.length - 1].loc.end.line + ) ] } else { scriptLinesRange = [ @@ -346,7 +374,10 @@ module.exports = { scriptComments[scriptComments.length - 1].loc.end.line ] } - const templateLinesRange = templateBody && [templateBody.loc.start.line, templateBody.loc.end.line] + const templateLinesRange = templateBody && [ + templateBody.loc.start.line, + templateBody.loc.end.line + ] // split (honors line-ending) const lines = sourceCode.lines @@ -355,15 +386,24 @@ module.exports = { const stringsByLine = strings.reduce(groupByLineNumber, {}) const templateLiterals = getAllTemplateLiterals() - const templateLiteralsByLine = templateLiterals.reduce(groupByLineNumber, {}) + const templateLiteralsByLine = templateLiterals.reduce( + groupByLineNumber, + {} + ) const regExpLiterals = getAllRegExpLiterals() const regExpLiteralsByLine = regExpLiterals.reduce(groupByLineNumber, {}) - const htmlAttributeValuesByLine = htmlAttributeValues.reduce(groupByLineNumber, {}) + const htmlAttributeValuesByLine = htmlAttributeValues.reduce( + groupByLineNumber, + {} + ) const htmlTextContents = getAllHTMLTextContents() - const htmlTextContentsByLine = htmlTextContents.reduce(groupByLineNumber, {}) + const htmlTextContentsByLine = htmlTextContents.reduce( + groupByLineNumber, + {} + ) const commentsByLine = comments.reduce(groupByLineNumber, {}) @@ -371,16 +411,23 @@ module.exports = { // i is zero-indexed, line numbers are one-indexed const lineNumber = i + 1 - const inScript = (scriptLinesRange && scriptLinesRange[0] <= lineNumber && lineNumber <= scriptLinesRange[1]) - const inTemplate = (templateLinesRange && templateLinesRange[0] <= lineNumber && lineNumber <= templateLinesRange[1]) + const inScript = + scriptLinesRange && + scriptLinesRange[0] <= lineNumber && + lineNumber <= scriptLinesRange[1] + const inTemplate = + templateLinesRange && + templateLinesRange[0] <= lineNumber && + lineNumber <= templateLinesRange[1] // check if line is inside a script or template. if (!inScript && !inTemplate) { // out of range. return } - const maxLength = inScript && inTemplate - ? Math.max(scriptMaxLength, templateMaxLength) - : inScript + const maxLength = + inScript && inTemplate + ? Math.max(scriptMaxLength, templateMaxLength) + : inScript ? scriptMaxLength : templateMaxLength @@ -388,7 +435,8 @@ module.exports = { (ignoreStrings && stringsByLine[lineNumber]) || (ignoreTemplateLiterals && templateLiteralsByLine[lineNumber]) || (ignoreRegExpLiterals && regExpLiteralsByLine[lineNumber]) || - (ignoreHTMLAttributeValues && htmlAttributeValuesByLine[lineNumber]) || + (ignoreHTMLAttributeValues && + htmlAttributeValuesByLine[lineNumber]) || (ignoreHTMLTextContents && htmlTextContentsByLine[lineNumber]) ) { // ignore this line @@ -413,7 +461,10 @@ module.exports = { if (isFullLineComment(line, lineNumber, comment)) { lineIsComment = true textToMeasure = line - } else if (ignoreTrailingComments && isTrailingComment(line, lineNumber, comment)) { + } else if ( + ignoreTrailingComments && + isTrailingComment(line, lineNumber, comment) + ) { textToMeasure = stripTrailingComment(line, comment) // ignore multiple trailing comments in the same line @@ -429,8 +480,10 @@ module.exports = { textToMeasure = line } - if ((ignorePattern && ignorePattern.test(textToMeasure)) || - (ignoreUrls && URL_REGEXP.test(textToMeasure))) { + if ( + (ignorePattern && ignorePattern.test(textToMeasure)) || + (ignoreUrls && URL_REGEXP.test(textToMeasure)) + ) { // ignore this line return } @@ -472,23 +525,19 @@ module.exports = { // Public API // -------------------------------------------------------------------------- - const bodyVisitor = utils.defineTemplateBodyVisitor(context, - { - 'VAttribute[directive=false] > VLiteral' (node) { - htmlAttributeValues.push(node) - } + const bodyVisitor = utils.defineTemplateBodyVisitor(context, { + 'VAttribute[directive=false] > VLiteral'(node) { + htmlAttributeValues.push(node) } - ) + }) - return Object.assign({}, bodyVisitor, - { - 'Program:exit' (node) { - if (bodyVisitor['Program:exit']) { - bodyVisitor['Program:exit'](node) - } - checkProgramForMaxLength(node) + return Object.assign({}, bodyVisitor, { + 'Program:exit'(node) { + if (bodyVisitor['Program:exit']) { + bodyVisitor['Program:exit'](node) } + checkProgramForMaxLength(node) } - ) + }) } } diff --git a/lib/rules/multiline-html-element-content-newline.js b/lib/rules/multiline-html-element-content-newline.js index f4a0bb447..b2332ae5d 100644 --- a/lib/rules/multiline-html-element-content-newline.js +++ b/lib/rules/multiline-html-element-content-newline.js @@ -16,22 +16,27 @@ const INLINE_ELEMENTS = require('../utils/inline-non-void-elements.json') // Helpers // ------------------------------------------------------------------------------ -function isMultilineElement (element) { +function isMultilineElement(element) { return element.loc.start.line < element.endTag.loc.start.line } -function parseOptions (options) { - return Object.assign({ - ignores: ['pre', 'textarea'].concat(INLINE_ELEMENTS), - ignoreWhenEmpty: true, - allowEmptyLines: false - }, options) +function parseOptions(options) { + return Object.assign( + { + ignores: ['pre', 'textarea'].concat(INLINE_ELEMENTS), + ignoreWhenEmpty: true, + allowEmptyLines: false + }, + options + ) } -function getPhrase (lineBreaks) { +function getPhrase(lineBreaks) { switch (lineBreaks) { - case 0: return 'no' - default: return `${lineBreaks}` + case 0: + return 'no' + default: + return `${lineBreaks}` } } /** @@ -41,7 +46,7 @@ function getPhrase (lineBreaks) { * @param {SourceCode} sourceCode The source code object of the current context. * @returns {boolean} `true` if the element is empty. */ -function isEmpty (node, sourceCode) { +function isEmpty(node, sourceCode) { const start = node.startTag.range[1] const end = node.endTag.range[0] return sourceCode.text.slice(start, end).trim() === '' @@ -55,52 +60,62 @@ module.exports = { meta: { type: 'layout', docs: { - description: 'require a line break before and after the contents of a multiline element', + description: + 'require a line break before and after the contents of a multiline element', categories: ['vue3-strongly-recommended', 'strongly-recommended'], - url: 'https://eslint.vuejs.org/rules/multiline-html-element-content-newline.html' + url: + 'https://eslint.vuejs.org/rules/multiline-html-element-content-newline.html' }, fixable: 'whitespace', - schema: [{ - type: 'object', - properties: { - ignoreWhenEmpty: { - type: 'boolean' - }, - ignores: { - type: 'array', - items: { type: 'string' }, - uniqueItems: true, - additionalItems: false + schema: [ + { + type: 'object', + properties: { + ignoreWhenEmpty: { + type: 'boolean' + }, + ignores: { + type: 'array', + items: { type: 'string' }, + uniqueItems: true, + additionalItems: false + }, + allowEmptyLines: { + type: 'boolean' + } }, - allowEmptyLines: { - type: 'boolean' - } - }, - additionalProperties: false - }], + additionalProperties: false + } + ], messages: { - unexpectedAfterClosingBracket: 'Expected 1 line break after opening tag (`<{{name}}>`), but {{actual}} line breaks found.', - unexpectedBeforeOpeningBracket: 'Expected 1 line break before closing tag (``), but {{actual}} line breaks found.' + unexpectedAfterClosingBracket: + 'Expected 1 line break after opening tag (`<{{name}}>`), but {{actual}} line breaks found.', + unexpectedBeforeOpeningBracket: + 'Expected 1 line break before closing tag (``), but {{actual}} line breaks found.' } }, - create (context) { + create(context) { const options = parseOptions(context.options[0]) const ignores = options.ignores const ignoreWhenEmpty = options.ignoreWhenEmpty const allowEmptyLines = options.allowEmptyLines - const template = context.parserServices.getTemplateBodyTokenStore && context.parserServices.getTemplateBodyTokenStore() + const template = + context.parserServices.getTemplateBodyTokenStore && + context.parserServices.getTemplateBodyTokenStore() const sourceCode = context.getSourceCode() let inIgnoreElement - function isIgnoredElement (node) { - return ignores.includes(node.name) || + function isIgnoredElement(node) { + return ( + ignores.includes(node.name) || ignores.includes(casing.pascalCase(node.rawName)) || ignores.includes(casing.kebabCase(node.rawName)) + ) } - function isInvalidLineBreaks (lineBreaks) { + function isInvalidLineBreaks(lineBreaks) { if (allowEmptyLines) { return lineBreaks === 0 } else { @@ -109,7 +124,7 @@ module.exports = { } return utils.defineTemplateBodyVisitor(context, { - 'VElement' (node) { + VElement(node) { if (inIgnoreElement) { return } @@ -127,20 +142,32 @@ module.exports = { return } - const getTokenOption = { includeComments: true, filter: (token) => token.type !== 'HTMLWhitespace' } + const getTokenOption = { + includeComments: true, + filter: (token) => token.type !== 'HTMLWhitespace' + } if ( ignoreWhenEmpty && node.children.length === 0 && - template.getFirstTokensBetween(node.startTag, node.endTag, getTokenOption).length === 0 + template.getFirstTokensBetween( + node.startTag, + node.endTag, + getTokenOption + ).length === 0 ) { return } - const contentFirst = template.getTokenAfter(node.startTag, getTokenOption) + const contentFirst = template.getTokenAfter( + node.startTag, + getTokenOption + ) const contentLast = template.getTokenBefore(node.endTag, getTokenOption) - const beforeLineBreaks = contentFirst.loc.start.line - node.startTag.loc.end.line - const afterLineBreaks = node.endTag.loc.start.line - contentLast.loc.end.line + const beforeLineBreaks = + contentFirst.loc.start.line - node.startTag.loc.end.line + const afterLineBreaks = + node.endTag.loc.start.line - contentLast.loc.end.line if (isInvalidLineBreaks(beforeLineBreaks)) { context.report({ node: template.getLastToken(node.startTag), @@ -153,7 +180,7 @@ module.exports = { name: node.rawName, actual: getPhrase(beforeLineBreaks) }, - fix (fixer) { + fix(fixer) { const range = [node.startTag.range[1], contentFirst.range[0]] return fixer.replaceTextRange(range, '\n') } @@ -176,14 +203,14 @@ module.exports = { name: node.name, actual: getPhrase(afterLineBreaks) }, - fix (fixer) { + fix(fixer) { const range = [contentLast.range[1], node.endTag.range[0]] return fixer.replaceTextRange(range, '\n') } }) } }, - 'VElement:exit' (node) { + 'VElement:exit'(node) { if (inIgnoreElement === node) { inIgnoreElement = null } diff --git a/lib/rules/mustache-interpolation-spacing.js b/lib/rules/mustache-interpolation-spacing.js index 6f7dbf655..83fb7886c 100644 --- a/lib/rules/mustache-interpolation-spacing.js +++ b/lib/rules/mustache-interpolation-spacing.js @@ -30,7 +30,7 @@ module.exports = { ] }, - create (context) { + create(context) { const options = context.options[0] || 'always' const template = context.parserServices.getTemplateBodyTokenStore && @@ -41,7 +41,7 @@ module.exports = { // ---------------------------------------------------------------------- return utils.defineTemplateBodyVisitor(context, { - 'VExpressionContainer[expression!=null]' (node) { + 'VExpressionContainer[expression!=null]'(node) { const openBrace = template.getFirstToken(node) const closeBrace = template.getLastToken(node) @@ -54,8 +54,12 @@ module.exports = { return } - const firstToken = template.getTokenAfter(openBrace, { includeComments: true }) - const lastToken = template.getTokenBefore(closeBrace, { includeComments: true }) + const firstToken = template.getTokenAfter(openBrace, { + includeComments: true + }) + const lastToken = template.getTokenBefore(closeBrace, { + includeComments: true + }) if (options === 'always') { if (openBrace.range[1] === firstToken.range[0]) { @@ -80,7 +84,8 @@ module.exports = { end: firstToken.loc.start }, message: "Expected no space after '{{', but found.", - fix: (fixer) => fixer.removeRange([openBrace.range[1], firstToken.range[0]]) + fix: (fixer) => + fixer.removeRange([openBrace.range[1], firstToken.range[0]]) }) } if (closeBrace.range[0] !== lastToken.range[1]) { @@ -90,7 +95,8 @@ module.exports = { end: closeBrace.loc.end }, message: "Expected no space before '}}', but found.", - fix: (fixer) => fixer.removeRange([lastToken.range[1], closeBrace.range[0]]) + fix: (fixer) => + fixer.removeRange([lastToken.range[1], closeBrace.range[0]]) }) } } diff --git a/lib/rules/name-property-casing.js b/lib/rules/name-property-casing.js index 26ae6bfa7..6e5a52190 100644 --- a/lib/rules/name-property-casing.js +++ b/lib/rules/name-property-casing.js @@ -16,7 +16,8 @@ module.exports = { meta: { type: 'suggestion', docs: { - description: 'enforce specific casing for the name property in Vue components', + description: + 'enforce specific casing for the name property in Vue components', categories: ['vue3-strongly-recommended', 'strongly-recommended'], url: 'https://eslint.vuejs.org/rules/name-property-casing.html', replacedBy: ['component-definition-name-casing'] @@ -30,21 +31,22 @@ module.exports = { ] }, - create (context) { + create(context) { const options = context.options[0] - const caseType = allowedCaseOptions.indexOf(options) !== -1 ? options : 'PascalCase' + const caseType = + allowedCaseOptions.indexOf(options) !== -1 ? options : 'PascalCase' // ---------------------------------------------------------------------- // Public // ---------------------------------------------------------------------- return utils.executeOnVue(context, (obj) => { - const node = obj.properties - .find(item => ( + const node = obj.properties.find( + (item) => item.type === 'Property' && item.key.name === 'name' && item.value.type === 'Literal' - )) + ) if (!node) return @@ -55,9 +57,13 @@ module.exports = { message: 'Property name "{{value}}" is not {{caseType}}.', data: { value: node.value.value, - caseType: caseType + caseType }, - fix: fixer => fixer.replaceText(node.value, node.value.raw.replace(node.value.value, value)) + fix: (fixer) => + fixer.replaceText( + node.value, + node.value.raw.replace(node.value.value, value) + ) }) } }) diff --git a/lib/rules/no-arrow-functions-in-watch.js b/lib/rules/no-arrow-functions-in-watch.js index 4df3ec27d..2fce3f87f 100644 --- a/lib/rules/no-arrow-functions-in-watch.js +++ b/lib/rules/no-arrow-functions-in-watch.js @@ -16,9 +16,11 @@ module.exports = { fixable: null, schema: [] }, - create (context) { + create(context) { return utils.executeOnVue(context, (obj) => { - const watchNode = obj.properties.find((property) => utils.getStaticPropertyName(property) === 'watch') + const watchNode = obj.properties.find( + (property) => utils.getStaticPropertyName(property) === 'watch' + ) if (watchNode == null) { return } @@ -27,7 +29,10 @@ module.exports = { return } for (const property of watchValue.properties) { - if (property.type === 'Property' && property.value.type === 'ArrowFunctionExpression') { + if ( + property.type === 'Property' && + property.value.type === 'ArrowFunctionExpression' + ) { context.report({ node: property, message: 'You should not use an arrow function to define a watcher.' diff --git a/lib/rules/no-async-in-computed-properties.js b/lib/rules/no-async-in-computed-properties.js index 96a29350f..34849d1c6 100644 --- a/lib/rules/no-async-in-computed-properties.js +++ b/lib/rules/no-async-in-computed-properties.js @@ -6,18 +6,9 @@ const utils = require('../utils') -const PROMISE_FUNCTIONS = [ - 'then', - 'catch', - 'finally' -] +const PROMISE_FUNCTIONS = ['then', 'catch', 'finally'] -const PROMISE_METHODS = [ - 'all', - 'race', - 'reject', - 'resolve' -] +const PROMISE_METHODS = ['all', 'race', 'reject', 'resolve'] const TIMED_FUNCTIONS = [ 'setTimeout', @@ -26,30 +17,32 @@ const TIMED_FUNCTIONS = [ 'requestAnimationFrame' ] -function isTimedFunction (node) { - return (( - node.type === 'CallExpression' && - node.callee.type === 'Identifier' && - TIMED_FUNCTIONS.indexOf(node.callee.name) !== -1 - ) || ( - node.type === 'CallExpression' && - node.callee.type === 'MemberExpression' && - node.callee.object.type === 'Identifier' && - node.callee.object.name === 'window' && ( - TIMED_FUNCTIONS.indexOf(node.callee.property.name) !== -1 - ) - )) && node.arguments.length +function isTimedFunction(node) { + return ( + ((node.type === 'CallExpression' && + node.callee.type === 'Identifier' && + TIMED_FUNCTIONS.indexOf(node.callee.name) !== -1) || + (node.type === 'CallExpression' && + node.callee.type === 'MemberExpression' && + node.callee.object.type === 'Identifier' && + node.callee.object.name === 'window' && + TIMED_FUNCTIONS.indexOf(node.callee.property.name) !== -1)) && + node.arguments.length + ) } -function isPromise (node) { - if (node.type === 'CallExpression' && node.callee.type === 'MemberExpression') { - return ( // hello.PROMISE_FUNCTION() - node.callee.property.type === 'Identifier' && - PROMISE_FUNCTIONS.indexOf(node.callee.property.name) !== -1 - ) || ( // Promise.PROMISE_METHOD() - node.callee.object.type === 'Identifier' && - node.callee.object.name === 'Promise' && - PROMISE_METHODS.indexOf(node.callee.property.name) !== -1 +function isPromise(node) { + if ( + node.type === 'CallExpression' && + node.callee.type === 'MemberExpression' + ) { + return ( + // hello.PROMISE_FUNCTION() + (node.callee.property.type === 'Identifier' && + PROMISE_FUNCTIONS.indexOf(node.callee.property.name) !== -1) || // Promise.PROMISE_METHOD() + (node.callee.object.type === 'Identifier' && + node.callee.object.name === 'Promise' && + PROMISE_METHODS.indexOf(node.callee.property.name) !== -1) ) } return false @@ -71,7 +64,7 @@ module.exports = { schema: [] }, - create (context) { + create(context) { const computedPropertiesMap = new Map() let scopeStack = { upper: null, body: null } @@ -83,7 +76,7 @@ module.exports = { timed: 'timed function' } - function onFunctionEnter (node, { node: vueNode }) { + function onFunctionEnter(node, { node: vueNode }) { if (node.async) { verify(node, node.body, 'async', computedPropertiesMap.get(vueNode)) } @@ -91,12 +84,12 @@ module.exports = { scopeStack = { upper: scopeStack, body: node.body } } - function onFunctionExit () { + function onFunctionExit() { scopeStack = scopeStack.upper } - function verify (node, targetBody, type, computedProperties) { - computedProperties.forEach(cp => { + function verify(node, targetBody, type, computedProperties) { + computedProperties.forEach((cp) => { if ( cp.value && node.loc.start.line >= cp.value.loc.start.line && @@ -104,8 +97,9 @@ module.exports = { targetBody === cp.value ) { context.report({ - node: node, - message: 'Unexpected {{expressionName}} in "{{propertyName}}" computed property.', + node, + message: + 'Unexpected {{expressionName}} in "{{propertyName}}" computed property.', data: { expressionName: expressionTypes[type], propertyName: cp.key @@ -115,28 +109,48 @@ module.exports = { }) } return utils.defineVueVisitor(context, { - onVueObjectEnter (node) { + onVueObjectEnter(node) { computedPropertiesMap.set(node, utils.getComputedProperties(node)) }, ':function': onFunctionEnter, ':function:exit': onFunctionExit, - NewExpression (node, { node: vueNode }) { + NewExpression(node, { node: vueNode }) { if (node.callee.name === 'Promise') { - verify(node, scopeStack.body, 'new', computedPropertiesMap.get(vueNode)) + verify( + node, + scopeStack.body, + 'new', + computedPropertiesMap.get(vueNode) + ) } }, - CallExpression (node, { node: vueNode }) { + CallExpression(node, { node: vueNode }) { if (isPromise(node)) { - verify(node, scopeStack.body, 'promise', computedPropertiesMap.get(vueNode)) + verify( + node, + scopeStack.body, + 'promise', + computedPropertiesMap.get(vueNode) + ) } else if (isTimedFunction(node)) { - verify(node, scopeStack.body, 'timed', computedPropertiesMap.get(vueNode)) + verify( + node, + scopeStack.body, + 'timed', + computedPropertiesMap.get(vueNode) + ) } }, - AwaitExpression (node, { node: vueNode }) { - verify(node, scopeStack.body, 'await', computedPropertiesMap.get(vueNode)) + AwaitExpression(node, { node: vueNode }) { + verify( + node, + scopeStack.body, + 'await', + computedPropertiesMap.get(vueNode) + ) } }) } diff --git a/lib/rules/no-boolean-default.js b/lib/rules/no-boolean-default.js index 84125af39..1f1e192df 100644 --- a/lib/rules/no-boolean-default.js +++ b/lib/rules/no-boolean-default.js @@ -10,7 +10,7 @@ const utils = require('../utils') // Rule Definition // ------------------------------------------------------------------------------ -function isBooleanProp (prop) { +function isBooleanProp(prop) { return ( prop.type === 'Property' && prop.key.type === 'Identifier' && @@ -20,17 +20,17 @@ function isBooleanProp (prop) { ) } -function getBooleanProps (props) { - return props - .filter(prop => ( +function getBooleanProps(props) { + return props.filter( + (prop) => prop.value && prop.value.properties && prop.value.properties.find(isBooleanProp) - )) + ) } -function getDefaultNode (propDef) { - return propDef.value.properties.find(p => { +function getDefaultNode(propDef) { + return propDef.value.properties.find((p) => { return ( p.type === 'Property' && p.key.type === 'Identifier' && @@ -55,7 +55,7 @@ module.exports = { ] }, - create (context) { + create(context) { return utils.executeOnVueComponent(context, (obj) => { const props = utils.getComponentProps(obj) const booleanProps = getBooleanProps(props) @@ -72,16 +72,14 @@ module.exports = { if (defaultNode) { context.report({ node: defaultNode, - message: 'Boolean prop should not set a default (Vue defaults it to false).' + message: + 'Boolean prop should not set a default (Vue defaults it to false).' }) } break case 'default-false': - if ( - defaultNode && - defaultNode.value.value !== false - ) { + if (defaultNode && defaultNode.value.value !== false) { context.report({ node: defaultNode, message: 'Boolean prop should only be defaulted to false.' diff --git a/lib/rules/no-confusing-v-for-v-if.js b/lib/rules/no-confusing-v-for-v-if.js index e99628cfc..43951a090 100644 --- a/lib/rules/no-confusing-v-for-v-if.js +++ b/lib/rules/no-confusing-v-for-v-if.js @@ -20,12 +20,12 @@ const utils = require('../utils') * @param {ASTNode} vIf The `v-if` attribute node to check. * @returns {boolean} `true` if the `v-if` is using the variable which is defined by the `v-for` directive. */ -function isUsingIterationVar (vIf) { +function isUsingIterationVar(vIf) { const element = vIf.parent.parent - return vIf.value.references.some(reference => - element.variables.some(variable => - variable.id.name === reference.id.name && - variable.kind === 'v-for' + return vIf.value.references.some((reference) => + element.variables.some( + (variable) => + variable.id.name === reference.id.name && variable.kind === 'v-for' ) ) } @@ -48,9 +48,9 @@ module.exports = { schema: [] }, - create (context) { + create(context) { return utils.defineTemplateBodyVisitor(context, { - "VAttribute[directive=true][key.name.name='if']" (node) { + "VAttribute[directive=true][key.name.name='if']"(node) { const element = node.parent.parent if (utils.hasDirective(element, 'for') && !isUsingIterationVar(node)) { diff --git a/lib/rules/no-custom-modifiers-on-v-model.js b/lib/rules/no-custom-modifiers-on-v-model.js index aa2fef9a5..ea80fb7a6 100644 --- a/lib/rules/no-custom-modifiers-on-v-model.js +++ b/lib/rules/no-custom-modifiers-on-v-model.js @@ -31,12 +31,13 @@ module.exports = { fixable: null, schema: [], messages: { - notSupportedModifier: "'v-model' directives don't support the modifier '{{name}}'." + notSupportedModifier: + "'v-model' directives don't support the modifier '{{name}}'." } }, - create (context) { + create(context) { return utils.defineTemplateBodyVisitor(context, { - "VAttribute[directive=true][key.name.name='model']" (node) { + "VAttribute[directive=true][key.name.name='model']"(node) { const element = node.parent.parent if (utils.isCustomComponent(element)) { diff --git a/lib/rules/no-deprecated-data-object-declaration.js b/lib/rules/no-deprecated-data-object-declaration.js index aa9c6d55d..02422c7e5 100644 --- a/lib/rules/no-deprecated-data-object-declaration.js +++ b/lib/rules/no-deprecated-data-object-declaration.js @@ -10,15 +10,15 @@ const utils = require('../utils') -function isOpenParen (token) { +function isOpenParen(token) { return token.type === 'Punctuator' && token.value === '(' } -function isCloseParen (token) { +function isCloseParen(token) { return token.type === 'Punctuator' && token.value === ')' } -function getFirstAndLastTokens (node, sourceCode) { +function getFirstAndLastTokens(node, sourceCode) { let first = sourceCode.getFirstToken(node) let last = sourceCode.getLastToken(node) @@ -43,35 +43,39 @@ module.exports = { meta: { type: 'problem', docs: { - description: 'disallow using deprecated object declaration on data (in Vue.js 3.0.0+)', + description: + 'disallow using deprecated object declaration on data (in Vue.js 3.0.0+)', categories: ['vue3-essential'], - url: 'https://eslint.vuejs.org/rules/no-deprecated-data-object-declaration.html' + url: + 'https://eslint.vuejs.org/rules/no-deprecated-data-object-declaration.html' }, fixable: 'code', schema: [], messages: { - objectDeclarationIsDeprecated: "Object declaration on \'data\' property is deprecated. Using function declaration instead." + objectDeclarationIsDeprecated: + "Object declaration on 'data' property is deprecated. Using function declaration instead." } }, - create (context) { + create(context) { const sourceCode = context.getSourceCode() return utils.executeOnVue(context, (obj) => { obj.properties - .filter(p => - p.type === 'Property' && - p.key.type === 'Identifier' && - p.key.name === 'data' && - p.value.type !== 'FunctionExpression' && - p.value.type !== 'ArrowFunctionExpression' && - p.value.type !== 'Identifier' + .filter( + (p) => + p.type === 'Property' && + p.key.type === 'Identifier' && + p.key.name === 'data' && + p.value.type !== 'FunctionExpression' && + p.value.type !== 'ArrowFunctionExpression' && + p.value.type !== 'Identifier' ) - .forEach(p => { + .forEach((p) => { context.report({ node: p, messageId: 'objectDeclarationIsDeprecated', - fix (fixer) { + fix(fixer) { const tokens = getFirstAndLastTokens(p.value, sourceCode) return [ diff --git a/lib/rules/no-deprecated-dollar-listeners-api.js b/lib/rules/no-deprecated-dollar-listeners-api.js index b833b462b..7c60cbbe5 100644 --- a/lib/rules/no-deprecated-dollar-listeners-api.js +++ b/lib/rules/no-deprecated-dollar-listeners-api.js @@ -20,7 +20,8 @@ module.exports = { docs: { description: 'disallow using deprecated `$listeners` (in Vue.js 3.0.0+)', categories: ['vue3-essential'], - url: 'https://eslint.vuejs.org/rules/no-deprecated-dollar-listeners-api.html' + url: + 'https://eslint.vuejs.org/rules/no-deprecated-dollar-listeners-api.html' }, fixable: null, schema: [], @@ -29,11 +30,11 @@ module.exports = { } }, - create (context) { + create(context) { return utils.defineTemplateBodyVisitor( context, { - 'VExpressionContainer' (node) { + VExpressionContainer(node) { for (const reference of node.references) { if (reference.variable != null) { // Not vm reference @@ -48,26 +49,24 @@ module.exports = { } } }, - utils.defineVueVisitor(context, - { - 'MemberExpression' (node) { - if ( - node.property.type !== 'Identifier' || - node.property.name !== '$listeners' - ) { - return - } - if (!utils.isThis(node.object, context)) { - return - } - - context.report({ - node: node.property, - messageId: 'deprecated' - }) + utils.defineVueVisitor(context, { + MemberExpression(node) { + if ( + node.property.type !== 'Identifier' || + node.property.name !== '$listeners' + ) { + return } + if (!utils.isThis(node.object, context)) { + return + } + + context.report({ + node: node.property, + messageId: 'deprecated' + }) } - ) + }) ) } } diff --git a/lib/rules/no-deprecated-events-api.js b/lib/rules/no-deprecated-events-api.js index 7989ffb5e..05d50bac1 100644 --- a/lib/rules/no-deprecated-events-api.js +++ b/lib/rules/no-deprecated-events-api.js @@ -25,32 +25,31 @@ module.exports = { fixable: null, schema: [], messages: { - noDeprecatedEventsApi: 'The Events api `$on`, `$off` `$once` is deprecated. Using external library instead, for example mitt.' + noDeprecatedEventsApi: + 'The Events api `$on`, `$off` `$once` is deprecated. Using external library instead, for example mitt.' } }, - create (context) { - return utils.defineVueVisitor(context, - { - 'CallExpression > MemberExpression' (node) { - const call = node.parent - if ( - call.callee !== node || - node.property.type !== 'Identifier' || - !['$on', '$off', '$once'].includes(node.property.name) - ) { - return - } - if (!utils.isThis(node.object, context)) { - return - } - - context.report({ - node: node.property, - messageId: 'noDeprecatedEventsApi' - }) + create(context) { + return utils.defineVueVisitor(context, { + 'CallExpression > MemberExpression'(node) { + const call = node.parent + if ( + call.callee !== node || + node.property.type !== 'Identifier' || + !['$on', '$off', '$once'].includes(node.property.name) + ) { + return + } + if (!utils.isThis(node.object, context)) { + return } + + context.report({ + node: node.property, + messageId: 'noDeprecatedEventsApi' + }) } - ) + }) } } diff --git a/lib/rules/no-deprecated-filter.js b/lib/rules/no-deprecated-filter.js index c0e6c945e..0229d6e2e 100644 --- a/lib/rules/no-deprecated-filter.js +++ b/lib/rules/no-deprecated-filter.js @@ -18,7 +18,8 @@ module.exports = { meta: { type: 'problem', docs: { - description: 'disallow using deprecated filters syntax (in Vue.js 3.0.0+)', + description: + 'disallow using deprecated filters syntax (in Vue.js 3.0.0+)', categories: ['vue3-essential'], url: 'https://eslint.vuejs.org/rules/no-deprecated-filter.html' }, @@ -29,9 +30,9 @@ module.exports = { } }, - create: function (context) { + create(context) { return utils.defineTemplateBodyVisitor(context, { - 'VFilterSequenceExpression' (node) { + VFilterSequenceExpression(node) { context.report({ node, loc: node.loc, diff --git a/lib/rules/no-deprecated-functional-template.js b/lib/rules/no-deprecated-functional-template.js index 7ab886230..cfaa8d957 100644 --- a/lib/rules/no-deprecated-functional-template.js +++ b/lib/rules/no-deprecated-functional-template.js @@ -18,9 +18,11 @@ module.exports = { meta: { type: 'problem', docs: { - description: 'disallow using deprecated the `functional` template (in Vue.js 3.0.0+)', + description: + 'disallow using deprecated the `functional` template (in Vue.js 3.0.0+)', categories: ['vue3-essential'], - url: 'https://eslint.vuejs.org/rules/no-deprecated-functional-template.html' + url: + 'https://eslint.vuejs.org/rules/no-deprecated-functional-template.html' }, fixable: null, schema: [], @@ -29,9 +31,9 @@ module.exports = { } }, - create (context) { + create(context) { return { - Program (program) { + Program(program) { const element = program.templateBody if (element == null) { return diff --git a/lib/rules/no-deprecated-html-element-is.js b/lib/rules/no-deprecated-html-element-is.js index b45a700f3..d62c3b479 100644 --- a/lib/rules/no-deprecated-html-element-is.js +++ b/lib/rules/no-deprecated-html-element-is.js @@ -18,7 +18,8 @@ module.exports = { meta: { type: 'problem', docs: { - description: 'disallow using deprecated the `is` attribute on HTML elements (in Vue.js 3.0.0+)', + description: + 'disallow using deprecated the `is` attribute on HTML elements (in Vue.js 3.0.0+)', categories: ['vue3-essential'], url: 'https://eslint.vuejs.org/rules/no-deprecated-html-element-is.html' }, @@ -29,9 +30,11 @@ module.exports = { } }, - create: function (context) { + create(context) { return utils.defineTemplateBodyVisitor(context, { - "VAttribute[directive=true][key.name.name='bind'][key.argument.name='is'], VAttribute[directive=false][key.name='is']" (node) { + "VAttribute[directive=true][key.name.name='bind'][key.argument.name='is'], VAttribute[directive=false][key.name='is']"( + node + ) { const element = node.parent.parent if ( !utils.isHtmlWellKnownElementName(element.rawName) && diff --git a/lib/rules/no-deprecated-inline-template.js b/lib/rules/no-deprecated-inline-template.js index ff57a227e..69bdfda46 100644 --- a/lib/rules/no-deprecated-inline-template.js +++ b/lib/rules/no-deprecated-inline-template.js @@ -18,7 +18,8 @@ module.exports = { meta: { type: 'problem', docs: { - description: 'disallow using deprecated `inline-template` attribute (in Vue.js 3.0.0+)', + description: + 'disallow using deprecated `inline-template` attribute (in Vue.js 3.0.0+)', categories: ['vue3-essential'], url: 'https://eslint.vuejs.org/rules/no-deprecated-inline-template.html' }, @@ -29,9 +30,11 @@ module.exports = { } }, - create: function (context) { + create(context) { return utils.defineTemplateBodyVisitor(context, { - "VAttribute[directive=false] > VIdentifier[rawName='inline-template']" (node) { + "VAttribute[directive=false] > VIdentifier[rawName='inline-template']"( + node + ) { context.report({ node, loc: node.loc, diff --git a/lib/rules/no-deprecated-scope-attribute.js b/lib/rules/no-deprecated-scope-attribute.js index 239bdf5e6..24ef41042 100644 --- a/lib/rules/no-deprecated-scope-attribute.js +++ b/lib/rules/no-deprecated-scope-attribute.js @@ -21,8 +21,10 @@ module.exports = { forbiddenScopeAttribute: '`scope` attributes are deprecated.' } }, - create (context) { - const templateBodyVisitor = scopeAttribute.createTemplateBodyVisitor(context) + create(context) { + const templateBodyVisitor = scopeAttribute.createTemplateBodyVisitor( + context + ) return utils.defineTemplateBodyVisitor(context, templateBodyVisitor) } } diff --git a/lib/rules/no-deprecated-slot-attribute.js b/lib/rules/no-deprecated-slot-attribute.js index 416179c83..c7174c12a 100644 --- a/lib/rules/no-deprecated-slot-attribute.js +++ b/lib/rules/no-deprecated-slot-attribute.js @@ -21,7 +21,7 @@ module.exports = { forbiddenSlotAttribute: '`slot` attributes are deprecated.' } }, - create (context) { + create(context) { const templateBodyVisitor = slotAttribute.createTemplateBodyVisitor(context) return utils.defineTemplateBodyVisitor(context, templateBodyVisitor) } diff --git a/lib/rules/no-deprecated-slot-scope-attribute.js b/lib/rules/no-deprecated-slot-scope-attribute.js index 3965493ea..1356016ed 100644 --- a/lib/rules/no-deprecated-slot-scope-attribute.js +++ b/lib/rules/no-deprecated-slot-scope-attribute.js @@ -11,9 +11,11 @@ module.exports = { meta: { type: 'suggestion', docs: { - description: 'disallow deprecated `slot-scope` attribute (in Vue.js 2.6.0+)', + description: + 'disallow deprecated `slot-scope` attribute (in Vue.js 2.6.0+)', categories: ['vue3-essential'], - url: 'https://eslint.vuejs.org/rules/no-deprecated-slot-scope-attribute.html' + url: + 'https://eslint.vuejs.org/rules/no-deprecated-slot-scope-attribute.html' }, fixable: 'code', schema: [], @@ -21,8 +23,11 @@ module.exports = { forbiddenSlotScopeAttribute: '`slot-scope` are deprecated.' } }, - create (context) { - const templateBodyVisitor = slotScopeAttribute.createTemplateBodyVisitor(context, { fixToUpgrade: true }) + create(context) { + const templateBodyVisitor = slotScopeAttribute.createTemplateBodyVisitor( + context, + { fixToUpgrade: true } + ) return utils.defineTemplateBodyVisitor(context, templateBodyVisitor) } } diff --git a/lib/rules/no-deprecated-v-bind-sync.js b/lib/rules/no-deprecated-v-bind-sync.js index b4c6fe8b1..b84ebf4de 100644 --- a/lib/rules/no-deprecated-v-bind-sync.js +++ b/lib/rules/no-deprecated-v-bind-sync.js @@ -18,20 +18,22 @@ module.exports = { meta: { type: 'problem', docs: { - description: 'disallow use of deprecated `.sync` modifier on `v-bind` directive (in Vue.js 3.0.0+)', + description: + 'disallow use of deprecated `.sync` modifier on `v-bind` directive (in Vue.js 3.0.0+)', categories: ['vue3-essential'], url: 'https://eslint.vuejs.org/rules/no-deprecated-v-bind-sync.html' }, fixable: 'code', schema: [], messages: { - syncModifierIsDeprecated: "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + syncModifierIsDeprecated: + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." } }, - create (context) { + create(context) { return utils.defineTemplateBodyVisitor(context, { - "VAttribute[directive=true][key.name.name='bind']" (node) { - if (node.key.modifiers.map(mod => mod.name).includes('sync')) { + "VAttribute[directive=true][key.name.name='bind']"(node) { + if (node.key.modifiers.map((mod) => mod.name).includes('sync')) { context.report({ node, loc: node.loc, @@ -43,7 +45,9 @@ module.exports = { return } - const bindArgument = context.getSourceCode().getText(node.key.argument) + const bindArgument = context + .getSourceCode() + .getText(node.key.argument) return fixer.replaceText(node.key, `v-model:${bindArgument}`) } }) diff --git a/lib/rules/no-deprecated-v-on-native-modifier.js b/lib/rules/no-deprecated-v-on-native-modifier.js index d93755436..16f1987c5 100644 --- a/lib/rules/no-deprecated-v-on-native-modifier.js +++ b/lib/rules/no-deprecated-v-on-native-modifier.js @@ -18,9 +18,11 @@ module.exports = { meta: { type: 'problem', docs: { - description: 'disallow using deprecated `.native` modifiers (in Vue.js 3.0.0+)', + description: + 'disallow using deprecated `.native` modifiers (in Vue.js 3.0.0+)', categories: ['vue3-essential'], - url: 'https://eslint.vuejs.org/rules/no-deprecated-v-on-native-modifier.html' + url: + 'https://eslint.vuejs.org/rules/no-deprecated-v-on-native-modifier.html' }, fixable: null, schema: [], @@ -29,9 +31,11 @@ module.exports = { } }, - create (context) { + create(context) { return utils.defineTemplateBodyVisitor(context, { - "VAttribute[directive=true][key.name.name='on'] > VDirectiveKey > VIdentifier[name='native']" (node) { + "VAttribute[directive=true][key.name.name='on'] > VDirectiveKey > VIdentifier[name='native']"( + node + ) { const key = node.parent if (!key.modifiers.includes(node)) return diff --git a/lib/rules/no-deprecated-v-on-number-modifiers.js b/lib/rules/no-deprecated-v-on-number-modifiers.js index 6e5125e4d..bf1fb88bd 100644 --- a/lib/rules/no-deprecated-v-on-number-modifiers.js +++ b/lib/rules/no-deprecated-v-on-number-modifiers.js @@ -19,27 +19,30 @@ module.exports = { meta: { type: 'problem', docs: { - description: 'disallow using deprecated number (keycode) modifiers (in Vue.js 3.0.0+)', + description: + 'disallow using deprecated number (keycode) modifiers (in Vue.js 3.0.0+)', categories: ['vue3-essential'], - url: 'https://eslint.vuejs.org/rules/no-deprecated-v-on-number-modifiers.html' + url: + 'https://eslint.vuejs.org/rules/no-deprecated-v-on-number-modifiers.html' }, fixable: 'code', schema: [], messages: { - numberModifierIsDeprecated: "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + numberModifierIsDeprecated: + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." } }, - create (context) { + create(context) { return utils.defineTemplateBodyVisitor(context, { - "VAttribute[directive=true][key.name.name='on'] > VDirectiveKey" (node) { - const modifier = node.modifiers.find(mod => Number.isInteger(parseInt(mod.name, 10))) + "VAttribute[directive=true][key.name.name='on'] > VDirectiveKey"(node) { + const modifier = node.modifiers.find((mod) => + Number.isInteger(parseInt(mod.name, 10)) + ) if (!modifier) return const keyCodes = parseInt(modifier.name, 10) - if ( - keyCodes > 9 || keyCodes < 0 - ) { + if (keyCodes > 9 || keyCodes < 0) { context.report({ node: modifier, messageId: 'numberModifierIsDeprecated', diff --git a/lib/rules/no-deprecated-vue-config-keycodes.js b/lib/rules/no-deprecated-vue-config-keycodes.js index 9bae48ab7..0de109ef1 100644 --- a/lib/rules/no-deprecated-vue-config-keycodes.js +++ b/lib/rules/no-deprecated-vue-config-keycodes.js @@ -12,9 +12,11 @@ module.exports = { meta: { type: 'problem', docs: { - description: 'disallow using deprecated `Vue.config.keyCodes` (in Vue.js 3.0.0+)', + description: + 'disallow using deprecated `Vue.config.keyCodes` (in Vue.js 3.0.0+)', categories: ['vue3-essential'], - url: 'https://eslint.vuejs.org/rules/no-deprecated-vue-config-keycodes.html' + url: + 'https://eslint.vuejs.org/rules/no-deprecated-vue-config-keycodes.html' }, fixable: null, schema: [], @@ -23,15 +25,19 @@ module.exports = { } }, - create: function (context) { + create(context) { return { - "MemberExpression[property.type='Identifier'][property.name='keyCodes']" (node) { + "MemberExpression[property.type='Identifier'][property.name='keyCodes']"( + node + ) { const config = node.object - if (config.type !== 'MemberExpression' || + if ( + config.type !== 'MemberExpression' || config.property.type !== 'Identifier' || config.property.name !== 'config' || config.object.type !== 'Identifier' || - config.object.name !== 'Vue') { + config.object.name !== 'Vue' + ) { return } context.report({ diff --git a/lib/rules/no-dupe-keys.js b/lib/rules/no-dupe-keys.js index 28018e445..dfbebdedf 100644 --- a/lib/rules/no-dupe-keys.js +++ b/lib/rules/no-dupe-keys.js @@ -34,7 +34,7 @@ module.exports = { ] }, - create (context) { + create(context) { const options = context.options[0] || {} const groups = new Set(GROUP_NAMES.concat(options.groups || [])) diff --git a/lib/rules/no-duplicate-attr-inheritance.js b/lib/rules/no-duplicate-attr-inheritance.js index 6ed2da07d..78e00b326 100644 --- a/lib/rules/no-duplicate-attr-inheritance.js +++ b/lib/rules/no-duplicate-attr-inheritance.js @@ -14,7 +14,8 @@ module.exports = { meta: { type: 'suggestion', docs: { - description: 'enforce `inheritAttrs` to be set to `false` when using `v-bind="$attrs"`', + description: + 'enforce `inheritAttrs` to be set to `false` when using `v-bind="$attrs"`', categories: undefined, recommended: false, url: 'https://eslint.vuejs.org/rules/no-duplicate-attr-inheritance.html' @@ -25,23 +26,29 @@ module.exports = { ] }, - create (context) { + create(context) { let inheritsAttrs = true return Object.assign( utils.executeOnVue(context, (node) => { - const inheritAttrsProp = node.properties.find(prop => (prop.type === 'Property' && utils.getStaticPropertyName(prop) === 'inheritAttrs')) + const inheritAttrsProp = node.properties.find( + (prop) => + prop.type === 'Property' && + utils.getStaticPropertyName(prop) === 'inheritAttrs' + ) if (inheritAttrsProp && inheritAttrsProp.value.type === 'Literal') { inheritsAttrs = inheritAttrsProp.value.value } }), utils.defineTemplateBodyVisitor(context, { - "VAttribute[directive=true][key.name.name='bind'][key.argument=null] > VExpressionContainer" (node) { + "VAttribute[directive=true][key.name.name='bind'][key.argument=null] > VExpressionContainer"( + node + ) { if (!inheritsAttrs) { return } - const attrsRef = node.references.find(reference => { + const attrsRef = node.references.find((reference) => { if (reference.variable != null) { // Not vm reference return false diff --git a/lib/rules/no-duplicate-attributes.js b/lib/rules/no-duplicate-attributes.js index 374daa39e..023dacf42 100644 --- a/lib/rules/no-duplicate-attributes.js +++ b/lib/rules/no-duplicate-attributes.js @@ -20,7 +20,7 @@ const utils = require('../utils') * @param {ASTNode} attribute The attribute node to get. * @returns {string} The name of the attribute. */ -function getName (attribute) { +function getName(attribute) { if (!attribute.directive) { return attribute.key.name } @@ -59,7 +59,7 @@ module.exports = { ] }, - create (context) { + create(context) { const options = context.options[0] || {} const allowCoexistStyle = options.allowCoexistStyle !== false const allowCoexistClass = options.allowCoexistClass !== false @@ -67,19 +67,22 @@ module.exports = { const directiveNames = new Set() const attributeNames = new Set() - function isDuplicate (name, isDirective) { - if ((allowCoexistStyle && name === 'style') || (allowCoexistClass && name === 'class')) { + function isDuplicate(name, isDirective) { + if ( + (allowCoexistStyle && name === 'style') || + (allowCoexistClass && name === 'class') + ) { return isDirective ? directiveNames.has(name) : attributeNames.has(name) } return directiveNames.has(name) || attributeNames.has(name) } return utils.defineTemplateBodyVisitor(context, { - 'VStartTag' () { + VStartTag() { directiveNames.clear() attributeNames.clear() }, - 'VAttribute' (node) { + VAttribute(node) { const name = getName(node) if (name == null) { return diff --git a/lib/rules/no-extra-parens.js b/lib/rules/no-extra-parens.js index d875659b5..4cc865a5b 100644 --- a/lib/rules/no-extra-parens.js +++ b/lib/rules/no-extra-parens.js @@ -7,13 +7,10 @@ const { isParenthesized } = require('eslint-utils') const { wrapCoreRule } = require('../utils') // eslint-disable-next-line no-invalid-meta, no-invalid-meta-docs-categories -module.exports = wrapCoreRule( - require('eslint/lib/rules/no-extra-parens'), - { - skipDynamicArguments: true, - create: createForVueSyntax - } -) +module.exports = wrapCoreRule(require('eslint/lib/rules/no-extra-parens'), { + skipDynamicArguments: true, + create: createForVueSyntax +}) /** * @typedef {import('vue-eslint-parser').AST.Token} Token @@ -27,7 +24,7 @@ module.exports = wrapCoreRule( * @param {Token} token The token to check. * @returns {boolean} `true` if the token is a left parenthesis. */ -function isLeftParen (token) { +function isLeftParen(token) { return token.type === 'Punctuator' && token.value === '(' } @@ -36,7 +33,7 @@ function isLeftParen (token) { * @param {Token} token The token to check. * @returns {boolean} `true` if the token is a right parenthesis. */ -function isRightParen (token) { +function isRightParen(token) { return token.type === 'Punctuator' && token.value === ')' } @@ -45,7 +42,7 @@ function isRightParen (token) { * @param {Token} token The token to check. * @returns {boolean} `true` if the token is a left brace. */ -function isLeftBrace (token) { +function isLeftBrace(token) { return token.type === 'Punctuator' && token.value === '{' } @@ -54,7 +51,7 @@ function isLeftBrace (token) { * @param {Token} token The token to check. * @returns {boolean} `true` if the token is a right brace. */ -function isRightBrace (token) { +function isRightBrace(token) { return token.type === 'Punctuator' && token.value === '}' } @@ -63,7 +60,7 @@ function isRightBrace (token) { * @param {Token} token The token to check. * @returns {boolean} `true` if the token is a left bracket. */ -function isLeftBracket (token) { +function isLeftBracket(token) { return token.type === 'Punctuator' && token.value === '[' } @@ -72,7 +69,7 @@ function isLeftBracket (token) { * @param {Token} token The token to check. * @returns {boolean} `true` if the token is a right bracket. */ -function isRightBracket (token) { +function isRightBracket(token) { return token.type === 'Punctuator' && token.value === ']' } @@ -81,19 +78,23 @@ function isRightBracket (token) { * @param {ASTNode} node The node to check * @returns {boolean} `true` if the given node is an IIFE */ -function isIIFE (node) { - return node.type === 'CallExpression' && node.callee.type === 'FunctionExpression' +function isIIFE(node) { + return ( + node.type === 'CallExpression' && node.callee.type === 'FunctionExpression' + ) } -function createForVueSyntax (context) { - const tokenStore = context.parserServices.getTemplateBodyTokenStore && context.parserServices.getTemplateBodyTokenStore() +function createForVueSyntax(context) { + const tokenStore = + context.parserServices.getTemplateBodyTokenStore && + context.parserServices.getTemplateBodyTokenStore() /** * Checks if the given node turns into a filter when unwraped. * @param {Expression} node node to evaluate * @returns {boolean} `true` if the given node turns into a filter when unwraped. */ - function isUnwrapChangeToFilter (expression) { + function isUnwrapChangeToFilter(expression) { let parenStack = null for (const token of tokenStore.getTokens(expression)) { if (!parenStack) { @@ -119,7 +120,7 @@ function createForVueSyntax (context) { /** * @param {VExpressionContainer} node */ - function verify (node) { + function verify(node) { let expression = node.expression if (!expression) { return @@ -134,7 +135,10 @@ function createForVueSyntax (context) { } if (!isParenthesized(2, expression, tokenStore)) { - if (isIIFE(expression) && !isParenthesized(expression.callee, tokenStore)) { + if ( + isIIFE(expression) && + !isParenthesized(expression.callee, tokenStore) + ) { return } if (isUnwrapChangeToFilter(expression)) { @@ -150,7 +154,7 @@ function createForVueSyntax (context) { * @returns {void} * @private */ - function report (node) { + function report(node) { const sourceCode = context.getSourceCode() const leftParenToken = tokenStore.getTokenBefore(node) const rightParenToken = tokenStore.getTokenAfter(node) @@ -159,13 +163,16 @@ function createForVueSyntax (context) { node, loc: leftParenToken.loc, messageId: 'unexpected', - fix (fixer) { - const parenthesizedSource = sourceCode.text.slice(leftParenToken.range[1], rightParenToken.range[0]) - - return fixer.replaceTextRange([ - leftParenToken.range[0], - rightParenToken.range[1] - ], parenthesizedSource) + fix(fixer) { + const parenthesizedSource = sourceCode.text.slice( + leftParenToken.range[1], + rightParenToken.range[0] + ) + + return fixer.replaceTextRange( + [leftParenToken.range[0], rightParenToken.range[1]], + parenthesizedSource + ) } }) } diff --git a/lib/rules/no-irregular-whitespace.js b/lib/rules/no-irregular-whitespace.js index e4e6fd426..dc2a0de1a 100644 --- a/lib/rules/no-irregular-whitespace.js +++ b/lib/rules/no-irregular-whitespace.js @@ -16,8 +16,8 @@ const utils = require('../utils') // ------------------------------------------------------------------------------ const ALL_IRREGULARS = /[\f\v\u0085\ufeff\u00a0\u1680\u180e\u2000\u2001\u2002\u2003\u2004\u2005\u2006\u2007\u2008\u2009\u200a\u200b\u202f\u205f\u3000\u2028\u2029]/u -const IRREGULAR_WHITESPACE = /[\f\v\u0085\ufeff\u00a0\u1680\u180e\u2000\u2001\u2002\u2003\u2004\u2005\u2006\u2007\u2008\u2009\u200a\u200b\u202f\u205f\u3000]+/mgu -const IRREGULAR_LINE_TERMINATORS = /[\u2028\u2029]/mgu +const IRREGULAR_WHITESPACE = /[\f\v\u0085\ufeff\u00a0\u1680\u180e\u2000\u2001\u2002\u2003\u2004\u2005\u2006\u2007\u2008\u2009\u200a\u200b\u202f\u205f\u3000]+/gmu +const IRREGULAR_LINE_TERMINATORS = /[\u2028\u2029]/gmu // ------------------------------------------------------------------------------ // Rule Definition @@ -70,7 +70,7 @@ module.exports = { } }, - create (context) { + create(context) { // Module store of error indexes that we have found let errorIndexes = [] @@ -91,11 +91,12 @@ module.exports = { * @returns {void} * @private */ - function removeWhitespaceError (node) { + function removeWhitespaceError(node) { const [startIndex, endIndex] = node.range - errorIndexes = errorIndexes - .filter(errorIndex => errorIndex < startIndex || endIndex <= errorIndex) + errorIndexes = errorIndexes.filter( + (errorIndex) => errorIndex < startIndex || endIndex <= errorIndex + ) } /** @@ -104,8 +105,8 @@ module.exports = { * @returns {void} * @private */ - function removeInvalidNodeErrorsInLiteral (node) { - const shouldCheckStrings = skipStrings && (typeof node.value === 'string') + function removeInvalidNodeErrorsInLiteral(node) { + const shouldCheckStrings = skipStrings && typeof node.value === 'string' const shouldCheckRegExps = skipRegExps && Boolean(node.regex) if (shouldCheckStrings || shouldCheckRegExps) { @@ -122,7 +123,7 @@ module.exports = { * @returns {void} * @private */ - function removeInvalidNodeErrorsInTemplateLiteral (node) { + function removeInvalidNodeErrorsInTemplateLiteral(node) { if (ALL_IRREGULARS.test(node.value.raw)) { removeWhitespaceError(node) } @@ -134,7 +135,7 @@ module.exports = { * @returns {void} * @private */ - function removeInvalidNodeErrorsInHTMLAttributeValue (node) { + function removeInvalidNodeErrorsInHTMLAttributeValue(node) { if (ALL_IRREGULARS.test(sourceCode.getText(node))) { removeWhitespaceError(node) } @@ -146,7 +147,7 @@ module.exports = { * @returns {void} * @private */ - function removeInvalidNodeErrorsInHTMLTextContent (node) { + function removeInvalidNodeErrorsInHTMLTextContent(node) { if (ALL_IRREGULARS.test(sourceCode.getText(node))) { removeWhitespaceError(node) } @@ -158,7 +159,7 @@ module.exports = { * @returns {void} * @private */ - function removeInvalidNodeErrorsInComment (node) { + function removeInvalidNodeErrorsInComment(node) { if (ALL_IRREGULARS.test(node.value)) { removeWhitespaceError(node) } @@ -169,7 +170,7 @@ module.exports = { * @returns {void} * @private */ - function checkForIrregularWhitespace () { + function checkForIrregularWhitespace() { const source = sourceCode.getText() let match while ((match = IRREGULAR_WHITESPACE.exec(source)) !== null) { @@ -185,21 +186,29 @@ module.exports = { if (!errorIndexes.length) { return {} } - const bodyVisitor = utils.defineTemplateBodyVisitor(context, - { - ...(skipHTMLAttributeValues ? { 'VAttribute[directive=false] > VLiteral': removeInvalidNodeErrorsInHTMLAttributeValue } : {}), - ...(skipHTMLTextContents ? { VText: removeInvalidNodeErrorsInHTMLTextContent } : {}), + const bodyVisitor = utils.defineTemplateBodyVisitor(context, { + ...(skipHTMLAttributeValues + ? { + 'VAttribute[directive=false] > VLiteral': removeInvalidNodeErrorsInHTMLAttributeValue + } + : {}), + ...(skipHTMLTextContents + ? { VText: removeInvalidNodeErrorsInHTMLTextContent } + : {}), - // inline scripts - Literal: removeInvalidNodeErrorsInLiteral, - ...(skipTemplates ? { TemplateElement: removeInvalidNodeErrorsInTemplateLiteral } : {}) - } - ) + // inline scripts + Literal: removeInvalidNodeErrorsInLiteral, + ...(skipTemplates + ? { TemplateElement: removeInvalidNodeErrorsInTemplateLiteral } + : {}) + }) return { ...bodyVisitor, Literal: removeInvalidNodeErrorsInLiteral, - ...(skipTemplates ? { TemplateElement: removeInvalidNodeErrorsInTemplateLiteral } : {}), - 'Program:exit' (node) { + ...(skipTemplates + ? { TemplateElement: removeInvalidNodeErrorsInTemplateLiteral } + : {}), + 'Program:exit'(node) { if (bodyVisitor['Program:exit']) { bodyVisitor['Program:exit'](node) } @@ -214,15 +223,17 @@ module.exports = { // Removes errors that occur outside script and template const [scriptStart, scriptEnd] = node.range - const [templateStart, templateEnd] = templateBody ? templateBody.range : [0, 0] - errorIndexes = errorIndexes - .filter(errorIndex => + const [templateStart, templateEnd] = templateBody + ? templateBody.range + : [0, 0] + errorIndexes = errorIndexes.filter( + (errorIndex) => (scriptStart <= errorIndex && errorIndex < scriptEnd) || - (templateStart <= errorIndex && errorIndex < templateEnd) - ) + (templateStart <= errorIndex && errorIndex < templateEnd) + ) // If we have any errors remaining report on them - errorIndexes.forEach(errorIndex => { + errorIndexes.forEach((errorIndex) => { context.report({ loc: sourceCode.getLocFromIndex(errorIndex), messageId: 'disallow' diff --git a/lib/rules/no-lifecycle-after-await.js b/lib/rules/no-lifecycle-after-await.js index 9ed65ce16..cafcde97c 100644 --- a/lib/rules/no-lifecycle-after-await.js +++ b/lib/rules/no-lifecycle-after-await.js @@ -6,7 +6,19 @@ const { ReferenceTracker } = require('eslint-utils') const utils = require('../utils') -const LIFECYCLE_HOOKS = ['onBeforeMount', 'onBeforeUnmount', 'onBeforeUpdate', 'onErrorCaptured', 'onMounted', 'onRenderTracked', 'onRenderTriggered', 'onUnmounted', 'onUpdated', 'onActivated', 'onDeactivated'] +const LIFECYCLE_HOOKS = [ + 'onBeforeMount', + 'onBeforeUnmount', + 'onBeforeUpdate', + 'onErrorCaptured', + 'onMounted', + 'onRenderTracked', + 'onRenderTriggered', + 'onUnmounted', + 'onUpdated', + 'onActivated', + 'onDeactivated' +] module.exports = { meta: { @@ -22,7 +34,7 @@ module.exports = { forbidden: 'The lifecycle hooks after `await` expression are forbidden.' } }, - create (context) { + create(context) { const lifecycleHookCallNodes = new Set() const setupFunctions = new Map() @@ -30,7 +42,7 @@ module.exports = { return Object.assign( { - 'Program' () { + Program() { const tracker = new ReferenceTracker(context.getScope()) const traceMap = { vue: { @@ -48,48 +60,46 @@ module.exports = { } } }, - utils.defineVueVisitor(context, - { - ':function' (node) { - scopeStack = { upper: scopeStack, functionNode: node } - }, - onSetupFunctionEnter (node) { - setupFunctions.set(node, { - setupProperty: node.parent, - afterAwait: false - }) - }, - 'AwaitExpression' () { - const setupFunctionData = setupFunctions.get(scopeStack.functionNode) - if (!setupFunctionData) { - return - } - setupFunctionData.afterAwait = true - }, - 'CallExpression' (node) { - const setupFunctionData = setupFunctions.get(scopeStack.functionNode) - if (!setupFunctionData || !setupFunctionData.afterAwait) { - return - } + utils.defineVueVisitor(context, { + ':function'(node) { + scopeStack = { upper: scopeStack, functionNode: node } + }, + onSetupFunctionEnter(node) { + setupFunctions.set(node, { + setupProperty: node.parent, + afterAwait: false + }) + }, + AwaitExpression() { + const setupFunctionData = setupFunctions.get(scopeStack.functionNode) + if (!setupFunctionData) { + return + } + setupFunctionData.afterAwait = true + }, + CallExpression(node) { + const setupFunctionData = setupFunctions.get(scopeStack.functionNode) + if (!setupFunctionData || !setupFunctionData.afterAwait) { + return + } - if (lifecycleHookCallNodes.has(node)) { - if (node.arguments.length >= 2) { - // Has target instance. e.g. `onMounted(() => {}, instance)` - return - } - context.report({ - node, - messageId: 'forbidden' - }) + if (lifecycleHookCallNodes.has(node)) { + if (node.arguments.length >= 2) { + // Has target instance. e.g. `onMounted(() => {}, instance)` + return } - }, - ':function:exit' (node) { - scopeStack = scopeStack.upper - - setupFunctions.delete(node) + context.report({ + node, + messageId: 'forbidden' + }) } }, - ) + ':function:exit'(node) { + scopeStack = scopeStack.upper + + setupFunctions.delete(node) + } + }) ) } } diff --git a/lib/rules/no-multi-spaces.js b/lib/rules/no-multi-spaces.js index 056d23bf0..3c79ee7d0 100644 --- a/lib/rules/no-multi-spaces.js +++ b/lib/rules/no-multi-spaces.js @@ -22,31 +22,34 @@ module.exports = { url: 'https://eslint.vuejs.org/rules/no-multi-spaces.html' }, fixable: 'whitespace', // or "code" or "whitespace" - schema: [{ - type: 'object', - properties: { - ignoreProperties: { - type: 'boolean' - } - }, - additionalProperties: false - }] + schema: [ + { + type: 'object', + properties: { + ignoreProperties: { + type: 'boolean' + } + }, + additionalProperties: false + } + ] }, /** * @param {RuleContext} context - The rule context. * @returns {Object} AST event handlers. */ - create (context) { + create(context) { const options = context.options[0] || {} const ignoreProperties = options.ignoreProperties === true return { - Program (node) { + Program(node) { if (context.parserServices.getTemplateBodyTokenStore == null) { context.report({ loc: { line: 1, column: 0 }, - message: 'Use the latest vue-eslint-parser. See also https://eslint.vuejs.org/user-guide/#what-is-the-use-the-latest-vue-eslint-parser-error.' + message: + 'Use the latest vue-eslint-parser. See also https://eslint.vuejs.org/user-guide/#what-is-the-use-the-latest-vue-eslint-parser-error.' }) return } @@ -55,15 +58,21 @@ module.exports = { } const sourceCode = context.getSourceCode() const tokenStore = context.parserServices.getTemplateBodyTokenStore() - const tokens = tokenStore.getTokens(node.templateBody, { includeComments: true }) + const tokens = tokenStore.getTokens(node.templateBody, { + includeComments: true + }) let prevToken = tokens.shift() for (const token of tokens) { const spaces = token.range[0] - prevToken.range[1] - const shouldIgnore = ignoreProperties && ( - isProperty(context, token) || isProperty(context, prevToken) - ) - if (spaces > 1 && token.loc.start.line === prevToken.loc.start.line && !shouldIgnore) { + const shouldIgnore = + ignoreProperties && + (isProperty(context, token) || isProperty(context, prevToken)) + if ( + spaces > 1 && + token.loc.start.line === prevToken.loc.start.line && + !shouldIgnore + ) { context.report({ node: token, loc: { @@ -71,7 +80,11 @@ module.exports = { end: token.loc.start }, message: "Multiple spaces found before '{{displayValue}}'.", - fix: (fixer) => fixer.replaceTextRange([prevToken.range[1], token.range[0]], ' '), + fix: (fixer) => + fixer.replaceTextRange( + [prevToken.range[1], token.range[0]], + ' ' + ), data: { displayValue: sourceCode.getText(token) } diff --git a/lib/rules/no-multiple-template-root.js b/lib/rules/no-multiple-template-root.js index 5705592ab..4fd0df0eb 100644 --- a/lib/rules/no-multiple-template-root.js +++ b/lib/rules/no-multiple-template-root.js @@ -26,11 +26,11 @@ module.exports = { schema: [] }, - create: function (context) { + create(context) { const sourceCode = context.getSourceCode() return { - Program (program) { + Program(program) { const element = program.templateBody if (element == null) { return diff --git a/lib/rules/no-mutating-props.js b/lib/rules/no-mutating-props.js index 341f1b22a..4498fc9f5 100644 --- a/lib/rules/no-mutating-props.js +++ b/lib/rules/no-mutating-props.js @@ -37,7 +37,7 @@ module.exports = { ] }, - create (context) { + create(context) { /** @type {Map>} */ const propsMap = new Map() /** @type { { type: 'export' | 'mark' | 'definition', object: ObjectExpression } | null } */ @@ -47,7 +47,7 @@ module.exports = { * @param {Node} node * @param {string} name */ - function report (node, name) { + function report(node, name) { context.report({ node, message: 'Unexpected mutation of "{{key}}" prop.', @@ -61,7 +61,7 @@ module.exports = { * @param {Node} node * @returns {VExpressionContainer} */ - function getVExpressionContainer (node) { + function getVExpressionContainer(node) { let n = node while (n.type !== 'VExpressionContainer') { n = n.parent @@ -72,7 +72,7 @@ module.exports = { * @param {MemberExpression|Property} node * @returns {string} */ - function getPropertyNameText (node) { + function getPropertyNameText(node) { const name = utils.getStaticPropertyName(node) if (name) { return name @@ -88,7 +88,7 @@ module.exports = { * @param {Node} node * @returns {node is Identifier} */ - function isVmReference (node) { + function isVmReference(node) { if (node.type !== 'Identifier') { return false } @@ -123,7 +123,7 @@ module.exports = { * @param {MemberExpression|Identifier} props * @param {string} name */ - function verifyMutating (props, name) { + function verifyMutating(props, name) { const invalid = utils.findMutating(props) if (invalid) { report(invalid.node, name) @@ -135,7 +135,7 @@ module.exports = { * @param {string[]} path * @returns {Generator<{ node: Identifier, path: string[] }>} */ - function * iterateParamProperties (param, path) { + function* iterateParamProperties(param, path) { if (!param) { return } @@ -145,105 +145,116 @@ module.exports = { path } } else if (param.type === 'RestElement') { - yield * iterateParamProperties(param.argument, path) + yield* iterateParamProperties(param.argument, path) } else if (param.type === 'AssignmentPattern') { - yield * iterateParamProperties(param.left, path) + yield* iterateParamProperties(param.left, path) } else if (param.type === 'ObjectPattern') { for (const prop of param.properties) { if (prop.type === 'Property') { const name = getPropertyNameText(prop) - yield * iterateParamProperties(prop.value, [...path, name]) + yield* iterateParamProperties(prop.value, [...path, name]) } else if (prop.type === 'RestElement') { - yield * iterateParamProperties(prop.argument, path) + yield* iterateParamProperties(prop.argument, path) } } } else if (param.type === 'ArrayPattern') { for (let index = 0; index < param.elements.length; index++) { const element = param.elements[index] - yield * iterateParamProperties(element, [...path, `${index}`]) + yield* iterateParamProperties(element, [...path, `${index}`]) } } } - return Object.assign({}, - utils.defineVueVisitor(context, - { - onVueObjectEnter (node) { - propsMap.set(node, new Set(utils.getComponentProps(node).map(p => p.propName))) - }, - onVueObjectExit (node, { type }) { - if (!vueObjectData || vueObjectData.type !== 'export') { - vueObjectData = { - type, - object: node - } - } - }, - onSetupFunctionEnter (node) { - /** @type {Pattern} */ - const propsParam = node.params[0] - if (!propsParam) { - // no arguments - return + return Object.assign( + {}, + utils.defineVueVisitor(context, { + onVueObjectEnter(node) { + propsMap.set( + node, + new Set(utils.getComponentProps(node).map((p) => p.propName)) + ) + }, + onVueObjectExit(node, { type }) { + if (!vueObjectData || vueObjectData.type !== 'export') { + vueObjectData = { + type, + object: node } - if (propsParam.type === 'RestElement' || propsParam.type === 'ArrayPattern') { - // cannot check - return + } + }, + onSetupFunctionEnter(node) { + /** @type {Pattern} */ + const propsParam = node.params[0] + if (!propsParam) { + // no arguments + return + } + if ( + propsParam.type === 'RestElement' || + propsParam.type === 'ArrayPattern' + ) { + // cannot check + return + } + for (const { node: prop, path } of iterateParamProperties( + propsParam, + [] + )) { + // @ts-ignore + const variable = findVariable(context.getScope(), prop) + if (!variable) { + continue } - for (const { node: prop, path } of iterateParamProperties(propsParam, [])) { - // @ts-ignore - const variable = findVariable(context.getScope(), prop) - if (!variable) { + + for (const reference of variable.references) { + if (!reference.isRead()) { continue } + /** @type {Identifier} */ + const id = reference.identifier - for (const reference of variable.references) { - if (!reference.isRead()) { + const invalid = utils.findMutating(id) + if (!invalid) { + continue + } + let name + if (path.length === 0) { + if (invalid.pathNodes.length === 0) { continue } - /** @type {Identifier} */ - const id = reference.identifier - - const invalid = utils.findMutating(id) - if (!invalid) { + const mem = invalid.pathNodes[0] + name = getPropertyNameText(mem) + } else { + if (invalid.pathNodes.length === 0 && invalid.kind !== 'call') { continue } - let name - if (path.length === 0) { - if (invalid.pathNodes.length === 0) { - continue - } - const mem = invalid.pathNodes[0] - name = getPropertyNameText(mem) - } else { - if (invalid.pathNodes.length === 0 && invalid.kind !== 'call') { - continue - } - name = path[0] - } - - report(invalid.node, name) + name = path[0] } + + report(invalid.node, name) } - }, - 'MemberExpression > :matches(Identifier, ThisExpression)' (node, { node: vueNode }) { - if (!utils.isThis(node, context)) { - return - } - /** @type {MemberExpression} */ - const mem = node.parent - if (mem.object !== node) { - return - } - const name = utils.getStaticPropertyName(mem) - if (name && propsMap.get(vueNode).has(name)) { - verifyMutating(mem, name) - } + } + }, + 'MemberExpression > :matches(Identifier, ThisExpression)'( + node, + { node: vueNode } + ) { + if (!utils.isThis(node, context)) { + return + } + /** @type {MemberExpression} */ + const mem = node.parent + if (mem.object !== node) { + return + } + const name = utils.getStaticPropertyName(mem) + if (name && propsMap.get(vueNode).has(name)) { + verifyMutating(mem, name) } } - ), + }), utils.defineTemplateBodyVisitor(context, { - 'VExpressionContainer MemberExpression > ThisExpression' (node) { + 'VExpressionContainer MemberExpression > ThisExpression'(node) { if (!vueObjectData) { return } @@ -257,7 +268,7 @@ module.exports = { verifyMutating(mem, name) } }, - 'VExpressionContainer Identifier' (node) { + 'VExpressionContainer Identifier'(node) { if (!vueObjectData) { return } @@ -269,7 +280,9 @@ module.exports = { verifyMutating(node, name) } }, - "VAttribute[directive=true][key.name.name='model'] VExpressionContainer > *" (node) { + "VAttribute[directive=true][key.name.name='model'] VExpressionContainer > *"( + node + ) { if (!vueObjectData) { return } diff --git a/lib/rules/no-parsing-error.js b/lib/rules/no-parsing-error.js index c01c5c9ba..d51fd7f61 100644 --- a/lib/rules/no-parsing-error.js +++ b/lib/rules/no-parsing-error.js @@ -10,44 +10,46 @@ // ------------------------------------------------------------------------------ // https://html.spec.whatwg.org/multipage/parsing.html#parse-errors -const DEFAULT_OPTIONS = Object.freeze(Object.assign(Object.create(null), { - 'abrupt-closing-of-empty-comment': true, - 'absence-of-digits-in-numeric-character-reference': true, - 'cdata-in-html-content': true, - 'character-reference-outside-unicode-range': true, - 'control-character-in-input-stream': true, - 'control-character-reference': true, - 'eof-before-tag-name': true, - 'eof-in-cdata': true, - 'eof-in-comment': true, - 'eof-in-tag': true, - 'incorrectly-closed-comment': true, - 'incorrectly-opened-comment': true, - 'invalid-first-character-of-tag-name': true, - 'missing-attribute-value': true, - 'missing-end-tag-name': true, - 'missing-semicolon-after-character-reference': true, - 'missing-whitespace-between-attributes': true, - 'nested-comment': true, - 'noncharacter-character-reference': true, - 'noncharacter-in-input-stream': true, - 'null-character-reference': true, - 'surrogate-character-reference': true, - 'surrogate-in-input-stream': true, - 'unexpected-character-in-attribute-name': true, - 'unexpected-character-in-unquoted-attribute-value': true, - 'unexpected-equals-sign-before-attribute-name': true, - 'unexpected-null-character': true, - 'unexpected-question-mark-instead-of-tag-name': true, - 'unexpected-solidus-in-tag': true, - 'unknown-named-character-reference': true, - 'end-tag-with-attributes': true, - 'duplicate-attribute': true, - 'end-tag-with-trailing-solidus': true, - 'non-void-html-element-start-tag-with-trailing-solidus': false, - 'x-invalid-end-tag': true, - 'x-invalid-namespace': true -})) +const DEFAULT_OPTIONS = Object.freeze( + Object.assign(Object.create(null), { + 'abrupt-closing-of-empty-comment': true, + 'absence-of-digits-in-numeric-character-reference': true, + 'cdata-in-html-content': true, + 'character-reference-outside-unicode-range': true, + 'control-character-in-input-stream': true, + 'control-character-reference': true, + 'eof-before-tag-name': true, + 'eof-in-cdata': true, + 'eof-in-comment': true, + 'eof-in-tag': true, + 'incorrectly-closed-comment': true, + 'incorrectly-opened-comment': true, + 'invalid-first-character-of-tag-name': true, + 'missing-attribute-value': true, + 'missing-end-tag-name': true, + 'missing-semicolon-after-character-reference': true, + 'missing-whitespace-between-attributes': true, + 'nested-comment': true, + 'noncharacter-character-reference': true, + 'noncharacter-in-input-stream': true, + 'null-character-reference': true, + 'surrogate-character-reference': true, + 'surrogate-in-input-stream': true, + 'unexpected-character-in-attribute-name': true, + 'unexpected-character-in-unquoted-attribute-value': true, + 'unexpected-equals-sign-before-attribute-name': true, + 'unexpected-null-character': true, + 'unexpected-question-mark-instead-of-tag-name': true, + 'unexpected-solidus-in-tag': true, + 'unknown-named-character-reference': true, + 'end-tag-with-attributes': true, + 'duplicate-attribute': true, + 'end-tag-with-trailing-solidus': true, + 'non-void-html-element-start-tag-with-trailing-solidus': false, + 'x-invalid-end-tag': true, + 'x-invalid-namespace': true + }) +) // ------------------------------------------------------------------------------ // Rule Definition @@ -74,11 +76,11 @@ module.exports = { ] }, - create (context) { + create(context) { const options = Object.assign({}, DEFAULT_OPTIONS, context.options[0] || {}) return { - Program (program) { + Program(program) { const node = program.templateBody if (node == null || node.errors == null) { return diff --git a/lib/rules/no-potential-component-option-typo.js b/lib/rules/no-potential-component-option-typo.js index 13d18f57e..a29d2acf0 100644 --- a/lib/rules/no-potential-component-option-typo.js +++ b/lib/rules/no-potential-component-option-typo.js @@ -17,7 +17,8 @@ module.exports = { description: 'disallow a potential typo in your component property', categories: undefined, recommended: false, - url: 'https://eslint.vuejs.org/rules/no-potential-component-option-typo.html' + url: + 'https://eslint.vuejs.org/rules/no-potential-component-option-typo.html' }, fixable: null, schema: [ @@ -41,18 +42,18 @@ module.exports = { }, threshold: { type: 'number', - 'minimum': 1 + minimum: 1 } } } ] }, - create: function (context) { + create(context) { const option = context.options[0] || {} - const custom = option['custom'] || [] - const presets = option['presets'] || ['vue'] - const threshold = option['threshold'] || 1 + const custom = option.custom || [] + const presets = option.presets || ['vue'] + const threshold = option.threshold || 1 let candidateOptions if (presets.includes('all')) { candidateOptions = Object.keys(vueComponentOptions).reduce((pre, cur) => { @@ -68,22 +69,24 @@ module.exports = { if (!candidateOptionList.length) { return {} } - return utils.executeOnVue(context, obj => { + return utils.executeOnVue(context, (obj) => { const componentInstanceOptions = obj.properties.filter( - p => p.type === 'Property' && p.key.type === 'Identifier' + (p) => p.type === 'Property' && p.key.type === 'Identifier' ) if (!componentInstanceOptions.length) { return {} } - componentInstanceOptions.forEach(option => { + componentInstanceOptions.forEach((option) => { const id = option.key const name = id.name if (candidateOptionSet.has(name)) { return } const potentialTypoList = candidateOptionList - .map(o => ({ option: o, distance: utils.editDistance(o, name) })) - .filter(({ distance, option }) => distance <= threshold && distance > 0) + .map((o) => ({ option: o, distance: utils.editDistance(o, name) })) + .filter( + ({ distance, option }) => distance <= threshold && distance > 0 + ) .sort((a, b) => a.distance - b.distance) if (potentialTypoList.length) { context.report({ @@ -96,7 +99,7 @@ module.exports = { }, suggest: potentialTypoList.map(({ option }) => ({ desc: `Replace property '${name}' to '${option}'`, - fix (fixer) { + fix(fixer) { return fixer.replaceText(id, option) } })) diff --git a/lib/rules/no-ref-as-operand.js b/lib/rules/no-ref-as-operand.js index 30ad6488a..11873edf0 100644 --- a/lib/rules/no-ref-as-operand.js +++ b/lib/rules/no-ref-as-operand.js @@ -9,20 +9,22 @@ module.exports = { meta: { type: 'suggestion', docs: { - description: 'disallow use of value wrapped by `ref()` (Composition API) as an operand', + description: + 'disallow use of value wrapped by `ref()` (Composition API) as an operand', categories: ['vue3-essential'], url: 'https://eslint.vuejs.org/rules/no-ref-as-operand.html' }, fixable: null, schema: [], messages: { - requireDotValue: 'Must use `.value` to read or write the value wrapped by `ref()`.' + requireDotValue: + 'Must use `.value` to read or write the value wrapped by `ref()`.' } }, - create (context) { + create(context) { const refReferenceIds = new Map() - function reportIfRefWrapped (node) { + function reportIfRefWrapped(node) { if (!refReferenceIds.has(node)) { return } @@ -32,7 +34,7 @@ module.exports = { }) } return { - 'Program' () { + Program() { const tracker = new ReferenceTracker(context.getScope()) const traceMap = { vue: { @@ -52,15 +54,18 @@ module.exports = { ) { continue } - const variable = findVariable(context.getScope(), variableDeclarator.id) + const variable = findVariable( + context.getScope(), + variableDeclarator.id + ) if (!variable) { continue } - const variableDeclaration = ( - variableDeclarator.parent && - variableDeclarator.parent.type === 'VariableDeclaration' && - variableDeclarator.parent - ) || null + const variableDeclaration = + (variableDeclarator.parent && + variableDeclarator.parent.type === 'VariableDeclaration' && + variableDeclarator.parent) || + null for (const reference of variable.references) { if (!reference.isRead()) { continue @@ -74,31 +79,31 @@ module.exports = { } }, // if (refValue) - 'IfStatement>Identifier' (node) { + 'IfStatement>Identifier'(node) { reportIfRefWrapped(node) }, // switch (refValue) - 'SwitchStatement>Identifier' (node) { + 'SwitchStatement>Identifier'(node) { reportIfRefWrapped(node) }, // -refValue, +refValue, !refValue, ~refValue, typeof refValue - 'UnaryExpression>Identifier' (node) { + 'UnaryExpression>Identifier'(node) { reportIfRefWrapped(node) }, // refValue++, refValue-- - 'UpdateExpression>Identifier' (node) { + 'UpdateExpression>Identifier'(node) { reportIfRefWrapped(node) }, // refValue+1, refValue-1 - 'BinaryExpression>Identifier' (node) { + 'BinaryExpression>Identifier'(node) { reportIfRefWrapped(node) }, // refValue+=1, refValue-=1, foo+=refValue, foo-=refValue - 'AssignmentExpression>Identifier' (node) { + 'AssignmentExpression>Identifier'(node) { reportIfRefWrapped(node) }, // refValue || other, refValue && other. ignore: other || refValue - 'LogicalExpression>Identifier' (node) { + 'LogicalExpression>Identifier'(node) { if (node.parent.left !== node) { return } @@ -107,13 +112,16 @@ module.exports = { if (!info) { return } - if (!info.variableDeclaration || info.variableDeclaration.kind !== 'const') { + if ( + !info.variableDeclaration || + info.variableDeclaration.kind !== 'const' + ) { return } reportIfRefWrapped(node) }, // refValue ? x : y - 'ConditionalExpression>Identifier' (node) { + 'ConditionalExpression>Identifier'(node) { if (node.parent.test !== node) { return } diff --git a/lib/rules/no-reserved-component-names.js b/lib/rules/no-reserved-component-names.js index c566684e6..258f1c517 100644 --- a/lib/rules/no-reserved-component-names.js +++ b/lib/rules/no-reserved-component-names.js @@ -31,13 +31,11 @@ const vueBuiltInComponents = [ 'slot' ] -const vue3BuiltInComponents = [ - 'teleport', - 'suspense' -] +const vue3BuiltInComponents = ['teleport', 'suspense'] const isLowercase = (word) => /^[a-z]*$/.test(word) -const capitalizeFirstLetter = (word) => word[0].toUpperCase() + word.substring(1, word.length) +const capitalizeFirstLetter = (word) => + word[0].toUpperCase() + word.substring(1, word.length) const RESERVED_NAMES_IN_HTML = new Set([ ...htmlElements, @@ -69,22 +67,25 @@ module.exports = { meta: { type: 'suggestion', docs: { - description: 'disallow the use of reserved names in component definitions', + description: + 'disallow the use of reserved names in component definitions', categories: undefined, url: 'https://eslint.vuejs.org/rules/no-reserved-component-names.html' }, fixable: null, - schema: [{ - type: 'object', - properties: { - disallowVueBuiltInComponents: { - type: 'boolean' - }, - disallowVue3BuiltInComponents: { - type: 'boolean' + schema: [ + { + type: 'object', + properties: { + disallowVueBuiltInComponents: { + type: 'boolean' + }, + disallowVue3BuiltInComponents: { + type: 'boolean' + } } } - }], + ], messages: { reserved: 'Name "{{name}}" is reserved.', reservedInHtml: 'Name "{{name}}" is reserved in HTML.', @@ -93,10 +94,12 @@ module.exports = { } }, - create (context) { + create(context) { const options = context.options[0] || {} - const disallowVueBuiltInComponents = options.disallowVueBuiltInComponents === true - const disallowVue3BuiltInComponents = options.disallowVue3BuiltInComponents === true + const disallowVueBuiltInComponents = + options.disallowVueBuiltInComponents === true + const disallowVue3BuiltInComponents = + options.disallowVue3BuiltInComponents === true const reservedNames = new Set([ ...RESERVED_NAMES_IN_HTML, @@ -105,15 +108,16 @@ module.exports = { ...RESERVED_NAMES_IN_OTHERS ]) - function canVerify (node) { - return node.type === 'Literal' || ( - node.type === 'TemplateLiteral' && - node.expressions.length === 0 && - node.quasis.length === 1 + function canVerify(node) { + return ( + node.type === 'Literal' || + (node.type === 'TemplateLiteral' && + node.expressions.length === 0 && + node.quasis.length === 1) ) } - function reportIfInvalid (node) { + function reportIfInvalid(node) { let name if (node.type === 'TemplateLiteral') { const quasis = node.quasis[0] @@ -126,19 +130,24 @@ module.exports = { } } - function report (node, name) { + function report(node, name) { context.report({ - node: node, - messageId: RESERVED_NAMES_IN_HTML.has(name) ? 'reservedInHtml' - : RESERVED_NAMES_IN_VUE.has(name) ? 'reservedInVue' - : RESERVED_NAMES_IN_VUE3.has(name) ? 'reservedInVue3' : 'reserved', + node, + messageId: RESERVED_NAMES_IN_HTML.has(name) + ? 'reservedInHtml' + : RESERVED_NAMES_IN_VUE.has(name) + ? 'reservedInVue' + : RESERVED_NAMES_IN_VUE3.has(name) + ? 'reservedInVue3' + : 'reserved', data: { - name: name + name } }) } - return Object.assign({}, + return Object.assign( + {}, utils.executeOnCallVueComponent(context, (node) => { if (node.arguments.length === 2) { const argument = node.arguments[0] @@ -150,16 +159,17 @@ module.exports = { }), utils.executeOnVue(context, (obj) => { // Report if a component has been registered locally with a reserved name. - utils.getRegisteredComponents(obj) + utils + .getRegisteredComponents(obj) .filter(({ name }) => reservedNames.has(name)) .forEach(({ node, name }) => report(node, name)) - const node = obj.properties - .find(item => ( + const node = obj.properties.find( + (item) => item.type === 'Property' && item.key.name === 'name' && canVerify(item.value) - )) + ) if (!node) return reportIfInvalid(node.value) diff --git a/lib/rules/no-reserved-keys.js b/lib/rules/no-reserved-keys.js index 249f10545..d17ce05df 100644 --- a/lib/rules/no-reserved-keys.js +++ b/lib/rules/no-reserved-keys.js @@ -38,7 +38,7 @@ module.exports = { ] }, - create (context) { + create(context) { const options = context.options[0] || {} const reservedKeys = new Set(RESERVED_KEYS.concat(options.reserved || [])) const groups = new Set(GROUP_NAMES.concat(options.groups || [])) @@ -53,7 +53,8 @@ module.exports = { if (o.groupName === 'data' && o.name[0] === '_') { context.report({ node: o.node, - message: "Keys starting with with '_' are reserved in '{{name}}' group.", + message: + "Keys starting with with '_' are reserved in '{{name}}' group.", data: { name: o.name } diff --git a/lib/rules/no-setup-props-destructure.js b/lib/rules/no-setup-props-destructure.js index fb992980c..c4f04edd4 100644 --- a/lib/rules/no-setup-props-destructure.js +++ b/lib/rules/no-setup-props-destructure.js @@ -17,26 +17,32 @@ module.exports = { fixable: null, schema: [], messages: { - destructuring: 'Destructuring the `props` will cause the value to lose reactivity.', - getProperty: 'Getting a value from the `props` in root scope of `setup()` will cause the value to lose reactivity.' + destructuring: + 'Destructuring the `props` will cause the value to lose reactivity.', + getProperty: + 'Getting a value from the `props` in root scope of `setup()` will cause the value to lose reactivity.' } }, - create (context) { + create(context) { const setupScopePropsReferenceIds = new Map() - function report (node, messageId) { + function report(node, messageId) { context.report({ node, messageId }) } - function verify (left, right, propsReferenceIds) { + function verify(left, right, propsReferenceIds) { if (!right) { return } - if (left.type !== 'ArrayPattern' && left.type !== 'ObjectPattern' && right.type !== 'MemberExpression') { + if ( + left.type !== 'ArrayPattern' && + left.type !== 'ObjectPattern' && + right.type !== 'MemberExpression' + ) { return } @@ -52,10 +58,10 @@ module.exports = { let scopeStack = null return utils.defineVueVisitor(context, { - ':function' (node) { + ':function'(node) { scopeStack = { upper: scopeStack, functionNode: node } }, - onSetupFunctionEnter (node) { + onSetupFunctionEnter(node) { const propsParam = node.params[0] if (!propsParam) { // no arguments @@ -65,7 +71,10 @@ module.exports = { // cannot check return } - if (propsParam.type === 'ArrayPattern' || propsParam.type === 'ObjectPattern') { + if ( + propsParam.type === 'ArrayPattern' || + propsParam.type === 'ObjectPattern' + ) { report(propsParam, 'destructuring') return } @@ -84,21 +93,25 @@ module.exports = { } setupScopePropsReferenceIds.set(node, propsReferenceIds) }, - 'VariableDeclarator' (node) { - const propsReferenceIds = setupScopePropsReferenceIds.get(scopeStack.functionNode) + VariableDeclarator(node) { + const propsReferenceIds = setupScopePropsReferenceIds.get( + scopeStack.functionNode + ) if (!propsReferenceIds) { return } verify(node.id, node.init, propsReferenceIds) }, - 'AssignmentExpression' (node) { - const propsReferenceIds = setupScopePropsReferenceIds.get(scopeStack.functionNode) + AssignmentExpression(node) { + const propsReferenceIds = setupScopePropsReferenceIds.get( + scopeStack.functionNode + ) if (!propsReferenceIds) { return } verify(node.left, node.right, propsReferenceIds) }, - ':function:exit' (node) { + ':function:exit'(node) { scopeStack = scopeStack.upper setupScopePropsReferenceIds.delete(node) diff --git a/lib/rules/no-shared-component-data.js b/lib/rules/no-shared-component-data.js index e94fbd0b8..2200f0e78 100644 --- a/lib/rules/no-shared-component-data.js +++ b/lib/rules/no-shared-component-data.js @@ -6,15 +6,15 @@ const utils = require('../utils') -function isOpenParen (token) { +function isOpenParen(token) { return token.type === 'Punctuator' && token.value === '(' } -function isCloseParen (token) { +function isCloseParen(token) { return token.type === 'Punctuator' && token.value === ')' } -function getFirstAndLastTokens (node, sourceCode) { +function getFirstAndLastTokens(node, sourceCode) { let first = sourceCode.getFirstToken(node) let last = sourceCode.getLastToken(node) @@ -47,24 +47,25 @@ module.exports = { schema: [] }, - create (context) { + create(context) { const sourceCode = context.getSourceCode() return utils.executeOnVueComponent(context, (obj) => { obj.properties - .filter(p => - p.type === 'Property' && - p.key.type === 'Identifier' && - p.key.name === 'data' && - p.value.type !== 'FunctionExpression' && - p.value.type !== 'ArrowFunctionExpression' && - p.value.type !== 'Identifier' + .filter( + (p) => + p.type === 'Property' && + p.key.type === 'Identifier' && + p.key.name === 'data' && + p.value.type !== 'FunctionExpression' && + p.value.type !== 'ArrowFunctionExpression' && + p.value.type !== 'Identifier' ) - .forEach(p => { + .forEach((p) => { context.report({ node: p, message: '`data` property in component must be a function.', - fix (fixer) { + fix(fixer) { const tokens = getFirstAndLastTokens(p.value, sourceCode) return [ diff --git a/lib/rules/no-side-effects-in-computed-properties.js b/lib/rules/no-side-effects-in-computed-properties.js index d1bcc3a99..59f3b37e7 100644 --- a/lib/rules/no-side-effects-in-computed-properties.js +++ b/lib/rules/no-side-effects-in-computed-properties.js @@ -22,42 +22,48 @@ module.exports = { docs: { description: 'disallow side effects in computed properties', categories: ['vue3-essential', 'essential'], - url: 'https://eslint.vuejs.org/rules/no-side-effects-in-computed-properties.html' + url: + 'https://eslint.vuejs.org/rules/no-side-effects-in-computed-properties.html' }, fixable: null, schema: [] }, - create (context) { + create(context) { /** @type {Map} */ const computedPropertiesMap = new Map() let scopeStack = { upper: null, body: null } - function onFunctionEnter (node) { + function onFunctionEnter(node) { scopeStack = { upper: scopeStack, body: node.body } } - function onFunctionExit () { + function onFunctionExit() { scopeStack = scopeStack.upper } return utils.defineVueVisitor(context, { - onVueObjectEnter (node) { + onVueObjectEnter(node) { computedPropertiesMap.set(node, utils.getComputedProperties(node)) }, ':function': onFunctionEnter, ':function:exit': onFunctionExit, - 'MemberExpression > :matches(Identifier, ThisExpression)' (node, { node: vueNode }) { + 'MemberExpression > :matches(Identifier, ThisExpression)'( + node, + { node: vueNode } + ) { const targetBody = scopeStack.body - const computedProperty = computedPropertiesMap.get(vueNode).find(cp => { - return ( - cp.value && - node.loc.start.line >= cp.value.loc.start.line && - node.loc.end.line <= cp.value.loc.end.line && - targetBody === cp.value - ) - }) + const computedProperty = computedPropertiesMap + .get(vueNode) + .find((cp) => { + return ( + cp.value && + node.loc.start.line >= cp.value.loc.start.line && + node.loc.end.line <= cp.value.loc.end.line && + targetBody === cp.value + ) + }) if (!computedProperty) { return } @@ -80,7 +86,6 @@ module.exports = { }) } } - } - ) + }) } } diff --git a/lib/rules/no-spaces-around-equal-signs-in-attribute.js b/lib/rules/no-spaces-around-equal-signs-in-attribute.js index 767017bc2..4bb32f03f 100644 --- a/lib/rules/no-spaces-around-equal-signs-in-attribute.js +++ b/lib/rules/no-spaces-around-equal-signs-in-attribute.js @@ -20,16 +20,17 @@ module.exports = { docs: { description: 'disallow spaces around equal signs in attribute', categories: ['vue3-strongly-recommended', 'strongly-recommended'], - url: 'https://eslint.vuejs.org/rules/no-spaces-around-equal-signs-in-attribute.html' + url: + 'https://eslint.vuejs.org/rules/no-spaces-around-equal-signs-in-attribute.html' }, fixable: 'whitespace', schema: [] }, - create (context) { + create(context) { const sourceCode = context.getSourceCode() return utils.defineTemplateBodyVisitor(context, { - 'VAttribute' (node) { + VAttribute(node) { if (!node.value) { return } @@ -46,7 +47,7 @@ module.exports = { }, message: 'Unexpected spaces found around equal signs.', data: {}, - fix: fixer => fixer.replaceTextRange(range, expect) + fix: (fixer) => fixer.replaceTextRange(range, expect) }) } } diff --git a/lib/rules/no-static-inline-styles.js b/lib/rules/no-static-inline-styles.js index 1955ccbe7..73421a97b 100644 --- a/lib/rules/no-static-inline-styles.js +++ b/lib/rules/no-static-inline-styles.js @@ -30,13 +30,13 @@ module.exports = { forbiddenStyleAttr: '`style` attributes are forbidden.' } }, - create (context) { + create(context) { /** * Checks whether if the given property node is a static value. * @param {AssignmentProperty} prop property node to check * @returns {boolean} `true` if the given property node is a static value. */ - function isStaticValue (prop) { + function isStaticValue(prop) { return ( !prop.computed && prop.value.type === 'Literal' && @@ -58,7 +58,7 @@ module.exports = { * @param {VAttribute} node `:style` node to check * @returns {AssignmentProperty[] | [VAttribute]} the static properties. */ - function getReportNodes (node) { + function getReportNodes(node) { const { value } = node if (!value) { return [] @@ -110,7 +110,7 @@ module.exports = { * Reports if the value is static. * @param {VAttribute} node `:style` node to check */ - function verifyVBindStyle (node) { + function verifyVBindStyle(node) { for (const n of getReportNodes(node)) { context.report({ node: n, @@ -120,7 +120,7 @@ module.exports = { } const visitor = { - "VAttribute[directive=false][key.name='style']" (node) { + "VAttribute[directive=false][key.name='style']"(node) { context.report({ node, messageId: 'forbiddenStyleAttr' diff --git a/lib/rules/no-template-key.js b/lib/rules/no-template-key.js index da54909d1..c7b06ef56 100644 --- a/lib/rules/no-template-key.js +++ b/lib/rules/no-template-key.js @@ -27,14 +27,18 @@ module.exports = { schema: [] }, - create (context) { + create(context) { return utils.defineTemplateBodyVisitor(context, { - "VElement[name='template']" (node) { - if (utils.hasAttribute(node, 'key') || utils.hasDirective(node, 'bind', 'key')) { + "VElement[name='template']"(node) { + if ( + utils.hasAttribute(node, 'key') || + utils.hasDirective(node, 'bind', 'key') + ) { context.report({ - node: node, + node, loc: node.loc, - message: "'`, errors: [ { - message: 'There should be no space before \',\'.', + message: "There should be no space before ','.", line: 3 }, { - message: 'A space is required after \',\'.', + message: "A space is required after ','.", line: 3 } ] @@ -181,11 +181,11 @@ tester.run('comma-spacing', rule, { `, errors: [ { - message: 'There should be no space before \',\'.', + message: "There should be no space before ','.", line: 3 }, { - message: 'A space is required after \',\'.', + message: "A space is required after ','.", line: 3 } ] @@ -201,11 +201,11 @@ tester.run('comma-spacing', rule, { `, errors: [ { - message: 'There should be no space before \',\'.', + message: "There should be no space before ','.", line: 3 }, { - message: 'A space is required after \',\'.', + message: "A space is required after ','.", line: 3 } ] @@ -225,11 +225,11 @@ tester.run('comma-spacing', rule, { `, errors: [ { - message: 'There should be no space before \',\'.', + message: "There should be no space before ','.", line: 4 }, { - message: 'A space is required after \',\'.', + message: "A space is required after ','.", line: 4 } ] @@ -245,11 +245,11 @@ tester.run('comma-spacing', rule, { `, errors: [ { - message: 'There should be no space before \',\'.', + message: "There should be no space before ','.", line: 3 }, { - message: 'A space is required after \',\'.', + message: "A space is required after ','.", line: 3 } ] @@ -270,11 +270,11 @@ tester.run('comma-spacing', rule, { `, errors: [ { - message: 'A space is required before \',\'.', + message: "A space is required before ','.", line: 4 }, { - message: 'There should be no space after \',\'.', + message: "There should be no space after ','.", line: 4 } ] diff --git a/tests/lib/rules/comma-style.js b/tests/lib/rules/comma-style.js index bd469d7a9..39135a697 100644 --- a/tests/lib/rules/comma-style.js +++ b/tests/lib/rules/comma-style.js @@ -25,7 +25,7 @@ tester.run('comma-style', rule, { `, - options: ['last', { exceptions: { ArrowFunctionExpression: false }}] + options: ['last', { exceptions: { ArrowFunctionExpression: false } }] }, { code: ` @@ -33,7 +33,7 @@ tester.run('comma-style', rule, { `, - options: ['first', { exceptions: { ArrowFunctionExpression: false }}] + options: ['first', { exceptions: { ArrowFunctionExpression: false } }] } ], invalid: [ @@ -65,7 +65,7 @@ tester.run('comma-style', rule, { `, - options: ['last', { exceptions: { ArrowFunctionExpression: false }}], + options: ['last', { exceptions: { ArrowFunctionExpression: false } }], output: ` `, - options: ['first', { exceptions: { ArrowFunctionExpression: false }}], + options: ['first', { exceptions: { ArrowFunctionExpression: false } }], output: ` ` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 0) }) @@ -70,7 +71,8 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 1) assert.deepEqual(messages[0].ruleId, 'vue/no-parsing-error') @@ -85,7 +87,8 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 2) assert.deepEqual(messages[0].ruleId, 'vue/no-parsing-error') @@ -103,7 +106,8 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 1) assert.deepEqual(messages[0].ruleId, 'vue/no-duplicate-attributes') @@ -120,7 +124,8 @@ describe('comment-directive', () => { var a ` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.strictEqual(messages.length, 1) assert.strictEqual(messages[0].ruleId, 'no-unused-vars') @@ -134,7 +139,8 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 0) }) @@ -145,13 +151,14 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 1) assert.deepEqual(messages[0].ruleId, 'vue/no-parsing-error') }) - it('don\'t disable rules if is on another line', () => { + it("don't disable rules if is on another line", () => { const code = ` ` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 2) assert.deepEqual(messages[0].ruleId, 'vue/no-parsing-error') @@ -175,7 +183,8 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 0) }) @@ -187,13 +196,14 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 1) assert.deepEqual(messages[0].ruleId, 'vue/no-parsing-error') }) - it('don\'t disable rules if is on another line', () => { + it("don't disable rules if is on another line", () => { const code = ` ` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 2) assert.deepEqual(messages[0].ruleId, 'vue/no-parsing-error') @@ -217,7 +228,8 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 2) assert.deepEqual(messages[0].ruleId, 'vue/no-parsing-error') @@ -235,7 +247,8 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 0) }) @@ -249,7 +262,8 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 2) assert.deepEqual(messages[0].ruleId, 'vue/no-parsing-error') @@ -267,7 +281,8 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 1) assert.deepEqual(messages[0].ruleId, 'vue/no-duplicate-attributes') @@ -280,7 +295,8 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 0) }) @@ -291,7 +307,8 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 1) assert.deepEqual(messages[0].ruleId, 'vue/no-parsing-error') @@ -304,7 +321,8 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 0) }) @@ -316,7 +334,8 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 1) assert.deepEqual(messages[0].ruleId, 'vue/no-parsing-error') @@ -331,12 +350,13 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 0) }) - it('don\'t disable rules if is on after block', () => { + it("don't disable rules if is on after block", () => { const code = ` @@ -345,7 +365,8 @@ describe('comment-directive', () => {
Hello
` - const messages = linter.executeOnText(code, 'test.vue').results[0].messages + const messages = linter.executeOnText(code, 'test.vue').results[0] + .messages assert.deepEqual(messages.length, 2) assert.deepEqual(messages[0].ruleId, 'vue/no-parsing-error') diff --git a/tests/lib/rules/component-definition-name-casing.js b/tests/lib/rules/component-definition-name-casing.js index 2317ea523..f62b7183b 100644 --- a/tests/lib/rules/component-definition-name-casing.js +++ b/tests/lib/rules/component-definition-name-casing.js @@ -22,7 +22,6 @@ const parserOptions = { const ruleTester = new RuleTester() ruleTester.run('component-definition-name-casing', rule, { - valid: [ { filename: 'test.vue', @@ -171,11 +170,13 @@ ruleTester.run('component-definition-name-casing', rule, { } `, parserOptions, - errors: [{ - message: 'Property name "foo-bar" is not PascalCase.', - type: 'Literal', - line: 3 - }] + errors: [ + { + message: 'Property name "foo-bar" is not PascalCase.', + type: 'Literal', + line: 3 + } + ] }, { filename: 'test.vue', @@ -186,11 +187,13 @@ ruleTester.run('component-definition-name-casing', rule, { `, output: null, parserOptions, - errors: [{ - message: 'Property name "foo bar" is not PascalCase.', - type: 'Literal', - line: 3 - }] + errors: [ + { + message: 'Property name "foo bar" is not PascalCase.', + type: 'Literal', + line: 3 + } + ] }, { filename: 'test.vue', @@ -201,11 +204,13 @@ ruleTester.run('component-definition-name-casing', rule, { `, output: null, parserOptions, - errors: [{ - message: 'Property name "foo!bar" is not PascalCase.', - type: 'Literal', - line: 3 - }] + errors: [ + { + message: 'Property name "foo!bar" is not PascalCase.', + type: 'Literal', + line: 3 + } + ] }, { filename: 'test.js', @@ -216,11 +221,13 @@ ruleTester.run('component-definition-name-casing', rule, { `, output: null, parserOptions: { ecmaVersion: 6 }, - errors: [{ - message: 'Property name "foo!bar" is not PascalCase.', - type: 'Literal', - line: 3 - }] + errors: [ + { + message: 'Property name "foo!bar" is not PascalCase.', + type: 'Literal', + line: 3 + } + ] }, { filename: 'test.vue', @@ -235,11 +242,13 @@ ruleTester.run('component-definition-name-casing', rule, { } `, parserOptions, - errors: [{ - message: 'Property name "foo_bar" is not PascalCase.', - type: 'Literal', - line: 3 - }] + errors: [ + { + message: 'Property name "foo_bar" is not PascalCase.', + type: 'Literal', + line: 3 + } + ] }, { filename: 'test.vue', @@ -255,11 +264,13 @@ ruleTester.run('component-definition-name-casing', rule, { `, options: ['PascalCase'], parserOptions, - errors: [{ - message: 'Property name "foo_bar" is not PascalCase.', - type: 'Literal', - line: 3 - }] + errors: [ + { + message: 'Property name "foo_bar" is not PascalCase.', + type: 'Literal', + line: 3 + } + ] }, { filename: 'test.vue', @@ -275,33 +286,39 @@ ruleTester.run('component-definition-name-casing', rule, { `, options: ['kebab-case'], parserOptions, - errors: [{ - message: 'Property name "foo_bar" is not kebab-case.', - type: 'Literal', - line: 3 - }] + errors: [ + { + message: 'Property name "foo_bar" is not kebab-case.', + type: 'Literal', + line: 3 + } + ] }, { filename: 'test.vue', code: `Vue.component('foo-bar', component)`, output: `Vue.component('FooBar', component)`, parserOptions, - errors: [{ - message: 'Property name "foo-bar" is not PascalCase.', - type: 'Literal', - line: 1 - }] + errors: [ + { + message: 'Property name "foo-bar" is not PascalCase.', + type: 'Literal', + line: 1 + } + ] }, { filename: 'test.vue', code: `app.component('foo-bar', component)`, output: `app.component('FooBar', component)`, parserOptions, - errors: [{ - message: 'Property name "foo-bar" is not PascalCase.', - type: 'Literal', - line: 1 - }] + errors: [ + { + message: 'Property name "foo-bar" is not PascalCase.', + type: 'Literal', + line: 1 + } + ] }, { filename: 'test.vue', @@ -309,33 +326,39 @@ ruleTester.run('component-definition-name-casing', rule, { output: `(Vue as VueConstructor).component('FooBar', component)`, parserOptions, parser: require.resolve('@typescript-eslint/parser'), - errors: [{ - message: 'Property name "foo-bar" is not PascalCase.', - type: 'Literal', - line: 1 - }] + errors: [ + { + message: 'Property name "foo-bar" is not PascalCase.', + type: 'Literal', + line: 1 + } + ] }, { filename: 'test.vue', code: `Vue.component('foo-bar', {})`, output: `Vue.component('FooBar', {})`, parserOptions, - errors: [{ - message: 'Property name "foo-bar" is not PascalCase.', - type: 'Literal', - line: 1 - }] + errors: [ + { + message: 'Property name "foo-bar" is not PascalCase.', + type: 'Literal', + line: 1 + } + ] }, { filename: 'test.vue', code: `app.component('foo-bar', {})`, output: `app.component('FooBar', {})`, parserOptions, - errors: [{ - message: 'Property name "foo-bar" is not PascalCase.', - type: 'Literal', - line: 1 - }] + errors: [ + { + message: 'Property name "foo-bar" is not PascalCase.', + type: 'Literal', + line: 1 + } + ] }, { filename: 'test.js', @@ -343,11 +366,13 @@ ruleTester.run('component-definition-name-casing', rule, { output: `Vue.component('FooBar', {})`, options: ['PascalCase'], parserOptions, - errors: [{ - message: 'Property name "foo_bar" is not PascalCase.', - type: 'Literal', - line: 1 - }] + errors: [ + { + message: 'Property name "foo_bar" is not PascalCase.', + type: 'Literal', + line: 1 + } + ] }, { filename: 'test.vue', @@ -355,11 +380,13 @@ ruleTester.run('component-definition-name-casing', rule, { output: `Vue.component('foo-bar', {})`, options: ['kebab-case'], parserOptions, - errors: [{ - message: 'Property name "foo_bar" is not kebab-case.', - type: 'Literal', - line: 1 - }] + errors: [ + { + message: 'Property name "foo_bar" is not kebab-case.', + type: 'Literal', + line: 1 + } + ] }, { filename: 'test.vue', @@ -367,11 +394,13 @@ ruleTester.run('component-definition-name-casing', rule, { output: `Vue.component(\`foo-bar\`, {})`, options: ['kebab-case'], parserOptions, - errors: [{ - message: 'Property name "foo_bar" is not kebab-case.', - type: 'TemplateLiteral', - line: 1 - }] + errors: [ + { + message: 'Property name "foo_bar" is not kebab-case.', + type: 'TemplateLiteral', + line: 1 + } + ] } ] }) diff --git a/tests/lib/rules/component-name-in-template-casing.js b/tests/lib/rules/component-name-in-template-casing.js index d468dce84..31c4ae832 100644 --- a/tests/lib/rules/component-name-in-template-casing.js +++ b/tests/lib/rules/component-name-in-template-casing.js @@ -45,17 +45,50 @@ tester.run('component-name-in-template-casing', rule, { }, // element types test - { code: '', options: ['PascalCase', { registeredComponentsOnly: false }] }, - { code: '', options: ['PascalCase', { registeredComponentsOnly: false }] }, - { code: '', options: ['PascalCase', { registeredComponentsOnly: false }] }, - { code: '', options: ['PascalCase', { registeredComponentsOnly: false }] }, - { code: '', options: ['PascalCase', { registeredComponentsOnly: false }] }, - { code: '', options: ['PascalCase', { registeredComponentsOnly: false }] }, - { code: '', options: ['PascalCase', { registeredComponentsOnly: false }] }, - { code: '', options: ['PascalCase', { registeredComponentsOnly: false }] }, - { code: '', options: ['PascalCase', { registeredComponentsOnly: false }] }, - { code: '', options: ['PascalCase', { registeredComponentsOnly: false }] }, - { code: '', options: ['PascalCase', { registeredComponentsOnly: false }] }, + { + code: '', + options: ['PascalCase', { registeredComponentsOnly: false }] + }, + { + code: '', + options: ['PascalCase', { registeredComponentsOnly: false }] + }, + { + code: '', + options: ['PascalCase', { registeredComponentsOnly: false }] + }, + { + code: '', + options: ['PascalCase', { registeredComponentsOnly: false }] + }, + { + code: '', + options: ['PascalCase', { registeredComponentsOnly: false }] + }, + { + code: '', + options: ['PascalCase', { registeredComponentsOnly: false }] + }, + { + code: '', + options: ['PascalCase', { registeredComponentsOnly: false }] + }, + { + code: '', + options: ['PascalCase', { registeredComponentsOnly: false }] + }, + { + code: '', + options: ['PascalCase', { registeredComponentsOnly: false }] + }, + { + code: '', + options: ['PascalCase', { registeredComponentsOnly: false }] + }, + { + code: '', + options: ['PascalCase', { registeredComponentsOnly: false }] + }, // kebab-case { @@ -82,11 +115,18 @@ tester.run('component-name-in-template-casing', rule, { // ignores { code: '', - options: ['PascalCase', { ignores: ['custom-element'], registeredComponentsOnly: false }] + options: [ + 'PascalCase', + { ignores: ['custom-element'], registeredComponentsOnly: false } + ] }, { - code: '', - options: ['PascalCase', { ignores: ['custom-element'], registeredComponentsOnly: false }] + code: + '', + options: [ + 'PascalCase', + { ignores: ['custom-element'], registeredComponentsOnly: false } + ] }, // regexp ignores { @@ -98,12 +138,21 @@ tester.run('component-name-in-template-casing', rule, { `, filename: 'test.vue', - options: ['PascalCase', { registeredComponentsOnly: false, ignores: ['/^global/'] }] + options: [ + 'PascalCase', + { registeredComponentsOnly: false, ignores: ['/^global/'] } + ] }, // Invalid EOF - { code: '', + options: ['PascalCase', { registeredComponentsOnly: false }] + }, + { + code: ' `, - options: [{ - singleline: 'never', - multiline: 'never' - }] + options: [ + { + singleline: 'never', + multiline: 'never' + } + ] }, { code: ` @@ -63,10 +67,12 @@ tester.run('html-closing-bracket-newline', rule, { `, - options: [{ - singleline: 'never', - multiline: 'always' - }] + options: [ + { + singleline: 'never', + multiline: 'always' + } + ] }, { code: ` @@ -75,10 +81,12 @@ tester.run('html-closing-bracket-newline', rule, { `, - options: [{ - singleline: 'never', - multiline: 'always' - }] + options: [ + { + singleline: 'never', + multiline: 'always' + } + ] }, { code: ` @@ -91,10 +99,12 @@ tester.run('html-closing-bracket-newline', rule, { `, - options: [{ - singleline: 'always', - multiline: 'never' - }] + options: [ + { + singleline: 'always', + multiline: 'never' + } + ] }, { code: ` @@ -107,10 +117,12 @@ tester.run('html-closing-bracket-newline', rule, { `, - options: [{ - singleline: 'always', - multiline: 'never' - }] + options: [ + { + singleline: 'always', + multiline: 'never' + } + ] }, // Ignore if no closing brackets @@ -175,10 +187,12 @@ tester.run('html-closing-bracket-newline', rule, {
`, - options: [{ - singleline: 'never', - multiline: 'never' - }], + options: [ + { + singleline: 'never', + multiline: 'never' + } + ], errors: [ 'Expected no line breaks before closing bracket, but 1 line break found.', 'Expected no line breaks before closing bracket, but 2 line breaks found.' @@ -200,10 +214,12 @@ tester.run('html-closing-bracket-newline', rule, { `, - options: [{ - singleline: 'never', - multiline: 'never' - }], + options: [ + { + singleline: 'never', + multiline: 'never' + } + ], errors: [ 'Expected no line breaks before closing bracket, but 1 line break found.' ] @@ -224,10 +240,12 @@ tester.run('html-closing-bracket-newline', rule, { `, - options: [{ - singleline: 'never', - multiline: 'always' - }], + options: [ + { + singleline: 'never', + multiline: 'always' + } + ], errors: [ 'Expected 1 line break before closing bracket, but no line breaks found.' ] @@ -247,10 +265,12 @@ tester.run('html-closing-bracket-newline', rule, { `, - options: [{ - singleline: 'never', - multiline: 'always' - }], + options: [ + { + singleline: 'never', + multiline: 'always' + } + ], errors: [ 'Expected no line breaks before closing bracket, but 1 line break found.', 'Expected no line breaks before closing bracket, but 1 line break found.' @@ -277,10 +297,12 @@ tester.run('html-closing-bracket-newline', rule, { `, - options: [{ - singleline: 'always', - multiline: 'never' - }], + options: [ + { + singleline: 'always', + multiline: 'never' + } + ], errors: [ 'Expected no line breaks before closing bracket, but 1 line break found.', 'Expected 1 line break before closing bracket, but no line breaks found.' @@ -305,10 +327,12 @@ tester.run('html-closing-bracket-newline', rule, { `, - options: [{ - singleline: 'always', - multiline: 'never' - }], + options: [ + { + singleline: 'always', + multiline: 'never' + } + ], errors: [ 'Expected 1 line break before closing bracket, but no line breaks found.', 'Expected 1 line break before closing bracket, but no line breaks found.' diff --git a/tests/lib/rules/html-closing-bracket-spacing.js b/tests/lib/rules/html-closing-bracket-spacing.js index b0080df0c..154ba87b2 100644 --- a/tests/lib/rules/html-closing-bracket-spacing.js +++ b/tests/lib/rules/html-closing-bracket-spacing.js @@ -15,7 +15,7 @@ const rule = require('../../../lib/rules/html-closing-bracket-spacing') // Tests // ----------------------------------------------------------------------------- -var ruleTester = new RuleTester({ +const ruleTester = new RuleTester({ parser: require.resolve('vue-eslint-parser'), parserOptions: { ecmaVersion: 2015 @@ -57,39 +57,92 @@ ruleTester.run('html-closing-bracket-spacing', rule, { code: '', output: '', errors: [ - { message: "Expected no space before '>', but found.", line: 2, column: 7, endColumn: 9 }, - { message: "Expected no space before '>', but found.", line: 3, column: 8, endColumn: 10 }, - { message: "Expected a space before '/>', but not found.", line: 4, column: 7, endColumn: 9 } + { + message: "Expected no space before '>', but found.", + line: 2, + column: 7, + endColumn: 9 + }, + { + message: "Expected no space before '>', but found.", + line: 3, + column: 8, + endColumn: 10 + }, + { + message: "Expected a space before '/>', but not found.", + line: 4, + column: 7, + endColumn: 9 + } ] }, { code: '', output: '', errors: [ - { message: "Expected no space before '>', but found.", line: 2, column: 11, endColumn: 13 }, - { message: "Expected a space before '/>', but not found.", line: 3, column: 11, endColumn: 13 } + { + message: "Expected no space before '>', but found.", + line: 2, + column: 11, + endColumn: 13 + }, + { + message: "Expected a space before '/>', but not found.", + line: 3, + column: 11, + endColumn: 13 + } ] }, { code: '', - output: '', + output: + '', errors: [ - { message: "Expected no space before '>', but found.", line: 2, column: 15, endColumn: 17 }, - { message: "Expected a space before '/>', but not found.", line: 3, column: 15, endColumn: 17 } + { + message: "Expected no space before '>', but found.", + line: 2, + column: 15, + endColumn: 17 + }, + { + message: "Expected a space before '/>', but not found.", + line: 3, + column: 15, + endColumn: 17 + } ] }, { code: '', output: '', - options: [{ - startTag: 'always', - endTag: 'always', - selfClosingTag: 'never' - }], + options: [ + { + startTag: 'always', + endTag: 'always', + selfClosingTag: 'never' + } + ], errors: [ - { message: "Expected a space before '>', but not found.", line: 2, column: 7, endColumn: 8 }, - { message: "Expected a space before '>', but not found.", line: 3, column: 8, endColumn: 9 }, - { message: "Expected no space before '/>', but found.", line: 4, column: 7, endColumn: 10 } + { + message: "Expected a space before '>', but not found.", + line: 2, + column: 7, + endColumn: 8 + }, + { + message: "Expected a space before '>', but not found.", + line: 3, + column: 8, + endColumn: 9 + }, + { + message: "Expected no space before '/>', but found.", + line: 4, + column: 7, + endColumn: 10 + } ] } ] diff --git a/tests/lib/rules/html-comment-content-newline.js b/tests/lib/rules/html-comment-content-newline.js index 8fa008e05..3755a5425 100644 --- a/tests/lib/rules/html-comment-content-newline.js +++ b/tests/lib/rules/html-comment-content-newline.js @@ -15,7 +15,6 @@ const tester = new RuleTester({ } }) tester.run('html-comment-content-newline', rule, { - valid: [ { code: ` @@ -256,10 +255,32 @@ tester.run('html-comment-content-newline', rule, { `, errors: [ - { message: 'Unexpected line breaks after \'\'.', line: 4, column: 20, endLine: 5, endColumn: 11 }, - { message: 'Expected line break after \'\'.', line: 7, column: 20, endColumn: 21 } + { + message: "Unexpected line breaks after ''.", + line: 4, + column: 20, + endLine: 5, + endColumn: 11 + }, + { + message: "Expected line break after ''.", + line: 7, + column: 20, + endColumn: 21 + } ] }, { @@ -277,10 +298,30 @@ tester.run('html-comment-content-newline', rule, { `, errors: [ - { message: 'Expected line break after \'\'.', line: 3, column: 22, endColumn: 22 }, - { message: 'Expected line break after \'\'.', line: 4, column: 24, endColumn: 26 } + { + message: "Expected line break after ''.", + line: 3, + column: 22, + endColumn: 22 + }, + { + message: "Expected line break after ''.", + line: 4, + column: 24, + endColumn: 26 + } ] }, { @@ -298,8 +339,20 @@ comment `, errors: [ - { message: 'Unexpected line breaks after \'\'.', line: 4, column: 8, endLine: 5, endColumn: 1 } + { + message: "Unexpected line breaks after ''.", + line: 4, + column: 8, + endLine: 5, + endColumn: 1 + } ] }, { @@ -315,8 +368,18 @@ comment `, errors: [ - { message: 'Expected line break after \'\'.', line: 3, column: 30, endColumn: 38 } + { + message: "Expected line break after ''.", + line: 3, + column: 30, + endColumn: 38 + } ] }, // exceptions @@ -360,7 +423,7 @@ comment `, errors: [ 'Expected line break after exception block.', - 'Expected line break before \'-->\'.' + "Expected line break before '-->'." ] }, { @@ -373,7 +436,11 @@ comment output: null, errors: [ 'Expected line break after exception block.', - { message: 'Expected line break before exception block.', line: 3, column: 27 } + { + message: 'Expected line break before exception block.', + line: 3, + column: 27 + } ] }, { @@ -386,9 +453,12 @@ comment output: null, errors: [ 'Expected line break after exception block.', - { message: 'Expected line break before exception block.', line: 3, column: 28 } + { + message: 'Expected line break before exception block.', + line: 3, + column: 28 + } ] } ] - }) diff --git a/tests/lib/rules/html-comment-content-spacing.js b/tests/lib/rules/html-comment-content-spacing.js index 699d4d1ea..b29c1a960 100644 --- a/tests/lib/rules/html-comment-content-spacing.js +++ b/tests/lib/rules/html-comment-content-spacing.js @@ -15,7 +15,6 @@ const tester = new RuleTester({ } }) tester.run('html-comment-content-spacing', rule, { - valid: [ { code: ` @@ -213,8 +212,18 @@ tester.run('html-comment-content-spacing', rule, { `, errors: [ - { message: 'Expected space after \'\'.', line: 3, column: 22, endColumn: 22 } + { + message: "Expected space after ''.", + line: 3, + column: 22, + endColumn: 22 + } ] }, { @@ -230,8 +239,18 @@ tester.run('html-comment-content-spacing', rule, { `, errors: [ - { message: 'Unexpected space after \'\'.', line: 3, column: 23, endColumn: 24 } + { + message: "Unexpected space after ''.", + line: 3, + column: 23, + endColumn: 24 + } ] }, { @@ -247,8 +266,18 @@ tester.run('html-comment-content-spacing', rule, { `, errors: [ - { message: 'Unexpected space after \'\'.', line: 3, column: 30, endColumn: 38 } + { + message: "Unexpected space after ''.", + line: 3, + column: 30, + endColumn: 38 + } ] }, // exceptions @@ -292,7 +321,7 @@ tester.run('html-comment-content-spacing', rule, { `, errors: [ 'Expected space after exception block.', - 'Expected space before \'-->\'.' + "Expected space before '-->'." ] }, { @@ -305,7 +334,11 @@ tester.run('html-comment-content-spacing', rule, { output: null, errors: [ 'Expected space after exception block.', - { message: 'Expected space before exception block.', line: 3, column: 27 } + { + message: 'Expected space before exception block.', + line: 3, + column: 27 + } ] }, { @@ -318,9 +351,12 @@ tester.run('html-comment-content-spacing', rule, { output: null, errors: [ 'Expected space after exception block.', - { message: 'Expected space before exception block.', line: 3, column: 28 } + { + message: 'Expected space before exception block.', + line: 3, + column: 28 + } ] } ] - }) diff --git a/tests/lib/rules/html-comment-indent.js b/tests/lib/rules/html-comment-indent.js index 0415b13f9..4ec5c6ee2 100644 --- a/tests/lib/rules/html-comment-indent.js +++ b/tests/lib/rules/html-comment-indent.js @@ -159,55 +159,62 @@ tester.run('html-comment-indent', rule, { --> `, - errors: [{ - message: 'Expected relative indentation of 2 spaces but found 0 spaces.', - line: 4, - column: 11, - endLine: 4, - endColumn: 11 - }, - { - message: 'Expected base point indentation of 10 spaces, but found 7 spaces.', - line: 7, - column: 1, - endLine: 7, - endColumn: 8 - }, - { - message: 'Expected relative indentation of 2 spaces but found 5 spaces.', - line: 8, - column: 11, - endLine: 8, - endColumn: 16 - }, - { - message: 'Expected relative indentation of 0 spaces but found 1 space.', - line: 9, - column: 11, - endLine: 9, - endColumn: 12 - }, - { - message: 'Expected space character, but found tab character.', - line: 11, - column: 14, - endLine: 11, - endColumn: 15 - }, - { - message: 'Expected space character, but found tab character.', - line: 12, - column: 13, - endLine: 12, - endColumn: 14 - }, - { - message: 'Expected base point indentation of 12 spaces, but found 11 spaces.', - line: 13, - column: 1, - endLine: 13, - endColumn: 12 - }] + errors: [ + { + message: + 'Expected relative indentation of 2 spaces but found 0 spaces.', + line: 4, + column: 11, + endLine: 4, + endColumn: 11 + }, + { + message: + 'Expected base point indentation of 10 spaces, but found 7 spaces.', + line: 7, + column: 1, + endLine: 7, + endColumn: 8 + }, + { + message: + 'Expected relative indentation of 2 spaces but found 5 spaces.', + line: 8, + column: 11, + endLine: 8, + endColumn: 16 + }, + { + message: + 'Expected relative indentation of 0 spaces but found 1 space.', + line: 9, + column: 11, + endLine: 9, + endColumn: 12 + }, + { + message: 'Expected space character, but found tab character.', + line: 11, + column: 14, + endLine: 11, + endColumn: 15 + }, + { + message: 'Expected space character, but found tab character.', + line: 12, + column: 13, + endLine: 12, + endColumn: 14 + }, + { + message: + 'Expected base point indentation of 12 spaces, but found 11 spaces.', + line: 13, + column: 1, + endLine: 13, + endColumn: 12 + } + ] }, { code: ` @@ -241,55 +248,59 @@ tester.run('html-comment-indent', rule, { --> `, - errors: [{ - message: 'Expected relative indentation of 1 tab but found 0 tabs.', - line: 4, - column: 11, - endLine: 4, - endColumn: 11 - }, - { - message: 'Expected base point indentation of 10 spaces, but found " \\t".', - line: 7, - column: 1, - endLine: 7, - endColumn: 10 - }, - { - message: 'Expected relative indentation of 1 tab but found 2 tabs.', - line: 8, - column: 11, - endLine: 8, - endColumn: 13 - }, - { - message: 'Expected relative indentation of 0 tabs but found 1 tab.', - line: 9, - column: 11, - endLine: 9, - endColumn: 12 - }, - { - message: 'Expected tab character, but found space character.', - line: 11, - column: 14, - endLine: 11, - endColumn: 15 - }, - { - message: 'Expected tab character, but found space character.', - line: 12, - column: 13, - endLine: 12, - endColumn: 14 - }, - { - message: 'Expected base point indentation of 12 spaces, but found 11 spaces.', - line: 13, - column: 1, - endLine: 13, - endColumn: 12 - }] + errors: [ + { + message: 'Expected relative indentation of 1 tab but found 0 tabs.', + line: 4, + column: 11, + endLine: 4, + endColumn: 11 + }, + { + message: + 'Expected base point indentation of 10 spaces, but found " \\t".', + line: 7, + column: 1, + endLine: 7, + endColumn: 10 + }, + { + message: 'Expected relative indentation of 1 tab but found 2 tabs.', + line: 8, + column: 11, + endLine: 8, + endColumn: 13 + }, + { + message: 'Expected relative indentation of 0 tabs but found 1 tab.', + line: 9, + column: 11, + endLine: 9, + endColumn: 12 + }, + { + message: 'Expected tab character, but found space character.', + line: 11, + column: 14, + endLine: 11, + endColumn: 15 + }, + { + message: 'Expected tab character, but found space character.', + line: 12, + column: 13, + endLine: 12, + endColumn: 14 + }, + { + message: + 'Expected base point indentation of 12 spaces, but found 11 spaces.', + line: 13, + column: 1, + endLine: 13, + endColumn: 12 + } + ] }, { code: ` @@ -323,55 +334,62 @@ tester.run('html-comment-indent', rule, { --> `, - errors: [{ - message: 'Expected relative indentation of 4 spaces but found 0 spaces.', - line: 4, - column: 11, - endLine: 4, - endColumn: 11 - }, - { - message: 'Expected base point indentation of 10 spaces, but found 5 spaces.', - line: 7, - column: 1, - endLine: 7, - endColumn: 6 - }, - { - message: 'Expected relative indentation of 4 spaces but found 8 spaces.', - line: 8, - column: 11, - endLine: 8, - endColumn: 19 - }, - { - message: 'Expected relative indentation of 0 spaces but found 2 spaces.', - line: 9, - column: 11, - endLine: 9, - endColumn: 13 - }, - { - message: 'Expected space character, but found tab character.', - line: 11, - column: 15, - endLine: 11, - endColumn: 16 - }, - { - message: 'Expected space character, but found tab character.', - line: 12, - column: 13, - endLine: 12, - endColumn: 14 - }, - { - message: 'Expected base point indentation of 12 spaces, but found 10 spaces.', - line: 13, - column: 1, - endLine: 13, - endColumn: 11 - }] + errors: [ + { + message: + 'Expected relative indentation of 4 spaces but found 0 spaces.', + line: 4, + column: 11, + endLine: 4, + endColumn: 11 + }, + { + message: + 'Expected base point indentation of 10 spaces, but found 5 spaces.', + line: 7, + column: 1, + endLine: 7, + endColumn: 6 + }, + { + message: + 'Expected relative indentation of 4 spaces but found 8 spaces.', + line: 8, + column: 11, + endLine: 8, + endColumn: 19 + }, + { + message: + 'Expected relative indentation of 0 spaces but found 2 spaces.', + line: 9, + column: 11, + endLine: 9, + endColumn: 13 + }, + { + message: 'Expected space character, but found tab character.', + line: 11, + column: 15, + endLine: 11, + endColumn: 16 + }, + { + message: 'Expected space character, but found tab character.', + line: 12, + column: 13, + endLine: 12, + endColumn: 14 + }, + { + message: + 'Expected base point indentation of 12 spaces, but found 10 spaces.', + line: 13, + column: 1, + endLine: 13, + endColumn: 11 + } + ] }, { code: ` @@ -405,55 +423,62 @@ tester.run('html-comment-indent', rule, { --> `, - errors: [{ - message: 'Expected relative indentation of 0 spaces but found 2 spaces.', - line: 4, - column: 11, - endLine: 4, - endColumn: 13 - }, - { - message: 'Expected base point indentation of 10 spaces, but found 8 spaces.', - line: 7, - column: 1, - endLine: 7, - endColumn: 9 - }, - { - message: 'Expected space character, but found tab character.', - line: 8, - column: 11, - endLine: 8, - endColumn: 12 - }, - { - message: 'Expected relative indentation of 0 spaces but found 2 spaces.', - line: 9, - column: 11, - endLine: 9, - endColumn: 13 - }, - { - message: 'Expected space character, but found tab character.', - line: 11, - column: 13, - endLine: 11, - endColumn: 14 - }, - { - message: 'Expected base point indentation of 12 spaces, but found " \\t".', - line: 12, - column: 1, - endLine: 12, - endColumn: 12 - }, - { - message: 'Expected base point indentation of 12 spaces, but found 10 spaces.', - line: 13, - column: 1, - endLine: 13, - endColumn: 11 - }] + errors: [ + { + message: + 'Expected relative indentation of 0 spaces but found 2 spaces.', + line: 4, + column: 11, + endLine: 4, + endColumn: 13 + }, + { + message: + 'Expected base point indentation of 10 spaces, but found 8 spaces.', + line: 7, + column: 1, + endLine: 7, + endColumn: 9 + }, + { + message: 'Expected space character, but found tab character.', + line: 8, + column: 11, + endLine: 8, + endColumn: 12 + }, + { + message: + 'Expected relative indentation of 0 spaces but found 2 spaces.', + line: 9, + column: 11, + endLine: 9, + endColumn: 13 + }, + { + message: 'Expected space character, but found tab character.', + line: 11, + column: 13, + endLine: 11, + endColumn: 14 + }, + { + message: + 'Expected base point indentation of 12 spaces, but found " \\t".', + line: 12, + column: 1, + endLine: 12, + endColumn: 12 + }, + { + message: + 'Expected base point indentation of 12 spaces, but found 10 spaces.', + line: 13, + column: 1, + endLine: 13, + endColumn: 11 + } + ] }, { code: ` @@ -488,22 +513,28 @@ tester.run('html-comment-indent', rule, { --> `, - errors: [{ - message: 'Expected relative indentation of 2 spaces but found 0 spaces.', - line: 5 - }, - { - message: 'Expected relative indentation of 2 spaces but found 4 spaces.', - line: 7 - }, - { - message: 'Expected relative indentation of 0 spaces but found 2 spaces.', - line: 12 - }, - { - message: 'Expected base point indentation of 10 spaces, but found 8 spaces.', - line: 14 - }] + errors: [ + { + message: + 'Expected relative indentation of 2 spaces but found 0 spaces.', + line: 5 + }, + { + message: + 'Expected relative indentation of 2 spaces but found 4 spaces.', + line: 7 + }, + { + message: + 'Expected relative indentation of 0 spaces but found 2 spaces.', + line: 12 + }, + { + message: + 'Expected base point indentation of 10 spaces, but found 8 spaces.', + line: 14 + } + ] }, { code: ` @@ -522,14 +553,18 @@ tester.run('html-comment-indent', rule, { comment --> `, - errors: [{ - message: 'Expected relative indentation of 2 spaces but found 0 spaces.', - line: 4 - }, - { - message: 'Expected relative indentation of 2 spaces but found 4 spaces.', - line: 6 - }] + errors: [ + { + message: + 'Expected relative indentation of 2 spaces but found 0 spaces.', + line: 4 + }, + { + message: + 'Expected relative indentation of 2 spaces but found 4 spaces.', + line: 6 + } + ] }, { code: ` @@ -550,18 +585,20 @@ comment --> --> `, - errors: [{ - message: 'Expected indentation of 2 spaces but found 0 spaces.', - line: 4 - }, - { - message: 'Expected indentation of 2 spaces but found 0 spaces.', - line: 5 - }, - { - message: 'Expected indentation of 0 spaces but found 2 spaces.', - line: 7 - }] + errors: [ + { + message: 'Expected indentation of 2 spaces but found 0 spaces.', + line: 4 + }, + { + message: 'Expected indentation of 2 spaces but found 0 spaces.', + line: 5 + }, + { + message: 'Expected indentation of 0 spaces but found 2 spaces.', + line: 7 + } + ] }, { code: ` @@ -582,18 +619,23 @@ comment --> --> `, - errors: [{ - message: 'Expected base point indentation of 2 spaces, but not found.', - line: 4 - }, - { - message: 'Expected base point indentation of 2 spaces, but not found.', - line: 5 - }, - { - message: 'Expected base point indentation of 2 spaces, but not found.', - line: 7 - }] + errors: [ + { + message: + 'Expected base point indentation of 2 spaces, but not found.', + line: 4 + }, + { + message: + 'Expected base point indentation of 2 spaces, but not found.', + line: 5 + }, + { + message: + 'Expected base point indentation of 2 spaces, but not found.', + line: 7 + } + ] }, { code: ` @@ -610,14 +652,18 @@ comment --> --> `, - errors: [{ - message: 'Expected relative indentation of 2 spaces but found 1 space.', - line: 4 - }, - { - message: 'Expected relative indentation of 0 spaces but found 1 space.', - line: 5 - }] + errors: [ + { + message: + 'Expected relative indentation of 2 spaces but found 1 space.', + line: 4 + }, + { + message: + 'Expected relative indentation of 0 spaces but found 1 space.', + line: 5 + } + ] }, { code: ` @@ -634,15 +680,18 @@ comment --> \t \t \t --> `, - errors: [{ - message: 'Expected base point indentation of " \\t \\t \\t ", but found 7 spaces.', - line: 4 - }, - { - message: 'Expected base point indentation of " \\t \\t \\t ", but found 7 spaces.', - line: 5 - }] + errors: [ + { + message: + 'Expected base point indentation of " \\t \\t \\t ", but found 7 spaces.', + line: 4 + }, + { + message: + 'Expected base point indentation of " \\t \\t \\t ", but found 7 spaces.', + line: 5 + } + ] } ] - }) diff --git a/tests/lib/rules/html-quotes.js b/tests/lib/rules/html-quotes.js index 95338825a..dd250054a 100644 --- a/tests/lib/rules/html-quotes.js +++ b/tests/lib/rules/html-quotes.js @@ -63,7 +63,7 @@ tester.run('html-quotes', rule, { }, { filename: 'test.vue', - code: "", + code: '', options: ['single', { avoidEscape: true }] }, @@ -73,7 +73,7 @@ tester.run('html-quotes', rule, { options: ['single'] }, { - code: '', + code: "', - output: '', + output: "", options: ['single'], errors: ['Expected to be enclosed by single quotes.'] }, { filename: 'test.vue', code: '', - output: '', + output: "", options: ['single'], errors: ['Expected to be enclosed by single quotes.'] }, { filename: 'test.vue', code: '', - output: '', + output: "", options: ['single'], errors: ['Expected to be enclosed by single quotes.'] }, { filename: 'test.vue', code: '', - output: '', + output: "", options: ['single'], errors: ['Expected to be enclosed by single quotes.'] }, @@ -196,14 +196,14 @@ tester.run('html-quotes', rule, { { filename: 'test.vue', code: '', - output: '', + output: "", options: ['double', { avoidEscape: true }], errors: ['Expected to be enclosed by double quotes.'] }, { filename: 'test.vue', - code: '', - output: "", + code: "", + output: '', options: ['single', { avoidEscape: true }], errors: ['Expected to be enclosed by single quotes.'] }, @@ -217,7 +217,7 @@ tester.run('html-quotes', rule, { { filename: 'test.vue', code: '', - output: '', + output: "", options: ['single', { avoidEscape: true }], errors: ['Expected to be enclosed by single quotes.'] } diff --git a/tests/lib/rules/html-self-closing.js b/tests/lib/rules/html-self-closing.js index fe819cec4..d548b79d9 100644 --- a/tests/lib/rules/html-self-closing.js +++ b/tests/lib/rules/html-self-closing.js @@ -33,23 +33,24 @@ const ALL_CODE = `` -const anyWith = (opts) => Object.assign( - { - svg: 'any', - math: 'any' - }, - opts, - { - html: Object.assign( - { - normal: 'any', - void: 'any', - component: 'any' - }, - opts.html || {} - ) - } -) +const anyWith = (opts) => + Object.assign( + { + svg: 'any', + math: 'any' + }, + opts, + { + html: Object.assign( + { + normal: 'any', + void: 'any', + component: 'any' + }, + opts.html || {} + ) + } + ) tester.run('html-self-closing', rule, { valid: [ @@ -64,7 +65,7 @@ tester.run('html-self-closing', rule, { { code: '', output: null, - options: [{ html: { normal: 'always' }}] + options: [{ html: { normal: 'always' } }] }, // Invalid EOF @@ -116,7 +117,7 @@ tester.run('html-self-closing', rule, { `, - options: [anyWith({ html: { normal: 'always' }})], + options: [anyWith({ html: { normal: 'always' } })], errors: [ { message: 'Require self-closing on HTML elements (
).', line: 2 } ] @@ -135,7 +136,7 @@ tester.run('html-self-closing', rule, { `, - options: [anyWith({ html: { normal: 'never' }})], + options: [anyWith({ html: { normal: 'never' } })], errors: [ { message: 'Disallow self-closing on HTML elements (
).', line: 3 } ] @@ -154,9 +155,12 @@ tester.run('html-self-closing', rule, { `, - options: [anyWith({ html: { void: 'always' }})], + options: [anyWith({ html: { void: 'always' } })], errors: [ - { message: 'Require self-closing on HTML void elements ().', line: 4 } + { + message: 'Require self-closing on HTML void elements ().', + line: 4 + } ] }, { @@ -173,9 +177,12 @@ tester.run('html-self-closing', rule, { `, - options: [anyWith({ html: { void: 'never' }})], + options: [anyWith({ html: { void: 'never' } })], errors: [ - { message: 'Disallow self-closing on HTML void elements ().', line: 5 } + { + message: 'Disallow self-closing on HTML void elements ().', + line: 5 + } ] }, { @@ -192,9 +199,13 @@ tester.run('html-self-closing', rule, { `, - options: [anyWith({ html: { component: 'always' }})], + options: [anyWith({ html: { component: 'always' } })], errors: [ - { message: 'Require self-closing on Vue.js custom components ().', line: 6 } + { + message: + 'Require self-closing on Vue.js custom components ().', + line: 6 + } ] }, { @@ -211,9 +222,13 @@ tester.run('html-self-closing', rule, { `, - options: [anyWith({ html: { component: 'never' }})], + options: [anyWith({ html: { component: 'never' } })], errors: [ - { message: 'Disallow self-closing on Vue.js custom components ().', line: 7 } + { + message: + 'Disallow self-closing on Vue.js custom components ().', + line: 7 + } ] }, { @@ -270,7 +285,10 @@ tester.run('html-self-closing', rule, { `, options: [anyWith({ math: 'always' })], errors: [ - { message: 'Require self-closing on MathML elements ().', line: 10 } + { + message: 'Require self-closing on MathML elements ().', + line: 10 + } ] }, { @@ -289,7 +307,10 @@ tester.run('html-self-closing', rule, { `, options: [anyWith({ math: 'never' })], errors: [ - { message: 'Disallow self-closing on MathML elements ().', line: 11 } + { + message: 'Disallow self-closing on MathML elements ().', + line: 11 + } ] } ] diff --git a/tests/lib/rules/jsx-uses-vars.js b/tests/lib/rules/jsx-uses-vars.js index c40d406fe..875fb9288 100644 --- a/tests/lib/rules/jsx-uses-vars.js +++ b/tests/lib/rules/jsx-uses-vars.js @@ -8,12 +8,12 @@ // Requirements // ------------------------------------------------------------------------------ -var eslint = require('eslint') -var rule = require('../../../lib/rules/jsx-uses-vars') -var ruleNoUnusedVars = require('eslint/lib/rules/no-unused-vars') +const eslint = require('eslint') +const rule = require('../../../lib/rules/jsx-uses-vars') +const ruleNoUnusedVars = require('eslint/lib/rules/no-unused-vars') -var RuleTester = eslint.RuleTester -var ruleTester = new RuleTester({ +const RuleTester = eslint.RuleTester +const ruleTester = new RuleTester({ parserOptions: { ecmaVersion: 6, sourceType: 'module', @@ -23,7 +23,7 @@ var ruleTester = new RuleTester({ } }) -var linter = ruleTester.linter || eslint.linter +const linter = ruleTester.linter || eslint.linter linter.defineRule('jsx-uses-vars', rule) // ------------------------------------------------------------------------------ @@ -31,7 +31,6 @@ linter.defineRule('jsx-uses-vars', rule) // ------------------------------------------------------------------------------ ruleTester.run('no-unused-vars', ruleNoUnusedVars, { - valid: [ { code: ` @@ -45,7 +44,8 @@ ruleTester.run('no-unused-vars', ruleNoUnusedVars, { }, }; ` - }, { + }, + { code: ` /* eslint jsx-uses-vars: 1 */ import SomeComponent from './SomeComponent.vue'; @@ -69,7 +69,8 @@ ruleTester.run('no-unused-vars', ruleNoUnusedVars, { } } ` - }, { + }, + { code: ` /* eslint jsx-uses-vars: 1 */ export default { @@ -94,10 +95,13 @@ ruleTester.run('no-unused-vars', ruleNoUnusedVars, { }, }; `, - errors: [{ - message: "'SomeComponent' is defined but never used." - }] - }, { + errors: [ + { + message: "'SomeComponent' is defined but never used." + } + ] + }, + { code: ` /* eslint jsx-uses-vars: 1 */ import SomeComponent from './SomeComponent.jsx'; @@ -111,9 +115,11 @@ ruleTester.run('no-unused-vars', ruleNoUnusedVars, { }, }; `, - errors: [{ - message: "'wrapper' is assigned a value but never used." - }] + errors: [ + { + message: "'wrapper' is assigned a value but never used." + } + ] } ] }) diff --git a/tests/lib/rules/key-spacing.js b/tests/lib/rules/key-spacing.js index ffca2f56c..519230e23 100644 --- a/tests/lib/rules/key-spacing.js +++ b/tests/lib/rules/key-spacing.js @@ -17,7 +17,7 @@ tester.run('key-spacing', rule, { '', { code: '', - options: [{ 'beforeColon': true }] + options: [{ beforeColon: true }] } ], invalid: [ @@ -31,7 +31,7 @@ tester.run('key-spacing', rule, { }, { code: '', - options: [{ 'beforeColon': true }], + options: [{ beforeColon: true }], output: '', errors: [ "Missing space after key 'a'.", diff --git a/tests/lib/rules/keyword-spacing.js b/tests/lib/rules/keyword-spacing.js index 314c4c1b1..dad5574e5 100644 --- a/tests/lib/rules/keyword-spacing.js +++ b/tests/lib/rules/keyword-spacing.js @@ -25,8 +25,7 @@ tester.run('keyword-spacing', rule, { " /> `, { - code: - ``, - options: [{ - ignores: ['IgnoreTag'] - }] + options: [ + { + ignores: ['IgnoreTag'] + } + ] }, { code: ` @@ -250,9 +254,11 @@ tester.run('multiline-html-element-content-newline', rule, { content content `, - options: [{ - ignores: ['IgnoreTag'] - }] + options: [ + { + ignores: ['IgnoreTag'] + } + ] }, // Ignore if no closing brackets @@ -283,7 +289,8 @@ content `, errors: [ { - message: 'Expected 1 line break after opening tag (`
`), but no line breaks found.', + message: + 'Expected 1 line break after opening tag (`
`), but no line breaks found.', line: 5, column: 12, type: 'HTMLTagClose', @@ -291,7 +298,8 @@ content endColumn: 12 }, { - message: 'Expected 1 line break before closing tag (`
`), but no line breaks found.', + message: + 'Expected 1 line break before closing tag (`
`), but no line breaks found.', line: 5, column: 19, type: 'HTMLEndTagOpen', @@ -320,14 +328,16 @@ content `, errors: [ { - message: 'Expected 1 line break after opening tag (`
`), but no line breaks found.', + message: + 'Expected 1 line break after opening tag (`
`), but no line breaks found.', line: 5, column: 12, endLine: 5, endColumn: 15 }, { - message: 'Expected 1 line break before closing tag (`
`), but no line breaks found.', + message: + 'Expected 1 line break before closing tag (`
`), but no line breaks found.', line: 5, column: 22, endLine: 5, @@ -353,14 +363,16 @@ content `, errors: [ { - message: 'Expected 1 line break after opening tag (`
`), but no line breaks found.', + message: + 'Expected 1 line break after opening tag (`
`), but no line breaks found.', line: 3, column: 16, endLine: 3, endColumn: 16 }, { - message: 'Expected 1 line break before closing tag (`
`), but no line breaks found.', + message: + 'Expected 1 line break before closing tag (`
`), but no line breaks found.', line: 4, column: 22, endLine: 4, @@ -710,7 +722,9 @@ content `, options: [{ ignoreWhenEmpty: false }], - errors: ['Expected 1 line break after opening tag (`
`), but no line breaks found.'] + errors: [ + 'Expected 1 line break after opening tag (`
`), but no line breaks found.' + ] } ] }) diff --git a/tests/lib/rules/mustache-interpolation-spacing.js b/tests/lib/rules/mustache-interpolation-spacing.js index 7c4787c69..45818fec8 100644 --- a/tests/lib/rules/mustache-interpolation-spacing.js +++ b/tests/lib/rules/mustache-interpolation-spacing.js @@ -21,7 +21,6 @@ const ruleTester = new RuleTester({ }) ruleTester.run('mustache-interpolation-spacing', rule, { - valid: [ { filename: 'test.vue', @@ -33,11 +32,13 @@ ruleTester.run('mustache-interpolation-spacing', rule, { }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', diff --git a/tests/lib/rules/name-property-casing.js b/tests/lib/rules/name-property-casing.js index ae2ed7dec..a7a8d41cc 100644 --- a/tests/lib/rules/name-property-casing.js +++ b/tests/lib/rules/name-property-casing.js @@ -22,7 +22,6 @@ const parserOptions = { const ruleTester = new RuleTester() ruleTester.run('name-property-casing', rule, { - valid: [ { filename: 'test.vue', @@ -86,11 +85,13 @@ ruleTester.run('name-property-casing', rule, { } `, parserOptions, - errors: [{ - message: 'Property name "foo-bar" is not PascalCase.', - type: 'Literal', - line: 3 - }] + errors: [ + { + message: 'Property name "foo-bar" is not PascalCase.', + type: 'Literal', + line: 3 + } + ] }, { filename: 'test.vue', @@ -101,11 +102,13 @@ ruleTester.run('name-property-casing', rule, { `, output: null, parserOptions, - errors: [{ - message: 'Property name "foo bar" is not PascalCase.', - type: 'Literal', - line: 3 - }] + errors: [ + { + message: 'Property name "foo bar" is not PascalCase.', + type: 'Literal', + line: 3 + } + ] }, { filename: 'test.vue', @@ -116,11 +119,13 @@ ruleTester.run('name-property-casing', rule, { `, output: null, parserOptions, - errors: [{ - message: 'Property name "foo!bar" is not PascalCase.', - type: 'Literal', - line: 3 - }] + errors: [ + { + message: 'Property name "foo!bar" is not PascalCase.', + type: 'Literal', + line: 3 + } + ] }, { filename: 'test.js', @@ -131,11 +136,13 @@ ruleTester.run('name-property-casing', rule, { `, output: null, parserOptions: { ecmaVersion: 6 }, - errors: [{ - message: 'Property name "foo!bar" is not PascalCase.', - type: 'Literal', - line: 3 - }] + errors: [ + { + message: 'Property name "foo!bar" is not PascalCase.', + type: 'Literal', + line: 3 + } + ] }, { filename: 'test.vue', @@ -150,11 +157,13 @@ ruleTester.run('name-property-casing', rule, { } `, parserOptions, - errors: [{ - message: 'Property name "foo_bar" is not PascalCase.', - type: 'Literal', - line: 3 - }] + errors: [ + { + message: 'Property name "foo_bar" is not PascalCase.', + type: 'Literal', + line: 3 + } + ] }, { filename: 'test.vue', @@ -170,11 +179,13 @@ ruleTester.run('name-property-casing', rule, { `, options: ['PascalCase'], parserOptions, - errors: [{ - message: 'Property name "foo_bar" is not PascalCase.', - type: 'Literal', - line: 3 - }] + errors: [ + { + message: 'Property name "foo_bar" is not PascalCase.', + type: 'Literal', + line: 3 + } + ] }, { filename: 'test.vue', @@ -190,11 +201,13 @@ ruleTester.run('name-property-casing', rule, { `, options: ['kebab-case'], parserOptions, - errors: [{ - message: 'Property name "foo_bar" is not kebab-case.', - type: 'Literal', - line: 3 - }] + errors: [ + { + message: 'Property name "foo_bar" is not kebab-case.', + type: 'Literal', + line: 3 + } + ] } ] }) diff --git a/tests/lib/rules/no-arrow-functions-in-watch.js b/tests/lib/rules/no-arrow-functions-in-watch.js index 5d5b5cd87..b98179a3b 100644 --- a/tests/lib/rules/no-arrow-functions-in-watch.js +++ b/tests/lib/rules/no-arrow-functions-in-watch.js @@ -150,10 +150,12 @@ ruleTester.run('no-arrow-functions-in-watch', rule, { bar: () => {} } }`, - errors: [{ - message: 'You should not use an arrow function to define a watcher.', - line: 5 - }] + errors: [ + { + message: 'You should not use an arrow function to define a watcher.', + line: 5 + } + ] }, { filename: 'test.vue', @@ -164,10 +166,12 @@ ruleTester.run('no-arrow-functions-in-watch', rule, { bar: () => {} } }`, - errors: [{ - message: 'You should not use an arrow function to define a watcher.', - line: 5 - }] + errors: [ + { + message: 'You should not use an arrow function to define a watcher.', + line: 5 + } + ] }, { filename: 'test.vue', @@ -208,10 +212,12 @@ ruleTester.run('no-arrow-functions-in-watch', rule, { 'e.f': function (val, oldVal) { /* ... */ } } }`, - errors: [{ - message: 'You should not use an arrow function to define a watcher.', - line: 15 - }] + errors: [ + { + message: 'You should not use an arrow function to define a watcher.', + line: 15 + } + ] } ] }) diff --git a/tests/lib/rules/no-async-in-computed-properties.js b/tests/lib/rules/no-async-in-computed-properties.js index 171271188..b7f0283eb 100644 --- a/tests/lib/rules/no-async-in-computed-properties.js +++ b/tests/lib/rules/no-async-in-computed-properties.js @@ -23,7 +23,6 @@ const parserOptions = { const ruleTester = new RuleTester() ruleTester.run('no-async-in-computed-properties', rule, { - valid: [ { filename: 'test.vue', @@ -240,13 +239,17 @@ ruleTester.run('no-async-in-computed-properties', rule, { } `, parserOptions, - errors: [{ - message: 'Unexpected async function declaration in "foo" computed property.', - line: 4 - }, { - message: 'Unexpected await operator in "foo" computed property.', - line: 5 - }] + errors: [ + { + message: + 'Unexpected async function declaration in "foo" computed property.', + line: 4 + }, + { + message: 'Unexpected await operator in "foo" computed property.', + line: 5 + } + ] }, { filename: 'test.vue', @@ -260,13 +263,17 @@ ruleTester.run('no-async-in-computed-properties', rule, { } `, parserOptions, - errors: [{ - message: 'Unexpected async function declaration in "foo" computed property.', - line: 4 - }, { - message: 'Unexpected Promise object in "foo" computed property.', - line: 5 - }] + errors: [ + { + message: + 'Unexpected async function declaration in "foo" computed property.', + line: 4 + }, + { + message: 'Unexpected Promise object in "foo" computed property.', + line: 5 + } + ] }, { filename: 'test.vue', @@ -280,10 +287,12 @@ ruleTester.run('no-async-in-computed-properties', rule, { } `, parserOptions, - errors: [{ - message: 'Unexpected asynchronous action in "foo" computed property.', - line: 5 - }] + errors: [ + { + message: 'Unexpected asynchronous action in "foo" computed property.', + line: 5 + } + ] }, { filename: 'test.vue', @@ -297,10 +306,12 @@ ruleTester.run('no-async-in-computed-properties', rule, { } `, parserOptions, - errors: [{ - message: 'Unexpected asynchronous action in "foo" computed property.', - line: 5 - }] + errors: [ + { + message: 'Unexpected asynchronous action in "foo" computed property.', + line: 5 + } + ] }, { filename: 'test.vue', @@ -314,10 +325,12 @@ ruleTester.run('no-async-in-computed-properties', rule, { } `, parserOptions, - errors: [{ - message: 'Unexpected asynchronous action in "foo" computed property.', - line: 5 - }] + errors: [ + { + message: 'Unexpected asynchronous action in "foo" computed property.', + line: 5 + } + ] }, { filename: 'test.vue', @@ -331,10 +344,12 @@ ruleTester.run('no-async-in-computed-properties', rule, { } `, parserOptions, - errors: [{ - message: 'Unexpected asynchronous action in "foo" computed property.', - line: 5 - }] + errors: [ + { + message: 'Unexpected asynchronous action in "foo" computed property.', + line: 5 + } + ] }, { filename: 'test.vue', @@ -348,10 +363,12 @@ ruleTester.run('no-async-in-computed-properties', rule, { } `, parserOptions, - errors: [{ - message: 'Unexpected asynchronous action in "foo" computed property.', - line: 5 - }] + errors: [ + { + message: 'Unexpected asynchronous action in "foo" computed property.', + line: 5 + } + ] }, { filename: 'test.vue', @@ -365,10 +382,12 @@ ruleTester.run('no-async-in-computed-properties', rule, { } `, parserOptions, - errors: [{ - message: 'Unexpected asynchronous action in "foo" computed property.', - line: 5 - }] + errors: [ + { + message: 'Unexpected asynchronous action in "foo" computed property.', + line: 5 + } + ] }, { filename: 'test.vue', @@ -382,10 +401,12 @@ ruleTester.run('no-async-in-computed-properties', rule, { } `, parserOptions, - errors: [{ - message: 'Unexpected asynchronous action in "foo" computed property.', - line: 5 - }] + errors: [ + { + message: 'Unexpected asynchronous action in "foo" computed property.', + line: 5 + } + ] }, { filename: 'test.vue', @@ -399,10 +420,12 @@ ruleTester.run('no-async-in-computed-properties', rule, { } `, parserOptions, - errors: [{ - message: 'Unexpected asynchronous action in "foo" computed property.', - line: 5 - }] + errors: [ + { + message: 'Unexpected asynchronous action in "foo" computed property.', + line: 5 + } + ] }, { filename: 'test.vue', @@ -418,10 +441,12 @@ ruleTester.run('no-async-in-computed-properties', rule, { } `, parserOptions, - errors: [{ - message: 'Unexpected asynchronous action in "foo" computed property.', - line: 6 - }] + errors: [ + { + message: 'Unexpected asynchronous action in "foo" computed property.', + line: 6 + } + ] }, { filename: 'test.vue', @@ -437,10 +462,12 @@ ruleTester.run('no-async-in-computed-properties', rule, { }) `, parserOptions: { ecmaVersion: 6 }, - errors: [{ - message: 'Unexpected asynchronous action in "foo" computed property.', - line: 6 - }] + errors: [ + { + message: 'Unexpected asynchronous action in "foo" computed property.', + line: 6 + } + ] }, { filename: 'test.vue', @@ -456,10 +483,12 @@ ruleTester.run('no-async-in-computed-properties', rule, { }) `, parserOptions: { ecmaVersion: 6 }, - errors: [{ - message: 'Unexpected asynchronous action in "foo" computed property.', - line: 6 - }] + errors: [ + { + message: 'Unexpected asynchronous action in "foo" computed property.', + line: 6 + } + ] }, { filename: 'test.vue', @@ -480,31 +509,40 @@ ruleTester.run('no-async-in-computed-properties', rule, { } `, parserOptions, - errors: [{ - message: 'Unexpected timed function in "foo" computed property.', - line: 5 - }, { - message: 'Unexpected timed function in "foo" computed property.', - line: 6 - }, { - message: 'Unexpected timed function in "foo" computed property.', - line: 7 - }, { - message: 'Unexpected timed function in "foo" computed property.', - line: 8 - }, { - message: 'Unexpected timed function in "foo" computed property.', - line: 9 - }, { - message: 'Unexpected timed function in "foo" computed property.', - line: 10 - }, { - message: 'Unexpected timed function in "foo" computed property.', - line: 11 - }, { - message: 'Unexpected timed function in "foo" computed property.', - line: 12 - }] + errors: [ + { + message: 'Unexpected timed function in "foo" computed property.', + line: 5 + }, + { + message: 'Unexpected timed function in "foo" computed property.', + line: 6 + }, + { + message: 'Unexpected timed function in "foo" computed property.', + line: 7 + }, + { + message: 'Unexpected timed function in "foo" computed property.', + line: 8 + }, + { + message: 'Unexpected timed function in "foo" computed property.', + line: 9 + }, + { + message: 'Unexpected timed function in "foo" computed property.', + line: 10 + }, + { + message: 'Unexpected timed function in "foo" computed property.', + line: 11 + }, + { + message: 'Unexpected timed function in "foo" computed property.', + line: 12 + } + ] } ] }) diff --git a/tests/lib/rules/no-boolean-default.js b/tests/lib/rules/no-boolean-default.js index c113514b9..7421a049d 100644 --- a/tests/lib/rules/no-boolean-default.js +++ b/tests/lib/rules/no-boolean-default.js @@ -8,22 +8,21 @@ // Requirements // ------------------------------------------------------------------------------ -var rule = require('../../../lib/rules/no-boolean-default') +const rule = require('../../../lib/rules/no-boolean-default') -var RuleTester = require('eslint').RuleTester +const RuleTester = require('eslint').RuleTester // ------------------------------------------------------------------------------ // Tests // ------------------------------------------------------------------------------ -var ruleTester = new RuleTester({ +const ruleTester = new RuleTester({ parserOptions: { ecmaVersion: 2018, sourceType: 'module' } }) ruleTester.run('no-boolean-default', rule, { - valid: [ { filename: 'test.vue', @@ -247,10 +246,12 @@ ruleTester.run('no-boolean-default', rule, { } `, options: ['default-false'], - errors: [{ - message: 'Boolean prop should only be defaulted to false.', - line: 6 - }] + errors: [ + { + message: 'Boolean prop should only be defaulted to false.', + line: 6 + } + ] }, { filename: 'test.vue', @@ -265,10 +266,12 @@ ruleTester.run('no-boolean-default', rule, { } `, options: ['default-false'], - errors: [{ - message: 'Boolean prop should only be defaulted to false.', - line: 6 - }] + errors: [ + { + message: 'Boolean prop should only be defaulted to false.', + line: 6 + } + ] }, { filename: 'test.vue', @@ -283,10 +286,13 @@ ruleTester.run('no-boolean-default', rule, { } `, options: ['no-default'], - errors: [{ - message: 'Boolean prop should not set a default (Vue defaults it to false).', - line: 6 - }] + errors: [ + { + message: + 'Boolean prop should not set a default (Vue defaults it to false).', + line: 6 + } + ] }, { filename: 'test.vue', @@ -301,10 +307,13 @@ ruleTester.run('no-boolean-default', rule, { } `, options: ['no-default'], - errors: [{ - message: 'Boolean prop should not set a default (Vue defaults it to false).', - line: 6 - }] + errors: [ + { + message: + 'Boolean prop should not set a default (Vue defaults it to false).', + line: 6 + } + ] } ] }) diff --git a/tests/lib/rules/no-confusing-v-for-v-if.js b/tests/lib/rules/no-confusing-v-for-v-if.js index 47959aeb4..c94d1b3ea 100644 --- a/tests/lib/rules/no-confusing-v-for-v-if.js +++ b/tests/lib/rules/no-confusing-v-for-v-if.js @@ -29,30 +29,36 @@ tester.run('no-confusing-v-for-v-if', rule, { }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' } ], invalid: [ { filename: 'test.vue', - code: '', + code: + '', errors: ["This 'v-if' should be moved to the wrapper element."] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["This 'v-if' should be moved to the wrapper element."] } ] diff --git a/tests/lib/rules/no-custom-modifiers-on-v-model.js b/tests/lib/rules/no-custom-modifiers-on-v-model.js index ad80cdb77..03b0459a4 100644 --- a/tests/lib/rules/no-custom-modifiers-on-v-model.js +++ b/tests/lib/rules/no-custom-modifiers-on-v-model.js @@ -21,7 +21,6 @@ const ruleTester = new RuleTester({ }) ruleTester.run('no-custom-modifiers-on-v-model', rule, { - valid: [ { filename: 'test.vue', diff --git a/tests/lib/rules/no-deprecated-data-object-declaration.js b/tests/lib/rules/no-deprecated-data-object-declaration.js index 1ced275c0..22aa31160 100644 --- a/tests/lib/rules/no-deprecated-data-object-declaration.js +++ b/tests/lib/rules/no-deprecated-data-object-declaration.js @@ -23,7 +23,6 @@ const parserOptions = { const ruleTester = new RuleTester() ruleTester.run('no-deprecated-data-object-declaration', rule, { - valid: [ { filename: 'test.js', @@ -160,10 +159,13 @@ return { }) `, parserOptions, - errors: [{ - message: "Object declaration on \'data\' property is deprecated. Using function declaration instead.", - line: 4 - }] + errors: [ + { + message: + "Object declaration on 'data' property is deprecated. Using function declaration instead.", + line: 4 + } + ] }, { filename: 'test.js', @@ -184,10 +186,13 @@ return { }) `, parserOptions, - errors: [{ - message: "Object declaration on \'data\' property is deprecated. Using function declaration instead.", - line: 3 - }] + errors: [ + { + message: + "Object declaration on 'data' property is deprecated. Using function declaration instead.", + line: 3 + } + ] }, { filename: 'test.vue', @@ -208,10 +213,13 @@ return { } `, parserOptions, - errors: [{ - message: "Object declaration on \'data\' property is deprecated. Using function declaration instead.", - line: 3 - }] + errors: [ + { + message: + "Object declaration on 'data' property is deprecated. Using function declaration instead.", + line: 3 + } + ] }, { filename: 'test.vue', @@ -232,10 +240,13 @@ return (/*b*/{ } `, parserOptions, - errors: [{ - message: "Object declaration on \'data\' property is deprecated. Using function declaration instead.", - line: 3 - }] + errors: [ + { + message: + "Object declaration on 'data' property is deprecated. Using function declaration instead.", + line: 3 + } + ] }, { filename: 'test.js', @@ -256,10 +267,13 @@ return { }) `, parserOptions, - errors: [{ - message: "Object declaration on \'data\' property is deprecated. Using function declaration instead.", - line: 3 - }] + errors: [ + { + message: + "Object declaration on 'data' property is deprecated. Using function declaration instead.", + line: 3 + } + ] }, { filename: 'test.js', @@ -280,10 +294,13 @@ return { }).mount('#app') `, parserOptions, - errors: [{ - message: "Object declaration on \'data\' property is deprecated. Using function declaration instead.", - line: 3 - }] + errors: [ + { + message: + "Object declaration on 'data' property is deprecated. Using function declaration instead.", + line: 3 + } + ] } ] }) diff --git a/tests/lib/rules/no-deprecated-dollar-listeners-api.js b/tests/lib/rules/no-deprecated-dollar-listeners-api.js index 98a0d6270..deaff0758 100644 --- a/tests/lib/rules/no-deprecated-dollar-listeners-api.js +++ b/tests/lib/rules/no-deprecated-dollar-listeners-api.js @@ -21,7 +21,6 @@ const ruleTester = new RuleTester({ parserOptions: { ecmaVersion: 2018, sourceType: 'module' } }) ruleTester.run('no-deprecated-dollar-listeners-api', rule, { - valid: [ { filename: 'test.vue', diff --git a/tests/lib/rules/no-deprecated-events-api.js b/tests/lib/rules/no-deprecated-events-api.js index 268c0a712..b52651aff 100644 --- a/tests/lib/rules/no-deprecated-events-api.js +++ b/tests/lib/rules/no-deprecated-events-api.js @@ -23,7 +23,6 @@ const parserOptions = { const ruleTester = new RuleTester() ruleTester.run('no-deprecated-events-api', rule, { - valid: [ { filename: 'test.js', @@ -130,10 +129,13 @@ ruleTester.run('no-deprecated-events-api', rule, { }) `, parserOptions, - errors: [{ - message: 'The Events api `$on`, `$off` `$once` is deprecated. Using external library instead, for example mitt.', - line: 4 - }] + errors: [ + { + message: + 'The Events api `$on`, `$off` `$once` is deprecated. Using external library instead, for example mitt.', + line: 4 + } + ] }, { filename: 'test.js', @@ -145,10 +147,13 @@ ruleTester.run('no-deprecated-events-api', rule, { }) `, parserOptions, - errors: [{ - message: 'The Events api `$on`, `$off` `$once` is deprecated. Using external library instead, for example mitt.', - line: 4 - }] + errors: [ + { + message: + 'The Events api `$on`, `$off` `$once` is deprecated. Using external library instead, for example mitt.', + line: 4 + } + ] }, { filename: 'test.vue', @@ -162,10 +167,13 @@ ruleTester.run('no-deprecated-events-api', rule, { } `, parserOptions, - errors: [{ - message: 'The Events api `$on`, `$off` `$once` is deprecated. Using external library instead, for example mitt.', - line: 4 - }] + errors: [ + { + message: + 'The Events api `$on`, `$off` `$once` is deprecated. Using external library instead, for example mitt.', + line: 4 + } + ] }, { filename: 'test.js', @@ -180,10 +188,13 @@ ruleTester.run('no-deprecated-events-api', rule, { }) `, parserOptions, - errors: [{ - message: 'The Events api `$on`, `$off` `$once` is deprecated. Using external library instead, for example mitt.', - line: 5 - }] + errors: [ + { + message: + 'The Events api `$on`, `$off` `$once` is deprecated. Using external library instead, for example mitt.', + line: 5 + } + ] } ] }) diff --git a/tests/lib/rules/no-deprecated-filter.js b/tests/lib/rules/no-deprecated-filter.js index 20957e465..7d9512819 100644 --- a/tests/lib/rules/no-deprecated-filter.js +++ b/tests/lib/rules/no-deprecated-filter.js @@ -50,7 +50,8 @@ ruleTester.run('no-deprecated-filter', rule, { }, { filename: 'test.vue', - code: '', + code: + '', errors: ['Filters are deprecated.'] }, { @@ -65,7 +66,8 @@ ruleTester.run('no-deprecated-filter', rule, { }, { filename: 'test.vue', - code: '', + code: + '', errors: ['Filters are deprecated.'] } ] diff --git a/tests/lib/rules/no-deprecated-inline-template.js b/tests/lib/rules/no-deprecated-inline-template.js index e64511acd..3ee8e999c 100644 --- a/tests/lib/rules/no-deprecated-inline-template.js +++ b/tests/lib/rules/no-deprecated-inline-template.js @@ -32,18 +32,21 @@ ruleTester.run('no-deprecated-inline-template', rule, { }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' } ], invalid: [ { filename: 'test.vue', - code: '', + code: + '', errors: [ { line: 1, @@ -56,12 +59,14 @@ ruleTester.run('no-deprecated-inline-template', rule, { }, { filename: 'test.vue', - code: '', + code: + '', errors: [{ messageId: 'unexpected' }] }, { filename: 'test.vue', - code: '', + code: + '', errors: [{ messageId: 'unexpected' }] } ] diff --git a/tests/lib/rules/no-deprecated-v-bind-sync.js b/tests/lib/rules/no-deprecated-v-bind-sync.js index 6cf900265..469d2f577 100644 --- a/tests/lib/rules/no-deprecated-v-bind-sync.js +++ b/tests/lib/rules/no-deprecated-v-bind-sync.js @@ -21,7 +21,6 @@ const ruleTester = new RuleTester({ }) ruleTester.run('no-deprecated-v-bind-sync', rule, { - valid: [ { filename: 'test.vue', @@ -46,109 +45,170 @@ ruleTester.run('no-deprecated-v-bind-sync', rule, { filename: 'test.vue', code: "", output: "", - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', code: "", output: "", - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', - code: "", + code: + "", output: "", - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', code: "", output: "", - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', code: "", output: "", - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', code: '', output: '', - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', - code: '', - output: '', - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + code: + '', + output: + '', + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', - code: '', - output: '', - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + code: + '', + output: + '', + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', - code: '', - output: '', - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + code: + '', + output: + '', + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', - code: '', - output: '', - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + code: + '', + output: + '', + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', - code: '', - output: '', - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + code: + '', + output: + '', + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', - code: '', - output: '', - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + code: + '', + output: + '', + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', - code: '', - output: '', - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + code: + '', + output: + '', + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', - code: '', - output: '', - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + code: + '', + output: + '', + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', - code: '', - output: '', - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + code: + '', + output: + '', + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', - code: '', - output: '', - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + code: + '', + output: + '', + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', - code: '', - output: '', - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + code: + '', + output: + '', + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] }, { filename: 'test.vue', - code: '', - output: '', - errors: ["'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead."] + code: + '', + output: + '', + errors: [ + "'.sync' modifier on 'v-bind' directive is deprecated. Use 'v-model:propName' instead." + ] } ] }) diff --git a/tests/lib/rules/no-deprecated-v-on-native-modifier.js b/tests/lib/rules/no-deprecated-v-on-native-modifier.js index 772a56918..d201cd478 100644 --- a/tests/lib/rules/no-deprecated-v-on-native-modifier.js +++ b/tests/lib/rules/no-deprecated-v-on-native-modifier.js @@ -21,7 +21,6 @@ const ruleTester = new RuleTester({ }) ruleTester.run('no-deprecated-v-on-native-modifier', rule, { - valid: [ { filename: 'test.vue', diff --git a/tests/lib/rules/no-deprecated-v-on-number-modifiers.js b/tests/lib/rules/no-deprecated-v-on-number-modifiers.js index 36d4bf003..9edf2a272 100644 --- a/tests/lib/rules/no-deprecated-v-on-number-modifiers.js +++ b/tests/lib/rules/no-deprecated-v-on-number-modifiers.js @@ -21,7 +21,6 @@ const ruleTester = new RuleTester({ }) ruleTester.run('no-deprecated-v-on-number-modifiers', rule, { - valid: [ { filename: 'test.vue', @@ -57,7 +56,8 @@ ruleTester.run('no-deprecated-v-on-number-modifiers', rule, { }, { filename: 'test.vue', - code: "" + code: + "" }, { filename: 'test.vue', @@ -78,97 +78,141 @@ ruleTester.run('no-deprecated-v-on-number-modifiers', rule, { filename: 'test.vue', code: "", output: "", - errors: ["'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead."] + errors: [ + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + ] }, { filename: 'test.vue', code: "", - output: "", - errors: ["'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead."] + output: + "", + errors: [ + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + ] }, { filename: 'test.vue', code: "", - output: "", - errors: ["'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead."] + output: + "", + errors: [ + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + ] }, { filename: 'test.vue', code: "", - output: "", - errors: ["'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead."] + output: + "", + errors: [ + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + ] }, { filename: 'test.vue', - code: "", - output: "", - errors: ["'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead."] + code: + "", + output: + "", + errors: [ + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + ] }, { filename: 'test.vue', - code: "", - output: "", - errors: ["'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead."] + code: + "", + output: + "", + errors: [ + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + ] }, { filename: 'test.vue', code: "", output: "", - errors: ["'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead."] + errors: [ + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + ] }, { filename: 'test.vue', code: "", - output: "", - errors: ["'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead."] + output: + "", + errors: [ + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + ] }, { filename: 'test.vue', code: "", - output: "", - errors: ["'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead."] + output: + "", + errors: [ + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + ] }, { filename: 'test.vue', code: "", - output: "", - errors: ["'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead."] + output: + "", + errors: [ + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + ] }, { filename: 'test.vue', code: "", - output: "", - errors: ["'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead."] + output: + "", + errors: [ + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + ] }, { filename: 'test.vue', code: "", - output: "", - errors: ["'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead."] + output: + "", + errors: [ + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + ] }, { filename: 'test.vue', code: "", output: null, - errors: ["'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead."] + errors: [ + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + ] }, { filename: 'test.vue', code: "", output: null, - errors: ["'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead."] + errors: [ + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + ] }, { filename: 'test.vue', code: "", output: null, - errors: ["'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead."] + errors: [ + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + ] }, { filename: 'test.vue', code: "", output: null, - errors: ["'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead."] + errors: [ + "'KeyboardEvent.keyCode' modifier on 'v-on' directive is deprecated. Using 'KeyboardEvent.key' instead." + ] }, { filename: 'test.vue', diff --git a/tests/lib/rules/no-deprecated-vue-config-keycodes.js b/tests/lib/rules/no-deprecated-vue-config-keycodes.js index 02fc42c4f..eebd7943c 100644 --- a/tests/lib/rules/no-deprecated-vue-config-keycodes.js +++ b/tests/lib/rules/no-deprecated-vue-config-keycodes.js @@ -21,7 +21,6 @@ const ruleTester = new RuleTester({ }) ruleTester.run('no-deprecated-vue-config-keycodes', rule, { - valid: [ { filename: 'test.js', @@ -41,15 +40,17 @@ ruleTester.run('no-deprecated-vue-config-keycodes', rule, { { filename: 'test.js', code: 'Vue.config.keyCodes = {}', - errors: [{ - message: '`Vue.config.keyCodes` are deprecated.', - line: 1, - column: 1, - type: 'MemberExpression', - // messageId: 'unexpected', - endLine: 1, - endColumn: 20 - }] + errors: [ + { + message: '`Vue.config.keyCodes` are deprecated.', + line: 1, + column: 1, + type: 'MemberExpression', + // messageId: 'unexpected', + endLine: 1, + endColumn: 20 + } + ] } ] }) diff --git a/tests/lib/rules/no-dupe-keys.js b/tests/lib/rules/no-dupe-keys.js index a3bc06e77..94c1eaf98 100644 --- a/tests/lib/rules/no-dupe-keys.js +++ b/tests/lib/rules/no-dupe-keys.js @@ -365,19 +365,24 @@ ruleTester.run('no-dupe-keys', rule, { } `, parserOptions: { ecmaVersion: 6, sourceType: 'module' }, - errors: [{ - message: 'Duplicated key \'foo\'.', - line: 5 - }, { - message: 'Duplicated key \'foo\'.', - line: 10 - }, { - message: 'Duplicated key \'foo\'.', - line: 14 - }, { - message: 'Duplicated key \'foo\'.', - line: 21 - }] + errors: [ + { + message: "Duplicated key 'foo'.", + line: 5 + }, + { + message: "Duplicated key 'foo'.", + line: 10 + }, + { + message: "Duplicated key 'foo'.", + line: 14 + }, + { + message: "Duplicated key 'foo'.", + line: 21 + } + ] }, { filename: 'test.vue', @@ -407,19 +412,24 @@ ruleTester.run('no-dupe-keys', rule, { } `, parserOptions: { ecmaVersion: 6, sourceType: 'module' }, - errors: [{ - message: 'Duplicated key \'foo\'.', - line: 5 - }, { - message: 'Duplicated key \'foo\'.', - line: 10 - }, { - message: 'Duplicated key \'foo\'.', - line: 14 - }, { - message: 'Duplicated key \'foo\'.', - line: 21 - }] + errors: [ + { + message: "Duplicated key 'foo'.", + line: 5 + }, + { + message: "Duplicated key 'foo'.", + line: 10 + }, + { + message: "Duplicated key 'foo'.", + line: 14 + }, + { + message: "Duplicated key 'foo'.", + line: 21 + } + ] }, { filename: 'test.vue', @@ -440,16 +450,20 @@ ruleTester.run('no-dupe-keys', rule, { } `, parserOptions: { ecmaVersion: 6, sourceType: 'module' }, - errors: [{ - message: 'Duplicated key \'foo\'.', - line: 5 - }, { - message: 'Duplicated key \'foo\'.', - line: 9 - }, { - message: 'Duplicated key \'foo\'.', - line: 12 - }] + errors: [ + { + message: "Duplicated key 'foo'.", + line: 5 + }, + { + message: "Duplicated key 'foo'.", + line: 9 + }, + { + message: "Duplicated key 'foo'.", + line: 12 + } + ] }, { filename: 'test.vue', @@ -481,19 +495,24 @@ ruleTester.run('no-dupe-keys', rule, { } `, parserOptions: { ecmaVersion: 6, sourceType: 'module' }, - errors: [{ - message: 'Duplicated key \'foo\'.', - line: 7 - }, { - message: 'Duplicated key \'foo\'.', - line: 13 - }, { - message: 'Duplicated key \'foo\'.', - line: 16 - }, { - message: 'Duplicated key \'foo\'.', - line: 23 - }] + errors: [ + { + message: "Duplicated key 'foo'.", + line: 7 + }, + { + message: "Duplicated key 'foo'.", + line: 13 + }, + { + message: "Duplicated key 'foo'.", + line: 16 + }, + { + message: "Duplicated key 'foo'.", + line: 23 + } + ] }, { filename: 'test.js', @@ -509,10 +528,12 @@ ruleTester.run('no-dupe-keys', rule, { `, options: [{ groups: ['foo'] }], parserOptions: { ecmaVersion: 6 }, - errors: [{ - message: 'Duplicated key \'bar\'.', - line: 7 - }] + errors: [ + { + message: "Duplicated key 'bar'.", + line: 7 + } + ] }, { filename: 'test.vue', @@ -533,10 +554,12 @@ ruleTester.run('no-dupe-keys', rule, { } `, parserOptions: { ecmaVersion: 6, sourceType: 'module' }, - errors: [{ - message: 'Duplicated key \'foo\'.', - line: 12 - }] + errors: [ + { + message: "Duplicated key 'foo'.", + line: 12 + } + ] }, { filename: 'test.vue', @@ -555,10 +578,12 @@ ruleTester.run('no-dupe-keys', rule, { } `, parserOptions: { ecmaVersion: 6, sourceType: 'module' }, - errors: [{ - message: 'Duplicated key \'foo\'.', - line: 10 - }] + errors: [ + { + message: "Duplicated key 'foo'.", + line: 10 + } + ] }, { filename: 'test.vue', @@ -575,10 +600,12 @@ ruleTester.run('no-dupe-keys', rule, { } `, parserOptions: { ecmaVersion: 6, sourceType: 'module' }, - errors: [{ - message: 'Duplicated key \'foo\'.', - line: 9 - }] + errors: [ + { + message: "Duplicated key 'foo'.", + line: 9 + } + ] }, { filename: 'test.vue', @@ -595,10 +622,12 @@ ruleTester.run('no-dupe-keys', rule, { } `, parserOptions: { ecmaVersion: 6, sourceType: 'module' }, - errors: [{ - message: 'Duplicated key \'foo\'.', - line: 9 - }] + errors: [ + { + message: "Duplicated key 'foo'.", + line: 9 + } + ] }, { filename: 'test.vue', @@ -615,10 +644,12 @@ ruleTester.run('no-dupe-keys', rule, { } `, parserOptions: { ecmaVersion: 6, sourceType: 'module' }, - errors: [{ - message: 'Duplicated key \'foo\'.', - line: 9 - }] + errors: [ + { + message: "Duplicated key 'foo'.", + line: 9 + } + ] }, { filename: 'test.vue', @@ -635,10 +666,12 @@ ruleTester.run('no-dupe-keys', rule, { } `, parserOptions: { ecmaVersion: 6, sourceType: 'module' }, - errors: [{ - message: 'Duplicated key \'foo\'.', - line: 9 - }] + errors: [ + { + message: "Duplicated key 'foo'.", + line: 9 + } + ] }, { filename: 'test.js', @@ -654,10 +687,12 @@ ruleTester.run('no-dupe-keys', rule, { `, options: [{ groups: ['foo'] }], parserOptions: { ecmaVersion: 6 }, - errors: [{ - message: 'Duplicated key \'bar\'.', - line: 7 - }] + errors: [ + { + message: "Duplicated key 'bar'.", + line: 7 + } + ] }, { filename: 'test.js', @@ -673,10 +708,12 @@ ruleTester.run('no-dupe-keys', rule, { `, options: [{ groups: ['foo'] }], parserOptions: { ecmaVersion: 6, sourceType: 'module' }, - errors: [{ - message: 'Duplicated key \'bar\'.', - line: 7 - }] + errors: [ + { + message: "Duplicated key 'bar'.", + line: 7 + } + ] } ] }) diff --git a/tests/lib/rules/no-duplicate-attr-inheritance.js b/tests/lib/rules/no-duplicate-attr-inheritance.js index 1c862ef8a..8c4917071 100644 --- a/tests/lib/rules/no-duplicate-attr-inheritance.js +++ b/tests/lib/rules/no-duplicate-attr-inheritance.js @@ -8,15 +8,15 @@ // Requirements // ------------------------------------------------------------------------------ -var rule = require('../../../lib/rules/no-duplicate-attr-inheritance') +const rule = require('../../../lib/rules/no-duplicate-attr-inheritance') -var RuleTester = require('eslint').RuleTester +const RuleTester = require('eslint').RuleTester // ------------------------------------------------------------------------------ // Tests // ------------------------------------------------------------------------------ -var ruleTester = new RuleTester({ +const ruleTester = new RuleTester({ parser: require.resolve('vue-eslint-parser'), parserOptions: { ecmaVersion: 2018, @@ -24,7 +24,6 @@ var ruleTester = new RuleTester({ } }) ruleTester.run('no-duplicate-attr-inheritance', rule, { - valid: [ { filename: 'test.vue', diff --git a/tests/lib/rules/no-duplicate-attributes.js b/tests/lib/rules/no-duplicate-attributes.js index baa79dc98..661cf1f33 100644 --- a/tests/lib/rules/no-duplicate-attributes.js +++ b/tests/lib/rules/no-duplicate-attributes.js @@ -33,7 +33,8 @@ tester.run('no-duplicate-attributes', rule, { }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', diff --git a/tests/lib/rules/no-empty-pattern.js b/tests/lib/rules/no-empty-pattern.js index f3b6f860e..b3747965e 100644 --- a/tests/lib/rules/no-empty-pattern.js +++ b/tests/lib/rules/no-empty-pattern.js @@ -247,6 +247,5 @@ tester.run('no-empty-pattern', rule, { } ] } - ] }) diff --git a/tests/lib/rules/no-extra-parens.js b/tests/lib/rules/no-extra-parens.js index b4851272a..9b7ce315f 100644 --- a/tests/lib/rules/no-extra-parens.js +++ b/tests/lib/rules/no-extra-parens.js @@ -157,13 +157,17 @@ tester.run('no-extra-parens', rule, { errors: [{ messageId: 'unexpected' }] }, { - code: '', - output: '', + code: + '', + output: + '', errors: [{ messageId: 'unexpected' }] }, { - code: '', - output: '', + code: + '', + output: + '', errors: [{ messageId: 'unexpected' }] }, { diff --git a/tests/lib/rules/no-irregular-whitespace.js b/tests/lib/rules/no-irregular-whitespace.js index 3814c3f23..85a0ad4aa 100644 --- a/tests/lib/rules/no-irregular-whitespace.js +++ b/tests/lib/rules/no-irregular-whitespace.js @@ -11,39 +11,77 @@ const tester = new RuleTester({ parserOptions: { ecmaVersion: 2018 } }) -const IRREGULAR_WHITESPACES = '\f\v\u0085\ufeff\u00a0\u1680\u180e\u2000\u2001\u2002\u2003\u2004\u2005\u2006\u2007\u2008\u2009\u200a\u200b\u202f\u205f\u3000'.split('') +const IRREGULAR_WHITESPACES = '\f\v\u0085\ufeff\u00a0\u1680\u180e\u2000\u2001\u2002\u2003\u2004\u2005\u2006\u2007\u2008\u2009\u200a\u200b\u202f\u205f\u3000'.split( + '' +) const IRREGULAR_LINE_TERMINATORS = '\u2028\u2029'.split('') -const ALL_IRREGULAR_WHITESPACES = [].concat(IRREGULAR_WHITESPACES, IRREGULAR_LINE_TERMINATORS) -const ALL_IRREGULAR_WHITESPACE_CODES = ALL_IRREGULAR_WHITESPACES.map(s => ('000' + s.charCodeAt(0).toString(16)).slice(-4)) +const ALL_IRREGULAR_WHITESPACES = [].concat( + IRREGULAR_WHITESPACES, + IRREGULAR_LINE_TERMINATORS +) +const ALL_IRREGULAR_WHITESPACE_CODES = ALL_IRREGULAR_WHITESPACES.map((s) => + `000${s.charCodeAt(0).toString(16)}`.slice(-4) +) tester.run('no-irregular-whitespace', rule, { valid: [ 'var a = \t\r\n b', '', // escapes - ...ALL_IRREGULAR_WHITESPACE_CODES.map(s => `/\\u${s}/+'\\u${s}'`), + ...ALL_IRREGULAR_WHITESPACE_CODES.map((s) => `/\\u${s}/+'\\u${s}'`), // html escapes - ...ALL_IRREGULAR_WHITESPACE_CODES - .map(s => ``), + ...ALL_IRREGULAR_WHITESPACE_CODES.map( + (s) => `` + ), // strings - ...IRREGULAR_WHITESPACES.map(s => `'${s}'`), - ...IRREGULAR_LINE_TERMINATORS.map(s => `'\\${s}'`), // multiline string - ...IRREGULAR_WHITESPACES.map(s => ``), + ...IRREGULAR_WHITESPACES.map((s) => `'${s}'`), + ...IRREGULAR_LINE_TERMINATORS.map((s) => `'\\${s}'`), // multiline string + ...IRREGULAR_WHITESPACES.map((s) => ``), // comments - ...IRREGULAR_WHITESPACES.map(s => ({ code: `//${s}`, options: [{ skipComments: true }] })), - ...ALL_IRREGULAR_WHITESPACES.map(s => ({ code: `/*${s}*/`, options: [{ skipComments: true }] })), - ...IRREGULAR_WHITESPACES.map(s => ({ code: ``, options: [{ skipComments: true }] })), - ...ALL_IRREGULAR_WHITESPACES.map(s => ({ code: ``, options: [{ skipComments: true }] })), + ...IRREGULAR_WHITESPACES.map((s) => ({ + code: `//${s}`, + options: [{ skipComments: true }] + })), + ...ALL_IRREGULAR_WHITESPACES.map((s) => ({ + code: `/*${s}*/`, + options: [{ skipComments: true }] + })), + ...IRREGULAR_WHITESPACES.map((s) => ({ + code: ``, + options: [{ skipComments: true }] + })), + ...ALL_IRREGULAR_WHITESPACES.map((s) => ({ + code: ``, + options: [{ skipComments: true }] + })), // regexps - ...IRREGULAR_WHITESPACES.map(s => ({ code: `/${s}/`, options: [{ skipRegExps: true }] })), - ...IRREGULAR_WHITESPACES.map(s => ({ code: ``, options: [{ skipRegExps: true }] })), + ...IRREGULAR_WHITESPACES.map((s) => ({ + code: `/${s}/`, + options: [{ skipRegExps: true }] + })), + ...IRREGULAR_WHITESPACES.map((s) => ({ + code: ``, + options: [{ skipRegExps: true }] + })), // templates - ...ALL_IRREGULAR_WHITESPACES.map(s => ({ code: `\`${s}\``, options: [{ skipTemplates: true }] })), - ...ALL_IRREGULAR_WHITESPACES.map(s => ({ code: ``, options: [{ skipTemplates: true }] })), + ...ALL_IRREGULAR_WHITESPACES.map((s) => ({ + code: `\`${s}\``, + options: [{ skipTemplates: true }] + })), + ...ALL_IRREGULAR_WHITESPACES.map((s) => ({ + code: ``, + options: [{ skipTemplates: true }] + })), // attribute values - ...ALL_IRREGULAR_WHITESPACES.map(s => ({ code: ``, options: [{ skipHTMLAttributeValues: true }] })), + ...ALL_IRREGULAR_WHITESPACES.map((s) => ({ + code: ``, + options: [{ skipHTMLAttributeValues: true }] + })), // text contents - ...ALL_IRREGULAR_WHITESPACES.map(s => ({ code: ``, options: [{ skipHTMLTextContents: true }] })), + ...ALL_IRREGULAR_WHITESPACES.map((s) => ({ + code: ``, + options: [{ skipHTMLTextContents: true }] + })), // outside `\u3000\u3000\u3000\u3000\u3000\u3000` ], @@ -129,117 +167,143 @@ tester.run('no-irregular-whitespace', rule, { ] }, // strings - ...IRREGULAR_WHITESPACES.map(s => ({ + ...IRREGULAR_WHITESPACES.map((s) => ({ code: `'${s}'`, options: [{ skipStrings: false }], - errors: [{ - message: 'Irregular whitespace not allowed.', - line: 1, - column: 2 - }] + errors: [ + { + message: 'Irregular whitespace not allowed.', + line: 1, + column: 2 + } + ] })), - ...IRREGULAR_LINE_TERMINATORS.map(s => ({ + ...IRREGULAR_LINE_TERMINATORS.map((s) => ({ code: `'\\${s}'`, options: [{ skipStrings: false }], - errors: [{ - message: 'Irregular whitespace not allowed.', - line: 1, - column: 3 - }] + errors: [ + { + message: 'Irregular whitespace not allowed.', + line: 1, + column: 3 + } + ] })), - ...IRREGULAR_WHITESPACES.map(s => ({ + ...IRREGULAR_WHITESPACES.map((s) => ({ code: ``, options: [{ skipStrings: false }], - errors: [{ - message: 'Irregular whitespace not allowed.', - line: 1, - column: 15 - }] + errors: [ + { + message: 'Irregular whitespace not allowed.', + line: 1, + column: 15 + } + ] })), // comments - ...IRREGULAR_WHITESPACES.map(s => ({ + ...IRREGULAR_WHITESPACES.map((s) => ({ code: `//${s}`, - errors: [{ - message: 'Irregular whitespace not allowed.', - line: 1, - column: 3 - }] + errors: [ + { + message: 'Irregular whitespace not allowed.', + line: 1, + column: 3 + } + ] })), - ...ALL_IRREGULAR_WHITESPACES.map(s => ({ + ...ALL_IRREGULAR_WHITESPACES.map((s) => ({ code: `/*${s}*/`, - errors: [{ - message: 'Irregular whitespace not allowed.', - line: 1, - column: 3 - }] + errors: [ + { + message: 'Irregular whitespace not allowed.', + line: 1, + column: 3 + } + ] })), - ...IRREGULAR_WHITESPACES.map(s => ({ + ...IRREGULAR_WHITESPACES.map((s) => ({ code: ``, - errors: [{ - message: 'Irregular whitespace not allowed.', - line: 1, - column: 22 - }] + errors: [ + { + message: 'Irregular whitespace not allowed.', + line: 1, + column: 22 + } + ] })), - ...ALL_IRREGULAR_WHITESPACES.map(s => ({ + ...ALL_IRREGULAR_WHITESPACES.map((s) => ({ code: ``, - errors: [{ - message: 'Irregular whitespace not allowed.', - line: 1, - column: 22 - }] + errors: [ + { + message: 'Irregular whitespace not allowed.', + line: 1, + column: 22 + } + ] })), // regexps - ...IRREGULAR_WHITESPACES.map(s => ({ + ...IRREGULAR_WHITESPACES.map((s) => ({ code: `/${s}/`, - errors: [{ - message: 'Irregular whitespace not allowed.', - line: 1, - column: 2 - }] + errors: [ + { + message: 'Irregular whitespace not allowed.', + line: 1, + column: 2 + } + ] })), - ...IRREGULAR_WHITESPACES.map(s => ({ + ...IRREGULAR_WHITESPACES.map((s) => ({ code: ``, - errors: [{ - message: 'Irregular whitespace not allowed.', - line: 1, - column: 20 - }] + errors: [ + { + message: 'Irregular whitespace not allowed.', + line: 1, + column: 20 + } + ] })), // templates - ...ALL_IRREGULAR_WHITESPACES.map(s => ({ + ...ALL_IRREGULAR_WHITESPACES.map((s) => ({ code: `\`${s}\``, - errors: [{ - message: 'Irregular whitespace not allowed.', - line: 1, - column: 2 - }] + errors: [ + { + message: 'Irregular whitespace not allowed.', + line: 1, + column: 2 + } + ] })), - ...ALL_IRREGULAR_WHITESPACES.map(s => ({ + ...ALL_IRREGULAR_WHITESPACES.map((s) => ({ code: ``, - errors: [{ - message: 'Irregular whitespace not allowed.', - line: 1, - column: 20 - }] + errors: [ + { + message: 'Irregular whitespace not allowed.', + line: 1, + column: 20 + } + ] })), // attribute values - ...ALL_IRREGULAR_WHITESPACES.map(s => ({ + ...ALL_IRREGULAR_WHITESPACES.map((s) => ({ code: ``, - errors: [{ - message: 'Irregular whitespace not allowed.', - line: 1, - column: 22 - }] + errors: [ + { + message: 'Irregular whitespace not allowed.', + line: 1, + column: 22 + } + ] })), // text contents - ...ALL_IRREGULAR_WHITESPACES.map(s => ({ + ...ALL_IRREGULAR_WHITESPACES.map((s) => ({ code: ``, - errors: [{ - message: 'Irregular whitespace not allowed.', - line: 1, - column: 16 - }] + errors: [ + { + message: 'Irregular whitespace not allowed.', + line: 1, + column: 16 + } + ] })), // options { @@ -260,12 +324,23 @@ tester.run('no-irregular-whitespace', rule, { var e = \`\f\` var f = \`\\f\` `, - options: [{ skipComments: true, skipStrings: true, skipTemplates: true, skipRegExps: true, skipHTMLAttributeValues: true, skipHTMLTextContents: true }], - errors: [{ - message: 'Irregular whitespace not allowed.', - line: 6, - column: 17 - }] + options: [ + { + skipComments: true, + skipStrings: true, + skipTemplates: true, + skipRegExps: true, + skipHTMLAttributeValues: true, + skipHTMLTextContents: true + } + ], + errors: [ + { + message: 'Irregular whitespace not allowed.', + line: 6, + column: 17 + } + ] } ] }) diff --git a/tests/lib/rules/no-lifecycle-after-await.js b/tests/lib/rules/no-lifecycle-after-await.js index 404ad18bd..dd1660790 100644 --- a/tests/lib/rules/no-lifecycle-after-await.js +++ b/tests/lib/rules/no-lifecycle-after-await.js @@ -125,7 +125,8 @@ tester.run('no-lifecycle-after-await', rule, { `, errors: [ { - message: 'The lifecycle hooks after `await` expression are forbidden.', + message: + 'The lifecycle hooks after `await` expression are forbidden.', line: 8, column: 11, endLine: 8, diff --git a/tests/lib/rules/no-multi-spaces.js b/tests/lib/rules/no-multi-spaces.js index 7a7947ad5..f7772dbe1 100644 --- a/tests/lib/rules/no-multi-spaces.js +++ b/tests/lib/rules/no-multi-spaces.js @@ -56,9 +56,11 @@ ruleTester.run('no-multi-spaces', rule, { /> `, - options: [{ - ignoreProperties: true - }] + options: [ + { + ignoreProperties: true + } + ] }, { code: ` @@ -71,19 +73,23 @@ ruleTester.run('no-multi-spaces', rule, { /> `, - options: [{ - ignoreProperties: true - }] + options: [ + { + ignoreProperties: true + } + ] } ], invalid: [ { code: '', output: '', - errors: [{ - message: "Multiple spaces found before '/>'.", - type: 'HTMLSelfClosingTagClose' - }] + errors: [ + { + message: "Multiple spaces found before '/>'.", + type: 'HTMLSelfClosingTagClose' + } + ] }, { code: '', @@ -130,26 +136,32 @@ ruleTester.run('no-multi-spaces', rule, { { code: '', output: '', - errors: [{ - message: "Multiple spaces found before '/>'.", - type: 'HTMLSelfClosingTagClose' - }] + errors: [ + { + message: "Multiple spaces found before '/>'.", + type: 'HTMLSelfClosingTagClose' + } + ] }, { code: '', output: '', - errors: [{ - message: "Multiple spaces found before '/>'.", - type: 'HTMLSelfClosingTagClose' - }] + errors: [ + { + message: "Multiple spaces found before '/>'.", + type: 'HTMLSelfClosingTagClose' + } + ] }, { code: '', output: '', - errors: [{ - message: "Multiple spaces found before '/>'.", - type: 'HTMLSelfClosingTagClose' - }] + errors: [ + { + message: "Multiple spaces found before '/>'.", + type: 'HTMLSelfClosingTagClose' + } + ] }, { code: '', @@ -186,7 +198,8 @@ ruleTester.run('no-multi-spaces', rule, { ] }, { - code: '', + code: + '', output: '', errors: [ { diff --git a/tests/lib/rules/no-multiple-template-root.js b/tests/lib/rules/no-multiple-template-root.js index 3c8a99bc5..aefaa1a63 100644 --- a/tests/lib/rules/no-multiple-template-root.js +++ b/tests/lib/rules/no-multiple-template-root.js @@ -8,9 +8,9 @@ // Requirements // ------------------------------------------------------------------------------ -var rule = require('../../../lib/rules/no-multiple-template-root') +const rule = require('../../../lib/rules/no-multiple-template-root') -var RuleTester = require('eslint').RuleTester +const RuleTester = require('eslint').RuleTester // ------------------------------------------------------------------------------ // Tests @@ -36,11 +36,13 @@ ruleTester.run('no-multiple-template-root', rule, { }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', @@ -52,7 +54,8 @@ ruleTester.run('no-multiple-template-root', rule, { }, { filename: 'test.vue', - code: '' + code: + '' } ], invalid: [ diff --git a/tests/lib/rules/no-mutating-props.js b/tests/lib/rules/no-mutating-props.js index d87df48b9..1e9e09737 100644 --- a/tests/lib/rules/no-mutating-props.js +++ b/tests/lib/rules/no-mutating-props.js @@ -24,7 +24,6 @@ const ruleTester = new RuleTester({ }) ruleTester.run('no-mutating-props', rule, { - valid: [ { filename: 'test.vue', @@ -617,9 +616,7 @@ ruleTester.run('no-mutating-props', rule, { } `, - errors: [ - 'Unexpected mutation of "[a]" prop.' - ] + errors: ['Unexpected mutation of "[a]" prop.'] }, { filename: 'test.vue', @@ -632,9 +629,7 @@ ruleTester.run('no-mutating-props', rule, { } `, - errors: [ - 'Unexpected mutation of "[a]" prop.' - ] + errors: ['Unexpected mutation of "[a]" prop.'] } ] }) diff --git a/tests/lib/rules/no-parsing-error.js b/tests/lib/rules/no-parsing-error.js index 51741b40a..c0c1ce617 100644 --- a/tests/lib/rules/no-parsing-error.js +++ b/tests/lib/rules/no-parsing-error.js @@ -37,7 +37,8 @@ tester.run('no-parsing-error', rule, { }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', @@ -195,7 +196,9 @@ tester.run('no-parsing-error', rule, { }, { code: '', - options: [{ 'non-void-html-element-start-tag-with-trailing-solidus': false }] + options: [ + { 'non-void-html-element-start-tag-with-trailing-solidus': false } + ] }, { code: '', @@ -235,7 +238,11 @@ tester.run('no-parsing-error', rule, { filename: 'test.vue', code: '', errors: [ - { message: 'Parsing error: Expected to be an expression, but got empty.', column: 24 } + { + message: + 'Parsing error: Expected to be an expression, but got empty.', + column: 24 + } ] }, { @@ -248,9 +255,7 @@ tester.run('no-parsing-error', rule, { { filename: 'test.vue', code: '', - errors: [ - { message: 'Parsing error: Unexpected token (.', column: 26 } - ] + errors: [{ message: 'Parsing error: Unexpected token (.', column: 26 }] }, { code: ``, @@ -265,7 +270,9 @@ tester.run('no-parsing-error', rule, { { code: ``, options: [{ 'absence-of-digits-in-numeric-character-reference': true }], - errors: ['Parsing error: absence-of-digits-in-numeric-character-reference.'] + errors: [ + 'Parsing error: absence-of-digits-in-numeric-character-reference.' + ] }, { code: '', @@ -380,7 +387,9 @@ tester.run('no-parsing-error', rule, { { code: '', options: [{ 'unexpected-character-in-unquoted-attribute-value': true }], - errors: ['Parsing error: unexpected-character-in-unquoted-attribute-value.'] + errors: [ + 'Parsing error: unexpected-character-in-unquoted-attribute-value.' + ] }, { code: '', @@ -424,8 +433,12 @@ tester.run('no-parsing-error', rule, { }, { code: '', - options: [{ 'non-void-html-element-start-tag-with-trailing-solidus': true }], - errors: ['Parsing error: non-void-html-element-start-tag-with-trailing-solidus.'] + options: [ + { 'non-void-html-element-start-tag-with-trailing-solidus': true } + ], + errors: [ + 'Parsing error: non-void-html-element-start-tag-with-trailing-solidus.' + ] }, { code: '', @@ -447,7 +460,9 @@ tester.run('no-parsing-error', rule, { }, { code: ``, - errors: ['Parsing error: absence-of-digits-in-numeric-character-reference.'] + errors: [ + 'Parsing error: absence-of-digits-in-numeric-character-reference.' + ] }, { code: '', @@ -539,7 +554,9 @@ tester.run('no-parsing-error', rule, { }, { code: '', - errors: ['Parsing error: unexpected-character-in-unquoted-attribute-value.'] + errors: [ + 'Parsing error: unexpected-character-in-unquoted-attribute-value.' + ] }, { code: '', diff --git a/tests/lib/rules/no-ref-as-operand.js b/tests/lib/rules/no-ref-as-operand.js index b8632c88b..6eeb11b54 100644 --- a/tests/lib/rules/no-ref-as-operand.js +++ b/tests/lib/rules/no-ref-as-operand.js @@ -117,21 +117,24 @@ tester.run('no-ref-as-operand', rule, { `, errors: [ { - message: 'Must use `.value` to read or write the value wrapped by `ref()`.', + message: + 'Must use `.value` to read or write the value wrapped by `ref()`.', line: 5, column: 7, endLine: 5, endColumn: 12 }, { - message: 'Must use `.value` to read or write the value wrapped by `ref()`.', + message: + 'Must use `.value` to read or write the value wrapped by `ref()`.', line: 6, column: 19, endLine: 6, endColumn: 24 }, { - message: 'Must use `.value` to read or write the value wrapped by `ref()`.', + message: + 'Must use `.value` to read or write the value wrapped by `ref()`.', line: 7, column: 23, endLine: 7, diff --git a/tests/lib/rules/no-reserved-component-names.js b/tests/lib/rules/no-reserved-component-names.js index a3bc3bb01..cdb3ab7a2 100644 --- a/tests/lib/rules/no-reserved-component-names.js +++ b/tests/lib/rules/no-reserved-component-names.js @@ -14,7 +14,9 @@ const RuleTester = require('eslint').RuleTester const htmlElements = require('../../../lib/utils/html-elements.json') const RESERVED_NAMES_IN_HTML = new Set([ ...htmlElements, - ...htmlElements.map((word) => word[0].toUpperCase() + word.substring(1, word.length)) + ...htmlElements.map( + (word) => word[0].toUpperCase() + word.substring(1, word.length) + ) ]) // ------------------------------------------------------------------------------ @@ -22,143 +24,275 @@ const RESERVED_NAMES_IN_HTML = new Set([ // ------------------------------------------------------------------------------ const invalidElements = [ - 'annotation-xml', 'AnnotationXml', - 'color-profile', 'ColorProfile', - 'font-face', 'FontFace', - 'font-face-src', 'FontFaceSrc', - 'font-face-uri', 'FontFaceUri', - 'font-face-format', 'FontFaceFormat', - 'font-face-name', 'FontFaceName', - 'missing-glyph', 'MissingGlyph', - 'html', 'Html', - 'body', 'Body', - 'base', 'Base', - 'head', 'Head', - 'link', 'Link', - 'meta', 'Meta', - 'style', 'Style', - 'title', 'Title', - 'address', 'Address', - 'article', 'Article', - 'aside', 'Aside', - 'footer', 'Footer', - 'header', 'Header', - 'h1', 'H1', - 'h2', 'H2', - 'h3', 'H3', - 'h4', 'H4', - 'h5', 'H5', - 'h6', 'H6', - 'hgroup', 'Hgroup', - 'nav', 'Nav', - 'section', 'Section', - 'div', 'Div', - 'dd', 'Dd', - 'dl', 'Dl', - 'dt', 'Dt', - 'figcaption', 'Figcaption', - 'figure', 'Figure', - 'hr', 'Hr', - 'img', 'Img', - 'li', 'Li', - 'main', 'Main', - 'ol', 'Ol', - 'p', 'P', - 'pre', 'Pre', - 'ul', 'Ul', - 'a', 'A', - 'b', 'B', - 'abbr', 'Abbr', - 'bdi', 'Bdi', - 'bdo', 'Bdo', - 'br', 'Br', - 'cite', 'Cite', - 'code', 'Code', - 'data', 'Data', - 'dfn', 'Dfn', - 'em', 'Em', - 'i', 'I', - 'kbd', 'Kbd', - 'mark', 'Mark', - 'q', 'Q', - 'rp', 'Rp', - 'rt', 'Rt', - 'rtc', 'Rtc', - 'ruby', 'Ruby', - 's', 'S', - 'samp', 'Samp', - 'small', 'Small', - 'span', 'Span', - 'strong', 'Strong', - 'sub', 'Sub', - 'sup', 'Sup', - 'time', 'Time', - 'u', 'U', - 'var', 'Var', - 'wbr', 'Wbr', - 'area', 'Area', - 'audio', 'Audio', - 'map', 'Map', - 'track', 'Track', - 'video', 'Video', - 'embed', 'Embed', - 'object', 'Object', - 'param', 'Param', - 'source', 'Source', - 'canvas', 'Canvas', - 'script', 'Script', - 'noscript', 'Noscript', - 'del', 'Del', - 'ins', 'Ins', - 'caption', 'Caption', - 'col', 'Col', - 'colgroup', 'Colgroup', - 'table', 'Table', - 'thead', 'Thead', - 'tbody', 'Tbody', - 'tfoot', 'Tfoot', - 'td', 'Td', - 'th', 'Th', - 'tr', 'Tr', - 'button', 'Button', - 'datalist', 'Datalist', - 'fieldset', 'Fieldset', - 'form', 'Form', - 'input', 'Input', - 'label', 'Label', - 'legend', 'Legend', - 'meter', 'Meter', - 'optgroup', 'Optgroup', - 'option', 'Option', - 'output', 'Output', - 'progress', 'Progress', - 'select', 'Select', - 'textarea', 'Textarea', - 'details', 'Details', - 'dialog', 'Dialog', - 'menu', 'Menu', - 'menuitem', 'menuitem', - 'summary', 'Summary', - 'content', 'Content', - 'element', 'Element', - 'shadow', 'Shadow', - 'template', 'Template', - 'slot', 'Slot', - 'blockquote', 'Blockquote', - 'iframe', 'Iframe', - 'noframes', 'Noframes', - 'picture', 'Picture', + 'annotation-xml', + 'AnnotationXml', + 'color-profile', + 'ColorProfile', + 'font-face', + 'FontFace', + 'font-face-src', + 'FontFaceSrc', + 'font-face-uri', + 'FontFaceUri', + 'font-face-format', + 'FontFaceFormat', + 'font-face-name', + 'FontFaceName', + 'missing-glyph', + 'MissingGlyph', + 'html', + 'Html', + 'body', + 'Body', + 'base', + 'Base', + 'head', + 'Head', + 'link', + 'Link', + 'meta', + 'Meta', + 'style', + 'Style', + 'title', + 'Title', + 'address', + 'Address', + 'article', + 'Article', + 'aside', + 'Aside', + 'footer', + 'Footer', + 'header', + 'Header', + 'h1', + 'H1', + 'h2', + 'H2', + 'h3', + 'H3', + 'h4', + 'H4', + 'h5', + 'H5', + 'h6', + 'H6', + 'hgroup', + 'Hgroup', + 'nav', + 'Nav', + 'section', + 'Section', + 'div', + 'Div', + 'dd', + 'Dd', + 'dl', + 'Dl', + 'dt', + 'Dt', + 'figcaption', + 'Figcaption', + 'figure', + 'Figure', + 'hr', + 'Hr', + 'img', + 'Img', + 'li', + 'Li', + 'main', + 'Main', + 'ol', + 'Ol', + 'p', + 'P', + 'pre', + 'Pre', + 'ul', + 'Ul', + 'a', + 'A', + 'b', + 'B', + 'abbr', + 'Abbr', + 'bdi', + 'Bdi', + 'bdo', + 'Bdo', + 'br', + 'Br', + 'cite', + 'Cite', + 'code', + 'Code', + 'data', + 'Data', + 'dfn', + 'Dfn', + 'em', + 'Em', + 'i', + 'I', + 'kbd', + 'Kbd', + 'mark', + 'Mark', + 'q', + 'Q', + 'rp', + 'Rp', + 'rt', + 'Rt', + 'rtc', + 'Rtc', + 'ruby', + 'Ruby', + 's', + 'S', + 'samp', + 'Samp', + 'small', + 'Small', + 'span', + 'Span', + 'strong', + 'Strong', + 'sub', + 'Sub', + 'sup', + 'Sup', + 'time', + 'Time', + 'u', + 'U', + 'var', + 'Var', + 'wbr', + 'Wbr', + 'area', + 'Area', + 'audio', + 'Audio', + 'map', + 'Map', + 'track', + 'Track', + 'video', + 'Video', + 'embed', + 'Embed', + 'object', + 'Object', + 'param', + 'Param', + 'source', + 'Source', + 'canvas', + 'Canvas', + 'script', + 'Script', + 'noscript', + 'Noscript', + 'del', + 'Del', + 'ins', + 'Ins', + 'caption', + 'Caption', + 'col', + 'Col', + 'colgroup', + 'Colgroup', + 'table', + 'Table', + 'thead', + 'Thead', + 'tbody', + 'Tbody', + 'tfoot', + 'Tfoot', + 'td', + 'Td', + 'th', + 'Th', + 'tr', + 'Tr', + 'button', + 'Button', + 'datalist', + 'Datalist', + 'fieldset', + 'Fieldset', + 'form', + 'Form', + 'input', + 'Input', + 'label', + 'Label', + 'legend', + 'Legend', + 'meter', + 'Meter', + 'optgroup', + 'Optgroup', + 'option', + 'Option', + 'output', + 'Output', + 'progress', + 'Progress', + 'select', + 'Select', + 'textarea', + 'Textarea', + 'details', + 'Details', + 'dialog', + 'Dialog', + 'menu', + 'Menu', + 'menuitem', + 'menuitem', + 'summary', + 'Summary', + 'content', + 'Content', + 'element', + 'Element', + 'shadow', + 'Shadow', + 'template', + 'Template', + 'slot', + 'Slot', + 'blockquote', + 'Blockquote', + 'iframe', + 'Iframe', + 'noframes', + 'Noframes', + 'picture', + 'Picture', // SVG elements - 'animate', 'Animate', + 'animate', + 'Animate', 'animateMotion', 'animateTransform', - 'circle', 'Circle', + 'circle', + 'Circle', 'clipPath', - 'defs', 'Defs', - 'desc', 'Desc', - 'discard', 'Discard', - 'ellipse', 'Ellipse', + 'defs', + 'Defs', + 'desc', + 'Desc', + 'discard', + 'Discard', + 'ellipse', + 'Ellipse', 'feBlend', 'feColorMatrix', 'feComponentTransfer', @@ -184,73 +318,122 @@ const invalidElements = [ 'feSpotLight', 'feTile', 'feTurbulence', - 'filter', 'Filter', + 'filter', + 'Filter', 'foreignObject', - 'g', 'G', - 'image', 'Image', - 'line', 'Line', + 'g', + 'G', + 'image', + 'Image', + 'line', + 'Line', 'linearGradient', - 'marker', 'Marker', - 'mask', 'Mask', - 'metadata', 'Metadata', - 'mpath', 'Mpath', - 'path', 'Path', - 'pattern', 'Pattern', - 'polygon', 'Polygon', - 'polyline', 'Polyline', + 'marker', + 'Marker', + 'mask', + 'Mask', + 'metadata', + 'Metadata', + 'mpath', + 'Mpath', + 'path', + 'Path', + 'pattern', + 'Pattern', + 'polygon', + 'Polygon', + 'polyline', + 'Polyline', 'radialGradient', - 'rect', 'Rect', - 'set', 'Set', - 'stop', 'Stop', - 'svg', 'Svg', - 'switch', 'Switch', - 'symbol', 'Symbol', - 'text', 'Text', + 'rect', + 'Rect', + 'set', + 'Set', + 'stop', + 'Stop', + 'svg', + 'Svg', + 'switch', + 'Switch', + 'symbol', + 'Symbol', + 'text', + 'Text', 'textPath', - 'tspan', 'Tspan', - 'unknown', 'Unknown', - 'use', 'Use', - 'view', 'View', + 'tspan', + 'Tspan', + 'unknown', + 'Unknown', + 'use', + 'Use', + 'view', + 'View', // Deprecated - 'acronym', 'Acronym', - 'applet', 'Applet', - 'basefont', 'Basefont', - 'bgsound', 'Bgsound', - 'big', 'Big', - 'blink', 'Blink', - 'center', 'Center', - 'command', 'Command', - 'dir', 'Dir', - 'font', 'Font', - 'frame', 'Frame', - 'frameset', 'Frameset', - 'isindex', 'Isindex', - 'keygen', 'Keygen', - 'listing', 'Listing', - 'marquee', 'Marquee', - 'multicol', 'Multicol', - 'nextid', 'Nextid', - 'nobr', 'Nobr', - 'noembed', 'Noembed', - 'plaintext', 'Plaintext', - 'spacer', 'Spacer', - 'strike', 'Strike', - 'tt', 'Tt', - 'xmp', 'Xmp' + 'acronym', + 'Acronym', + 'applet', + 'Applet', + 'basefont', + 'Basefont', + 'bgsound', + 'Bgsound', + 'big', + 'Big', + 'blink', + 'Blink', + 'center', + 'Center', + 'command', + 'Command', + 'dir', + 'Dir', + 'font', + 'Font', + 'frame', + 'Frame', + 'frameset', + 'Frameset', + 'isindex', + 'Isindex', + 'keygen', + 'Keygen', + 'listing', + 'Listing', + 'marquee', + 'Marquee', + 'multicol', + 'Multicol', + 'nextid', + 'Nextid', + 'nobr', + 'Nobr', + 'noembed', + 'Noembed', + 'plaintext', + 'Plaintext', + 'spacer', + 'Spacer', + 'strike', + 'Strike', + 'tt', + 'Tt', + 'xmp', + 'Xmp' ] const vue2BuiltInComponents = [ - 'component', 'Component', - 'transition', 'Transition', - 'transition-group', 'TransitionGroup', - 'keep-alive', 'KeepAlive' + 'component', + 'Component', + 'transition', + 'Transition', + 'transition-group', + 'TransitionGroup', + 'keep-alive', + 'KeepAlive' ] -const vue3BuiltInComponents = [ - 'teleport', 'Teleport', - 'suspense', 'Suspense' -] +const vue3BuiltInComponents = ['teleport', 'Teleport', 'suspense', 'Suspense'] const parserOptions = { ecmaVersion: 2018, @@ -259,7 +442,6 @@ const parserOptions = { const ruleTester = new RuleTester() ruleTester.run('no-reserved-component-names', rule, { - valid: [ { filename: 'test.vue', @@ -294,7 +476,12 @@ ruleTester.run('no-reserved-component-names', rule, { name: 'FooBar' } `, - options: [{ disallowVueBuiltInComponents: true, disallowVue3BuiltInComponents: true }], + options: [ + { + disallowVueBuiltInComponents: true, + disallowVue3BuiltInComponents: true + } + ], parserOptions }, { @@ -351,7 +538,7 @@ ruleTester.run('no-reserved-component-names', rule, { code: `fn1(component.data)`, parserOptions }, - ...vue2BuiltInComponents.map(name => { + ...vue2BuiltInComponents.map((name) => { return { filename: `${name}.vue`, code: ` @@ -362,7 +549,7 @@ ruleTester.run('no-reserved-component-names', rule, { parserOptions } }), - ...vue3BuiltInComponents.map(name => { + ...vue3BuiltInComponents.map((name) => { return { filename: `${name}.vue`, code: ` @@ -373,7 +560,7 @@ ruleTester.run('no-reserved-component-names', rule, { parserOptions } }), - ...vue3BuiltInComponents.map(name => { + ...vue3BuiltInComponents.map((name) => { return { filename: `${name}.vue`, code: ` @@ -388,7 +575,7 @@ ruleTester.run('no-reserved-component-names', rule, { ], invalid: [ - ...invalidElements.map(name => { + ...invalidElements.map((name) => { return { filename: `${name}.vue`, code: ` @@ -397,67 +584,87 @@ ruleTester.run('no-reserved-component-names', rule, { } `, parserOptions, - errors: [{ - messageId: RESERVED_NAMES_IN_HTML.has(name) ? 'reservedInHtml' : 'reserved', - data: { name }, - type: 'Literal', - line: 3 - }] + errors: [ + { + messageId: RESERVED_NAMES_IN_HTML.has(name) + ? 'reservedInHtml' + : 'reserved', + data: { name }, + type: 'Literal', + line: 3 + } + ] } }), - ...invalidElements.map(name => { + ...invalidElements.map((name) => { return { filename: 'test.vue', code: `Vue.component('${name}', component)`, parserOptions, - errors: [{ - messageId: RESERVED_NAMES_IN_HTML.has(name) ? 'reservedInHtml' : 'reserved', - data: { name }, - type: 'Literal', - line: 1 - }] + errors: [ + { + messageId: RESERVED_NAMES_IN_HTML.has(name) + ? 'reservedInHtml' + : 'reserved', + data: { name }, + type: 'Literal', + line: 1 + } + ] } }), - ...invalidElements.map(name => { + ...invalidElements.map((name) => { return { filename: 'test.vue', code: `app.component('${name}', component)`, parserOptions, - errors: [{ - messageId: RESERVED_NAMES_IN_HTML.has(name) ? 'reservedInHtml' : 'reserved', - data: { name }, - type: 'Literal', - line: 1 - }] + errors: [ + { + messageId: RESERVED_NAMES_IN_HTML.has(name) + ? 'reservedInHtml' + : 'reserved', + data: { name }, + type: 'Literal', + line: 1 + } + ] } }), - ...invalidElements.map(name => { + ...invalidElements.map((name) => { return { filename: 'test.vue', code: `Vue.component(\`${name}\`, {})`, parserOptions, - errors: [{ - messageId: RESERVED_NAMES_IN_HTML.has(name) ? 'reservedInHtml' : 'reserved', - data: { name }, - type: 'TemplateLiteral', - line: 1 - }] + errors: [ + { + messageId: RESERVED_NAMES_IN_HTML.has(name) + ? 'reservedInHtml' + : 'reserved', + data: { name }, + type: 'TemplateLiteral', + line: 1 + } + ] } }), - ...invalidElements.map(name => { + ...invalidElements.map((name) => { return { filename: 'test.vue', code: `app.component(\`${name}\`, {})`, parserOptions, - errors: [{ - messageId: RESERVED_NAMES_IN_HTML.has(name) ? 'reservedInHtml' : 'reserved', - data: { name }, - type: 'TemplateLiteral', - line: 1 - }] + errors: [ + { + messageId: RESERVED_NAMES_IN_HTML.has(name) + ? 'reservedInHtml' + : 'reserved', + data: { name }, + type: 'TemplateLiteral', + line: 1 + } + ] } }), - ...invalidElements.map(name => { + ...invalidElements.map((name) => { return { filename: 'test.vue', code: `export default { @@ -466,15 +673,19 @@ ruleTester.run('no-reserved-component-names', rule, { } }`, parserOptions, - errors: [{ - messageId: RESERVED_NAMES_IN_HTML.has(name) ? 'reservedInHtml' : 'reserved', - data: { name }, - type: 'Property', - line: 3 - }] + errors: [ + { + messageId: RESERVED_NAMES_IN_HTML.has(name) + ? 'reservedInHtml' + : 'reserved', + data: { name }, + type: 'Property', + line: 3 + } + ] } }), - ...vue2BuiltInComponents.map(name => { + ...vue2BuiltInComponents.map((name) => { return { filename: `${name}.vue`, code: ` @@ -484,15 +695,17 @@ ruleTester.run('no-reserved-component-names', rule, { `, parserOptions, options: [{ disallowVueBuiltInComponents: true }], - errors: [{ - messageId: 'reservedInVue', - data: { name }, - type: 'Literal', - line: 3 - }] + errors: [ + { + messageId: 'reservedInVue', + data: { name }, + type: 'Literal', + line: 3 + } + ] } }), - ...vue2BuiltInComponents.map(name => { + ...vue2BuiltInComponents.map((name) => { return { filename: `${name}.vue`, code: ` @@ -502,15 +715,17 @@ ruleTester.run('no-reserved-component-names', rule, { `, parserOptions, options: [{ disallowVue3BuiltInComponents: true }], - errors: [{ - messageId: 'reservedInVue', - data: { name }, - type: 'Literal', - line: 3 - }] + errors: [ + { + messageId: 'reservedInVue', + data: { name }, + type: 'Literal', + line: 3 + } + ] } }), - ...vue3BuiltInComponents.map(name => { + ...vue3BuiltInComponents.map((name) => { return { filename: `${name}.vue`, code: ` @@ -520,12 +735,14 @@ ruleTester.run('no-reserved-component-names', rule, { `, parserOptions, options: [{ disallowVue3BuiltInComponents: true }], - errors: [{ - messageId: 'reservedInVue3', - data: { name }, - type: 'Literal', - line: 3 - }] + errors: [ + { + messageId: 'reservedInVue3', + data: { name }, + type: 'Literal', + line: 3 + } + ] } }) ] diff --git a/tests/lib/rules/no-reserved-keys.js b/tests/lib/rules/no-reserved-keys.js index f3bc64acb..fdd5e01f4 100644 --- a/tests/lib/rules/no-reserved-keys.js +++ b/tests/lib/rules/no-reserved-keys.js @@ -129,10 +129,12 @@ ruleTester.run('no-reserved-keys', rule, { }) `, parserOptions: { ecmaVersion: 6 }, - errors: [{ - message: "Key '$el' is reserved.", - line: 4 - }] + errors: [ + { + message: "Key '$el' is reserved.", + line: 4 + } + ] }, { filename: 'test.js', @@ -146,10 +148,12 @@ ruleTester.run('no-reserved-keys', rule, { }) `, parserOptions: { ecmaVersion: 6 }, - errors: [{ - message: "Key '$el' is reserved.", - line: 5 - }] + errors: [ + { + message: "Key '$el' is reserved.", + line: 5 + } + ] }, { filename: 'test.js', @@ -161,10 +165,12 @@ ruleTester.run('no-reserved-keys', rule, { }) `, parserOptions: { ecmaVersion: 6 }, - errors: [{ - message: "Keys starting with with '_' are reserved in '_foo' group.", - line: 4 - }] + errors: [ + { + message: "Keys starting with with '_' are reserved in '_foo' group.", + line: 4 + } + ] }, { filename: 'test.js', @@ -178,10 +184,12 @@ ruleTester.run('no-reserved-keys', rule, { }) `, parserOptions: { ecmaVersion: 6 }, - errors: [{ - message: "Keys starting with with '_' are reserved in '_foo' group.", - line: 5 - }] + errors: [ + { + message: "Keys starting with with '_' are reserved in '_foo' group.", + line: 5 + } + ] }, { filename: 'test.js', @@ -193,10 +201,12 @@ ruleTester.run('no-reserved-keys', rule, { }) `, parserOptions: { ecmaVersion: 6 }, - errors: [{ - message: "Keys starting with with '_' are reserved in '_foo' group.", - line: 4 - }] + errors: [ + { + message: "Keys starting with with '_' are reserved in '_foo' group.", + line: 4 + } + ] }, { filename: 'test.js', @@ -209,10 +219,12 @@ ruleTester.run('no-reserved-keys', rule, { `, options: [{ reserved: ['bar'], groups: ['foo'] }], parserOptions: { ecmaVersion: 6 }, - errors: [{ - message: "Key 'bar' is reserved.", - line: 4 - }] + errors: [ + { + message: "Key 'bar' is reserved.", + line: 4 + } + ] } ] }) diff --git a/tests/lib/rules/no-restricted-syntax.js b/tests/lib/rules/no-restricted-syntax.js index 9887a6ea3..e7b3d4480 100644 --- a/tests/lib/rules/no-restricted-syntax.js +++ b/tests/lib/rules/no-restricted-syntax.js @@ -20,8 +20,8 @@ tester.run('no-restricted-syntax', rule, { `, options: [ { - 'selector': 'CallExpression', - 'message': 'Call expressions are not allowed.' + selector: 'CallExpression', + message: 'Call expressions are not allowed.' } ] }, @@ -32,8 +32,8 @@ tester.run('no-restricted-syntax', rule, { `, options: [ { - 'selector': 'CallExpression', - 'message': 'Call expressions are not allowed.' + selector: 'CallExpression', + message: 'Call expressions are not allowed.' } ] } @@ -46,8 +46,8 @@ tester.run('no-restricted-syntax', rule, { `, options: [ { - 'selector': 'CallExpression', - 'message': 'Call expressions are not allowed.' + selector: 'CallExpression', + message: 'Call expressions are not allowed.' } ], errors: [ @@ -71,27 +71,31 @@ tester.run('no-restricted-syntax', rule, { `, options: [ { - 'selector': 'VElement > VExpressionContainer CallExpression', - 'message': 'Call expressions are not allowed inside mustache interpolation.' + selector: 'VElement > VExpressionContainer CallExpression', + message: + 'Call expressions are not allowed inside mustache interpolation.' } ], errors: [ { - message: 'Call expressions are not allowed inside mustache interpolation.', + message: + 'Call expressions are not allowed inside mustache interpolation.', line: 3, column: 20, endLine: 3, endColumn: 25 }, { - message: 'Call expressions are not allowed inside mustache interpolation.', + message: + 'Call expressions are not allowed inside mustache interpolation.', line: 4, column: 20, endLine: 4, endColumn: 29 }, { - message: 'Call expressions are not allowed inside mustache interpolation.', + message: + 'Call expressions are not allowed inside mustache interpolation.', line: 5, column: 20, endLine: 5, @@ -111,14 +115,16 @@ tester.run('no-restricted-syntax', rule, { ], errors: [ { - message: 'Using \'CallExpression[callee.type=\'Identifier\'][callee.name=\'$gettext\'] TemplateLiteral\' is not allowed.', + message: + "Using 'CallExpression[callee.type='Identifier'][callee.name='$gettext'] TemplateLiteral' is not allowed.", line: 3, column: 29, endLine: 3, endColumn: 34 }, { - message: 'Using \'CallExpression[callee.type=\'Identifier\'][callee.name=\'$gettext\'] TemplateLiteral\' is not allowed.', + message: + "Using 'CallExpression[callee.type='Identifier'][callee.name='$gettext'] TemplateLiteral' is not allowed.", line: 3, column: 48, endLine: 3, @@ -134,11 +140,14 @@ tester.run('no-restricted-syntax', rule, { `, options: [ { - 'selector': 'CallExpression', - 'message': 'Call expressions are not allowed.' + selector: 'CallExpression', + message: 'Call expressions are not allowed.' } ], - errors: ['Call expressions are not allowed.', 'Call expressions are not allowed.'] + errors: [ + 'Call expressions are not allowed.', + 'Call expressions are not allowed.' + ] } ] }) diff --git a/tests/lib/rules/no-shared-component-data.js b/tests/lib/rules/no-shared-component-data.js index ade9e9efe..38303b2ee 100644 --- a/tests/lib/rules/no-shared-component-data.js +++ b/tests/lib/rules/no-shared-component-data.js @@ -23,7 +23,6 @@ const parserOptions = { const ruleTester = new RuleTester() ruleTester.run('no-shared-component-data', rule, { - valid: [ { filename: 'test.js', @@ -139,10 +138,12 @@ return { }) `, parserOptions, - errors: [{ - message: '`data` property in component must be a function.', - line: 3 - }] + errors: [ + { + message: '`data` property in component must be a function.', + line: 3 + } + ] }, { filename: 'test.js', @@ -163,10 +164,12 @@ return { }) `, parserOptions, - errors: [{ - message: '`data` property in component must be a function.', - line: 3 - }] + errors: [ + { + message: '`data` property in component must be a function.', + line: 3 + } + ] }, { filename: 'test.vue', @@ -187,10 +190,12 @@ return { } `, parserOptions, - errors: [{ - message: '`data` property in component must be a function.', - line: 3 - }] + errors: [ + { + message: '`data` property in component must be a function.', + line: 3 + } + ] }, { filename: 'test.vue', @@ -211,10 +216,12 @@ return (/*b*/{ } `, parserOptions, - errors: [{ - message: '`data` property in component must be a function.', - line: 3 - }] + errors: [ + { + message: '`data` property in component must be a function.', + line: 3 + } + ] } ] }) diff --git a/tests/lib/rules/no-side-effects-in-computed-properties.js b/tests/lib/rules/no-side-effects-in-computed-properties.js index fa14ef248..b2f341a18 100644 --- a/tests/lib/rules/no-side-effects-in-computed-properties.js +++ b/tests/lib/rules/no-side-effects-in-computed-properties.js @@ -206,28 +206,36 @@ ruleTester.run('no-side-effects-in-computed-properties', rule, { } })`, parserOptions, - errors: [{ - line: 4, - message: 'Unexpected side effect in "test1" computed property.' - }, { - line: 9, - message: 'Unexpected side effect in "test2" computed property.' - }, { - line: 10, - message: 'Unexpected side effect in "test2" computed property.' - }, { - line: 14, - message: 'Unexpected side effect in "test3" computed property.' - }, { - line: 17, - message: 'Unexpected side effect in "test4" computed property.' - }, { - line: 21, - message: 'Unexpected side effect in "test5" computed property.' - }, { - line: 25, - message: 'Unexpected side effect in "test6" computed property.' - }] + errors: [ + { + line: 4, + message: 'Unexpected side effect in "test1" computed property.' + }, + { + line: 9, + message: 'Unexpected side effect in "test2" computed property.' + }, + { + line: 10, + message: 'Unexpected side effect in "test2" computed property.' + }, + { + line: 14, + message: 'Unexpected side effect in "test3" computed property.' + }, + { + line: 17, + message: 'Unexpected side effect in "test4" computed property.' + }, + { + line: 21, + message: 'Unexpected side effect in "test5" computed property.' + }, + { + line: 25, + message: 'Unexpected side effect in "test6" computed property.' + } + ] }, { code: `Vue.component('test', { @@ -262,22 +270,28 @@ ruleTester.run('no-side-effects-in-computed-properties', rule, { } })`, parserOptions, - errors: [{ - line: 5, - message: 'Unexpected side effect in "test1" computed property.' - }, { - line: 11, - message: 'Unexpected side effect in "test2" computed property.' - }, { - line: 12, - message: 'Unexpected side effect in "test2" computed property.' - }, { - line: 18, - message: 'Unexpected side effect in "test3" computed property.' - }, { - line: 23, - message: 'Unexpected side effect in "test4" computed property.' - }] + errors: [ + { + line: 5, + message: 'Unexpected side effect in "test1" computed property.' + }, + { + line: 11, + message: 'Unexpected side effect in "test2" computed property.' + }, + { + line: 12, + message: 'Unexpected side effect in "test2" computed property.' + }, + { + line: 18, + message: 'Unexpected side effect in "test3" computed property.' + }, + { + line: 23, + message: 'Unexpected side effect in "test4" computed property.' + } + ] }, { filename: 'test.vue', @@ -291,10 +305,12 @@ ruleTester.run('no-side-effects-in-computed-properties', rule, { }); `, parserOptions, - errors: [{ - line: 5, - message: 'Unexpected side effect in "test1" computed property.' - }], + errors: [ + { + line: 5, + message: 'Unexpected side effect in "test1" computed property.' + } + ], parser: require.resolve('@typescript-eslint/parser') }, diff --git a/tests/lib/rules/no-spaces-around-equal-signs-in-attribute.js b/tests/lib/rules/no-spaces-around-equal-signs-in-attribute.js index 600a025be..9e475a5d6 100644 --- a/tests/lib/rules/no-spaces-around-equal-signs-in-attribute.js +++ b/tests/lib/rules/no-spaces-around-equal-signs-in-attribute.js @@ -22,7 +22,7 @@ tester.run('no-spaces-around-equal-signs-in-attribute', rule, { valid: [ '', '', - '', + "", '', '', '', @@ -69,8 +69,8 @@ tester.run('no-spaces-around-equal-signs-in-attribute', rule, { ] }, { - code: '', - output: '', + code: "", + output: "", errors: [ { message: 'Unexpected spaces found around equal signs.', @@ -134,8 +134,7 @@ tester.run('no-spaces-around-equal-signs-in-attribute', rule, { ] }, { - code: - ` `, - errors: [{ - message: "This 'v-if' should be moved to the wrapper element.", - line: 6 - }] + errors: [ + { + message: "This 'v-if' should be moved to the wrapper element.", + line: 6 + } + ] }, { filename: 'test.vue', - code: '', - errors: [{ - message: "The 'list()' expression inside 'v-for' directive should be replaced with a computed property that returns filtered array instead. You should not mix 'v-for' with 'v-if'.", - line: 1 - }] + code: + '', + errors: [ + { + message: + "The 'list()' expression inside 'v-for' directive should be replaced with a computed property that returns filtered array instead. You should not mix 'v-for' with 'v-if'.", + line: 1 + } + ] }, { filename: 'test.vue', - code: '', - errors: [{ - message: "The '5' expression inside 'v-for' directive should be replaced with a computed property that returns filtered array instead. You should not mix 'v-for' with 'v-if'.", - line: 1 - }] + code: + '', + errors: [ + { + message: + "The '5' expression inside 'v-for' directive should be replaced with a computed property that returns filtered array instead. You should not mix 'v-for' with 'v-if'.", + line: 1 + } + ] } ] }) diff --git a/tests/lib/rules/no-v-model-argument.js b/tests/lib/rules/no-v-model-argument.js index 5cf5c5952..cba98ebe4 100644 --- a/tests/lib/rules/no-v-model-argument.js +++ b/tests/lib/rules/no-v-model-argument.js @@ -21,7 +21,6 @@ const ruleTester = new RuleTester({ }) ruleTester.run('no-v-model-argument', rule, { - valid: [ { filename: 'test.vue', @@ -32,12 +31,14 @@ ruleTester.run('no-v-model-argument', rule, { invalid: [ { filename: 'test.vue', - code: '', + code: + '', errors: ["'v-model' directives require no argument."] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["'v-model' directives require no argument."] } ] diff --git a/tests/lib/rules/prop-name-casing.js b/tests/lib/rules/prop-name-casing.js index 5290ec07d..eb932b299 100644 --- a/tests/lib/rules/prop-name-casing.js +++ b/tests/lib/rules/prop-name-casing.js @@ -22,7 +22,6 @@ const parserOptions = { const ruleTester = new RuleTester() ruleTester.run('prop-name-casing', rule, { - valid: [ { filename: 'test.vue', @@ -361,11 +360,13 @@ ruleTester.run('prop-name-casing', rule, { } `, parserOptions, - errors: [{ - message: 'Prop "greeting_text" is not in camelCase.', - type: 'Property', - line: 4 - }] + errors: [ + { + message: 'Prop "greeting_text" is not in camelCase.', + type: 'Property', + line: 4 + } + ] }, { filename: 'test.vue', @@ -378,11 +379,13 @@ ruleTester.run('prop-name-casing', rule, { `, options: ['camelCase'], parserOptions, - errors: [{ - message: 'Prop "greeting_text" is not in camelCase.', - type: 'Property', - line: 4 - }] + errors: [ + { + message: 'Prop "greeting_text" is not in camelCase.', + type: 'Property', + line: 4 + } + ] }, { filename: 'test.vue', @@ -393,11 +396,13 @@ ruleTester.run('prop-name-casing', rule, { `, options: ['camelCase'], parserOptions, - errors: [{ - message: 'Prop "greeting_text" is not in camelCase.', - type: 'Literal', - line: 3 - }] + errors: [ + { + message: 'Prop "greeting_text" is not in camelCase.', + type: 'Literal', + line: 3 + } + ] }, { filename: 'test.vue', @@ -410,11 +415,13 @@ ruleTester.run('prop-name-casing', rule, { `, options: ['snake_case'], parserOptions, - errors: [{ - message: 'Prop "greetingText" is not in snake_case.', - type: 'Property', - line: 4 - }] + errors: [ + { + message: 'Prop "greetingText" is not in snake_case.', + type: 'Property', + line: 4 + } + ] }, { filename: 'test.vue', @@ -427,11 +434,13 @@ ruleTester.run('prop-name-casing', rule, { `, options: ['camelCase'], parserOptions, - errors: [{ - message: 'Prop "greeting-text" is not in camelCase.', - type: 'Property', - line: 4 - }] + errors: [ + { + message: 'Prop "greeting-text" is not in camelCase.', + type: 'Property', + line: 4 + } + ] }, { filename: 'test.vue', @@ -444,11 +453,13 @@ ruleTester.run('prop-name-casing', rule, { `, options: ['snake_case'], parserOptions, - errors: [{ - message: 'Prop "greeting-text" is not in snake_case.', - type: 'Property', - line: 4 - }] + errors: [ + { + message: 'Prop "greeting-text" is not in snake_case.', + type: 'Property', + line: 4 + } + ] }, { filename: 'test.vue', @@ -460,11 +471,13 @@ ruleTester.run('prop-name-casing', rule, { } `, parserOptions, - errors: [{ - message: 'Prop "greeting_text" is not in camelCase.', - type: 'Property', - line: 4 - }] + errors: [ + { + message: 'Prop "greeting_text" is not in camelCase.', + type: 'Property', + line: 4 + } + ] }, { // computed property name @@ -477,11 +490,13 @@ ruleTester.run('prop-name-casing', rule, { } `, parserOptions, - errors: [{ - message: 'Prop "greeting-text" is not in camelCase.', - type: 'Property', - line: 4 - }] + errors: [ + { + message: 'Prop "greeting-text" is not in camelCase.', + type: 'Property', + line: 4 + } + ] }, { // shorthand @@ -494,11 +509,13 @@ ruleTester.run('prop-name-casing', rule, { } `, parserOptions, - errors: [{ - message: 'Prop "greeting_text" is not in camelCase.', - type: 'Property', - line: 4 - }] + errors: [ + { + message: 'Prop "greeting_text" is not in camelCase.', + type: 'Property', + line: 4 + } + ] }, { filename: 'test.vue', @@ -510,11 +527,13 @@ ruleTester.run('prop-name-casing', rule, { } `, parserOptions, - errors: [{ - message: 'Prop "abc-123-def" is not in camelCase.', - type: 'Property', - line: 4 - }] + errors: [ + { + message: 'Prop "abc-123-def" is not in camelCase.', + type: 'Property', + line: 4 + } + ] }, { // Parentheses computed property name @@ -527,11 +546,13 @@ ruleTester.run('prop-name-casing', rule, { } `, parserOptions, - errors: [{ - message: 'Prop "greeting-text" is not in camelCase.', - type: 'Property', - line: 4 - }] + errors: [ + { + message: 'Prop "greeting-text" is not in camelCase.', + type: 'Property', + line: 4 + } + ] }, { filename: 'test.vue', @@ -558,6 +579,5 @@ ruleTester.run('prop-name-casing', rule, { parserOptions, errors: ['Prop "_itemName" is not in snake_case.'] } - ] }) diff --git a/tests/lib/rules/require-default-prop.js b/tests/lib/rules/require-default-prop.js index b544921bd..ce292774e 100644 --- a/tests/lib/rules/require-default-prop.js +++ b/tests/lib/rules/require-default-prop.js @@ -21,7 +21,6 @@ const parserOptions = { const ruleTester = new RuleTester({ parserOptions }) ruleTester.run('require-default-prop', rule, { - valid: [ { filename: 'test.vue', @@ -205,25 +204,32 @@ ruleTester.run('require-default-prop', rule, { } } `, - errors: [{ - message: `Prop 'a' requires default value to be set.`, - line: 4 - }, { - message: `Prop 'b' requires default value to be set.`, - line: 5 - }, { - message: `Prop 'c' requires default value to be set.`, - line: 6 - }, { - message: `Prop 'd' requires default value to be set.`, - line: 9 - }, { - message: `Prop 'e' requires default value to be set.`, - line: 13 - }, { - message: `Prop 'f' requires default value to be set.`, - line: 14 - }] + errors: [ + { + message: `Prop 'a' requires default value to be set.`, + line: 4 + }, + { + message: `Prop 'b' requires default value to be set.`, + line: 5 + }, + { + message: `Prop 'c' requires default value to be set.`, + line: 6 + }, + { + message: `Prop 'd' requires default value to be set.`, + line: 9 + }, + { + message: `Prop 'e' requires default value to be set.`, + line: 13 + }, + { + message: `Prop 'f' requires default value to be set.`, + line: 14 + } + ] }, { filename: 'test.vue', @@ -237,10 +243,12 @@ ruleTester.run('require-default-prop', rule, { }); `, parser: require.resolve('@typescript-eslint/parser'), - errors: [{ - message: `Prop 'a' requires default value to be set.`, - line: 4 - }] + errors: [ + { + message: `Prop 'a' requires default value to be set.`, + line: 4 + } + ] }, { filename: 'test.vue', @@ -254,10 +262,12 @@ ruleTester.run('require-default-prop', rule, { }); `, parser: require.resolve('@typescript-eslint/parser'), - errors: [{ - message: `Prop 'a' requires default value to be set.`, - line: 4 - }] + errors: [ + { + message: `Prop 'a' requires default value to be set.`, + line: 4 + } + ] }, // computed propertys @@ -273,19 +283,24 @@ ruleTester.run('require-default-prop', rule, { } }; `, - errors: [{ - message: `Prop 'a' requires default value to be set.`, - line: 4 - }, { - message: `Prop 'b' requires default value to be set.`, - line: 5 - }, { - message: `Prop 'c' requires default value to be set.`, - line: 6 - }, { - message: `Prop 'd' requires default value to be set.`, - line: 7 - }] + errors: [ + { + message: `Prop 'a' requires default value to be set.`, + line: 4 + }, + { + message: `Prop 'b' requires default value to be set.`, + line: 5 + }, + { + message: `Prop 'c' requires default value to be set.`, + line: 6 + }, + { + message: `Prop 'd' requires default value to be set.`, + line: 7 + } + ] }, // unknown static name { @@ -299,16 +314,20 @@ ruleTester.run('require-default-prop', rule, { } }; `, - errors: [{ - message: `Prop '[foo]' requires default value to be set.`, - line: 4 - }, { - message: `Prop '[bar()]' requires default value to be set.`, - line: 5 - }, { - message: `Prop '[baz.baz]' requires default value to be set.`, - line: 6 - }] + errors: [ + { + message: `Prop '[foo]' requires default value to be set.`, + line: 4 + }, + { + message: `Prop '[bar()]' requires default value to be set.`, + line: 5 + }, + { + message: `Prop '[baz.baz]' requires default value to be set.`, + line: 6 + } + ] }, { // https://github.com/vuejs/eslint-plugin-vue/issues/1040 @@ -322,7 +341,7 @@ ruleTester.run('require-default-prop', rule, { } } `, - errors: ['Prop \'foo\' requires default value to be set.'] + errors: ["Prop 'foo' requires default value to be set."] }, { filename: 'unknown-prop-details-test.vue', @@ -335,7 +354,7 @@ ruleTester.run('require-default-prop', rule, { } } `, - errors: ['Prop \'foo\' requires default value to be set.'] + errors: ["Prop 'foo' requires default value to be set."] } ] }) diff --git a/tests/lib/rules/require-explicit-emits.js b/tests/lib/rules/require-explicit-emits.js index 0a084ab43..1db1edb2b 100644 --- a/tests/lib/rules/require-explicit-emits.js +++ b/tests/lib/rules/require-explicit-emits.js @@ -382,7 +382,8 @@ tester.run('require-explicit-emits', rule, { endColumn: 33, suggestions: [ { - desc: 'Add the `emits` option with array syntax and define "foo" event.', + desc: + 'Add the `emits` option with array syntax and define "foo" event.', output: ` `, - errors: [{ messageId: 'expectedLongform', data: { actual: 'v-slot', argument: 'default' }}], + errors: [ + { + messageId: 'expectedLongform', + data: { actual: 'v-slot', argument: 'default' } + } + ], options: [{ default: 'longform' }] }, { @@ -346,7 +396,12 @@ tester.run('v-slot-style', rule, { `, - errors: [{ messageId: 'expectedVSlot', data: { actual: '#default', argument: 'default' }}], + errors: [ + { + messageId: 'expectedVSlot', + data: { actual: '#default', argument: 'default' } + } + ], options: [{ default: 'v-slot' }] }, { @@ -364,7 +419,12 @@ tester.run('v-slot-style', rule, { `, - errors: [{ messageId: 'expectedVSlot', data: { actual: 'v-slot:default', argument: 'default' }}], + errors: [ + { + messageId: 'expectedVSlot', + data: { actual: 'v-slot:default', argument: 'default' } + } + ], options: [{ default: 'v-slot' }] }, @@ -383,7 +443,12 @@ tester.run('v-slot-style', rule, { `, - errors: [{ messageId: 'expectedShorthand', data: { actual: 'v-slot:foo', argument: 'foo' }}] + errors: [ + { + messageId: 'expectedShorthand', + data: { actual: 'v-slot:foo', argument: 'foo' } + } + ] }, { code: ` @@ -400,7 +465,12 @@ tester.run('v-slot-style', rule, { `, - errors: [{ messageId: 'expectedLongform', data: { actual: '#foo', argument: 'foo' }}], + errors: [ + { + messageId: 'expectedLongform', + data: { actual: '#foo', argument: 'foo' } + } + ], options: [{ named: 'longform' }] }, @@ -419,7 +489,12 @@ tester.run('v-slot-style', rule, { `, - errors: [{ messageId: 'expectedShorthand', data: { actual: 'v-slot:[foo]', argument: '[foo]' }}] + errors: [ + { + messageId: 'expectedShorthand', + data: { actual: 'v-slot:[foo]', argument: '[foo]' } + } + ] }, { code: ` @@ -436,7 +511,12 @@ tester.run('v-slot-style', rule, { `, - errors: [{ messageId: 'expectedLongform', data: { actual: '#[foo]', argument: '[foo]' }}], + errors: [ + { + messageId: 'expectedLongform', + data: { actual: '#[foo]', argument: '[foo]' } + } + ], options: [{ named: 'longform' }] } ] diff --git a/tests/lib/rules/valid-template-root.js b/tests/lib/rules/valid-template-root.js index 033188cca..212fefc8d 100644 --- a/tests/lib/rules/valid-template-root.js +++ b/tests/lib/rules/valid-template-root.js @@ -41,11 +41,13 @@ tester.run('valid-template-root', rule, { }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', @@ -57,7 +59,8 @@ tester.run('valid-template-root', rule, { }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', @@ -117,12 +120,16 @@ tester.run('valid-template-root', rule, { { filename: 'test.vue', code: '', - errors: ["The template root with 'src' attribute is required to be empty."] + errors: [ + "The template root with 'src' attribute is required to be empty." + ] }, { filename: 'test.vue', code: '', - errors: ["The template root with 'src' attribute is required to be empty."] + errors: [ + "The template root with 'src' attribute is required to be empty." + ] } ] }) diff --git a/tests/lib/rules/valid-v-bind-sync.js b/tests/lib/rules/valid-v-bind-sync.js index 4f939aa16..385f5d991 100644 --- a/tests/lib/rules/valid-v-bind-sync.js +++ b/tests/lib/rules/valid-v-bind-sync.js @@ -51,51 +51,63 @@ tester.run('valid-v-bind-sync', rule, { }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, // not .sync { @@ -128,12 +140,15 @@ tester.run('valid-v-bind-sync', rule, { `, - errors: [{ - message: "'.sync' modifiers require the attribute value which is valid as LHS.", - line: 3, - column: 24, - endColumn: 41 - }] + errors: [ + { + message: + "'.sync' modifiers require the attribute value which is valid as LHS.", + line: 3, + column: 24, + endColumn: 41 + } + ] }, { filename: 'test.vue', @@ -142,12 +157,15 @@ tester.run('valid-v-bind-sync', rule, { `, - errors: [{ - message: "'.sync' modifiers require the attribute value which is valid as LHS.", - line: 3, - column: 24, - endColumn: 47 - }] + errors: [ + { + message: + "'.sync' modifiers require the attribute value which is valid as LHS.", + line: 3, + column: 24, + endColumn: 47 + } + ] }, { filename: 'test.vue', @@ -156,12 +174,15 @@ tester.run('valid-v-bind-sync', rule, { `, - errors: [{ - message: "'.sync' modifiers aren't supported on non Vue-components.", - line: 3, - column: 18, - endColumn: 33 - }] + errors: [ + { + message: + "'.sync' modifiers aren't supported on non Vue-components.", + line: 3, + column: 18, + endColumn: 33 + } + ] }, { filename: 'test.vue', @@ -170,12 +191,15 @@ tester.run('valid-v-bind-sync', rule, { `, - errors: [{ - message: "'.sync' modifiers require the attribute value which is valid as LHS.", - line: 3, - column: 24, - endColumn: 41 - }] + errors: [ + { + message: + "'.sync' modifiers require the attribute value which is valid as LHS.", + line: 3, + column: 24, + endColumn: 41 + } + ] }, { filename: 'test.vue', @@ -184,12 +208,15 @@ tester.run('valid-v-bind-sync', rule, { `, - errors: [{ - message: "'.sync' modifiers require the attribute value which is valid as LHS.", - line: 3, - column: 24, - endColumn: 46 - }] + errors: [ + { + message: + "'.sync' modifiers require the attribute value which is valid as LHS.", + line: 3, + column: 24, + endColumn: 46 + } + ] }, { filename: 'test.vue', @@ -198,12 +225,15 @@ tester.run('valid-v-bind-sync', rule, { `, - errors: [{ - message: "'.sync' modifiers aren't supported on non Vue-components.", - line: 3, - column: 18, - endColumn: 39 - }] + errors: [ + { + message: + "'.sync' modifiers aren't supported on non Vue-components.", + line: 3, + column: 18, + endColumn: 39 + } + ] }, { filename: 'test.vue', @@ -214,12 +244,15 @@ tester.run('valid-v-bind-sync', rule, {
`, - errors: [{ - message: "'.sync' modifiers cannot update the iteration variable 'x' itself.", - line: 4, - column: 26, - endColumn: 39 - }] + errors: [ + { + message: + "'.sync' modifiers cannot update the iteration variable 'x' itself.", + line: 4, + column: 26, + endColumn: 39 + } + ] }, { filename: 'test.vue', @@ -230,12 +263,15 @@ tester.run('valid-v-bind-sync', rule, {
`, - errors: [{ - message: "'.sync' modifiers cannot update the iteration variable 'e' itself.", - line: 4, - column: 26, - endColumn: 45 - }] + errors: [ + { + message: + "'.sync' modifiers cannot update the iteration variable 'e' itself.", + line: 4, + column: 26, + endColumn: 45 + } + ] }, { filename: 'test.vue', @@ -250,10 +286,13 @@ tester.run('valid-v-bind-sync', rule, {
`, - errors: [{ - message: "'.sync' modifiers cannot update the iteration variable 'e1' itself.", - line: 6 - }] + errors: [ + { + message: + "'.sync' modifiers cannot update the iteration variable 'e1' itself.", + line: 6 + } + ] }, { filename: 'test.vue', @@ -264,10 +303,13 @@ tester.run('valid-v-bind-sync', rule, {
`, - errors: [{ - message: "'.sync' modifiers cannot update the iteration variable 'index' itself.", - line: 4 - }] + errors: [ + { + message: + "'.sync' modifiers cannot update the iteration variable 'index' itself.", + line: 4 + } + ] }, { filename: 'test.vue', @@ -276,17 +318,23 @@ tester.run('valid-v-bind-sync', rule, {
`, - errors: ["'.sync' modifiers aren't supported on
non Vue-components."] + errors: [ + "'.sync' modifiers aren't supported on
non Vue-components." + ] }, { filename: 'test.vue', code: '', - errors: ["'.sync' modifiers require the attribute value which is valid as LHS."] + errors: [ + "'.sync' modifiers require the attribute value which is valid as LHS." + ] }, { filename: 'test.vue', code: '', - errors: ["'.sync' modifiers require the attribute value which is valid as LHS."] + errors: [ + "'.sync' modifiers require the attribute value which is valid as LHS." + ] } ] }) diff --git a/tests/lib/rules/valid-v-else-if.js b/tests/lib/rules/valid-v-else-if.js index b0c18093f..778d07339 100644 --- a/tests/lib/rules/valid-v-else-if.js +++ b/tests/lib/rules/valid-v-else-if.js @@ -29,11 +29,13 @@ tester.run('valid-v-else-if', rule, { }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', @@ -43,57 +45,82 @@ tester.run('valid-v-else-if', rule, { invalid: [ { filename: 'test.vue', - code: '', - errors: ["'v-else-if' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive."] + code: + '', + errors: [ + "'v-else-if' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive." + ] }, { filename: 'test.vue', code: '', - errors: ["'v-else-if' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive."] + errors: [ + "'v-else-if' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive." + ] }, { filename: 'test.vue', code: '', - errors: ["'v-else-if' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive."] + errors: [ + "'v-else-if' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive." + ] }, { filename: 'test.vue', - code: '', - errors: ["'v-else-if' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive."] + code: + '', + errors: [ + "'v-else-if' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive." + ] }, { filename: 'test.vue', - code: '', - errors: ["'v-else-if' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive."] + code: + '', + errors: [ + "'v-else-if' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive." + ] }, { filename: 'test.vue', - code: '', - errors: ["'v-else-if' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive."] + code: + '', + errors: [ + "'v-else-if' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive." + ] }, { filename: 'test.vue', - code: '', - errors: ["'v-else-if' and 'v-if' directives can't exist on the same element."] + code: + '', + errors: [ + "'v-else-if' and 'v-if' directives can't exist on the same element." + ] }, { filename: 'test.vue', - code: '', - errors: ["'v-else-if' and 'v-else' directives can't exist on the same element."] + code: + '', + errors: [ + "'v-else-if' and 'v-else' directives can't exist on the same element." + ] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["'v-else-if' directives require no argument."] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["'v-else-if' directives require no modifier."] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["'v-else-if' directives require that attribute value."] } ] diff --git a/tests/lib/rules/valid-v-else.js b/tests/lib/rules/valid-v-else.js index 7825e4dfb..1e235f9b5 100644 --- a/tests/lib/rules/valid-v-else.js +++ b/tests/lib/rules/valid-v-else.js @@ -29,11 +29,13 @@ tester.run('valid-v-else', rule, { }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', @@ -44,56 +46,79 @@ tester.run('valid-v-else', rule, { { filename: 'test.vue', code: '', - errors: ["'v-else' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive."] + errors: [ + "'v-else' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive." + ] }, { filename: 'test.vue', code: '', - errors: ["'v-else' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive."] + errors: [ + "'v-else' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive." + ] }, { filename: 'test.vue', code: '', - errors: ["'v-else' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive."] + errors: [ + "'v-else' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive." + ] }, { filename: 'test.vue', code: '', - errors: ["'v-else' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive."] + errors: [ + "'v-else' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive." + ] }, { filename: 'test.vue', - code: '', - errors: ["'v-else' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive."] + code: + '', + errors: [ + "'v-else' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive." + ] }, { filename: 'test.vue', - code: '', - errors: ["'v-else' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive."] + code: + '', + errors: [ + "'v-else' directives require being preceded by the element which has a 'v-if' or 'v-else-if' directive." + ] }, { filename: 'test.vue', - code: '', - errors: ["'v-else' and 'v-if' directives can't exist on the same element. You may want 'v-else-if' directives."] + code: + '', + errors: [ + "'v-else' and 'v-if' directives can't exist on the same element. You may want 'v-else-if' directives." + ] }, { filename: 'test.vue', - code: '', - errors: ["'v-else' and 'v-else-if' directives can't exist on the same element."] + code: + '', + errors: [ + "'v-else' and 'v-else-if' directives can't exist on the same element." + ] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["'v-else' directives require no argument."] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["'v-else' directives require no modifier."] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["'v-else' directives require no attribute value."] } ] diff --git a/tests/lib/rules/valid-v-for.js b/tests/lib/rules/valid-v-for.js index d83b634a3..74a1ea614 100644 --- a/tests/lib/rules/valid-v-for.js +++ b/tests/lib/rules/valid-v-for.js @@ -37,55 +37,68 @@ tester.run('valid-v-for', rule, { }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', - code: '' + code: + '' }, { filename: 'test.vue', @@ -134,92 +147,123 @@ tester.run('valid-v-for', rule, { }, { filename: 'test.vue', - code: '', + code: + '', errors: ["Invalid alias ''."] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["Invalid alias ''."] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["Invalid alias ''."] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["Invalid alias '{b,c}'."] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["Invalid alias '{c,d}'."] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["Custom elements in iteration require 'v-bind:key' directives."] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["Custom elements in iteration require 'v-bind:key' directives."] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["Custom elements in iteration require 'v-bind:key' directives."] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["Custom elements in iteration require 'v-bind:key' directives."] }, { filename: 'test.vue', - code: '', - errors: ["Expected 'v-bind:key' directive to use the variables which are defined by the 'v-for' directive."] + code: + '', + errors: [ + "Expected 'v-bind:key' directive to use the variables which are defined by the 'v-for' directive." + ] }, { filename: 'test.vue', - code: '', - errors: ["Expected 'v-bind:key' directive to use the variables which are defined by the 'v-for' directive."] + code: + '', + errors: [ + "Expected 'v-bind:key' directive to use the variables which are defined by the 'v-for' directive." + ] }, { filename: 'test.vue', - code: '', - errors: ["Expected 'v-bind:key' directive to use the variables which are defined by the 'v-for' directive."] + code: + '', + errors: [ + "Expected 'v-bind:key' directive to use the variables which are defined by the 'v-for' directive." + ] }, { filename: 'test.vue', - code: '', - errors: ["Expected 'v-bind:key' directive to use the variables which are defined by the 'v-for' directive."] + code: + '', + errors: [ + "Expected 'v-bind:key' directive to use the variables which are defined by the 'v-for' directive." + ] }, { filename: 'test.vue', - code: '', - errors: ["Expected 'v-bind:key' directive to use the variables which are defined by the 'v-for' directive."] + code: + '', + errors: [ + "Expected 'v-bind:key' directive to use the variables which are defined by the 'v-for' directive." + ] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["Custom elements in iteration require 'v-bind:key' directives."] }, { filename: 'test.vue', - code: '', + code: + '', errors: ["'v-for' directives require that attribute value."] }, { filename: 'test.vue', - code: '', - errors: ["Expected 'v-bind:key' directive to use the variables which are defined by the 'v-for' directive."] + code: + '', + errors: [ + "Expected 'v-bind:key' directive to use the variables which are defined by the 'v-for' directive." + ] }, { filename: 'test.vue', - errors: ["Expected 'v-bind:key' directive to use the variables which are defined by the 'v-for' directive."], + errors: [ + "Expected 'v-bind:key' directive to use the variables which are defined by the 'v-for' directive." + ], code: `