"use strict";
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
var _toConsumableArray2 = _interopRequireDefault(require("@babel/runtime/helpers/toConsumableArray"));
var _jsxAstUtils = require("jsx-ast-utils");
var _schemas = require("../util/schemas");
var _hasAccessibleChild = _interopRequireDefault(require("../util/hasAccessibleChild"));
var _isPresentationRole = _interopRequireDefault(require("../util/isPresentationRole"));
/**
* @fileoverview Enforce all elements that require alternative text have it.
* @author Ethan Cohen
*/
// ----------------------------------------------------------------------------
// Rule Definition
// ----------------------------------------------------------------------------
var DEFAULT_ELEMENTS = ['img', 'object', 'area', 'input[type="image"]'];
var schema = (0, _schemas.generateObjSchema)({
elements: _schemas.arraySchema,
img: _schemas.arraySchema,
object: _schemas.arraySchema,
area: _schemas.arraySchema,
'input[type="image"]': _schemas.arraySchema
});
var ariaLabelHasValue = function ariaLabelHasValue(prop) {
var value = (0, _jsxAstUtils.getPropValue)(prop);
if (value === undefined) {
return false;
}
if (typeof value === 'string' && value.length === 0) {
return false;
}
return true;
};
var ruleByElement = {
img(context, node) {
var nodeType = (0, _jsxAstUtils.elementType)(node);
var altProp = (0, _jsxAstUtils.getProp)(node.attributes, 'alt'); // Missing alt prop error.
if (altProp === undefined) {
if ((0, _isPresentationRole["default"])(nodeType, node.attributes)) {
context.report({
node,
message: 'Prefer alt="" over a presentational role. First rule of aria is to not use aria if it can be achieved via native HTML.'
});
return;
} // Check for `aria-label` to provide text alternative
// Don't create an error if the attribute is used correctly. But if it
// isn't, suggest that the developer use `alt` instead.
var ariaLabelProp = (0, _jsxAstUtils.getProp)(node.attributes, 'aria-label');
if (ariaLabelProp !== undefined) {
if (!ariaLabelHasValue(ariaLabelProp)) {
context.report({
node,
message: 'The aria-label attribute must have a value. The alt attribute is preferred over aria-label for images.'
});
}
return;
} // Check for `aria-labelledby` to provide text alternative
// Don't create an error if the attribute is used correctly. But if it
// isn't, suggest that the developer use `alt` instead.
var ariaLabelledbyProp = (0, _jsxAstUtils.getProp)(node.attributes, 'aria-labelledby');
if (ariaLabelledbyProp !== undefined) {
if (!ariaLabelHasValue(ariaLabelledbyProp)) {
context.report({
node,
message: 'The aria-labelledby attribute must have a value. The alt attribute is preferred over aria-labelledby for images.'
});
}
return;
}
context.report({
node,
message: "".concat(nodeType, " elements must have an alt prop, either with meaningful text, or an empty string for decorative images.")
});
return;
} // Check if alt prop is undefined.
var altValue = (0, _jsxAstUtils.getPropValue)(altProp);
var isNullValued = altProp.value === null; //
if (altValue && !isNullValued || altValue === '') {
return;
} // Undefined alt prop error.
context.report({
node,
message: "Invalid alt value for ".concat(nodeType, ". Use alt=\"\" for presentational images.")
});
},
object(context, node) {
var ariaLabelProp = (0, _jsxAstUtils.getProp)(node.attributes, 'aria-label');
var arialLabelledByProp = (0, _jsxAstUtils.getProp)(node.attributes, 'aria-labelledby');
var hasLabel = ariaLabelHasValue(ariaLabelProp) || ariaLabelHasValue(arialLabelledByProp);
var titleProp = (0, _jsxAstUtils.getLiteralPropValue)((0, _jsxAstUtils.getProp)(node.attributes, 'title'));
var hasTitleAttr = !!titleProp;
if (hasLabel || hasTitleAttr || (0, _hasAccessibleChild["default"])(node.parent)) {
return;
}
context.report({
node,
message: 'Embedded