
测试【免费下载链接】axe-coreAccessibility engine for automated Web UI testing项目地址https://gitcode.com/gh_mirrors/ax/axe-core点击查看免费下载本篇指南围绕 axe-core 官方文档 doc/examples/test-patterns.md 展开系统梳理 axe-core自动化 Web UI 无障碍测试引擎的测试约定与分层架构从 commons 工具函数、check evaluate 的单元测试到基于 HTML JSON 配对文件的规则集成测试、完整页面集成测试与虚拟规则测试。读完本文你将掌握 axe-core 测试文件的组织位置、每种测试的固定写法、断言方式与常见陷阱可以直接照着模式为新的规则或检查项补齐测试。测试分层总览单元测试与集成测试的分工axe-core 的测试体系分为两大层单元测试与集成测试。单元测试直接调用被测试函数commons 工具函数或 check 的 evaluate 方法不经过完整的规则引擎集成测试则通过axe.run()或axe.runVirtualRule()走真实审计流程验证规则在真实 DOM / 虚拟节点上的最终行为。两者依赖同一套测试基础设施test/testutils.js中的axe.testUtils命名空间。该文件在测试启动时被注入全局提供了MockCheckContext、queryFixture、queryShadowFixture、getCheckEvaluate、checkSetup等核心方法并为整个测试套件注册全局 mochabeforeEach/afterEach钩子registerHooks在每条用例前后重置 axe 状态并清空#fixture元素。编写任何测试前建议先阅读 test/testutils.js 了解这些工具的行为。单元测试一Commons 工具函数Commons 是 axe-core 对外暴露的公共工具库如axe.commons.text、axe.commons.dom、axe.commons.color等对这些纯函数编写单元测试时直接使用 mocha 的describe/it与 chai 的assert断言即可不需要 fixture 或虚拟节点。官方文档给出的text.sanitize示例体现了 commons 测试的典型写法describe(text.sanitize, function () { it(should collapse whitespace and trim, function () { assert.equal(axe.commons.text.sanitize(\thi\t), hi); assert.equal(axe.commons.text.sanitize(\t\nhi \t), hi); assert.equal(axe.commons.text.sanitize(hello\u00A0there), hello there); }); it(should accept null, function () { assert.equal(axe.commons.text.sanitize(null), ); }); });要点通过全局axe.commons.*直接访问工具函数无需任何 DOM 准备一个it内可包含多个assert.equal覆盖不同输入这里覆盖了制表符、换行、不间断空格\u00A0与null边界测试文件通常放在 test/commons 目录下与源码一一对应的子目录中如test/commons/text/仓库中已有大量同类示例可参考。单元测试二Check 的 evaluate 方法与 commons 不同check 的 evaluate 方法需要真实的this上下文用于收集data()、relatedNodes()、异步结果等因此单元测试必须借助axe.testUtils.MockCheckContext()构造上下文再通过axe.testUtils.getCheckEvaluate(checkId)拿到包装后的 evaluate 函数用.call()绑定上下文调用。官方文档以aria-allowed-attr为例describe(aria-allowed-attr, function () { const fixture document.getElementById(fixture); const checkContext axe.testUtils.MockCheckContext(); afterEach(function () { checkContext.reset(); }); it(should return true if all ARIA attributes are allowed, function () { const vNode queryFixture( div roletextbox aria-placeholderfoo idtarget/div ); assert.isTrue( axe.testUtils .getCheckEvaluate(aria-allowed-attr) .call(checkContext, vNode.actualNode, {}, vNode) ); }); });这里有几层细节值得展开queryFixture(html)来自test/testutils.js的工具方法它把 HTML 注入#fixture元素testUtils.fixtureSetup随后执行axe.setup()构建虚拟树最后按默认选择器#target找到目标节点并返回其VirtualNode在 test/testutils.js 中定义找不到目标时断言失败并给出明确提示。因此被测 HTML 片段中必须包含idtarget的元素。MockCheckContext()返回一个模拟的 check 上下文对象包含_data、_relatedNodes、_onAsync字段以及async()、data()、relatedNodes()、reset()方法实现见 test/testutils.js。每次用例结束后调用checkContext.reset()清空上一次的data、relatedNodes与异步回调避免用例间相互污染。getCheckEvaluate(checkId, testOptions)返回 evaluate 包装器它会在调用前合并 check 的默认选项check.getOptions(options)并在调用后自动校验返回结果是否有对应的 pass / fail / incomplete 消息从axe._audit.data.checks[checkId].messages中查证。这意味着即使你的用例只关心返回值消息完整性也会被隐式验证。对只在规则none数组中使用的 check其消息键与结果相反返回false时查pass消息包装器会自动处理该语义。调用签名.call(checkContext, vNode.actualNode, {}, vNode)三个参数分别是真实 DOM 节点、选项对象这里为空{}、虚拟节点——这正是 check evaluate 在引擎内的标准调用签名见 lib/checks/aria/aria-allowed-attr-evaluate.js 等实现。单元测试三Shadow DOM 场景当被测逻辑需要覆盖 Shadow DOM 内容时使用queryShadowFixture同时准备**宿主light DOM与影子边界shadow DOM**两份 HTMLit(should work with Shadow DOM, function () { const vNode queryShadowFixture( div idhost/div, div rolebutton idtargetTest/div ); // Test your function against the shadow DOM content });queryShadowFixture(content, shadowContent, targetSelector)的实现要点见 test/testutils.js将content注入 fixture在容器上调用attachShadow({ mode: open })再把shadowContent写入 shadow root目标查询优先在 shadow root 内查找#target找不到再回退到 light DOMtargetSelector也可传对象{ shadow, target }自定义两边的选择器挂载完 shadow DOM 后才执行axe.setup()确保扁平化树composed tree包含影子内容返回的仍是目标节点的VirtualNode。需要说明的是随着浏览器对**声明式 Shadow DOMdeclarative shadow DOM**支持度的提升test/testutils.js 中已通过正则/template\sshadowrootmode\s*\s*([]?)open\1/自动检测template shadowrootmodeopen片段并在queryFixture、checkSetup中自动改用setHTMLUnsafe解析、按从深到浅顺序在多层 shadow root 中定位#target。因此新写的 Shadow DOM 用例推荐直接用声明式写法配合queryFixture旧的queryShadowFixture/shadowCheckSetup在源码注释中已被标记为 deprecated。集成测试规则的 HTML JSON 配对文件规则rule级别的行为变更需要配套集成测试。官方文档明确了两类放置位置mocha 托管的规则测试test/integration/rules/rule-name/目录存放规则的 HTML 与 JSON 配对文件完整 HTML 页面测试test/integration/full/rule-name/目录面向需要完整页面上下文的规则如 landmark、页面级规则。文档以aria-allowed-attr为例给出了 HTML 与 JSON 配对文件的格式。HTML 文件如aria-allowed-attr.htmldiv roletextbox aria-placeholderfoo idpass1Valid/div div rolebutton aria-placeholderinvalid idfail1Invalid/div实际仓库中这一目录的命名约定更细test/integration/rules/aria-allowed-attr/下拆分为passes.html、failures.html、incomplete.html三份 HTML分别对应通过、违规、不完整三类预期每份文件内部元素以pass0、pass1… 与fail1、fail2… 等 id 递增编号测试框架按 JSON 中列出的 id 选择器逐一断言可对照 test/integration/rules/aria-allowed-attr/passes.html 与 test/integration/rules/aria-allowed-attr/failures.json。JSON 文件如aria-allowed-attr.json{ description: aria-allowed-attr test, rule: aria-allowed-attr, violations: [[#fail1]], passes: [[#pass1]] }字段说明description测试描述rule被测规则 id必须与lib/rules/rule-name.json中注册的规则 id 一致passes/violations通过 / 违规元素的 id 数组元素 id 使用axe selector 数组格式数组的每个元素依次表示一层 DOM 边界。iframe 内元素的定位格式当目标元素位于 iframe 内部时选择器必须写出跨边界路径——先指向 iframe 元素本身再指向其中的元素{ violations: [[iframe, #fail-inside-iframe]] }这是 axe selector 数组格式的典型应用数组第 1 项是 iframe 的 CSS 选择器第 2 项是 iframe 文档内的目标选择器多层 iframe 依此类推。相关实现可参考test/testutils.js中的shadowQuerySelector与runPartialRecursive后者会递归遍历各 frame 的上下文分别调用axe.runPartial。完整页面集成测试full-page对 landmark 规则、页面级规则这类必须运行在完整 HTML 文档上的规则test/integration/rules/rule/中注入片段的方式不够用应改用test/integration/full/rule-name/。这些测试针对完整 HTML 文档运行axe.run()而不是注入碎片。仓库中的典型结构是每个场景一对*.html*.js文件例如 test/integration/full/landmark-banner-is-top-level/ 下同时存在landmark-banner-is-top-level-pass.html/-pass.js与landmark-banner-is-top-level-fail.html/-fail.js。JS 文件在before钩子中等待嵌套 frame 加载完成后执行axe.run再分别断言 violations / passes / inapplicable / incomplete 的数量例如 test/integration/full/landmark-banner-is-top-level/landmark-banner-is-top-level-pass.jsdescribe(landmark-banner-is-top-level test pass, () { let results; before(done { axe.testUtils.awaitNestedLoad(() { axe.run( { runOnly: { type: rule, values: [landmark-banner-is-top-level] } }, (err, r) { assert.isNull(err); results r; done(); } ); }); }); // ... });关键工具是axe.testUtils.awaitNestedLoad()test/testutils.js它会等待当前文档readyState complete并递归等待所有嵌套 iframe 加载完成再执行回调——对于含 frame 的页面级测试这是必需的等待手段。断言语义与规则集成测试一致results.violations、results.passes[0].nodes、results.inapplicable、results.incomplete分别对应违规、通过、不适用、不完整四类结果。test/integration/full/aria-hidden-body/pass.jstest/integration/full/aria-hidden-body/pass.js是另一个更精简的同类范例。虚拟规则测试virtual rules某些规则不需要真实 DOM仅凭虚拟节点serialized node data即可运行这类规则应在虚拟规则测试中验证其与axe.run()在序列化节点数据上的兼容性。官方文档描述的目录为test/virtual-rules/在当前仓库中对应实现位于test/integration/virtual-rules/内含 48 个*.js测试文件并由 test/test-virtual-rules.js 通过 glob 批量加载运行。每个规则一个describe核心 API 是axe.runVirtualRule(ruleId, vNodeData)describe(aria-allowed-attr virtual-rule, () { it(should pass for required attributes, () { const results axe.runVirtualRule(aria-allowed-attr, { nodeName: div, attributes: { role: checkbox, aria-checked: true } }); assert.lengthOf(results.passes, 1); assert.lengthOf(results.violations, 0); assert.lengthOf(results.incomplete, 0); }); // ... });虚拟节点数据以nodeNameattributes描述元素test/integration/virtual-rules/aria-allowed-attr.js。完整的aria-allowed-attr虚拟规则测试覆盖了必需属性通过、允许属性通过、非法未注册属性通过、无 role 时的全局属性通过、无 role 时的非全局属性违规、role 不允许的属性违规、隐式 rolea href#下的属性违规、通过axe.configure({ standards: { ariaAttrs: {...} } })注入 unsupported 属性后的违规、自定义元素custom-elm1上的非全局属性返回 incomplete以及废弃属性aria-grabbed返回 incomplete、废弃属性叠加违规属性时判违规等边界场景。虚拟规则测试的价值在于它不依赖浏览器 DOM 渲染直接以节点数据驱动完整审计流水线能快速验证规则在纯数据形态下的判定逻辑是补充真实 DOM 集成测试的高性价比手段。因此文档建议为合适的规则新增或同步更新虚拟规则测试。测试约定速查与最佳实践综合官方文档与仓库实现编写 axe-core 测试时可遵循以下约定commons 函数测试放在test/commons/对应子目录直接用assert断言函数返回值无需 DOM。check evaluate 测试用MockCheckContext()管理上下文queryFixture()注入 HTML 并定位#targetgetCheckEvaluate(checkId).call(ctx, node, options, vNode)执行afterEach中checkContext.reset()。Shadow DOM优先用声明式template shadowrootmodeopen配合queryFixture需要传统写法时使用queryShadowFixture。规则集成测试在test/integration/rules/rule/下放置 HTML JSON 配对文件passes/failures/incompleteid 用 axe selector 数组格式iframe 内元素写[iframe, #target]。页面级规则放入test/integration/full/rule/用awaitNestedLoad等待加载后用axe.run断言各类结果数量。虚拟规则在test/integration/virtual-rules/中为规则添加axe.runVirtualRule用例覆盖 pass / violation / incomplete 三类结果。这套模式覆盖了从最小单元到完整页面的全部测试层级。任何改动尤其是规则与 check 行为变更都应按上述约定补齐对应测试并在本地跑通对应测试文件后再提交以保持 axe-core 高覆盖率的测试传统。赞分享测试【免费下载链接】axe-coreAccessibility engine for automated Web UI testing项目地址https://gitcode.com/gh_mirrors/ax/axe-core点击查看免费下载相关推荐Bottlerocket 测试指南从单元测试到 TestSys 集成测试的完整实践Bottlerocket 测试指南从单元测试到 TestSys 集成测试的完整实践 本指南以 Bottlerocket 仓库根目录下的 TESTING.md操作系统云原生安全Camunda Platform 测试指南从单元测试规则到集成测试与多数据库验证的完整实践Camunda Platform 测试指南从单元测试规则到集成测试与多数据库验证的完整实践 本文是 Camunda Platformcamunda bpm后端工作流自动化流程编排5大主流平台社交媒体数据采集解决方案MediaCrawler-new深度解析5大主流平台社交媒体数据采集解决方案MediaCrawler new深度解析 在数据驱动的互联网时代社交媒体已成为信息获取和市场洞察的重要来源。然而面对小网页爬虫后端上一篇碧蓝航线Alas脚本智能自动化配置全攻略下一篇10分钟清出20GBMac上Czkawka磁盘清理实战指南创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考