diff --git a/.changeset/brown-eels-care.md b/.changeset/brown-eels-care.md new file mode 100644 index 000000000..6d26027f0 --- /dev/null +++ b/.changeset/brown-eels-care.md @@ -0,0 +1,5 @@ +--- +"eslint-plugin-vue": minor +--- + +Use `error` instead of `warn` in configs when `VUE_ESLINT_ALWAYS_ERROR` env variable is `"true"` diff --git a/docs/user-guide/index.md b/docs/user-guide/index.md index 103471f61..4d8e40b24 100644 --- a/docs/user-guide/index.md +++ b/docs/user-guide/index.md @@ -73,6 +73,8 @@ You can use the following configs by adding them to `eslint.config.js`. :::warning Reporting rules By default, all rules from **base** and **essential** categories report ESLint errors. Other rules - because they're not covering potential bugs in the application - report warnings. What does it mean? By default - nothing, but if you want - you can set up a threshold and break the build after a certain amount of warnings, instead of any. More information [here](https://eslint.org/docs/user-guide/command-line-interface#handling-warnings). + +Alternatively, you can set `process.env.VUE_ESLINT_ALWAYS_ERROR` to `true` in your configuration file to have `error` be used by all rules. ::: #### Specifying Globals (`eslint.config.js`) diff --git a/lib/configs/flat/vue2-recommended.js b/lib/configs/flat/vue2-recommended.js index 8a972bf3d..8dfcec9dd 100644 --- a/lib/configs/flat/vue2-recommended.js +++ b/lib/configs/flat/vue2-recommended.js @@ -6,19 +6,22 @@ 'use strict' const config = require('./vue2-strongly-recommended.js') +const ruleLevel = + process.env.VUE_ESLINT_ALWAYS_ERROR === 'true' ? 'error' : 'warn' + module.exports = [ ...config, { name: 'vue/vue2-recommended/rules', rules: { - 'vue/attributes-order': 'warn', - 'vue/block-order': 'warn', - 'vue/no-lone-template': 'warn', - 'vue/no-multiple-slot-args': 'warn', - 'vue/no-required-prop-with-default': 'warn', - 'vue/no-v-html': 'warn', - 'vue/order-in-components': 'warn', - 'vue/this-in-template': 'warn' + 'vue/attributes-order': ruleLevel, + 'vue/block-order': ruleLevel, + 'vue/no-lone-template': ruleLevel, + 'vue/no-multiple-slot-args': ruleLevel, + 'vue/no-required-prop-with-default': ruleLevel, + 'vue/no-v-html': ruleLevel, + 'vue/order-in-components': ruleLevel, + 'vue/this-in-template': ruleLevel } } ] diff --git a/lib/configs/flat/vue2-strongly-recommended.js b/lib/configs/flat/vue2-strongly-recommended.js index e4913f40c..d05f5feb6 100644 --- a/lib/configs/flat/vue2-strongly-recommended.js +++ b/lib/configs/flat/vue2-strongly-recommended.js @@ -6,34 +6,37 @@ 'use strict' const config = require('./vue2-essential.js') +const ruleLevel = + process.env.VUE_ESLINT_ALWAYS_ERROR === 'true' ? 'error' : 'warn' + module.exports = [ ...config, { name: 'vue/vue2-strongly-recommended/rules', rules: { - 'vue/attribute-hyphenation': 'warn', - 'vue/component-definition-name-casing': 'warn', - 'vue/first-attribute-linebreak': 'warn', - 'vue/html-closing-bracket-newline': 'warn', - 'vue/html-closing-bracket-spacing': 'warn', - 'vue/html-end-tags': 'warn', - 'vue/html-indent': 'warn', - 'vue/html-quotes': 'warn', - 'vue/html-self-closing': 'warn', - 'vue/max-attributes-per-line': 'warn', - 'vue/multiline-html-element-content-newline': 'warn', - 'vue/mustache-interpolation-spacing': 'warn', - 'vue/no-multi-spaces': 'warn', - 'vue/no-spaces-around-equal-signs-in-attribute': 'warn', - 'vue/no-template-shadow': 'warn', - 'vue/one-component-per-file': 'warn', - 'vue/prop-name-casing': 'warn', - 'vue/require-default-prop': 'warn', - 'vue/require-prop-types': 'warn', - 'vue/singleline-html-element-content-newline': 'warn', - 'vue/v-bind-style': 'warn', - 'vue/v-on-style': 'warn', - 'vue/v-slot-style': 'warn' + 'vue/attribute-hyphenation': ruleLevel, + 'vue/component-definition-name-casing': ruleLevel, + 'vue/first-attribute-linebreak': ruleLevel, + 'vue/html-closing-bracket-newline': ruleLevel, + 'vue/html-closing-bracket-spacing': ruleLevel, + 'vue/html-end-tags': ruleLevel, + 'vue/html-indent': ruleLevel, + 'vue/html-quotes': ruleLevel, + 'vue/html-self-closing': ruleLevel, + 'vue/max-attributes-per-line': ruleLevel, + 'vue/multiline-html-element-content-newline': ruleLevel, + 'vue/mustache-interpolation-spacing': ruleLevel, + 'vue/no-multi-spaces': ruleLevel, + 'vue/no-spaces-around-equal-signs-in-attribute': ruleLevel, + 'vue/no-template-shadow': ruleLevel, + 'vue/one-component-per-file': ruleLevel, + 'vue/prop-name-casing': ruleLevel, + 'vue/require-default-prop': ruleLevel, + 'vue/require-prop-types': ruleLevel, + 'vue/singleline-html-element-content-newline': ruleLevel, + 'vue/v-bind-style': ruleLevel, + 'vue/v-on-style': ruleLevel, + 'vue/v-slot-style': ruleLevel } } ] diff --git a/lib/configs/flat/vue3-recommended.js b/lib/configs/flat/vue3-recommended.js index 21be71a8d..f46bc901a 100644 --- a/lib/configs/flat/vue3-recommended.js +++ b/lib/configs/flat/vue3-recommended.js @@ -6,19 +6,22 @@ 'use strict' const config = require('./vue3-strongly-recommended.js') +const ruleLevel = + process.env.VUE_ESLINT_ALWAYS_ERROR === 'true' ? 'error' : 'warn' + module.exports = [ ...config, { name: 'vue/recommended/rules', rules: { - 'vue/attributes-order': 'warn', - 'vue/block-order': 'warn', - 'vue/no-lone-template': 'warn', - 'vue/no-multiple-slot-args': 'warn', - 'vue/no-required-prop-with-default': 'warn', - 'vue/no-v-html': 'warn', - 'vue/order-in-components': 'warn', - 'vue/this-in-template': 'warn' + 'vue/attributes-order': ruleLevel, + 'vue/block-order': ruleLevel, + 'vue/no-lone-template': ruleLevel, + 'vue/no-multiple-slot-args': ruleLevel, + 'vue/no-required-prop-with-default': ruleLevel, + 'vue/no-v-html': ruleLevel, + 'vue/order-in-components': ruleLevel, + 'vue/this-in-template': ruleLevel } } ] diff --git a/lib/configs/flat/vue3-strongly-recommended.js b/lib/configs/flat/vue3-strongly-recommended.js index fee1d3bb8..48db1aa90 100644 --- a/lib/configs/flat/vue3-strongly-recommended.js +++ b/lib/configs/flat/vue3-strongly-recommended.js @@ -6,42 +6,45 @@ 'use strict' const config = require('./vue3-essential.js') +const ruleLevel = + process.env.VUE_ESLINT_ALWAYS_ERROR === 'true' ? 'error' : 'warn' + module.exports = [ ...config, { name: 'vue/strongly-recommended/rules', rules: { - 'vue/attribute-hyphenation': 'warn', - 'vue/component-definition-name-casing': 'warn', - 'vue/first-attribute-linebreak': 'warn', - 'vue/html-closing-bracket-newline': 'warn', - 'vue/html-closing-bracket-spacing': 'warn', - 'vue/html-end-tags': 'warn', - 'vue/html-indent': 'warn', - 'vue/html-quotes': 'warn', - 'vue/html-self-closing': 'warn', - 'vue/max-attributes-per-line': 'warn', - 'vue/multiline-html-element-content-newline': 'warn', - 'vue/mustache-interpolation-spacing': 'warn', - 'vue/no-multi-spaces': 'warn', - 'vue/no-spaces-around-equal-signs-in-attribute': 'warn', - 'vue/no-template-shadow': 'warn', - 'vue/one-component-per-file': 'warn', - 'vue/prop-name-casing': 'warn', - 'vue/require-default-prop': 'warn', - 'vue/require-explicit-emits': 'warn', - 'vue/require-prop-types': 'warn', - 'vue/singleline-html-element-content-newline': 'warn', - 'vue/v-bind-style': 'warn', + 'vue/attribute-hyphenation': ruleLevel, + 'vue/component-definition-name-casing': ruleLevel, + 'vue/first-attribute-linebreak': ruleLevel, + 'vue/html-closing-bracket-newline': ruleLevel, + 'vue/html-closing-bracket-spacing': ruleLevel, + 'vue/html-end-tags': ruleLevel, + 'vue/html-indent': ruleLevel, + 'vue/html-quotes': ruleLevel, + 'vue/html-self-closing': ruleLevel, + 'vue/max-attributes-per-line': ruleLevel, + 'vue/multiline-html-element-content-newline': ruleLevel, + 'vue/mustache-interpolation-spacing': ruleLevel, + 'vue/no-multi-spaces': ruleLevel, + 'vue/no-spaces-around-equal-signs-in-attribute': ruleLevel, + 'vue/no-template-shadow': ruleLevel, + 'vue/one-component-per-file': ruleLevel, + 'vue/prop-name-casing': ruleLevel, + 'vue/require-default-prop': ruleLevel, + 'vue/require-explicit-emits': ruleLevel, + 'vue/require-prop-types': ruleLevel, + 'vue/singleline-html-element-content-newline': ruleLevel, + 'vue/v-bind-style': ruleLevel, 'vue/v-on-event-hyphenation': [ - 'warn', + ruleLevel, 'always', { autofix: true } ], - 'vue/v-on-style': 'warn', - 'vue/v-slot-style': 'warn' + 'vue/v-on-style': ruleLevel, + 'vue/v-slot-style': ruleLevel } } ] diff --git a/lib/configs/vue2-recommended.js b/lib/configs/vue2-recommended.js index 9892867c1..a9957d27d 100644 --- a/lib/configs/vue2-recommended.js +++ b/lib/configs/vue2-recommended.js @@ -3,16 +3,19 @@ * This file has been automatically generated, * in order to update its content execute "npm run update" */ +const ruleLevel = + process.env.VUE_ESLINT_ALWAYS_ERROR === 'true' ? 'error' : 'warn' + module.exports = { extends: require.resolve('./vue2-strongly-recommended'), rules: { - 'vue/attributes-order': 'warn', - 'vue/block-order': 'warn', - 'vue/no-lone-template': 'warn', - 'vue/no-multiple-slot-args': 'warn', - 'vue/no-required-prop-with-default': 'warn', - 'vue/no-v-html': 'warn', - 'vue/order-in-components': 'warn', - 'vue/this-in-template': 'warn' + 'vue/attributes-order': ruleLevel, + 'vue/block-order': ruleLevel, + 'vue/no-lone-template': ruleLevel, + 'vue/no-multiple-slot-args': ruleLevel, + 'vue/no-required-prop-with-default': ruleLevel, + 'vue/no-v-html': ruleLevel, + 'vue/order-in-components': ruleLevel, + 'vue/this-in-template': ruleLevel } } diff --git a/lib/configs/vue2-strongly-recommended.js b/lib/configs/vue2-strongly-recommended.js index e7b0f3dc7..47ca2ca7f 100644 --- a/lib/configs/vue2-strongly-recommended.js +++ b/lib/configs/vue2-strongly-recommended.js @@ -3,31 +3,34 @@ * This file has been automatically generated, * in order to update its content execute "npm run update" */ +const ruleLevel = + process.env.VUE_ESLINT_ALWAYS_ERROR === 'true' ? 'error' : 'warn' + module.exports = { extends: require.resolve('./vue2-essential'), rules: { - 'vue/attribute-hyphenation': 'warn', - 'vue/component-definition-name-casing': 'warn', - 'vue/first-attribute-linebreak': 'warn', - 'vue/html-closing-bracket-newline': 'warn', - 'vue/html-closing-bracket-spacing': 'warn', - 'vue/html-end-tags': 'warn', - 'vue/html-indent': 'warn', - 'vue/html-quotes': 'warn', - 'vue/html-self-closing': 'warn', - 'vue/max-attributes-per-line': 'warn', - 'vue/multiline-html-element-content-newline': 'warn', - 'vue/mustache-interpolation-spacing': 'warn', - 'vue/no-multi-spaces': 'warn', - 'vue/no-spaces-around-equal-signs-in-attribute': 'warn', - 'vue/no-template-shadow': 'warn', - 'vue/one-component-per-file': 'warn', - 'vue/prop-name-casing': 'warn', - 'vue/require-default-prop': 'warn', - 'vue/require-prop-types': 'warn', - 'vue/singleline-html-element-content-newline': 'warn', - 'vue/v-bind-style': 'warn', - 'vue/v-on-style': 'warn', - 'vue/v-slot-style': 'warn' + 'vue/attribute-hyphenation': ruleLevel, + 'vue/component-definition-name-casing': ruleLevel, + 'vue/first-attribute-linebreak': ruleLevel, + 'vue/html-closing-bracket-newline': ruleLevel, + 'vue/html-closing-bracket-spacing': ruleLevel, + 'vue/html-end-tags': ruleLevel, + 'vue/html-indent': ruleLevel, + 'vue/html-quotes': ruleLevel, + 'vue/html-self-closing': ruleLevel, + 'vue/max-attributes-per-line': ruleLevel, + 'vue/multiline-html-element-content-newline': ruleLevel, + 'vue/mustache-interpolation-spacing': ruleLevel, + 'vue/no-multi-spaces': ruleLevel, + 'vue/no-spaces-around-equal-signs-in-attribute': ruleLevel, + 'vue/no-template-shadow': ruleLevel, + 'vue/one-component-per-file': ruleLevel, + 'vue/prop-name-casing': ruleLevel, + 'vue/require-default-prop': ruleLevel, + 'vue/require-prop-types': ruleLevel, + 'vue/singleline-html-element-content-newline': ruleLevel, + 'vue/v-bind-style': ruleLevel, + 'vue/v-on-style': ruleLevel, + 'vue/v-slot-style': ruleLevel } } diff --git a/lib/configs/vue3-recommended.js b/lib/configs/vue3-recommended.js index 083f6c65b..1346a6da3 100644 --- a/lib/configs/vue3-recommended.js +++ b/lib/configs/vue3-recommended.js @@ -3,16 +3,19 @@ * This file has been automatically generated, * in order to update its content execute "npm run update" */ +const ruleLevel = + process.env.VUE_ESLINT_ALWAYS_ERROR === 'true' ? 'error' : 'warn' + module.exports = { extends: require.resolve('./vue3-strongly-recommended'), rules: { - 'vue/attributes-order': 'warn', - 'vue/block-order': 'warn', - 'vue/no-lone-template': 'warn', - 'vue/no-multiple-slot-args': 'warn', - 'vue/no-required-prop-with-default': 'warn', - 'vue/no-v-html': 'warn', - 'vue/order-in-components': 'warn', - 'vue/this-in-template': 'warn' + 'vue/attributes-order': ruleLevel, + 'vue/block-order': ruleLevel, + 'vue/no-lone-template': ruleLevel, + 'vue/no-multiple-slot-args': ruleLevel, + 'vue/no-required-prop-with-default': ruleLevel, + 'vue/no-v-html': ruleLevel, + 'vue/order-in-components': ruleLevel, + 'vue/this-in-template': ruleLevel } } diff --git a/lib/configs/vue3-strongly-recommended.js b/lib/configs/vue3-strongly-recommended.js index a3f854fc4..6b984eb4f 100644 --- a/lib/configs/vue3-strongly-recommended.js +++ b/lib/configs/vue3-strongly-recommended.js @@ -3,39 +3,42 @@ * This file has been automatically generated, * in order to update its content execute "npm run update" */ +const ruleLevel = + process.env.VUE_ESLINT_ALWAYS_ERROR === 'true' ? 'error' : 'warn' + module.exports = { extends: require.resolve('./vue3-essential'), rules: { - 'vue/attribute-hyphenation': 'warn', - 'vue/component-definition-name-casing': 'warn', - 'vue/first-attribute-linebreak': 'warn', - 'vue/html-closing-bracket-newline': 'warn', - 'vue/html-closing-bracket-spacing': 'warn', - 'vue/html-end-tags': 'warn', - 'vue/html-indent': 'warn', - 'vue/html-quotes': 'warn', - 'vue/html-self-closing': 'warn', - 'vue/max-attributes-per-line': 'warn', - 'vue/multiline-html-element-content-newline': 'warn', - 'vue/mustache-interpolation-spacing': 'warn', - 'vue/no-multi-spaces': 'warn', - 'vue/no-spaces-around-equal-signs-in-attribute': 'warn', - 'vue/no-template-shadow': 'warn', - 'vue/one-component-per-file': 'warn', - 'vue/prop-name-casing': 'warn', - 'vue/require-default-prop': 'warn', - 'vue/require-explicit-emits': 'warn', - 'vue/require-prop-types': 'warn', - 'vue/singleline-html-element-content-newline': 'warn', - 'vue/v-bind-style': 'warn', + 'vue/attribute-hyphenation': ruleLevel, + 'vue/component-definition-name-casing': ruleLevel, + 'vue/first-attribute-linebreak': ruleLevel, + 'vue/html-closing-bracket-newline': ruleLevel, + 'vue/html-closing-bracket-spacing': ruleLevel, + 'vue/html-end-tags': ruleLevel, + 'vue/html-indent': ruleLevel, + 'vue/html-quotes': ruleLevel, + 'vue/html-self-closing': ruleLevel, + 'vue/max-attributes-per-line': ruleLevel, + 'vue/multiline-html-element-content-newline': ruleLevel, + 'vue/mustache-interpolation-spacing': ruleLevel, + 'vue/no-multi-spaces': ruleLevel, + 'vue/no-spaces-around-equal-signs-in-attribute': ruleLevel, + 'vue/no-template-shadow': ruleLevel, + 'vue/one-component-per-file': ruleLevel, + 'vue/prop-name-casing': ruleLevel, + 'vue/require-default-prop': ruleLevel, + 'vue/require-explicit-emits': ruleLevel, + 'vue/require-prop-types': ruleLevel, + 'vue/singleline-html-element-content-newline': ruleLevel, + 'vue/v-bind-style': ruleLevel, 'vue/v-on-event-hyphenation': [ - 'warn', + ruleLevel, 'always', { autofix: true } ], - 'vue/v-on-style': 'warn', - 'vue/v-slot-style': 'warn' + 'vue/v-on-style': ruleLevel, + 'vue/v-slot-style': ruleLevel } } diff --git a/tools/update-lib-configs.js b/tools/update-lib-configs.js index 0c2845e45..d7e857e50 100644 --- a/tools/update-lib-configs.js +++ b/tools/update-lib-configs.js @@ -44,17 +44,24 @@ function formatRules(rules, categoryId) { return [rule.ruleId, options] }) ) - return JSON.stringify(obj, null, 2) + // use the ruleLevel variable for rules set to warn so that they can + // be made to error with an env variable if desired + return JSON.stringify(obj, null, 2).replaceAll('"warn"', 'ruleLevel') } function formatCategory(category) { const extendsCategoryId = extendsCategories[category.categoryId] + const formattedRules = formatRules(category.rules, category.categoryId) + const ruleLevelVariable = formattedRules.includes('ruleLevel') + ? "\nconst ruleLevel = process.env.VUE_ESLINT_ALWAYS_ERROR === 'true' ? 'error' : 'warn'\n" + : '' + if (extendsCategoryId == null) { return `/* * IMPORTANT! * This file has been automatically generated, * in order to update its content execute "npm run update" - */ + */${ruleLevelVariable} module.exports = { parserOptions: { ecmaVersion: 'latest', @@ -63,7 +70,7 @@ module.exports = { plugins: [ 'vue' ], - rules: ${formatRules(category.rules, category.categoryId)}, + rules: ${formattedRules}, overrides: [ { files: '*.vue', @@ -77,10 +84,10 @@ module.exports = { * IMPORTANT! * This file has been automatically generated, * in order to update its content execute "npm run update" - */ + */${ruleLevelVariable} module.exports = { extends: require.resolve('./${extendsCategoryId}'), - rules: ${formatRules(category.rules, category.categoryId)} + rules: ${formattedRules} } ` } diff --git a/tools/update-lib-flat-configs.js b/tools/update-lib-flat-configs.js index e55fb2d01..6894f00d6 100644 --- a/tools/update-lib-flat-configs.js +++ b/tools/update-lib-flat-configs.js @@ -44,17 +44,24 @@ function formatRules(rules, categoryId) { return [rule.ruleId, options] }) ) - return JSON.stringify(obj, null, 2) + // use the ruleLevel variable for rules set to warn so that they can + // be made to error with an env variable if desired + return JSON.stringify(obj, null, 2).replaceAll('"warn"', 'ruleLevel') } function formatCategory(category) { const extendsCategoryId = extendsCategories[category.categoryId] + const formattedRules = formatRules(category.rules, category.categoryId) + const ruleLevelVariable = formattedRules.includes('ruleLevel') + ? "\nconst ruleLevel = process.env.VUE_ESLINT_ALWAYS_ERROR === 'true' ? 'error' : 'warn'\n" + : '' + if (category.categoryId === 'base') { return `/* * IMPORTANT! * This file has been automatically generated, * in order to update its content execute "npm run update" - */ + */${ruleLevelVariable} module.exports = [ { name: 'vue/base/setup', @@ -79,7 +86,7 @@ module.exports = [ parser: require('vue-eslint-parser'), sourceType: 'module', }, - rules: ${formatRules(category.rules, category.categoryId)}, + rules: ${formattedRules}, processor: 'vue/vue' } ] @@ -93,11 +100,13 @@ module.exports = [ 'use strict' const config = require('./${extendsCategoryId}.js') +${ruleLevelVariable} + module.exports = [ ...config, { name: 'vue/${category.categoryId.replace(/^vue3-/u, '')}/rules', - rules: ${formatRules(category.rules, category.categoryId)}, + rules: ${formattedRules}, } ] `
Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.
Alternative Proxies: