testaro 27.0.0 → 28.0.0

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.
Files changed (118) hide show
  1. package/CONTRIBUTING.md +3 -1
  2. package/README.md +14 -3
  3. package/package.json +2 -1
  4. package/procs/aslint.js +83 -0
  5. package/procs/nav.js +56 -14
  6. package/procs/standardize.js +36 -0
  7. package/run.js +35 -22
  8. package/tests/aslint.js +83 -0
  9. package/tests/axe.js +4 -0
  10. package/tests/qualWeb.js +6 -0
  11. package/aslint/LICENSE +0 -362
  12. package/aslint/README.md +0 -260
  13. package/aslint/app/rules/abstract-rule.ts +0 -83
  14. package/aslint/app/rules/aslint/incorrect-technique-for-hiding-content/incorrect-technique-for-hiding-content.documentation.md +0 -36
  15. package/aslint/app/rules/aslint/incorrect-technique-for-hiding-content/incorrect-technique-for-hiding-content.test.ts +0 -113
  16. package/aslint/app/rules/aslint/incorrect-technique-for-hiding-content/incorrect-technique-for-hiding-content.ts +0 -103
  17. package/aslint/app/rules/aslint/invalid-attribute-dir-value/invalid-attribute-dir-value.documentation.md +0 -34
  18. package/aslint/app/rules/aslint/invalid-attribute-dir-value/invalid-attribute-dir-value.test.ts +0 -82
  19. package/aslint/app/rules/aslint/invalid-attribute-dir-value/invalid-attribute-dir-value.ts +0 -44
  20. package/aslint/app/rules/aslint/label-duplicated-content-title/label-duplicated-content-title.documentation.md +0 -40
  21. package/aslint/app/rules/aslint/label-duplicated-content-title/label-duplicated-content-title.test.ts +0 -48
  22. package/aslint/app/rules/aslint/label-duplicated-content-title/label-duplicated-content-title.ts +0 -37
  23. package/aslint/app/rules/aslint/links-language-destination/links-language-destination.test.ts +0 -50
  24. package/aslint/app/rules/aslint/links-language-destination/links-language-destination.ts +0 -70
  25. package/aslint/app/rules/aslint/main-element-only-one/main-element-only-one.test.ts +0 -55
  26. package/aslint/app/rules/aslint/main-element-only-one/main-element-only-one.ts +0 -83
  27. package/aslint/app/rules/aslint/main-landmark-must-be-top-level/main-landmark-must-be-top-level.test.ts +0 -12
  28. package/aslint/app/rules/aslint/main-landmark-must-be-top-level/main-landmark-must-be-top-level.ts +0 -73
  29. package/aslint/app/rules/aslint/minimum-font-size/minimum-font-size.test.ts +0 -12
  30. package/aslint/app/rules/aslint/minimum-font-size/minimum-font-size.ts +0 -87
  31. package/aslint/app/rules/aslint/missing-href-on-a/missing-href-on-a.test.ts +0 -48
  32. package/aslint/app/rules/aslint/missing-href-on-a/missing-href-on-a.ts +0 -40
  33. package/aslint/app/rules/aslint/misused-aria-on-focusable-element/misused-aria-on-focusable-element.test.ts +0 -12
  34. package/aslint/app/rules/aslint/misused-aria-on-focusable-element/misused-aria-on-focusable-element.ts +0 -66
  35. package/aslint/app/rules/aslint/misused-input-attribute/misused-input-attribute.test.ts +0 -12
  36. package/aslint/app/rules/aslint/misused-input-attribute/misused-input-attribute.ts +0 -134
  37. package/aslint/app/rules/aslint/misused-required-attribute/misused-required-attribute.test.ts +0 -12
  38. package/aslint/app/rules/aslint/misused-required-attribute/misused-required-attribute.ts +0 -90
  39. package/aslint/app/rules/aslint/navigation-landmark-restrictions/navigation-landmark-restrictions.test.ts +0 -12
  40. package/aslint/app/rules/aslint/navigation-landmark-restrictions/navigation-landmark-restrictions.ts +0 -48
  41. package/aslint/app/rules/aslint/obsolete-html-attributes/obsolete-html-attributes.test.ts +0 -12
  42. package/aslint/app/rules/aslint/obsolete-html-attributes/obsolete-html-attributes.ts +0 -148
  43. package/aslint/app/rules/aslint/obsolete-html-elements/obsolete-html-elements.test.ts +0 -12
  44. package/aslint/app/rules/aslint/obsolete-html-elements/obsolete-html-elements.ts +0 -66
  45. package/aslint/app/rules/aslint/outline-zero/outline-zero.test.ts +0 -12
  46. package/aslint/app/rules/aslint/outline-zero/outline-zero.ts +0 -85
  47. package/aslint/app/rules/aslint/overlay/overlay.test.ts +0 -122
  48. package/aslint/app/rules/aslint/overlay/overlay.ts +0 -141
  49. package/aslint/app/rules/aslint/redundant/aria-role-dialog/aria-role-dialog.documentation.md +0 -49
  50. package/aslint/app/rules/aslint/redundant/aria-role-dialog/aria-role-dialog.test.ts +0 -91
  51. package/aslint/app/rules/aslint/redundant/aria-role-dialog/aria-role-dialog.ts +0 -62
  52. package/aslint/app/rules/aslint/redundant/capital-letters-words/capital-letters-words.documentation.md +0 -44
  53. package/aslint/app/rules/aslint/redundant/capital-letters-words/capital-letters-words.test.ts +0 -111
  54. package/aslint/app/rules/aslint/redundant/capital-letters-words/capital-letters-words.ts +0 -120
  55. package/aslint/app/rules/aslint/redundant/contentinfo-landmark-only-one/contentinfo-landmark-only-one.documentation.md +0 -45
  56. package/aslint/app/rules/aslint/redundant/contentinfo-landmark-only-one/contentinfo-landmark-only-one.test.ts +0 -63
  57. package/aslint/app/rules/aslint/redundant/contentinfo-landmark-only-one/contentinfo-landmark-only-one.ts +0 -44
  58. package/aslint/app/rules/aslint/redundant/empty-title-attribute/empty-title-attribute.documentation.md +0 -55
  59. package/aslint/app/rules/aslint/redundant/empty-title-attribute/empty-title-attribute.test.ts +0 -80
  60. package/aslint/app/rules/aslint/redundant/empty-title-attribute/empty-title-attribute.ts +0 -58
  61. package/aslint/app/rules/aslint/redundant/flash-content/flash-content.documentation.md +0 -48
  62. package/aslint/app/rules/aslint/redundant/flash-content/flash-content.test.ts +0 -52
  63. package/aslint/app/rules/aslint/redundant/flash-content/flash-content.ts +0 -32
  64. package/aslint/app/rules/aslint/redundant/font-style-italic/font-style-italic.documentation.md +0 -44
  65. package/aslint/app/rules/aslint/redundant/font-style-italic/font-style-italic.test.ts +0 -12
  66. package/aslint/app/rules/aslint/redundant/font-style-italic/font-style-italic.ts +0 -83
  67. package/aslint/app/rules/aslint/redundant/h1-must-be/h1-must-be.documentation.md +0 -46
  68. package/aslint/app/rules/aslint/redundant/h1-must-be/h1-must-be.test.ts +0 -46
  69. package/aslint/app/rules/aslint/redundant/h1-must-be/h1-must-be.ts +0 -36
  70. package/aslint/app/rules/aslint/role-application/role-application.test.ts +0 -48
  71. package/aslint/app/rules/aslint/role-application/role-application.ts +0 -38
  72. package/aslint/app/rules/aslint/rtl-content/rtl-content.test.ts +0 -12
  73. package/aslint/app/rules/aslint/rtl-content/rtl-content.ts +0 -75
  74. package/aslint/app/rules/aslint/unclear-uri-on-a/unclear-anchor-uri.test.ts +0 -12
  75. package/aslint/app/rules/aslint/unclear-uri-on-a/unclear-anchor-uri.ts +0 -48
  76. package/aslint/app/rules/aslint/unimportant/aria-hidden-false/aria-hidden-false.test.ts +0 -73
  77. package/aslint/app/rules/aslint/unimportant/aria-hidden-false/aria-hidden-false.ts +0 -34
  78. package/aslint/app/rules/aslint/unimportant/aria-hidden-false/aria-hidden.documentation.md +0 -32
  79. package/aslint/app/rules/aslint/unimportant/content-editable-missing-attributes/content-editable-missing-attributes.docmentation.md +0 -48
  80. package/aslint/app/rules/aslint/unimportant/content-editable-missing-attributes/content-editable-missing-attributes.test.ts +0 -67
  81. package/aslint/app/rules/aslint/unimportant/content-editable-missing-attributes/content-editable-missing-attributes.ts +0 -63
  82. package/aslint/app/rules/aslint/unsupported-role-on-element/unsupported-role-on-element.test.ts +0 -12
  83. package/aslint/app/rules/aslint/unsupported-role-on-element/unsupported-role-on-element.ts +0 -63
  84. package/aslint/app/rules/aslint/used/elements-not-allowed-in-head/elements-not-allowed-in-head.documentation.md +0 -65
  85. package/aslint/app/rules/aslint/used/elements-not-allowed-in-head/elements-not-allowed-in-head.test.ts +0 -53
  86. package/aslint/app/rules/aslint/used/elements-not-allowed-in-head/elements-not-allowed-in-head.ts +0 -47
  87. package/aslint/app/rules/aslint/used/headings-sibling-unique/headings-sibling-unique.documentation.md +0 -57
  88. package/aslint/app/rules/aslint/used/headings-sibling-unique/headings-sibling-unique.test.ts +0 -52
  89. package/aslint/app/rules/aslint/used/headings-sibling-unique/headings-sibling-unique.ts +0 -63
  90. package/aslint/app/rules/aslint/used/horizontal-rule/horizontal-rule.documentation.md +0 -39
  91. package/aslint/app/rules/aslint/used/horizontal-rule/horizontal-rule.test.ts +0 -66
  92. package/aslint/app/rules/aslint/used/horizontal-rule/horizontal-rule.ts +0 -37
  93. package/aslint/utils/aria.test.ts +0 -12
  94. package/aslint/utils/aria.ts +0 -120
  95. package/aslint/utils/async.test.ts +0 -25
  96. package/aslint/utils/async.ts +0 -22
  97. package/aslint/utils/common.test.ts +0 -239
  98. package/aslint/utils/common.ts +0 -168
  99. package/aslint/utils/console.test.ts +0 -85
  100. package/aslint/utils/console.ts +0 -89
  101. package/aslint/utils/css.test.ts +0 -153
  102. package/aslint/utils/css.ts +0 -191
  103. package/aslint/utils/dom.test.ts +0 -627
  104. package/aslint/utils/dom.ts +0 -1051
  105. package/aslint/utils/env.test.ts +0 -14
  106. package/aslint/utils/env.ts +0 -8
  107. package/aslint/utils/func.test.ts +0 -160
  108. package/aslint/utils/func.ts +0 -70
  109. package/aslint/utils/global.test.ts +0 -12
  110. package/aslint/utils/global.ts +0 -25
  111. package/aslint/utils/object.test.ts +0 -524
  112. package/aslint/utils/object.ts +0 -278
  113. package/aslint/utils/report.test.ts +0 -56
  114. package/aslint/utils/report.ts +0 -36
  115. package/aslint/utils/text.test.ts +0 -270
  116. package/aslint/utils/text.ts +0 -165
  117. package/aslint/utils/time.test.ts +0 -43
  118. package/aslint/utils/time.ts +0 -33
@@ -1,120 +0,0 @@
1
- import { DomUtility } from '../../../utils/dom';
2
- import { Css } from '../../../utils/css';
3
- import { TextUtility } from '../../../utils/text';
4
- import { CATEGORY_TYPE } from '../../../constants/categoryType';
5
- import { IIssueReport } from '../../../interfaces/rule-issue.interface';
6
- import { TranslateService } from '../../../services/translate';
7
- import { $severity } from '../../../constants/accessibility';
8
- import { $accessibilityAuditRules } from '../../../constants/accessibility';
9
- import { AbstractRule, IAbstractRuleConfig } from '../../abstract-rule';
10
-
11
- export class CapitalLettersWords extends AbstractRule {
12
- protected selector: string = `*${[
13
- ':root',
14
- 'head',
15
- 'style',
16
- 'script',
17
- 'noscript',
18
- 'meta',
19
- 'link',
20
- 'br',
21
- 'hr',
22
- 'object',
23
- 'svg',
24
- 'path',
25
- 'defs',
26
- 'rect',
27
- 'clippath',
28
- 'use',
29
- 'g',
30
- 'b',
31
- 'filter',
32
- 'img',
33
- 'picture',
34
- 'input',
35
- 'iframe',
36
- 'code',
37
- 'metadata',
38
- ':empty'
39
- ].map((i: string): string => {
40
- return `:not(${i})`;
41
- }).join('')}`;
42
-
43
- protected ruleConfig: IAbstractRuleConfig = {
44
- id: TextUtility.convertUnderscoresToDashes($accessibilityAuditRules.capital_letters_words),
45
- links: [
46
- {
47
- content: 'Dyslexia Font and Style Guide',
48
- url: 'https://www.dyslexia-reading-well.com/dyslexia-font.html'
49
- },
50
- {
51
- content: 'Typefaces for dyslexia',
52
- url: 'https://bdatech.org/what-technology/typefaces-for-dyslexia/'
53
- }
54
- ],
55
- recommendations: [],
56
- severity: $severity.high,
57
- type: CATEGORY_TYPE.BEST_PRACTICE
58
- };
59
-
60
- public validate(nodes: HTMLElement[]): void {
61
- const onlyWordsWithUpperCases = (word: string): boolean => {
62
- return TextUtility.isUpperCase(word);
63
- };
64
-
65
- const processNode = (element: HTMLElement): void => {
66
- const report: IIssueReport = {
67
- message: '',
68
- node: element,
69
- ruleId: this.ruleConfig.id
70
- };
71
-
72
- let reportMessage: string = '';
73
-
74
- let words: string[];
75
- let onlyWordsWithUpperCase: string[] = [];
76
-
77
- const text: string = DomUtility.getTextFromDescendantContent(element).trim();
78
-
79
- words = text.split(' ');
80
-
81
- if (text.length > 0 && words.length > 0) {
82
- if (Css.isCssTextTransformUsed(element)) {
83
- reportMessage = TranslateService.instant('capital_letters_words_report_message1', [text.toUpperCase()]);
84
- } else {
85
-
86
- onlyWordsWithUpperCase = words.filter(onlyWordsWithUpperCases);
87
-
88
- if (onlyWordsWithUpperCase.length > 1) {
89
- reportMessage = TranslateService.instant('capital_letters_words_report_message2');
90
- }
91
- }
92
- }
93
-
94
- const titleAttribute: string | null = element.getAttribute('title');
95
-
96
- if (typeof titleAttribute === 'string' && titleAttribute.trim().length > 0) {
97
- words = titleAttribute.split(' ');
98
- onlyWordsWithUpperCase = words.filter(onlyWordsWithUpperCases);
99
-
100
- if (onlyWordsWithUpperCase.length > 1) {
101
- if (reportMessage.length === 0) {
102
- reportMessage = TranslateService.instant('capital_letters_words_report_message3', [titleAttribute]);
103
- } else {
104
- reportMessage = TranslateService.instant('capital_letters_words_report_message4', [titleAttribute]);
105
- }
106
- }
107
- }
108
-
109
- if (reportMessage.length === 0) {
110
- return;
111
- }
112
-
113
- report.message = `${reportMessage} ${TranslateService.instant('capital_letters_words_report_explanation')}`;
114
-
115
- this.validator.report(report);
116
- };
117
-
118
- nodes.forEach(processNode);
119
- }
120
- }
@@ -1,45 +0,0 @@
1
- # contentinfo-landmark-only-one
2
-
3
- ## Rule id
4
-
5
- `contentinfo-landmark-only-one`
6
-
7
- ## Definition
8
-
9
- This rule verifies if there is no more than 1 element with an attribute `role="contentinfo"`.
10
-
11
- ## Purpose
12
-
13
- Based on https://www.w3.org/TR/wai-aria/#contentinfo
14
-
15
- > Within any document or application, the author SHOULD mark no more than one element with the contentinfo role.
16
-
17
-
18
- ## Test cases
19
-
20
- ### Passed
21
-
22
- The rule passes when all of the following cases are fulfilled:
23
-
24
- 1. There is no more than 1 element with an attribute `role="contentinfo"`
25
-
26
- ## WCAG Success Criteria
27
-
28
- Not Applicable
29
-
30
- ## Best Practice
31
-
32
- Yes
33
-
34
- ## User Impact
35
-
36
- * **Severity**: low
37
- * **Disabilities Affected**:
38
- * Visual:
39
- * blindness
40
-
41
- ## Resources
42
-
43
- * https://www.w3.org/TR/wai-aria/#contentinfo
44
- * http://www.w3.org/TR/WCAG20-TECHS/ARIA11
45
-
@@ -1,63 +0,0 @@
1
- import { ContentinfoLandmarkOnlyOne } from './contentinfo-landmark-only-one';
2
- import { DomUtility } from '../../../utils/dom';
3
- import { Validator } from '../../../validator';
4
-
5
- describe('Rules', () => {
6
-
7
- describe('ContentinfoLandmarkOnlyOne', () => {
8
-
9
- let fakeDom;
10
-
11
- new ContentinfoLandmarkOnlyOne().registerValidator();
12
-
13
- beforeEach(() => {
14
- fakeDom = document.createElement('div');
15
- fakeDom.id = 'fakedom';
16
- document.body.appendChild(fakeDom);
17
-
18
- Validator.reset();
19
- });
20
-
21
- afterEach(() => {
22
- DomUtility.remove(document.getElementById('fakedom'));
23
- fakeDom = undefined;
24
- });
25
-
26
- it('should return one report when there is an element with more than one attribute role="contentinfo"', () => {
27
- fakeDom.innerHTML = '<div role="contentinfo"></div><div role="contentinfo"></div>';
28
-
29
- const nodes = DomUtility.querySelectorAllExclude('[role=contentinfo]', fakeDom);
30
-
31
- new ContentinfoLandmarkOnlyOne().validate(nodes);
32
-
33
- expect(Object.keys(Validator.getReports()).length).toBe(2);
34
- expect(Validator.getReport('report_0').message).toBe('Expected attribute <code>role&#x3D;&quot;contentinfo&quot;</code> to be defined only once. You have 2 .');
35
- expect(Validator.getReport('report_0').node.nodeName.toLowerCase()).toBe('div');
36
- expect(Validator.getReport('report_0').ruleId).toBe('contentinfo-landmark-only-one');
37
- expect(Validator.getReport('report_1').message).toBe('Expected attribute <code>role&#x3D;&quot;contentinfo&quot;</code> to be defined only once. You have 2 .');
38
- expect(Validator.getReport('report_1').node.nodeName.toLowerCase()).toBe('div');
39
- expect(Validator.getReport('report_1').ruleId).toBe('contentinfo-landmark-only-one');
40
- });
41
-
42
- it('should return no reports when there is 1 element with attribute role="contentinfo"', () => {
43
- fakeDom.innerHTML = '<div role="contentinfo">';
44
-
45
- const nodes = DomUtility.querySelectorAllExclude('[role=contentinfo]', fakeDom);
46
-
47
- new ContentinfoLandmarkOnlyOne().validate(nodes);
48
-
49
- expect(Object.keys(Validator.getReports()).length).toBe(0);
50
- });
51
-
52
- it('should return no reports when there is no elements with attribute role="contentinfo"', () => {
53
- fakeDom.innerHTML = '<div>contentinfo</div>';
54
- const nodes = DomUtility.querySelectorAllExclude('[role=contentinfo]', fakeDom);
55
-
56
- new ContentinfoLandmarkOnlyOne().validate(nodes);
57
-
58
- expect(Object.keys(Validator.getReports()).length).toBe(0);
59
- });
60
-
61
- });
62
-
63
- });
@@ -1,44 +0,0 @@
1
- import { TextUtility } from '../../../utils/text';
2
- import { CATEGORY_TYPE } from '../../../constants/categoryType';
3
- import { IIssueReport } from '../../../interfaces/rule-issue.interface';
4
- import { $accessibilityAuditRules, $severity } from '../../../constants/accessibility';
5
- import { TranslateService } from '../../../services/translate';
6
- import { AbstractRule, IAbstractRuleConfig } from '../../abstract-rule';
7
-
8
- export class ContentinfoLandmarkOnlyOne extends AbstractRule {
9
- protected selector: string = '[role="contentinfo"]';
10
- protected ruleConfig: IAbstractRuleConfig = {
11
- id: TextUtility.convertUnderscoresToDashes($accessibilityAuditRules.contentinfo_landmark_only_one),
12
- links: [
13
- {
14
- content: 'ARIA11: Using ARIA landmarks to identify regions of a page',
15
- url: 'http://www.w3.org/TR/WCAG20-TECHS/ARIA11'
16
- },
17
- {
18
- content: 'Accessible Rich Internet Applications (WAI-ARIA) 1.0 Specification: contentinfo role',
19
- url: 'https://www.w3.org/TR/wai-aria/#contentinfo'
20
- }
21
- ],
22
- recommendations: [],
23
- severity: $severity.low,
24
- type: CATEGORY_TYPE.BEST_PRACTICE
25
- };
26
-
27
- public validate(nodes: Element[]): void {
28
- const total: number = nodes.length;
29
-
30
- if (total > 1) {
31
- nodes.forEach((element: Element): void => {
32
- const reportMessage: string = TranslateService.instant('contentinfo_landmark_only_one_report_message', [TextUtility.escape('role="contentinfo"'), total, '.']);
33
-
34
- const report: IIssueReport = {
35
- message: reportMessage,
36
- node: element,
37
- ruleId: this.ruleConfig.id
38
- };
39
-
40
- this.validator.report(report);
41
- });
42
- }
43
- }
44
- }
@@ -1,55 +0,0 @@
1
- # empty-title-attribute
2
-
3
- ## Rule id
4
-
5
- `empty-title-attribute`
6
-
7
- ## Definition
8
-
9
- This rule verifies if there are elements that have an attribute `title` with an empty value. This includes also whitespaces.
10
-
11
- ## Purpose
12
-
13
- `title` attribute should not be empty. This will ensure that the value of `title` will be processed in a predictable way. As a side effect removing an empty value of `title` attribute will make the code smaller, which means less data to transfer and faster processing by e.g. the browser.
14
-
15
- Following elements are being skip while evaluating this rule:
16
-
17
- <img/>,
18
- <html>,
19
- <head>,
20
- <title>,
21
- <body>,
22
- <link/>,
23
- <meta>,
24
- <title>,
25
- <style>,
26
- <script>,
27
- <noscript>,
28
- <iframe>,
29
- <br/>,
30
- <hr/>
31
-
32
- ## Test cases
33
-
34
- ### Passed
35
-
36
- The rule passes when element have an attribute `title` with non-empty value. This includes also whitespaces.
37
-
38
- ## WCAG Success Criteria
39
-
40
- Not Applicable
41
-
42
- ## Best Practice
43
-
44
- Yes
45
-
46
- ## User Impact
47
-
48
- * **Severity**: low
49
- * **Disabilities Affected**:
50
- * Visual:
51
- * blindness
52
-
53
- ## Resources
54
-
55
- * https://developer.mozilla.org/en-US/docs/Web/HTML/Global_attributes/title#accessibility_concerns
@@ -1,80 +0,0 @@
1
- import { DomUtility } from '../../../utils/dom';
2
- import { Validator } from '../../../validator';
3
- import { EmptyTitleAttribute } from './empty-title-attribute';
4
-
5
- describe('Rules', () => {
6
-
7
- describe('EmptyTitleAttribute', () => {
8
-
9
- const selector: string = `[title]${[
10
- ':not(img)',
11
- ':not(html)',
12
- ':not(head)',
13
- ':not(title)',
14
- ':not(body)',
15
- ':not(link)',
16
- ':not(meta)',
17
- ':not(title)',
18
- ':not(style)',
19
- ':not(script)',
20
- ':not(noscript)',
21
- ':not(iframe)',
22
- ':not(br)',
23
- ':not(hr)'
24
- ].join('')}`;
25
-
26
- let fakeDom;
27
-
28
- new EmptyTitleAttribute().registerValidator();
29
-
30
- beforeEach(() => {
31
- fakeDom = document.createElement('div');
32
- fakeDom.id = 'fakedom';
33
- document.body.appendChild(fakeDom);
34
-
35
- Validator.reset();
36
- });
37
-
38
- afterEach(() => {
39
- DomUtility.remove(document.getElementById('fakedom'));
40
- fakeDom = undefined;
41
- });
42
-
43
- it('should return one report when there is an element with defined an attribute title with an empty value', () => {
44
- fakeDom.innerHTML = '<div title="">test</div>';
45
-
46
- const nodes = DomUtility.querySelectorAllExclude(selector, fakeDom);
47
-
48
- new EmptyTitleAttribute().validate(nodes);
49
-
50
- expect(Object.keys(Validator.getReports()).length).toBe(1);
51
- expect(Validator.getReport('report_0').message).toBe('You have an attribute <code>title</code> with an empty content.');
52
- expect(Validator.getReport('report_0').node.nodeName.toLowerCase()).toBe('div');
53
- expect(Validator.getReport('report_0').ruleId).toBe('empty-title-attribute');
54
- });
55
-
56
- it('should return one report when there is an element with defined an attribute title with an empty value (only spaces)', () => {
57
- fakeDom.innerHTML = '<div title=" ">test</div>';
58
-
59
- const nodes = DomUtility.querySelectorAllExclude(selector, fakeDom);
60
-
61
- new EmptyTitleAttribute().validate(nodes);
62
-
63
- expect(Object.keys(Validator.getReports()).length).toBe(1);
64
- expect(Validator.getReport('report_0').message).toBe('You have an attribute <code>title</code> with an empty content.');
65
- expect(Validator.getReport('report_0').node.nodeName.toLowerCase()).toBe('div');
66
- expect(Validator.getReport('report_0').ruleId).toBe('empty-title-attribute');
67
- });
68
-
69
- it('should return no reports when there is an element with attribute title and non-empty value', () => {
70
- fakeDom.innerHTML = '<div title="some title">test</div>';
71
-
72
- const nodes = DomUtility.querySelectorAllExclude(selector, fakeDom);
73
-
74
- new EmptyTitleAttribute().validate(nodes);
75
-
76
- expect(Object.keys(Validator.getReports()).length).toBe(0);
77
- });
78
-
79
- });
80
- });
@@ -1,58 +0,0 @@
1
- import { CATEGORY_TYPE } from '../../../constants/categoryType';
2
- import { IIssueReport } from '../../../interfaces/rule-issue.interface';
3
- import { TextUtility } from '../../../utils/text';
4
- import { TranslateService } from '../../../services/translate';
5
- import { $accessibilityAuditRules, $severity } from '../../../constants/accessibility';
6
- import { AbstractRule, IAbstractRuleConfig } from '../../abstract-rule';
7
-
8
- export class EmptyTitleAttribute extends AbstractRule {
9
- protected selector: string = `[title]${[
10
- ':not(img)',
11
- ':not(html)',
12
- ':not(head)',
13
- ':not(title)',
14
- ':not(body)',
15
- ':not(link)',
16
- ':not(meta)',
17
- ':not(title)',
18
- ':not(style)',
19
- ':not(script)',
20
- ':not(noscript)',
21
- ':not(iframe)',
22
- ':not(br)',
23
- ':not(hr)'
24
- ].join('')}`;
25
-
26
- protected ruleConfig: IAbstractRuleConfig = {
27
- id: TextUtility.convertUnderscoresToDashes($accessibilityAuditRules.empty_title_attribute),
28
- links: [
29
- {
30
- content: 'H67: Using null alt text and no title attribute on img elements for images that AT should ignore',
31
- url: 'https://www.w3.org/TR/WCAG20-TECHS/H67.html'
32
- }
33
- ],
34
- recommendations: [],
35
- severity: $severity.low,
36
- type: CATEGORY_TYPE.BEST_PRACTICE
37
- };
38
-
39
- public validate(elements: Element[]): void {
40
- const reportEmptyTitle = (element: Element): void => {
41
- const titleAttribute: string | null = element.getAttribute('title');
42
-
43
- if (titleAttribute === null || titleAttribute.trim().length > 0) {
44
- return;
45
- }
46
-
47
- const report: IIssueReport = {
48
- message: TranslateService.instant('empty_title_attribute_report_message'),
49
- node: element,
50
- ruleId: this.ruleConfig.id
51
- };
52
-
53
- this.validator.report(report);
54
- };
55
-
56
- elements.forEach(reportEmptyTitle);
57
- }
58
- }
@@ -1,48 +0,0 @@
1
- # flash-content
2
-
3
- ## Rule id
4
-
5
- `flash-content`
6
-
7
- ## Definition
8
-
9
- This rule verifies if there are Adobe Flash Player components.
10
-
11
- ## Purpose
12
-
13
- > Since Adobe no longer supports Flash Player after December 31, 2020 and blocked Flash content from running in Flash Player beginning January 12, 2021, Adobe strongly recommends all users immediately uninstall Flash Player to help protect their systems.
14
-
15
- Source: https://www.adobe.com/products/flashplayer/end-of-life.html
16
-
17
- Due to above security reasons and poor an accessibility support Adobe Flash player should be removed.
18
-
19
- Following elements are being considered as Adobe Flash Player while evaluating this rule:
20
-
21
- CSS selector:
22
-
23
- [classid="clsid:D27CDB6E-AE6D-11cf-96B8-444553540000"], embed[type="application/x-shockwave-flash"], object[type="application/x-shockwave-flash"]
24
-
25
- ## Test cases
26
-
27
- ### Passed
28
-
29
- The rule passes when there are no elements that refers to Adobe Flash Player.
30
-
31
- ## WCAG Success Criteria
32
-
33
- Not Applicable
34
-
35
- ## Best Practice
36
-
37
- Yes
38
-
39
- ## User Impact
40
-
41
- * **Severity**: low
42
- * **Disabilities Affected**:
43
- * Visual:
44
- * blindness
45
-
46
- ## Resources
47
-
48
- * https://www.adobe.com/products/flashplayer/end-of-life.html
@@ -1,52 +0,0 @@
1
- import { FlashContent } from './flash-content';
2
- import { DomUtility } from '../../../utils/dom';
3
- import { Validator } from '../../../validator';
4
-
5
- describe('Rules', () => {
6
-
7
- describe('#flash-content', () => {
8
-
9
- let fakeDom;
10
-
11
- new FlashContent().registerValidator();
12
-
13
- beforeEach(() => {
14
- fakeDom = document.createElement('div');
15
- fakeDom.id = 'fakedom';
16
- document.body.appendChild(fakeDom);
17
-
18
- Validator.reset();
19
- });
20
-
21
- afterEach(() => {
22
- DomUtility.remove(document.getElementById('fakedom'));
23
- fakeDom = undefined;
24
- });
25
-
26
- it('should return one report for one flash object', () => {
27
- const objectEl = document.createElement('object');
28
-
29
- objectEl.setAttribute('classid', 'clsid:D27CDB6E-AE6D-11cf-96B8-444553540000');
30
- objectEl.setAttribute('codebase', 'http://download.macromedia.com/pub/shockwave/cabs/flash/swflash.cab#version=7,0,19,0');
31
- fakeDom.appendChild(objectEl);
32
-
33
- const nodes = DomUtility.querySelectorAllExclude('[classid="clsid:D27CDB6E-AE6D-11cf-96B8-444553540000"]', fakeDom);
34
-
35
- new FlashContent().validate(nodes);
36
-
37
- expect(Object.keys(Validator.getReports()).length).toBe(1);
38
- });
39
-
40
- it('should return no reports where there are no flash objects', () => {
41
- fakeDom.innerHTML = '<a href="#">test</a>';
42
-
43
- const nodes = DomUtility.querySelectorAllExclude('[classid="clsid:D27CDB6E-AE6D-11cf-96B8-444553540000"]', fakeDom);
44
-
45
- new FlashContent().validate(nodes);
46
-
47
- expect(Object.keys(Validator.getReports()).length).toBe(0);
48
- });
49
-
50
- });
51
-
52
- });
@@ -1,32 +0,0 @@
1
- import { CATEGORY_TYPE } from '../../../constants/categoryType';
2
- import { IIssueReport } from '../../../interfaces/rule-issue.interface';
3
- import { TextUtility } from '../../../utils/text';
4
- import { TranslateService } from '../../../services/translate';
5
- import { $severity } from '../../../constants/accessibility';
6
- import { $accessibilityAuditRules } from '../../../constants/accessibility';
7
- import { AbstractRule, IAbstractRuleConfig } from '../../abstract-rule';
8
-
9
- export class FlashContent extends AbstractRule {
10
- protected selector: string = '[classid="clsid:D27CDB6E-AE6D-11cf-96B8-444553540000"], embed[type="application/x-shockwave-flash"], object[type="application/x-shockwave-flash"]';
11
- protected ruleConfig: IAbstractRuleConfig = {
12
- id: TextUtility.convertUnderscoresToDashes($accessibilityAuditRules.flash_content),
13
- links: [],
14
- recommendations: [],
15
- severity: $severity.critical,
16
- type: CATEGORY_TYPE.BEST_PRACTICE
17
- };
18
-
19
- public validate(elements: Element[]): void {
20
- const reportFlash = (element: Element): void => {
21
- const problem: IIssueReport = {
22
- message: TranslateService.instant('flash_content_report_message'),
23
- node: element,
24
- ruleId: this.ruleConfig.id
25
- };
26
-
27
- this.validator.report(problem);
28
- };
29
-
30
- elements.forEach(reportFlash);
31
- }
32
- }
@@ -1,44 +0,0 @@
1
- # font-style-italic
2
-
3
- ## Rule id
4
-
5
- `font-style-italic`
6
-
7
- ## Definition
8
-
9
- This rule verifies if there is defined `font-style` type `italic` for a text with length > 80 chars.
10
-
11
- ## Purpose
12
-
13
- [WCAG Understanding Guideline 3.1](https://www.w3.org/TR/UNDERSTANDING-WCAG20/meaning.html) includes an advisory technique for "avoiding chunks of italic text". Similarly [WebAIM advises](https://webaim.org/articles/evaluatingcognitive/#readability) as follows: "Do not use italics or bold on long sections of text", but at the same time "use various stylistic elements (italics, bold, color, brief animation, or differently-styled content) to highlight important content".
14
-
15
- This rule checks 2 cases:
16
-
17
- * Determine reasonable text length - must be < 80 chars.
18
- * Determine if element has defined `font-style` type `italic`.
19
-
20
- ## Test cases
21
-
22
- ### Passed
23
-
24
- The rule passes when specified element contains text with length > 80 chars and have no defined style `font-style` type `italic`.
25
-
26
- ## WCAG Success Criteria
27
-
28
- Not Applicable
29
-
30
- ## Best Practice
31
-
32
- Yes
33
-
34
- ## User Impact
35
-
36
- * **Severity**: low
37
- * **Disabilities Affected**:
38
- * Visual:
39
- * blindness
40
-
41
- ## Resources
42
-
43
- * https://www.w3.org/TR/UNDERSTANDING-WCAG20/meaning.html
44
- * https://webaim.org/articles/evaluatingcognitive/#readability
@@ -1,12 +0,0 @@
1
- import { FontStyleItalic } from './font-style-italic';
2
-
3
- describe('Rules', () => {
4
-
5
- describe('FontStyleItalic', () => {
6
-
7
- it('should indicate that class exists', () => {
8
- expect(FontStyleItalic).toBeDefined();
9
- });
10
-
11
- });
12
- });