jsx-props-no-multi-spaces.js 1.7 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364
  1. /**
  2. * @fileoverview Disallow multiple spaces between inline JSX props
  3. * @author Adrian Moennich
  4. */
  5. 'use strict';
  6. const docsUrl = require('../util/docsUrl');
  7. // ------------------------------------------------------------------------------
  8. // Rule Definition
  9. // ------------------------------------------------------------------------------
  10. module.exports = {
  11. meta: {
  12. docs: {
  13. description: 'Disallow multiple spaces between inline JSX props',
  14. category: 'Stylistic Issues',
  15. recommended: false,
  16. url: docsUrl('jsx-props-no-multi-spaces')
  17. },
  18. fixable: 'code',
  19. schema: []
  20. },
  21. create: function (context) {
  22. const sourceCode = context.getSourceCode();
  23. function getPropName(propNode) {
  24. if (propNode.type === 'JSXSpreadAttribute') {
  25. return sourceCode.getText(propNode.argument);
  26. } else if (propNode.type === 'JSXIdentifier') {
  27. return propNode.name;
  28. }
  29. return propNode.name.name;
  30. }
  31. function checkSpacing(prev, node) {
  32. if (prev.loc.end.line !== node.loc.end.line) {
  33. return;
  34. }
  35. const between = sourceCode.text.slice(prev.range[1], node.range[0]);
  36. if (between !== ' ') {
  37. context.report({
  38. node: node,
  39. message: `Expected only one space between "${getPropName(prev)}" and "${getPropName(node)}"`,
  40. fix: function(fixer) {
  41. return fixer.replaceTextRange([prev.range[1], node.range[0]], ' ');
  42. }
  43. });
  44. }
  45. }
  46. return {
  47. JSXOpeningElement: function (node) {
  48. node.attributes.reduce((prev, prop) => {
  49. checkSpacing(prev, prop);
  50. return prop;
  51. }, node.name);
  52. }
  53. };
  54. }
  55. };