UNPKG

@jsxtools/eslint-plugin-jsx-a11y

Version:

Static AST checker for accessibility rules on JSX elements for flat ESLint Config.

48 lines (45 loc) 2.1 kB
const emojiRegex = require('emoji-regex'); const safeRegexTest = require('safe-regex-test'); const jsxAstUtils = require('../util/module/jsx-ast-utils.cjs'); const schemas = require('../util/schemas.cjs'); const getElementType = require('../util/getElementType.cjs'); const isHiddenFromScreenReader = require('../util/isHiddenFromScreenReader.cjs'); const errorMessage = 'Emojis should be wrapped in <span>, have role="img", and have an accessible description with aria-label or aria-labelledby.'; const schema = schemas.generateObjSchema(); const ruleOfAccessibleEmoji = { meta: { docs: { description: "Enforce emojis are wrapped in `<span>` and provide screenreader access.", url: "https://github.com/jsx-eslint/eslint-plugin-jsx-a11y/tree/HEAD/docs/rules/accessible-emoji.md" }, deprecated: true, schema: [schema] }, create: (context) => { const elementType = getElementType(context); const testEmoji = safeRegexTest.default(emojiRegex.default()); return { JSXOpeningElement: (node) => { const literalChildValue = node.parent.children.find((child) => child.type === "Literal" || child.type === "JSXText"); if (literalChildValue && testEmoji(literalChildValue.value)) { const elementIsHidden = isHiddenFromScreenReader(elementType(node), node.attributes); if (elementIsHidden) { return; } const rolePropValue = jsxAstUtils.getLiteralPropValue(jsxAstUtils.getProp(node.attributes, "role")); const ariaLabelProp = jsxAstUtils.getProp(node.attributes, "aria-label"); const arialLabelledByProp = jsxAstUtils.getProp(node.attributes, "aria-labelledby"); const hasLabel = ariaLabelProp !== void 0 || arialLabelledByProp !== void 0; const isSpan = elementType(node) === "span"; if (hasLabel === false || rolePropValue !== "img" || isSpan === false) { context.report({ node, message: errorMessage }); } } } }; } }; module.exports = ruleOfAccessibleEmoji;