@arcaauth/eslint-plugin-jsx-a11y 6.10.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.babelrc +17 -0
- package/.eslintrc +44 -0
- package/CHANGELOG.md +774 -0
- package/LICENSE.md +8 -0
- package/README.md +423 -0
- package/__mocks__/IdentifierMock.js +15 -0
- package/__mocks__/JSXAttributeMock.js +39 -0
- package/__mocks__/JSXElementMock.js +37 -0
- package/__mocks__/JSXExpressionContainerMock.js +15 -0
- package/__mocks__/JSXSpreadAttributeMock.js +18 -0
- package/__mocks__/JSXTextMock.js +17 -0
- package/__mocks__/LiteralMock.js +17 -0
- package/__mocks__/genInteractives.js +218 -0
- package/__tests__/__util__/axeMapping.js +6 -0
- package/__tests__/__util__/helpers/getESLintCoreRule.js +9 -0
- package/__tests__/__util__/helpers/parsers.js +186 -0
- package/__tests__/__util__/parserOptionsMapper.js +53 -0
- package/__tests__/__util__/ruleOptionsMapperFactory.js +33 -0
- package/__tests__/index-test.js +40 -0
- package/__tests__/src/rules/accessible-emoji-test.js +66 -0
- package/__tests__/src/rules/alt-text-test.js +291 -0
- package/__tests__/src/rules/anchor-ambiguous-text-test.js +117 -0
- package/__tests__/src/rules/anchor-has-content-test.js +54 -0
- package/__tests__/src/rules/anchor-is-valid-test.js +532 -0
- package/__tests__/src/rules/aria-activedescendant-has-tabindex-test.js +95 -0
- package/__tests__/src/rules/aria-props-test.js +69 -0
- package/__tests__/src/rules/aria-proptypes-test.js +311 -0
- package/__tests__/src/rules/aria-role-test.js +118 -0
- package/__tests__/src/rules/aria-unsupported-elements-test.js +75 -0
- package/__tests__/src/rules/autocomplete-valid-test.js +77 -0
- package/__tests__/src/rules/click-events-have-key-events-test.js +77 -0
- package/__tests__/src/rules/control-has-associated-label-test.js +327 -0
- package/__tests__/src/rules/heading-has-content-test.js +85 -0
- package/__tests__/src/rules/html-has-lang-test.js +42 -0
- package/__tests__/src/rules/iframe-has-title-test.js +55 -0
- package/__tests__/src/rules/img-redundant-alt-test.js +137 -0
- package/__tests__/src/rules/interactive-supports-focus-test.js +267 -0
- package/__tests__/src/rules/label-has-associated-control-test.js +243 -0
- package/__tests__/src/rules/label-has-for-test.js +235 -0
- package/__tests__/src/rules/lang-test.js +59 -0
- package/__tests__/src/rules/media-has-caption-test.js +220 -0
- package/__tests__/src/rules/mouse-events-have-key-events-test.js +154 -0
- package/__tests__/src/rules/no-access-key-test.js +48 -0
- package/__tests__/src/rules/no-aria-hidden-on-focusable-test.js +44 -0
- package/__tests__/src/rules/no-autofocus-test.js +68 -0
- package/__tests__/src/rules/no-distracting-elements-test.js +51 -0
- package/__tests__/src/rules/no-interactive-element-to-noninteractive-role-test.js +405 -0
- package/__tests__/src/rules/no-noninteractive-element-interactions-test.js +502 -0
- package/__tests__/src/rules/no-noninteractive-element-to-interactive-role-test.js +500 -0
- package/__tests__/src/rules/no-noninteractive-tabindex-test.js +123 -0
- package/__tests__/src/rules/no-onchange-test.js +57 -0
- package/__tests__/src/rules/no-redundant-roles-test.js +98 -0
- package/__tests__/src/rules/no-static-element-interactions-test.js +501 -0
- package/__tests__/src/rules/prefer-tag-over-role-test.js +63 -0
- package/__tests__/src/rules/role-has-required-aria-props-test.js +134 -0
- package/__tests__/src/rules/role-supports-aria-props-test.js +570 -0
- package/__tests__/src/rules/scope-test.js +50 -0
- package/__tests__/src/rules/tabindex-no-positive-test.js +55 -0
- package/__tests__/src/util/attributesComparator-test.js +91 -0
- package/__tests__/src/util/getAccessibleChildText-test.js +174 -0
- package/__tests__/src/util/getComputedRole-test.js +71 -0
- package/__tests__/src/util/getElementType-test.js +154 -0
- package/__tests__/src/util/getExplicitRole-test.js +35 -0
- package/__tests__/src/util/getImplicitRole-test.js +25 -0
- package/__tests__/src/util/getSuggestion-test.js +33 -0
- package/__tests__/src/util/getTabIndex-test.js +85 -0
- package/__tests__/src/util/hasAccessibleChild-test.js +157 -0
- package/__tests__/src/util/implicitRoles/input-test.js +87 -0
- package/__tests__/src/util/implicitRoles/menu-test.js +20 -0
- package/__tests__/src/util/implicitRoles/menuitem-test.js +38 -0
- package/__tests__/src/util/isAbstractRole-test.js +51 -0
- package/__tests__/src/util/isContentEditable-test.js +52 -0
- package/__tests__/src/util/isDOMElement-test.js +30 -0
- package/__tests__/src/util/isDisabledElement-test.js +88 -0
- package/__tests__/src/util/isFocusable-test.js +111 -0
- package/__tests__/src/util/isInteractiveElement-test.js +104 -0
- package/__tests__/src/util/isInteractiveRole-test.js +59 -0
- package/__tests__/src/util/isNonInteractiveElement-test.js +97 -0
- package/__tests__/src/util/isNonInteractiveRole-test.js +59 -0
- package/__tests__/src/util/isNonLiteralProperty-test.js +52 -0
- package/__tests__/src/util/isSemanticRoleElement-test.js +72 -0
- package/__tests__/src/util/mayContainChildComponent-test.js +219 -0
- package/__tests__/src/util/mayHaveAccessibleLabel-test.js +256 -0
- package/__tests__/src/util/parserOptionsMapper-test.js +93 -0
- package/__tests__/src/util/schemas-test.js +35 -0
- package/docs/rules/accessible-emoji.md +30 -0
- package/docs/rules/alt-text.md +168 -0
- package/docs/rules/anchor-ambiguous-text.md +91 -0
- package/docs/rules/anchor-has-content.md +64 -0
- package/docs/rules/anchor-is-valid.md +270 -0
- package/docs/rules/aria-activedescendant-has-tabindex.md +52 -0
- package/docs/rules/aria-props.md +29 -0
- package/docs/rules/aria-proptypes.md +30 -0
- package/docs/rules/aria-role.md +51 -0
- package/docs/rules/aria-unsupported-elements.md +30 -0
- package/docs/rules/autocomplete-valid.md +49 -0
- package/docs/rules/click-events-have-key-events.md +28 -0
- package/docs/rules/control-has-associated-label.md +113 -0
- package/docs/rules/heading-has-content.md +67 -0
- package/docs/rules/html-has-lang.md +31 -0
- package/docs/rules/iframe-has-title.md +37 -0
- package/docs/rules/img-redundant-alt.md +48 -0
- package/docs/rules/interactive-supports-focus.md +156 -0
- package/docs/rules/label-has-associated-control.md +152 -0
- package/docs/rules/label-has-for.md +130 -0
- package/docs/rules/lang.md +31 -0
- package/docs/rules/media-has-caption.md +48 -0
- package/docs/rules/mouse-events-have-key-events.md +58 -0
- package/docs/rules/no-access-key.md +30 -0
- package/docs/rules/no-aria-hidden-on-focusable.md +37 -0
- package/docs/rules/no-autofocus.md +43 -0
- package/docs/rules/no-distracting-elements.md +41 -0
- package/docs/rules/no-interactive-element-to-noninteractive-role.md +73 -0
- package/docs/rules/no-noninteractive-element-interactions.md +145 -0
- package/docs/rules/no-noninteractive-element-to-interactive-role.md +76 -0
- package/docs/rules/no-noninteractive-tabindex.md +115 -0
- package/docs/rules/no-onchange.md +36 -0
- package/docs/rules/no-redundant-roles.md +46 -0
- package/docs/rules/no-static-element-interactions.md +114 -0
- package/docs/rules/prefer-tag-over-role.md +32 -0
- package/docs/rules/role-has-required-aria-props.md +31 -0
- package/docs/rules/role-supports-aria-props.md +39 -0
- package/docs/rules/scope.md +30 -0
- package/docs/rules/tabindex-no-positive.md +32 -0
- package/lib/configs/flat-config-base.js +11 -0
- package/lib/configs/legacy-config-base.js +9 -0
- package/lib/index.js +209 -0
- package/lib/rules/accessible-emoji.js +63 -0
- package/lib/rules/alt-text.js +218 -0
- package/lib/rules/anchor-ambiguous-text.js +64 -0
- package/lib/rules/anchor-has-content.js +60 -0
- package/lib/rules/anchor-is-valid.js +122 -0
- package/lib/rules/aria-activedescendant-has-tabindex.js +66 -0
- package/lib/rules/aria-props.js +59 -0
- package/lib/rules/aria-proptypes.js +114 -0
- package/lib/rules/aria-role.js +89 -0
- package/lib/rules/aria-unsupported-elements.js +64 -0
- package/lib/rules/autocomplete-valid.js +67 -0
- package/lib/rules/click-events-have-key-events.js +68 -0
- package/lib/rules/control-has-associated-label.js +103 -0
- package/lib/rules/heading-has-content.js +61 -0
- package/lib/rules/html-has-lang.js +50 -0
- package/lib/rules/iframe-has-title.js +50 -0
- package/lib/rules/img-redundant-alt.js +88 -0
- package/lib/rules/interactive-supports-focus.js +87 -0
- package/lib/rules/label-has-associated-control.js +127 -0
- package/lib/rules/label-has-for.js +150 -0
- package/lib/rules/lang.js +68 -0
- package/lib/rules/media-has-caption.js +96 -0
- package/lib/rules/mouse-events-have-key-events.js +94 -0
- package/lib/rules/no-access-key.js +43 -0
- package/lib/rules/no-aria-hidden-on-focusable.js +47 -0
- package/lib/rules/no-autofocus.js +62 -0
- package/lib/rules/no-distracting-elements.js +54 -0
- package/lib/rules/no-interactive-element-to-noninteractive-role.js +81 -0
- package/lib/rules/no-noninteractive-element-interactions.js +95 -0
- package/lib/rules/no-noninteractive-element-to-interactive-role.js +80 -0
- package/lib/rules/no-noninteractive-tabindex.js +109 -0
- package/lib/rules/no-onchange.js +52 -0
- package/lib/rules/no-redundant-roles.js +86 -0
- package/lib/rules/no-static-element-interactions.js +102 -0
- package/lib/rules/prefer-tag-over-role.js +75 -0
- package/lib/rules/role-has-required-aria-props.js +88 -0
- package/lib/rules/role-supports-aria-props.js +78 -0
- package/lib/rules/scope.js +58 -0
- package/lib/rules/tabindex-no-positive.js +53 -0
- package/lib/util/attributesComparator.js +34 -0
- package/lib/util/getAccessibleChildText.js +55 -0
- package/lib/util/getComputedRole.js +19 -0
- package/lib/util/getElementType.js +30 -0
- package/lib/util/getExplicitRole.js +27 -0
- package/lib/util/getImplicitRole.js +24 -0
- package/lib/util/getSuggestion.js +32 -0
- package/lib/util/getTabIndex.js +34 -0
- package/lib/util/hasAccessibleChild.js +30 -0
- package/lib/util/implicitRoles/a.js +17 -0
- package/lib/util/implicitRoles/area.js +17 -0
- package/lib/util/implicitRoles/article.js +13 -0
- package/lib/util/implicitRoles/aside.js +13 -0
- package/lib/util/implicitRoles/body.js +13 -0
- package/lib/util/implicitRoles/button.js +13 -0
- package/lib/util/implicitRoles/datalist.js +13 -0
- package/lib/util/implicitRoles/details.js +13 -0
- package/lib/util/implicitRoles/dialog.js +13 -0
- package/lib/util/implicitRoles/form.js +13 -0
- package/lib/util/implicitRoles/h1.js +13 -0
- package/lib/util/implicitRoles/h2.js +13 -0
- package/lib/util/implicitRoles/h3.js +13 -0
- package/lib/util/implicitRoles/h4.js +13 -0
- package/lib/util/implicitRoles/h5.js +13 -0
- package/lib/util/implicitRoles/h6.js +13 -0
- package/lib/util/implicitRoles/hr.js +13 -0
- package/lib/util/implicitRoles/img.js +31 -0
- package/lib/util/implicitRoles/index.js +82 -0
- package/lib/util/implicitRoles/input.js +38 -0
- package/lib/util/implicitRoles/li.js +13 -0
- package/lib/util/implicitRoles/link.js +17 -0
- package/lib/util/implicitRoles/menu.js +19 -0
- package/lib/util/implicitRoles/menuitem.js +28 -0
- package/lib/util/implicitRoles/meter.js +13 -0
- package/lib/util/implicitRoles/nav.js +13 -0
- package/lib/util/implicitRoles/ol.js +13 -0
- package/lib/util/implicitRoles/option.js +13 -0
- package/lib/util/implicitRoles/output.js +13 -0
- package/lib/util/implicitRoles/progress.js +13 -0
- package/lib/util/implicitRoles/section.js +13 -0
- package/lib/util/implicitRoles/select.js +13 -0
- package/lib/util/implicitRoles/tbody.js +13 -0
- package/lib/util/implicitRoles/textarea.js +13 -0
- package/lib/util/implicitRoles/tfoot.js +13 -0
- package/lib/util/implicitRoles/thead.js +13 -0
- package/lib/util/implicitRoles/ul.js +13 -0
- package/lib/util/isAbstractRole.js +23 -0
- package/lib/util/isContentEditable.js +13 -0
- package/lib/util/isDOMElement.js +15 -0
- package/lib/util/isDisabledElement.js +23 -0
- package/lib/util/isFocusable.js +23 -0
- package/lib/util/isHiddenFromScreenReader.js +26 -0
- package/lib/util/isInteractiveElement.js +116 -0
- package/lib/util/isInteractiveRole.js +54 -0
- package/lib/util/isNonInteractiveElement.js +131 -0
- package/lib/util/isNonInteractiveRole.js +55 -0
- package/lib/util/isNonLiteralProperty.js +29 -0
- package/lib/util/isPresentationRole.js +13 -0
- package/lib/util/isSemanticRoleElement.js +54 -0
- package/lib/util/mayContainChildComponent.js +50 -0
- package/lib/util/mayHaveAccessibleLabel.js +95 -0
- package/lib/util/schemas.js +52 -0
- package/package.json +120 -0
|
@@ -0,0 +1,150 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports["default"] = void 0;
|
|
7
|
+
var _jsxAstUtils = require("jsx-ast-utils");
|
|
8
|
+
var _schemas = require("../util/schemas");
|
|
9
|
+
var _getElementType = _interopRequireDefault(require("../util/getElementType"));
|
|
10
|
+
var _hasAccessibleChild = _interopRequireDefault(require("../util/hasAccessibleChild"));
|
|
11
|
+
function _interopRequireDefault(e) { return e && e.__esModule ? e : { "default": e }; }
|
|
12
|
+
/**
|
|
13
|
+
* @fileoverview Enforce label tags have htmlFor attribute.
|
|
14
|
+
* @author Ethan Cohen
|
|
15
|
+
*/
|
|
16
|
+
|
|
17
|
+
// ----------------------------------------------------------------------------
|
|
18
|
+
// Rule Definition
|
|
19
|
+
// ----------------------------------------------------------------------------
|
|
20
|
+
|
|
21
|
+
var enumValues = ['nesting', 'id'];
|
|
22
|
+
var schema = {
|
|
23
|
+
type: 'object',
|
|
24
|
+
properties: {
|
|
25
|
+
components: _schemas.arraySchema,
|
|
26
|
+
required: {
|
|
27
|
+
oneOf: [{
|
|
28
|
+
type: 'string',
|
|
29
|
+
"enum": enumValues
|
|
30
|
+
}, (0, _schemas.generateObjSchema)({
|
|
31
|
+
some: (0, _schemas.enumArraySchema)(enumValues)
|
|
32
|
+
}, ['some']), (0, _schemas.generateObjSchema)({
|
|
33
|
+
every: (0, _schemas.enumArraySchema)(enumValues)
|
|
34
|
+
}, ['every'])]
|
|
35
|
+
},
|
|
36
|
+
allowChildren: {
|
|
37
|
+
type: 'boolean'
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
};
|
|
41
|
+
// Breadth-first search, assuming that HTML for forms is shallow.
|
|
42
|
+
function validateNesting(node) {
|
|
43
|
+
var queue = node.parent.children.slice();
|
|
44
|
+
var child;
|
|
45
|
+
var opener;
|
|
46
|
+
while (queue.length) {
|
|
47
|
+
child = queue.shift();
|
|
48
|
+
opener = child.openingElement;
|
|
49
|
+
if (child.type === 'JSXElement' && opener && (opener.name.name === 'input' || opener.name.name === 'textarea' || opener.name.name === 'select')) {
|
|
50
|
+
return true;
|
|
51
|
+
}
|
|
52
|
+
if (child.children) {
|
|
53
|
+
queue = queue.concat(child.children);
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
return false;
|
|
57
|
+
}
|
|
58
|
+
function validateID(_ref, context) {
|
|
59
|
+
var _settings$jsxA11y$at, _settings$jsxA11y, _settings$jsxA11y$att;
|
|
60
|
+
var attributes = _ref.attributes;
|
|
61
|
+
var settings = context.settings;
|
|
62
|
+
var htmlForAttributes = (_settings$jsxA11y$at = (_settings$jsxA11y = settings['jsx-a11y']) === null || _settings$jsxA11y === void 0 ? void 0 : (_settings$jsxA11y$att = _settings$jsxA11y.attributes) === null || _settings$jsxA11y$att === void 0 ? void 0 : _settings$jsxA11y$att["for"]) !== null && _settings$jsxA11y$at !== void 0 ? _settings$jsxA11y$at : ['htmlFor'];
|
|
63
|
+
for (var i = 0; i < htmlForAttributes.length; i += 1) {
|
|
64
|
+
var attribute = htmlForAttributes[i];
|
|
65
|
+
if ((0, _jsxAstUtils.hasProp)(attributes, attribute)) {
|
|
66
|
+
var htmlForAttr = (0, _jsxAstUtils.getProp)(attributes, attribute);
|
|
67
|
+
var htmlForValue = (0, _jsxAstUtils.getPropValue)(htmlForAttr);
|
|
68
|
+
return htmlForAttr !== false && !!htmlForValue;
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
return false;
|
|
72
|
+
}
|
|
73
|
+
function validate(node, required, allowChildren, elementType, context) {
|
|
74
|
+
if (allowChildren === true) {
|
|
75
|
+
return (0, _hasAccessibleChild["default"])(node.parent, elementType);
|
|
76
|
+
}
|
|
77
|
+
if (required === 'nesting') {
|
|
78
|
+
return validateNesting(node);
|
|
79
|
+
}
|
|
80
|
+
return validateID(node, context);
|
|
81
|
+
}
|
|
82
|
+
function getValidityStatus(node, required, allowChildren, elementType, context) {
|
|
83
|
+
if (Array.isArray(required.some)) {
|
|
84
|
+
var _isValid = required.some.some(function (rule) {
|
|
85
|
+
return validate(node, rule, allowChildren, elementType, context);
|
|
86
|
+
});
|
|
87
|
+
var _message = !_isValid ? "Form label must have ANY of the following types of associated control: ".concat(required.some.join(', ')) : null;
|
|
88
|
+
return {
|
|
89
|
+
isValid: _isValid,
|
|
90
|
+
message: _message
|
|
91
|
+
};
|
|
92
|
+
}
|
|
93
|
+
if (Array.isArray(required.every)) {
|
|
94
|
+
var _isValid2 = required.every.every(function (rule) {
|
|
95
|
+
return validate(node, rule, allowChildren, elementType, context);
|
|
96
|
+
});
|
|
97
|
+
var _message2 = !_isValid2 ? "Form label must have ALL of the following types of associated control: ".concat(required.every.join(', ')) : null;
|
|
98
|
+
return {
|
|
99
|
+
isValid: _isValid2,
|
|
100
|
+
message: _message2
|
|
101
|
+
};
|
|
102
|
+
}
|
|
103
|
+
var isValid = validate(node, required, allowChildren, elementType, context);
|
|
104
|
+
var message = !isValid ? "Form label must have the following type of associated control: ".concat(required) : null;
|
|
105
|
+
return {
|
|
106
|
+
isValid,
|
|
107
|
+
message
|
|
108
|
+
};
|
|
109
|
+
}
|
|
110
|
+
var _default = exports["default"] = {
|
|
111
|
+
meta: {
|
|
112
|
+
deprecated: true,
|
|
113
|
+
replacedBy: ['label-has-associated-control'],
|
|
114
|
+
docs: {
|
|
115
|
+
description: 'Enforce that `<label>` elements have the `htmlFor` prop.',
|
|
116
|
+
url: 'https://github.com/jsx-eslint/eslint-plugin-jsx-a11y/tree/HEAD/docs/rules/label-has-for.md'
|
|
117
|
+
},
|
|
118
|
+
schema: [schema]
|
|
119
|
+
},
|
|
120
|
+
create: function create(context) {
|
|
121
|
+
var elementType = (0, _getElementType["default"])(context);
|
|
122
|
+
return {
|
|
123
|
+
JSXOpeningElement(node) {
|
|
124
|
+
var options = context.options[0] || {};
|
|
125
|
+
var componentOptions = options.components || [];
|
|
126
|
+
var typesToValidate = ['label'].concat(componentOptions);
|
|
127
|
+
var nodeType = elementType(node);
|
|
128
|
+
|
|
129
|
+
// Only check 'label' elements and custom types.
|
|
130
|
+
if (typesToValidate.indexOf(nodeType) === -1) {
|
|
131
|
+
return;
|
|
132
|
+
}
|
|
133
|
+
var required = options.required || {
|
|
134
|
+
every: ['nesting', 'id']
|
|
135
|
+
};
|
|
136
|
+
var allowChildren = options.allowChildren || false;
|
|
137
|
+
var _getValidityStatus = getValidityStatus(node, required, allowChildren, elementType, context),
|
|
138
|
+
isValid = _getValidityStatus.isValid,
|
|
139
|
+
message = _getValidityStatus.message;
|
|
140
|
+
if (!isValid) {
|
|
141
|
+
context.report({
|
|
142
|
+
node,
|
|
143
|
+
message
|
|
144
|
+
});
|
|
145
|
+
}
|
|
146
|
+
}
|
|
147
|
+
};
|
|
148
|
+
}
|
|
149
|
+
};
|
|
150
|
+
module.exports = exports.default;
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports["default"] = void 0;
|
|
7
|
+
var _jsxAstUtils = require("jsx-ast-utils");
|
|
8
|
+
var _languageTags = _interopRequireDefault(require("language-tags"));
|
|
9
|
+
var _schemas = require("../util/schemas");
|
|
10
|
+
var _getElementType = _interopRequireDefault(require("../util/getElementType"));
|
|
11
|
+
function _interopRequireDefault(e) { return e && e.__esModule ? e : { "default": e }; }
|
|
12
|
+
/**
|
|
13
|
+
* @fileoverview Enforce lang attribute has a valid value.
|
|
14
|
+
* @author Ethan Cohen
|
|
15
|
+
*/
|
|
16
|
+
|
|
17
|
+
// ----------------------------------------------------------------------------
|
|
18
|
+
// Rule Definition
|
|
19
|
+
// ----------------------------------------------------------------------------
|
|
20
|
+
|
|
21
|
+
var errorMessage = 'lang attribute must have a valid value.';
|
|
22
|
+
var schema = (0, _schemas.generateObjSchema)();
|
|
23
|
+
var _default = exports["default"] = {
|
|
24
|
+
meta: {
|
|
25
|
+
docs: {
|
|
26
|
+
url: 'https://github.com/jsx-eslint/eslint-plugin-jsx-a11y/tree/HEAD/docs/rules/lang.md',
|
|
27
|
+
description: 'Enforce lang attribute has a valid value.'
|
|
28
|
+
},
|
|
29
|
+
schema: [schema]
|
|
30
|
+
},
|
|
31
|
+
create: function create(context) {
|
|
32
|
+
var elementType = (0, _getElementType["default"])(context);
|
|
33
|
+
return {
|
|
34
|
+
JSXAttribute: function JSXAttribute(node) {
|
|
35
|
+
var name = (0, _jsxAstUtils.propName)(node);
|
|
36
|
+
if (name && name.toUpperCase() !== 'LANG') {
|
|
37
|
+
return;
|
|
38
|
+
}
|
|
39
|
+
var parent = node.parent;
|
|
40
|
+
var type = elementType(parent);
|
|
41
|
+
if (type && type !== 'html') {
|
|
42
|
+
return;
|
|
43
|
+
}
|
|
44
|
+
var value = (0, _jsxAstUtils.getLiteralPropValue)(node);
|
|
45
|
+
|
|
46
|
+
// Don't check identifiers
|
|
47
|
+
if (value === null) {
|
|
48
|
+
return;
|
|
49
|
+
}
|
|
50
|
+
if (value === undefined) {
|
|
51
|
+
context.report({
|
|
52
|
+
node,
|
|
53
|
+
message: errorMessage
|
|
54
|
+
});
|
|
55
|
+
return;
|
|
56
|
+
}
|
|
57
|
+
if (_languageTags["default"].check(value)) {
|
|
58
|
+
return;
|
|
59
|
+
}
|
|
60
|
+
context.report({
|
|
61
|
+
node,
|
|
62
|
+
message: errorMessage
|
|
63
|
+
});
|
|
64
|
+
}
|
|
65
|
+
};
|
|
66
|
+
}
|
|
67
|
+
};
|
|
68
|
+
module.exports = exports.default;
|
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports["default"] = void 0;
|
|
7
|
+
var _jsxAstUtils = require("jsx-ast-utils");
|
|
8
|
+
var _arrayPrototype = _interopRequireDefault(require("array.prototype.flatmap"));
|
|
9
|
+
var _schemas = require("../util/schemas");
|
|
10
|
+
var _getElementType = _interopRequireDefault(require("../util/getElementType"));
|
|
11
|
+
function _interopRequireDefault(e) { return e && e.__esModule ? e : { "default": e }; }
|
|
12
|
+
/**
|
|
13
|
+
* @fileoverview <audio> and <video> elements must have a <track> for captions.
|
|
14
|
+
* @author Ethan Cohen
|
|
15
|
+
*
|
|
16
|
+
*/
|
|
17
|
+
|
|
18
|
+
// ----------------------------------------------------------------------------
|
|
19
|
+
// Rule Definition
|
|
20
|
+
// ----------------------------------------------------------------------------
|
|
21
|
+
|
|
22
|
+
var errorMessage = 'Media elements such as <audio> and <video> must have a <track> for captions.';
|
|
23
|
+
var MEDIA_TYPES = ['audio', 'video'];
|
|
24
|
+
var schema = (0, _schemas.generateObjSchema)({
|
|
25
|
+
audio: _schemas.arraySchema,
|
|
26
|
+
video: _schemas.arraySchema,
|
|
27
|
+
track: _schemas.arraySchema
|
|
28
|
+
});
|
|
29
|
+
var isMediaType = function isMediaType(context, type) {
|
|
30
|
+
var options = context.options[0] || {};
|
|
31
|
+
return MEDIA_TYPES.concat((0, _arrayPrototype["default"])(MEDIA_TYPES, function (mediaType) {
|
|
32
|
+
return options[mediaType];
|
|
33
|
+
})).some(function (typeToCheck) {
|
|
34
|
+
return typeToCheck === type;
|
|
35
|
+
});
|
|
36
|
+
};
|
|
37
|
+
var isTrackType = function isTrackType(context, type) {
|
|
38
|
+
var options = context.options[0] || {};
|
|
39
|
+
return ['track'].concat(options.track || []).some(function (typeToCheck) {
|
|
40
|
+
return typeToCheck === type;
|
|
41
|
+
});
|
|
42
|
+
};
|
|
43
|
+
var _default = exports["default"] = {
|
|
44
|
+
meta: {
|
|
45
|
+
docs: {
|
|
46
|
+
url: 'https://github.com/jsx-eslint/eslint-plugin-jsx-a11y/tree/HEAD/docs/rules/media-has-caption.md',
|
|
47
|
+
description: 'Enforces that `<audio>` and `<video>` elements must have a `<track>` for captions.'
|
|
48
|
+
},
|
|
49
|
+
schema: [schema]
|
|
50
|
+
},
|
|
51
|
+
create: function create(context) {
|
|
52
|
+
var elementType = (0, _getElementType["default"])(context);
|
|
53
|
+
return {
|
|
54
|
+
JSXElement: function JSXElement(node) {
|
|
55
|
+
var element = node.openingElement;
|
|
56
|
+
var type = elementType(element);
|
|
57
|
+
if (!isMediaType(context, type)) {
|
|
58
|
+
return;
|
|
59
|
+
}
|
|
60
|
+
var mutedProp = (0, _jsxAstUtils.getProp)(element.attributes, 'muted');
|
|
61
|
+
var mutedPropVal = (0, _jsxAstUtils.getLiteralPropValue)(mutedProp);
|
|
62
|
+
if (mutedPropVal === true) {
|
|
63
|
+
return;
|
|
64
|
+
}
|
|
65
|
+
// $FlowFixMe https://github.com/facebook/flow/issues/1414
|
|
66
|
+
var trackChildren = node.children.filter(function (child) {
|
|
67
|
+
if (child.type !== 'JSXElement') {
|
|
68
|
+
return false;
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
// $FlowFixMe https://github.com/facebook/flow/issues/1414
|
|
72
|
+
return isTrackType(context, elementType(child.openingElement));
|
|
73
|
+
});
|
|
74
|
+
if (trackChildren.length === 0) {
|
|
75
|
+
context.report({
|
|
76
|
+
node: element,
|
|
77
|
+
message: errorMessage
|
|
78
|
+
});
|
|
79
|
+
return;
|
|
80
|
+
}
|
|
81
|
+
var hasCaption = trackChildren.some(function (track) {
|
|
82
|
+
var kindProp = (0, _jsxAstUtils.getProp)(track.openingElement.attributes, 'kind');
|
|
83
|
+
var kindPropValue = (0, _jsxAstUtils.getLiteralPropValue)(kindProp) || '';
|
|
84
|
+
return kindPropValue.toLowerCase() === 'captions';
|
|
85
|
+
});
|
|
86
|
+
if (!hasCaption) {
|
|
87
|
+
context.report({
|
|
88
|
+
node: element,
|
|
89
|
+
message: errorMessage
|
|
90
|
+
});
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
};
|
|
94
|
+
}
|
|
95
|
+
};
|
|
96
|
+
module.exports = exports.default;
|
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports["default"] = void 0;
|
|
7
|
+
var _ariaQuery = require("aria-query");
|
|
8
|
+
var _jsxAstUtils = require("jsx-ast-utils");
|
|
9
|
+
var _schemas = require("../util/schemas");
|
|
10
|
+
function _typeof(o) { "@babel/helpers - typeof"; return _typeof = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function (o) { return typeof o; } : function (o) { return o && "function" == typeof Symbol && o.constructor === Symbol && o !== Symbol.prototype ? "symbol" : typeof o; }, _typeof(o); }
|
|
11
|
+
function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; }
|
|
12
|
+
function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? ownKeys(Object(t), !0).forEach(function (r) { _defineProperty(e, r, t[r]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function (r) { Object.defineProperty(e, r, Object.getOwnPropertyDescriptor(t, r)); }); } return e; }
|
|
13
|
+
function _defineProperty(e, r, t) { return (r = _toPropertyKey(r)) in e ? Object.defineProperty(e, r, { value: t, enumerable: !0, configurable: !0, writable: !0 }) : e[r] = t, e; }
|
|
14
|
+
function _toPropertyKey(t) { var i = _toPrimitive(t, "string"); return "symbol" == _typeof(i) ? i : i + ""; }
|
|
15
|
+
function _toPrimitive(t, r) { if ("object" != _typeof(t) || !t) return t; var e = t[Symbol.toPrimitive]; if (void 0 !== e) { var i = e.call(t, r || "default"); if ("object" != _typeof(i)) return i; throw new TypeError("@@toPrimitive must return a primitive value."); } return ("string" === r ? String : Number)(t); } /**
|
|
16
|
+
* @fileoverview Enforce onmouseover/onmouseout are
|
|
17
|
+
* accompanied by onfocus/onblur.
|
|
18
|
+
* @author Ethan Cohen
|
|
19
|
+
*
|
|
20
|
+
*/ // ----------------------------------------------------------------------------
|
|
21
|
+
// Rule Definition
|
|
22
|
+
// ----------------------------------------------------------------------------
|
|
23
|
+
var schema = (0, _schemas.generateObjSchema)({
|
|
24
|
+
hoverInHandlers: _objectSpread(_objectSpread({}, _schemas.arraySchema), {}, {
|
|
25
|
+
description: 'An array of events that need to be accompanied by `onFocus`'
|
|
26
|
+
}),
|
|
27
|
+
hoverOutHandlers: _objectSpread(_objectSpread({}, _schemas.arraySchema), {}, {
|
|
28
|
+
description: 'An array of events that need to be accompanied by `onBlur`'
|
|
29
|
+
})
|
|
30
|
+
});
|
|
31
|
+
|
|
32
|
+
// Use `onMouseOver` and `onMouseOut` by default if no config is
|
|
33
|
+
// passed in for backwards compatibility
|
|
34
|
+
var DEFAULT_HOVER_IN_HANDLERS = ['onMouseOver'];
|
|
35
|
+
var DEFAULT_HOVER_OUT_HANDLERS = ['onMouseOut'];
|
|
36
|
+
var _default = exports["default"] = {
|
|
37
|
+
meta: {
|
|
38
|
+
docs: {
|
|
39
|
+
url: 'https://github.com/jsx-eslint/eslint-plugin-jsx-a11y/tree/HEAD/docs/rules/mouse-events-have-key-events.md',
|
|
40
|
+
description: 'Enforce that `onMouseOver`/`onMouseOut` are accompanied by `onFocus`/`onBlur` for keyboard-only users.'
|
|
41
|
+
},
|
|
42
|
+
schema: [schema]
|
|
43
|
+
},
|
|
44
|
+
create: function create(context) {
|
|
45
|
+
return {
|
|
46
|
+
JSXOpeningElement: function JSXOpeningElement(node) {
|
|
47
|
+
var _options$0$hoverInHan, _options$, _options$0$hoverOutHa, _options$2;
|
|
48
|
+
var name = node.name.name;
|
|
49
|
+
if (!_ariaQuery.dom.get(name)) {
|
|
50
|
+
return;
|
|
51
|
+
}
|
|
52
|
+
var options = context.options;
|
|
53
|
+
var hoverInHandlers = (_options$0$hoverInHan = (_options$ = options[0]) === null || _options$ === void 0 ? void 0 : _options$.hoverInHandlers) !== null && _options$0$hoverInHan !== void 0 ? _options$0$hoverInHan : DEFAULT_HOVER_IN_HANDLERS;
|
|
54
|
+
var hoverOutHandlers = (_options$0$hoverOutHa = (_options$2 = options[0]) === null || _options$2 === void 0 ? void 0 : _options$2.hoverOutHandlers) !== null && _options$0$hoverOutHa !== void 0 ? _options$0$hoverOutHa : DEFAULT_HOVER_OUT_HANDLERS;
|
|
55
|
+
var attributes = node.attributes;
|
|
56
|
+
|
|
57
|
+
// Check hover in / onfocus pairing
|
|
58
|
+
var firstHoverInHandlerWithValue = hoverInHandlers.find(function (handler) {
|
|
59
|
+
var prop = (0, _jsxAstUtils.getProp)(attributes, handler);
|
|
60
|
+
var propValue = (0, _jsxAstUtils.getPropValue)(prop);
|
|
61
|
+
return propValue != null;
|
|
62
|
+
});
|
|
63
|
+
if (firstHoverInHandlerWithValue != null) {
|
|
64
|
+
var hasOnFocus = (0, _jsxAstUtils.getProp)(attributes, 'onFocus');
|
|
65
|
+
var onFocusValue = (0, _jsxAstUtils.getPropValue)(hasOnFocus);
|
|
66
|
+
if (hasOnFocus === false || onFocusValue === null || onFocusValue === undefined) {
|
|
67
|
+
context.report({
|
|
68
|
+
node: (0, _jsxAstUtils.getProp)(attributes, firstHoverInHandlerWithValue),
|
|
69
|
+
message: "".concat(firstHoverInHandlerWithValue, " must be accompanied by onFocus for accessibility.")
|
|
70
|
+
});
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
// Check hover out / onblur pairing
|
|
75
|
+
var firstHoverOutHandlerWithValue = hoverOutHandlers.find(function (handler) {
|
|
76
|
+
var prop = (0, _jsxAstUtils.getProp)(attributes, handler);
|
|
77
|
+
var propValue = (0, _jsxAstUtils.getPropValue)(prop);
|
|
78
|
+
return propValue != null;
|
|
79
|
+
});
|
|
80
|
+
if (firstHoverOutHandlerWithValue != null) {
|
|
81
|
+
var hasOnBlur = (0, _jsxAstUtils.getProp)(attributes, 'onBlur');
|
|
82
|
+
var onBlurValue = (0, _jsxAstUtils.getPropValue)(hasOnBlur);
|
|
83
|
+
if (hasOnBlur === false || onBlurValue === null || onBlurValue === undefined) {
|
|
84
|
+
context.report({
|
|
85
|
+
node: (0, _jsxAstUtils.getProp)(attributes, firstHoverOutHandlerWithValue),
|
|
86
|
+
message: "".concat(firstHoverOutHandlerWithValue, " must be accompanied by onBlur for accessibility.")
|
|
87
|
+
});
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
};
|
|
92
|
+
}
|
|
93
|
+
};
|
|
94
|
+
module.exports = exports.default;
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports["default"] = void 0;
|
|
7
|
+
var _jsxAstUtils = require("jsx-ast-utils");
|
|
8
|
+
var _schemas = require("../util/schemas");
|
|
9
|
+
/**
|
|
10
|
+
* @fileoverview Enforce no accesskey attribute on element.
|
|
11
|
+
* @author Ethan Cohen
|
|
12
|
+
*/
|
|
13
|
+
|
|
14
|
+
// ----------------------------------------------------------------------------
|
|
15
|
+
// Rule Definition
|
|
16
|
+
// ----------------------------------------------------------------------------
|
|
17
|
+
|
|
18
|
+
var errorMessage = 'No access key attribute allowed. Inconsistencies between keyboard shortcuts and keyboard commands used by screen readers and keyboard-only users create a11y complications.';
|
|
19
|
+
var schema = (0, _schemas.generateObjSchema)();
|
|
20
|
+
var _default = exports["default"] = {
|
|
21
|
+
meta: {
|
|
22
|
+
docs: {
|
|
23
|
+
url: 'https://github.com/jsx-eslint/eslint-plugin-jsx-a11y/tree/HEAD/docs/rules/no-access-key.md',
|
|
24
|
+
description: 'Enforce that the `accessKey` prop is not used on any element to avoid complications with keyboard commands used by a screen reader.'
|
|
25
|
+
},
|
|
26
|
+
schema: [schema]
|
|
27
|
+
},
|
|
28
|
+
create: function create(context) {
|
|
29
|
+
return {
|
|
30
|
+
JSXOpeningElement: function JSXOpeningElement(node) {
|
|
31
|
+
var accessKey = (0, _jsxAstUtils.getProp)(node.attributes, 'accesskey');
|
|
32
|
+
var accessKeyValue = (0, _jsxAstUtils.getPropValue)(accessKey);
|
|
33
|
+
if (accessKey && accessKeyValue) {
|
|
34
|
+
context.report({
|
|
35
|
+
node,
|
|
36
|
+
message: errorMessage
|
|
37
|
+
});
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
};
|
|
41
|
+
}
|
|
42
|
+
};
|
|
43
|
+
module.exports = exports.default;
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports["default"] = void 0;
|
|
7
|
+
var _jsxAstUtils = require("jsx-ast-utils");
|
|
8
|
+
var _getElementType = _interopRequireDefault(require("../util/getElementType"));
|
|
9
|
+
var _isFocusable = _interopRequireDefault(require("../util/isFocusable"));
|
|
10
|
+
var _schemas = require("../util/schemas");
|
|
11
|
+
function _interopRequireDefault(e) { return e && e.__esModule ? e : { "default": e }; }
|
|
12
|
+
/**
|
|
13
|
+
* @fileoverview Enforce aria-hidden is not used on interactive elements or contain interactive elements.
|
|
14
|
+
* @author Kate Higa
|
|
15
|
+
*/
|
|
16
|
+
|
|
17
|
+
// ----------------------------------------------------------------------------
|
|
18
|
+
// Rule Definition
|
|
19
|
+
// ----------------------------------------------------------------------------
|
|
20
|
+
|
|
21
|
+
var schema = (0, _schemas.generateObjSchema)();
|
|
22
|
+
var _default = exports["default"] = {
|
|
23
|
+
meta: {
|
|
24
|
+
docs: {
|
|
25
|
+
url: 'https://github.com/jsx-eslint/eslint-plugin-jsx-a11y/tree/HEAD/docs/rules/no-aria-hidden-on-focusable.md',
|
|
26
|
+
description: 'Disallow `aria-hidden="true"` from being set on focusable elements.'
|
|
27
|
+
},
|
|
28
|
+
schema: [schema]
|
|
29
|
+
},
|
|
30
|
+
create(context) {
|
|
31
|
+
var elementType = (0, _getElementType["default"])(context);
|
|
32
|
+
return {
|
|
33
|
+
JSXOpeningElement(node) {
|
|
34
|
+
var attributes = node.attributes;
|
|
35
|
+
var type = elementType(node);
|
|
36
|
+
var isAriaHidden = (0, _jsxAstUtils.getPropValue)((0, _jsxAstUtils.getProp)(attributes, 'aria-hidden')) === true;
|
|
37
|
+
if (isAriaHidden && (0, _isFocusable["default"])(type, attributes)) {
|
|
38
|
+
context.report({
|
|
39
|
+
node,
|
|
40
|
+
message: 'aria-hidden="true" must not be set on focusable elements.'
|
|
41
|
+
});
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
};
|
|
45
|
+
}
|
|
46
|
+
};
|
|
47
|
+
module.exports = exports.default;
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports["default"] = void 0;
|
|
7
|
+
var _jsxAstUtils = require("jsx-ast-utils");
|
|
8
|
+
var _ariaQuery = require("aria-query");
|
|
9
|
+
var _schemas = require("../util/schemas");
|
|
10
|
+
var _getElementType = _interopRequireDefault(require("../util/getElementType"));
|
|
11
|
+
function _interopRequireDefault(e) { return e && e.__esModule ? e : { "default": e }; }
|
|
12
|
+
/**
|
|
13
|
+
* @fileoverview Enforce autoFocus prop is not used.
|
|
14
|
+
* @author Ethan Cohen <@evcohen>
|
|
15
|
+
*/
|
|
16
|
+
|
|
17
|
+
// ----------------------------------------------------------------------------
|
|
18
|
+
// Rule Definition
|
|
19
|
+
// ----------------------------------------------------------------------------
|
|
20
|
+
|
|
21
|
+
var errorMessage = 'The autoFocus prop should not be used, as it can reduce usability and accessibility for users.';
|
|
22
|
+
var schema = (0, _schemas.generateObjSchema)({
|
|
23
|
+
ignoreNonDOM: {
|
|
24
|
+
type: 'boolean',
|
|
25
|
+
"default": false
|
|
26
|
+
}
|
|
27
|
+
});
|
|
28
|
+
var _default = exports["default"] = {
|
|
29
|
+
meta: {
|
|
30
|
+
docs: {
|
|
31
|
+
url: 'https://github.com/jsx-eslint/eslint-plugin-jsx-a11y/tree/HEAD/docs/rules/no-autofocus.md',
|
|
32
|
+
description: 'Enforce autoFocus prop is not used.'
|
|
33
|
+
},
|
|
34
|
+
schema: [schema]
|
|
35
|
+
},
|
|
36
|
+
create: function create(context) {
|
|
37
|
+
var elementType = (0, _getElementType["default"])(context);
|
|
38
|
+
return {
|
|
39
|
+
JSXAttribute: function JSXAttribute(attribute) {
|
|
40
|
+
// Determine if ignoreNonDOM is set to true
|
|
41
|
+
// If true, then do not run rule.
|
|
42
|
+
var options = context.options[0] || {};
|
|
43
|
+
var ignoreNonDOM = !!options.ignoreNonDOM;
|
|
44
|
+
if (ignoreNonDOM) {
|
|
45
|
+
var type = elementType(attribute.parent);
|
|
46
|
+
if (!_ariaQuery.dom.get(type)) {
|
|
47
|
+
return;
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
// Don't normalize, since React only recognizes autoFocus on low-level DOM elements.
|
|
52
|
+
if ((0, _jsxAstUtils.propName)(attribute) === 'autoFocus') {
|
|
53
|
+
context.report({
|
|
54
|
+
node: attribute,
|
|
55
|
+
message: errorMessage
|
|
56
|
+
});
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
};
|
|
60
|
+
}
|
|
61
|
+
};
|
|
62
|
+
module.exports = exports.default;
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports["default"] = void 0;
|
|
7
|
+
var _schemas = require("../util/schemas");
|
|
8
|
+
var _getElementType = _interopRequireDefault(require("../util/getElementType"));
|
|
9
|
+
function _interopRequireDefault(e) { return e && e.__esModule ? e : { "default": e }; }
|
|
10
|
+
/**
|
|
11
|
+
* @fileoverview Enforce distracting elements are not used.
|
|
12
|
+
* @author Ethan Cohen
|
|
13
|
+
*/
|
|
14
|
+
|
|
15
|
+
// ----------------------------------------------------------------------------
|
|
16
|
+
// Rule Definition
|
|
17
|
+
// ----------------------------------------------------------------------------
|
|
18
|
+
|
|
19
|
+
var errorMessage = function errorMessage(element) {
|
|
20
|
+
return "Do not use <".concat(element, "> elements as they can create visual accessibility issues and are deprecated.");
|
|
21
|
+
};
|
|
22
|
+
var DEFAULT_ELEMENTS = ['marquee', 'blink'];
|
|
23
|
+
var schema = (0, _schemas.generateObjSchema)({
|
|
24
|
+
elements: (0, _schemas.enumArraySchema)(DEFAULT_ELEMENTS)
|
|
25
|
+
});
|
|
26
|
+
var _default = exports["default"] = {
|
|
27
|
+
meta: {
|
|
28
|
+
docs: {
|
|
29
|
+
url: 'https://github.com/jsx-eslint/eslint-plugin-jsx-a11y/tree/HEAD/docs/rules/no-distracting-elements.md',
|
|
30
|
+
description: 'Enforce distracting elements are not used.'
|
|
31
|
+
},
|
|
32
|
+
schema: [schema]
|
|
33
|
+
},
|
|
34
|
+
create: function create(context) {
|
|
35
|
+
var elementType = (0, _getElementType["default"])(context);
|
|
36
|
+
return {
|
|
37
|
+
JSXOpeningElement: function JSXOpeningElement(node) {
|
|
38
|
+
var options = context.options[0] || {};
|
|
39
|
+
var elementOptions = options.elements || DEFAULT_ELEMENTS;
|
|
40
|
+
var type = elementType(node);
|
|
41
|
+
var distractingElement = elementOptions.find(function (element) {
|
|
42
|
+
return type === element;
|
|
43
|
+
});
|
|
44
|
+
if (distractingElement) {
|
|
45
|
+
context.report({
|
|
46
|
+
node,
|
|
47
|
+
message: errorMessage(distractingElement)
|
|
48
|
+
});
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
};
|
|
52
|
+
}
|
|
53
|
+
};
|
|
54
|
+
module.exports = exports.default;
|