From 48107fbf2f6071536df3a68b8d03374a21065780 Mon Sep 17 00:00:00 2001 From: Armano Date: Mon, 14 Aug 2017 11:56:06 +0200 Subject: [PATCH 1/2] Add `mustache-curly-spacing` rule. fixes #150 --- docs/rules/mustache-curly-spacing.md | 67 +++++++++ lib/rules/mustache-curly-spacing.js | 89 ++++++++++++ tests/lib/rules/mustache-curly-spacing.js | 168 ++++++++++++++++++++++ 3 files changed, 324 insertions(+) create mode 100644 docs/rules/mustache-curly-spacing.md create mode 100644 lib/rules/mustache-curly-spacing.js create mode 100644 tests/lib/rules/mustache-curly-spacing.js diff --git a/docs/rules/mustache-curly-spacing.md b/docs/rules/mustache-curly-spacing.md new file mode 100644 index 000000000..97a9d3ee1 --- /dev/null +++ b/docs/rules/mustache-curly-spacing.md @@ -0,0 +1,67 @@ +# Enforce spacing on the style of mustache curly brackets. (mustache-curly-spacing) + +- :wrench: The `--fix` option on the [command line](http://eslint.org/docs/user-guide/command-line-interface#fix) can automatically fix some of the problems reported by this rule. + +## :book: Rule Details + +This rule aims to enforce unified spacing of curly brackets. + +:-1: Examples of **incorrect** code for this rule: + +```html + +``` + +:+1: Examples of **correct** code for this rule: + +```html + +``` + +## :wrench: Options + +Default spacing is set to `always` + +``` +'vue/mustache-curly-spacing': [2, 'always'|'never'] +``` + +### `"always"` - Expect one space between expression and curly brackets. + +:+1: Examples of **correct** code`: + +```html + +``` + +:-1: Examples of **incorrect** code`: + +```html + +``` + +### `"never"` - Expect no spaces between expression and curly brackets. + +:+1: Examples of **correct** code`: + +```html + +``` + +:-1: Examples of **incorrect** code`: + +```html + +``` diff --git a/lib/rules/mustache-curly-spacing.js b/lib/rules/mustache-curly-spacing.js new file mode 100644 index 000000000..20c3fed7e --- /dev/null +++ b/lib/rules/mustache-curly-spacing.js @@ -0,0 +1,89 @@ +/** + * @fileoverview Enforce spacing on the style of mustache curly brackets. + * @author Armano + */ +'use strict' + +// ------------------------------------------------------------------------------ +// Requirements +// ------------------------------------------------------------------------------ + +const utils = require('../utils') + +// ------------------------------------------------------------------------------ +// Rule Definition +// ------------------------------------------------------------------------------ + +module.exports = { + meta: { + docs: { + description: 'Enforce spacing on the style of mustache curly brackets.', + category: 'Stylistic Issues', + recommended: false + }, + fixable: 'whitespace', + schema: [ + { + enum: ['always', 'never'] + } + ] + }, + + create (context) { + const options = context.options[0] + const optSpaces = options !== 'never' + const template = context.parserServices.getTemplateBodyTokenStore && context.parserServices.getTemplateBodyTokenStore() + + // ---------------------------------------------------------------------- + // Helpers + // ---------------------------------------------------------------------- + + function checkTokens (leftToken, rightToken) { + if (leftToken.loc.end.line === rightToken.loc.start.line) { + const spaces = rightToken.loc.start.column - leftToken.loc.end.column + if (optSpaces === (spaces === 0)) { + context.report({ + node: rightToken, + loc: { + start: leftToken.loc.end, + end: rightToken.loc.start + }, + message: 'Found {{spaces}} whitespaces, {{type}} expected.', + data: { + spaces: spaces === 0 ? 'none' : spaces, + type: optSpaces ? '1' : 'none' + }, + fix: (fixer) => fixer.replaceTextRange([leftToken.range[1], rightToken.range[0]], optSpaces ? ' ' : '') + }) + } + } + } + + // ---------------------------------------------------------------------- + // Public + // ---------------------------------------------------------------------- + + utils.registerTemplateBodyVisitor(context, { + 'VExpressionContainer[expression!=null]' (node) { + const tokens = template.getTokens(node, { + includeComments: true, + filter: token => token.type !== 'HTMLWhitespace' // When there is only whitespace between ignore it + }) + + const startToken = tokens.shift() + if (!startToken || startToken.type !== 'VExpressionStart') return + const endToken = tokens.pop() + if (!endToken || endToken.type !== 'VExpressionEnd') return + + if (tokens.length > 0) { + checkTokens(startToken, tokens[0]) + checkTokens(tokens[tokens.length - 1], endToken) + } else { + checkTokens(startToken, endToken) + } + } + }) + + return { } + } +} diff --git a/tests/lib/rules/mustache-curly-spacing.js b/tests/lib/rules/mustache-curly-spacing.js new file mode 100644 index 000000000..d6442cd1a --- /dev/null +++ b/tests/lib/rules/mustache-curly-spacing.js @@ -0,0 +1,168 @@ +/** + * @fileoverview Enforce spacing on the style of mustache curly brackets. + * @author Armano + */ +'use strict' + +// ------------------------------------------------------------------------------ +// Requirements +// ------------------------------------------------------------------------------ + +const rule = require('../../../lib/rules/mustache-curly-spacing') +const RuleTester = require('eslint').RuleTester + +// ------------------------------------------------------------------------------ +// Tests +// ------------------------------------------------------------------------------ + +const ruleTester = new RuleTester({ + parser: 'vue-eslint-parser', + parserOptions: { ecmaVersion: 2015 } +}) + +ruleTester.run('mustache-curly-spacing', rule, { + + valid: [ + { + filename: 'test.vue', + code: '' + }, + { + filename: 'test.vue', + code: '' + }, + { + filename: 'test.vue', + code: '' + }, + { + filename: 'test.vue', + code: '' + }, + { + filename: 'test.vue', + code: '' + }, + { + filename: 'test.vue', + code: '' + }, + { + filename: 'test.vue', + code: '', + options: ['always'] + }, + { + filename: 'test.vue', + code: '', + options: ['never'] + }, + { + filename: 'test.vue', + code: '', + options: ['never'] + }, + { + filename: 'test.vue', + code: '', + options: ['always'] + }, + { + filename: 'test.vue', + code: '', + options: ['always'] + }, + { + filename: 'test.vue', + code: '', + options: ['never'] + }, + { + filename: 'test.vue', + code: '', + options: ['always'] + } + ], + + invalid: [ + { + filename: 'test.vue', + code: '', + output: '', + options: ['always'], + errors: [{ + message: 'Found none whitespaces, 1 expected.', + type: 'VExpressionEnd' + }] + }, + { + filename: 'test.vue', + code: '', + output: '', + options: ['always'], + errors: [{ + message: 'Found none whitespaces, 1 expected.', + type: 'Identifier' + }] + }, + { + filename: 'test.vue', + code: '', + output: '', + options: ['never'], + errors: [{ + message: 'Found 1 whitespaces, none expected.', + type: 'Identifier' + }] + }, + { + filename: 'test.vue', + code: '', + output: '', + options: ['never'], + errors: [{ + message: 'Found 1 whitespaces, none expected.', + type: 'VExpressionEnd' + }] + }, + { + filename: 'test.vue', + code: '', + output: '', + options: ['always'], + errors: [{ + message: 'Found none whitespaces, 1 expected.', + type: 'Identifier' + }, { + message: 'Found none whitespaces, 1 expected.', + type: 'VExpressionEnd' + }] + }, + { + filename: 'test.vue', + code: '', + output: '', + options: ['never'], + errors: [{ + message: 'Found 1 whitespaces, none expected.', + type: 'Identifier' + }, { + message: 'Found 1 whitespaces, none expected.', + type: 'VExpressionEnd' + }] + }, + { + filename: 'test.vue', + code: '', + output: '', + options: ['never'], + errors: [{ + message: 'Found 3 whitespaces, none expected.', + type: 'Identifier' + }, { + message: 'Found 3 whitespaces, none expected.', + type: 'VExpressionEnd' + }] + } + ] +}) From 64ce055258b88e0861cc0f6f92fab92804b65300 Mon Sep 17 00:00:00 2001 From: Armano Date: Tue, 15 Aug 2017 13:52:09 +0200 Subject: [PATCH 2/2] Rename mustache-curly-spacing to mustache-interpolation-spacing --- ...curly-spacing.md => mustache-interpolation-spacing.md} | 6 +++--- ...curly-spacing.js => mustache-interpolation-spacing.js} | 8 +++++--- ...curly-spacing.js => mustache-interpolation-spacing.js} | 6 +++--- 3 files changed, 11 insertions(+), 9 deletions(-) rename docs/rules/{mustache-curly-spacing.md => mustache-interpolation-spacing.md} (82%) rename lib/rules/{mustache-curly-spacing.js => mustache-interpolation-spacing.js} (92%) rename tests/lib/rules/{mustache-curly-spacing.js => mustache-interpolation-spacing.js} (95%) diff --git a/docs/rules/mustache-curly-spacing.md b/docs/rules/mustache-interpolation-spacing.md similarity index 82% rename from docs/rules/mustache-curly-spacing.md rename to docs/rules/mustache-interpolation-spacing.md index 97a9d3ee1..4844d15ab 100644 --- a/docs/rules/mustache-curly-spacing.md +++ b/docs/rules/mustache-interpolation-spacing.md @@ -1,10 +1,10 @@ -# Enforce spacing on the style of mustache curly brackets. (mustache-curly-spacing) +# enforce unified spacing in mustache interpolations. (mustache-interpolation-spacing) - :wrench: The `--fix` option on the [command line](http://eslint.org/docs/user-guide/command-line-interface#fix) can automatically fix some of the problems reported by this rule. ## :book: Rule Details -This rule aims to enforce unified spacing of curly brackets. +This rule aims to enforce unified spacing in mustache interpolations. :-1: Examples of **incorrect** code for this rule: @@ -27,7 +27,7 @@ This rule aims to enforce unified spacing of curly brackets. Default spacing is set to `always` ``` -'vue/mustache-curly-spacing': [2, 'always'|'never'] +'vue/mustache-interpolation-spacing': [2, 'always'|'never'] ``` ### `"always"` - Expect one space between expression and curly brackets. diff --git a/lib/rules/mustache-curly-spacing.js b/lib/rules/mustache-interpolation-spacing.js similarity index 92% rename from lib/rules/mustache-curly-spacing.js rename to lib/rules/mustache-interpolation-spacing.js index 20c3fed7e..4ea93e96a 100644 --- a/lib/rules/mustache-curly-spacing.js +++ b/lib/rules/mustache-interpolation-spacing.js @@ -1,5 +1,5 @@ /** - * @fileoverview Enforce spacing on the style of mustache curly brackets. + * @fileoverview enforce unified spacing in mustache interpolations. * @author Armano */ 'use strict' @@ -17,7 +17,7 @@ const utils = require('../utils') module.exports = { meta: { docs: { - description: 'Enforce spacing on the style of mustache curly brackets.', + description: 'enforce unified spacing in mustache interpolations.', category: 'Stylistic Issues', recommended: false }, @@ -41,7 +41,9 @@ module.exports = { function checkTokens (leftToken, rightToken) { if (leftToken.loc.end.line === rightToken.loc.start.line) { const spaces = rightToken.loc.start.column - leftToken.loc.end.column - if (optSpaces === (spaces === 0)) { + const noSpacesFound = spaces === 0 + + if (optSpaces === noSpacesFound) { context.report({ node: rightToken, loc: { diff --git a/tests/lib/rules/mustache-curly-spacing.js b/tests/lib/rules/mustache-interpolation-spacing.js similarity index 95% rename from tests/lib/rules/mustache-curly-spacing.js rename to tests/lib/rules/mustache-interpolation-spacing.js index d6442cd1a..84c8ef971 100644 --- a/tests/lib/rules/mustache-curly-spacing.js +++ b/tests/lib/rules/mustache-interpolation-spacing.js @@ -1,5 +1,5 @@ /** - * @fileoverview Enforce spacing on the style of mustache curly brackets. + * @fileoverview enforce unified spacing in mustache interpolations. * @author Armano */ 'use strict' @@ -8,7 +8,7 @@ // Requirements // ------------------------------------------------------------------------------ -const rule = require('../../../lib/rules/mustache-curly-spacing') +const rule = require('../../../lib/rules/mustache-interpolation-spacing') const RuleTester = require('eslint').RuleTester // ------------------------------------------------------------------------------ @@ -20,7 +20,7 @@ const ruleTester = new RuleTester({ parserOptions: { ecmaVersion: 2015 } }) -ruleTester.run('mustache-curly-spacing', rule, { +ruleTester.run('mustache-interpolation-spacing', rule, { valid: [ {