@najemi-software/vitest-dom 0.13.0 → 0.14.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 (94) hide show
  1. package/dist/extend-expect.d.ts +1 -3
  2. package/dist/extend-expect.js +2 -6
  3. package/dist/extend-expect.js.map +1 -1
  4. package/dist/matchers/css-parse.d.ts +30 -0
  5. package/dist/matchers/css-parse.js +514 -0
  6. package/dist/matchers/css-parse.js.map +1 -0
  7. package/dist/matchers/to-be-checked.d.ts +2 -0
  8. package/dist/matchers/to-be-checked.js +52 -0
  9. package/dist/matchers/to-be-checked.js.map +1 -0
  10. package/dist/matchers/to-be-disabled.d.ts +3 -0
  11. package/dist/matchers/to-be-disabled.js +74 -0
  12. package/dist/matchers/to-be-disabled.js.map +1 -0
  13. package/dist/matchers/to-be-empty-dom-element.d.ts +2 -0
  14. package/dist/matchers/to-be-empty-dom-element.js +31 -0
  15. package/dist/matchers/to-be-empty-dom-element.js.map +1 -0
  16. package/dist/matchers/to-be-empty.d.ts +3 -0
  17. package/dist/matchers/to-be-empty.js +18 -0
  18. package/dist/matchers/to-be-empty.js.map +1 -0
  19. package/dist/matchers/to-be-in-the-document.d.ts +2 -0
  20. package/dist/matchers/to-be-in-the-document.js +24 -0
  21. package/dist/matchers/to-be-in-the-document.js.map +1 -0
  22. package/dist/matchers/to-be-in-the-dom.d.ts +3 -0
  23. package/dist/matchers/to-be-in-the-dom.js +23 -0
  24. package/dist/matchers/to-be-in-the-dom.js.map +1 -0
  25. package/dist/matchers/to-be-invalid.d.ts +3 -0
  26. package/dist/matchers/to-be-invalid.js +50 -0
  27. package/dist/matchers/to-be-invalid.js.map +1 -0
  28. package/dist/matchers/to-be-partially-checked.d.ts +2 -0
  29. package/dist/matchers/to-be-partially-checked.js +36 -0
  30. package/dist/matchers/to-be-partially-checked.js.map +1 -0
  31. package/dist/matchers/to-be-required.d.ts +2 -0
  32. package/dist/matchers/to-be-required.js +40 -0
  33. package/dist/matchers/to-be-required.js.map +1 -0
  34. package/dist/matchers/to-be-visible.d.ts +2 -0
  35. package/dist/matchers/to-be-visible.js +46 -0
  36. package/dist/matchers/to-be-visible.js.map +1 -0
  37. package/dist/matchers/to-contain-element.d.ts +2 -0
  38. package/dist/matchers/to-contain-element.js +19 -0
  39. package/dist/matchers/to-contain-element.js.map +1 -0
  40. package/dist/matchers/to-contain-html.d.ts +2 -0
  41. package/dist/matchers/to-contain-html.js +25 -0
  42. package/dist/matchers/to-contain-html.js.map +1 -0
  43. package/dist/matchers/to-have-accessible-description.d.ts +4 -0
  44. package/dist/matchers/to-have-accessible-description.js +28 -0
  45. package/dist/matchers/to-have-accessible-description.js.map +1 -0
  46. package/dist/matchers/to-have-accessible-errormessage.d.ts +2 -0
  47. package/dist/matchers/to-have-accessible-errormessage.js +48 -0
  48. package/dist/matchers/to-have-accessible-errormessage.js.map +1 -0
  49. package/dist/matchers/to-have-accessible-name.d.ts +3 -0
  50. package/dist/matchers/to-have-accessible-name.js +27 -0
  51. package/dist/matchers/to-have-accessible-name.js.map +1 -0
  52. package/dist/matchers/to-have-attribute.d.ts +2 -0
  53. package/dist/matchers/to-have-attribute.js +34 -0
  54. package/dist/matchers/to-have-attribute.js.map +1 -0
  55. package/dist/matchers/to-have-class.d.ts +2 -0
  56. package/dist/matchers/to-have-class.js +56 -0
  57. package/dist/matchers/to-have-class.js.map +1 -0
  58. package/dist/matchers/to-have-description.d.ts +4 -0
  59. package/dist/matchers/to-have-description.js +30 -0
  60. package/dist/matchers/to-have-description.js.map +1 -0
  61. package/dist/matchers/to-have-display-value.d.ts +2 -0
  62. package/dist/matchers/to-have-display-value.js +31 -0
  63. package/dist/matchers/to-have-display-value.js.map +1 -0
  64. package/dist/matchers/to-have-errormessage.d.ts +3 -0
  65. package/dist/matchers/to-have-errormessage.js +39 -0
  66. package/dist/matchers/to-have-errormessage.js.map +1 -0
  67. package/dist/matchers/to-have-focus.d.ts +2 -0
  68. package/dist/matchers/to-have-focus.js +22 -0
  69. package/dist/matchers/to-have-focus.js.map +1 -0
  70. package/dist/matchers/to-have-form-values.d.ts +2 -0
  71. package/dist/matchers/to-have-form-values.js +67 -0
  72. package/dist/matchers/to-have-form-values.js.map +1 -0
  73. package/dist/matchers/to-have-style.d.ts +2 -0
  74. package/dist/matchers/to-have-style.js +59 -0
  75. package/dist/matchers/to-have-style.js.map +1 -0
  76. package/dist/matchers/to-have-text-content.d.ts +4 -0
  77. package/dist/matchers/to-have-text-content.js +18 -0
  78. package/dist/matchers/to-have-text-content.js.map +1 -0
  79. package/dist/matchers/to-have-value.d.ts +2 -0
  80. package/dist/matchers/to-have-value.js +27 -0
  81. package/dist/matchers/to-have-value.js.map +1 -0
  82. package/dist/matchers/types.d.ts +13 -0
  83. package/dist/matchers/types.js +2 -0
  84. package/dist/matchers/types.js.map +1 -0
  85. package/dist/matchers/utils.d.ts +43 -0
  86. package/dist/matchers/utils.js +217 -0
  87. package/dist/matchers/utils.js.map +1 -0
  88. package/dist/matchers.d.ts +682 -83
  89. package/dist/matchers.js +25 -56
  90. package/dist/matchers.js.map +1 -1
  91. package/package.json +9 -5
  92. package/dist/chunk-DARZWRGS.js +0 -1546
  93. package/dist/chunk-DARZWRGS.js.map +0 -1
  94. package/dist/matchers-CEKfObS0.d.ts +0 -661
@@ -0,0 +1,74 @@
1
+ import { checkHtmlElement, getTag } from "./utils.js";
2
+ // form elements that support 'disabled'
3
+ const FORM_TAGS = ["fieldset", "input", "select", "optgroup", "option", "button", "textarea"];
4
+ /*
5
+ * According to specification:
6
+ * If <fieldset> is disabled, the form controls that are its descendants,
7
+ * except descendants of its first optional <legend> element, are disabled
8
+ *
9
+ * https://html.spec.whatwg.org/multipage/form-elements.html#concept-fieldset-disabled
10
+ *
11
+ * This method tests whether element is first legend child of fieldset parent
12
+ */
13
+ function isFirstLegendChildOfFieldset(element, parent) {
14
+ return (getTag(element) === "legend" &&
15
+ getTag(parent) === "fieldset" &&
16
+ element.isSameNode(Array.from(parent.children).find((child) => getTag(child) === "legend")));
17
+ }
18
+ function isElementDisabledByParent(element, parent) {
19
+ return isElementDisabled(parent) && !isFirstLegendChildOfFieldset(element, parent);
20
+ }
21
+ function isCustomElement(tag) {
22
+ return tag.includes("-");
23
+ }
24
+ /*
25
+ * Only certain form elements and custom elements can actually be disabled:
26
+ * https://html.spec.whatwg.org/multipage/semantics-other.html#disabled-elements
27
+ */
28
+ function canElementBeDisabled(element) {
29
+ const tag = getTag(element);
30
+ return FORM_TAGS.includes(tag) || isCustomElement(tag);
31
+ }
32
+ function isElementDisabled(element) {
33
+ return canElementBeDisabled(element) && element.hasAttribute("disabled");
34
+ }
35
+ function isAncestorDisabled(element) {
36
+ const parent = element.parentElement;
37
+ return Boolean(parent) && (isElementDisabledByParent(element, parent) || isAncestorDisabled(parent));
38
+ }
39
+ function isElementOrAncestorDisabled(element) {
40
+ return canElementBeDisabled(element) && (isElementDisabled(element) || isAncestorDisabled(element));
41
+ }
42
+ export function toBeDisabled(element) {
43
+ checkHtmlElement(element, toBeDisabled, this);
44
+ const isDisabled = isElementOrAncestorDisabled(element);
45
+ return {
46
+ pass: isDisabled,
47
+ message: () => {
48
+ const is = isDisabled ? "is" : "is not";
49
+ return [
50
+ this.utils.matcherHint(`${this.isNot ? ".not" : ""}.toBeDisabled`, "element", ""),
51
+ "",
52
+ `Received element ${is} disabled:`,
53
+ ` ${this.utils.printReceived(element.cloneNode(false))}`,
54
+ ].join("\n");
55
+ },
56
+ };
57
+ }
58
+ export function toBeEnabled(element) {
59
+ checkHtmlElement(element, toBeEnabled, this);
60
+ const isEnabled = !isElementOrAncestorDisabled(element);
61
+ return {
62
+ pass: isEnabled,
63
+ message: () => {
64
+ const is = isEnabled ? "is" : "is not";
65
+ return [
66
+ this.utils.matcherHint(`${this.isNot ? ".not" : ""}.toBeEnabled`, "element", ""),
67
+ "",
68
+ `Received element ${is} enabled:`,
69
+ ` ${this.utils.printReceived(element.cloneNode(false))}`,
70
+ ].join("\n");
71
+ },
72
+ };
73
+ }
74
+ //# sourceMappingURL=to-be-disabled.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"to-be-disabled.js","sourceRoot":"","sources":["../../src/matchers/to-be-disabled.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ import type { MatcherResult } from "./types.js";
2
+ export declare function toBeEmptyDOMElement(element: Element): MatcherResult;
@@ -0,0 +1,31 @@
1
+ import { checkHtmlElement } from "./utils.js";
2
+ export function toBeEmptyDOMElement(element) {
3
+ checkHtmlElement(element, toBeEmptyDOMElement, this);
4
+ return {
5
+ pass: isEmptyElement(element),
6
+ message: () => {
7
+ return [
8
+ this.utils.matcherHint(`${this.isNot ? ".not" : ""}.toBeEmptyDOMElement`, "element", ""),
9
+ "",
10
+ "Received:",
11
+ ` ${this.utils.printReceived(element.innerHTML)}`,
12
+ ].join("\n");
13
+ },
14
+ };
15
+ }
16
+ /**
17
+ * Identifies if an element doesn't contain child nodes (excluding comments)
18
+ * ℹ The literal 8 is Node.COMMENT_NODE. It is used directly instead of the
19
+ * Node constant so the matcher doesn't depend on a global Node existing in
20
+ * the consumer's test environment (this project tests with happy-dom, but
21
+ * consumers may run any environment; historically this guarded against
22
+ * https://github.com/jsdom/jsdom/issues/2220 under jsdom).
23
+ *
24
+ * @param {*} element an HtmlElement or SVGElement
25
+ * @return {*} true if the element only contains comments or none
26
+ */
27
+ function isEmptyElement(element) {
28
+ const nonCommentChildNodes = [...element.childNodes].filter((node) => node.nodeType !== 8);
29
+ return nonCommentChildNodes.length === 0;
30
+ }
31
+ //# sourceMappingURL=to-be-empty-dom-element.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"to-be-empty-dom-element.js","sourceRoot":"","sources":["../../src/matchers/to-be-empty-dom-element.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,gBAAgB,EAAE,MAAM,YAAY,CAAC;AAE9C,MAAM,UAAU,mBAAmB,CAAC,OAAgB;IAChD,gBAAgB,CAAC,OAAO,EAAE,mBAAmB,EAAE,IAAI,CAAC,CAAC;IAErD,OAAO;QACH,IAAI,EAAE,cAAc,CAAC,OAAO,CAAC;QAC7B,OAAO,EAAE,GAAG,EAAE;YACV,OAAO;gBACH,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,sBAAsB,EAAE,SAAS,EAAE,EAAE,CAAC;gBACxF,EAAE;gBACF,WAAW;gBACX,KAAK,IAAI,CAAC,KAAK,CAAC,aAAa,CAAC,OAAO,CAAC,SAAS,CAAC,EAAE;aACrD,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACjB,CAAC;KACJ,CAAC;AACN,CAAC;AAED;;;;;;;;;;GAUG;AACH,SAAS,cAAc,CAAC,OAAO;IAC3B,MAAM,oBAAoB,GAAG,CAAC,GAAG,OAAO,CAAC,UAAU,CAAC,CAAC,MAAM,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,QAAQ,KAAK,CAAC,CAAC,CAAC;IAC3F,OAAO,oBAAoB,CAAC,MAAM,KAAK,CAAC,CAAC;AAC7C,CAAC"}
@@ -0,0 +1,3 @@
1
+ import type { MatcherResult } from "./types.js";
2
+ /** @deprecated */
3
+ export declare function toBeEmpty(element: Element): MatcherResult;
@@ -0,0 +1,18 @@
1
+ import { checkHtmlElement, deprecate } from "./utils.js";
2
+ /** @deprecated */
3
+ export function toBeEmpty(element) {
4
+ deprecate("toBeEmpty", "Please use instead toBeEmptyDOMElement for finding empty nodes in the DOM.");
5
+ checkHtmlElement(element, toBeEmpty, this);
6
+ return {
7
+ pass: element.innerHTML === "",
8
+ message: () => {
9
+ return [
10
+ this.utils.matcherHint(`${this.isNot ? ".not" : ""}.toBeEmpty`, "element", ""),
11
+ "",
12
+ "Received:",
13
+ ` ${this.utils.printReceived(element.innerHTML)}`,
14
+ ].join("\n");
15
+ },
16
+ };
17
+ }
18
+ //# sourceMappingURL=to-be-empty.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"to-be-empty.js","sourceRoot":"","sources":["../../src/matchers/to-be-empty.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,gBAAgB,EAAE,SAAS,EAAE,MAAM,YAAY,CAAC;AAEzD,kBAAkB;AAClB,MAAM,UAAU,SAAS,CAAC,OAAgB;IACtC,SAAS,CAAC,WAAW,EAAE,4EAA4E,CAAC,CAAC;IACrG,gBAAgB,CAAC,OAAO,EAAE,SAAS,EAAE,IAAI,CAAC,CAAC;IAE3C,OAAO;QACH,IAAI,EAAE,OAAO,CAAC,SAAS,KAAK,EAAE;QAC9B,OAAO,EAAE,GAAG,EAAE;YACV,OAAO;gBACH,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,YAAY,EAAE,SAAS,EAAE,EAAE,CAAC;gBAC9E,EAAE;gBACF,WAAW;gBACX,KAAK,IAAI,CAAC,KAAK,CAAC,aAAa,CAAC,OAAO,CAAC,SAAS,CAAC,EAAE;aACrD,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACjB,CAAC;KACJ,CAAC;AACN,CAAC"}
@@ -0,0 +1,2 @@
1
+ import type { MatcherResult } from "./types.js";
2
+ export declare function toBeInTheDocument(element: Element): MatcherResult;
@@ -0,0 +1,24 @@
1
+ import { checkHtmlElement } from "./utils.js";
2
+ export function toBeInTheDocument(element) {
3
+ if (element !== null || !this.isNot) {
4
+ checkHtmlElement(element, toBeInTheDocument, this);
5
+ }
6
+ const pass = element === null ? false : element.ownerDocument === element.getRootNode({ composed: true });
7
+ const errorFound = () => {
8
+ return `expected document not to contain element, found ${this.utils.stringify(element.cloneNode(true))} instead`;
9
+ };
10
+ const errorNotFound = () => {
11
+ return `element could not be found in the document`;
12
+ };
13
+ return {
14
+ pass,
15
+ message: () => {
16
+ return [
17
+ this.utils.matcherHint(`${this.isNot ? ".not" : ""}.toBeInTheDocument`, "element", ""),
18
+ "",
19
+ this.utils.RECEIVED_COLOR(this.isNot ? errorFound() : errorNotFound()),
20
+ ].join("\n");
21
+ },
22
+ };
23
+ }
24
+ //# sourceMappingURL=to-be-in-the-document.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"to-be-in-the-document.js","sourceRoot":"","sources":["../../src/matchers/to-be-in-the-document.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,gBAAgB,EAAE,MAAM,YAAY,CAAC;AAE9C,MAAM,UAAU,iBAAiB,CAAC,OAAgB;IAC9C,IAAI,OAAO,KAAK,IAAI,IAAI,CAAC,IAAI,CAAC,KAAK,EAAE,CAAC;QAClC,gBAAgB,CAAC,OAAO,EAAE,iBAAiB,EAAE,IAAI,CAAC,CAAC;IACvD,CAAC;IAED,MAAM,IAAI,GAAG,OAAO,KAAK,IAAI,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,OAAO,CAAC,aAAa,KAAK,OAAO,CAAC,WAAW,CAAC,EAAE,QAAQ,EAAE,IAAI,EAAE,CAAC,CAAC;IAE1G,MAAM,UAAU,GAAG,GAAG,EAAE;QACpB,OAAO,mDAAmD,IAAI,CAAC,KAAK,CAAC,SAAS,CAC1E,OAAO,CAAC,SAAS,CAAC,IAAI,CAAC,CAC1B,UAAU,CAAC;IAChB,CAAC,CAAC;IACF,MAAM,aAAa,GAAG,GAAG,EAAE;QACvB,OAAO,4CAA4C,CAAC;IACxD,CAAC,CAAC;IAEF,OAAO;QACH,IAAI;QACJ,OAAO,EAAE,GAAG,EAAE;YACV,OAAO;gBACH,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,oBAAoB,EAAE,SAAS,EAAE,EAAE,CAAC;gBACtF,EAAE;gBACF,IAAI,CAAC,KAAK,CAAC,cAAc,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,UAAU,EAAE,CAAC,CAAC,CAAC,aAAa,EAAE,CAAC;aACzE,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACjB,CAAC;KACJ,CAAC;AACN,CAAC"}
@@ -0,0 +1,3 @@
1
+ import type { MatcherResult } from "./types.js";
2
+ /** @deprecated */
3
+ export declare function toBeInTheDOM(element: Element, container?: HTMLElement | SVGElement): MatcherResult;
@@ -0,0 +1,23 @@
1
+ import { checkHtmlElement, deprecate } from "./utils.js";
2
+ /** @deprecated */
3
+ export function toBeInTheDOM(element, container) {
4
+ deprecate("toBeInTheDOM", "Please use toBeInTheDocument for searching the entire document and toContainElement for searching a specific container.");
5
+ if (element) {
6
+ checkHtmlElement(element, toBeInTheDOM, this);
7
+ }
8
+ if (container) {
9
+ checkHtmlElement(container, toBeInTheDOM, this);
10
+ }
11
+ return {
12
+ pass: container ? container.contains(element) : !!element,
13
+ message: () => {
14
+ return [
15
+ this.utils.matcherHint(`${this.isNot ? ".not" : ""}.toBeInTheDOM`, "element", ""),
16
+ "",
17
+ "Received:",
18
+ ` ${this.utils.printReceived(element ? element.cloneNode(false) : element)}`,
19
+ ].join("\n");
20
+ },
21
+ };
22
+ }
23
+ //# sourceMappingURL=to-be-in-the-dom.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"to-be-in-the-dom.js","sourceRoot":"","sources":["../../src/matchers/to-be-in-the-dom.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,gBAAgB,EAAE,SAAS,EAAE,MAAM,YAAY,CAAC;AAEzD,kBAAkB;AAClB,MAAM,UAAU,YAAY,CAAC,OAAgB,EAAE,SAAoC;IAC/E,SAAS,CACL,cAAc,EACd,yHAAyH,CAC5H,CAAC;IAEF,IAAI,OAAO,EAAE,CAAC;QACV,gBAAgB,CAAC,OAAO,EAAE,YAAY,EAAE,IAAI,CAAC,CAAC;IAClD,CAAC;IAED,IAAI,SAAS,EAAE,CAAC;QACZ,gBAAgB,CAAC,SAAS,EAAE,YAAY,EAAE,IAAI,CAAC,CAAC;IACpD,CAAC;IAED,OAAO;QACH,IAAI,EAAE,SAAS,CAAC,CAAC,CAAC,SAAS,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,OAAO;QACzD,OAAO,EAAE,GAAG,EAAE;YACV,OAAO;gBACH,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,eAAe,EAAE,SAAS,EAAE,EAAE,CAAC;gBACjF,EAAE;gBACF,WAAW;gBACX,KAAK,IAAI,CAAC,KAAK,CAAC,aAAa,CAAC,OAAO,CAAC,CAAC,CAAC,OAAO,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,EAAE;aAChF,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACjB,CAAC;KACJ,CAAC;AACN,CAAC"}
@@ -0,0 +1,3 @@
1
+ import type { MatcherResult } from "./types.js";
2
+ export declare function toBeInvalid(element: Element): MatcherResult;
3
+ export declare function toBeValid(element: Element): MatcherResult;
@@ -0,0 +1,50 @@
1
+ import { checkHtmlElement, getTag } from "./utils.js";
2
+ const FORM_TAGS = ["form", "input", "select", "textarea"];
3
+ function isElementHavingAriaInvalid(element) {
4
+ return element.hasAttribute("aria-invalid") && element.getAttribute("aria-invalid") !== "false";
5
+ }
6
+ function isSupportsValidityMethod(element) {
7
+ return FORM_TAGS.includes(getTag(element));
8
+ }
9
+ function isElementInvalid(element) {
10
+ const isHaveAriaInvalid = isElementHavingAriaInvalid(element);
11
+ if (isSupportsValidityMethod(element)) {
12
+ return isHaveAriaInvalid || !element.checkValidity();
13
+ }
14
+ else {
15
+ return isHaveAriaInvalid;
16
+ }
17
+ }
18
+ export function toBeInvalid(element) {
19
+ checkHtmlElement(element, toBeInvalid, this);
20
+ const isInvalid = isElementInvalid(element);
21
+ return {
22
+ pass: isInvalid,
23
+ message: () => {
24
+ const is = isInvalid ? "is" : "is not";
25
+ return [
26
+ this.utils.matcherHint(`${this.isNot ? ".not" : ""}.toBeInvalid`, "element", ""),
27
+ "",
28
+ `Received element ${is} currently invalid:`,
29
+ ` ${this.utils.printReceived(element.cloneNode(false))}`,
30
+ ].join("\n");
31
+ },
32
+ };
33
+ }
34
+ export function toBeValid(element) {
35
+ checkHtmlElement(element, toBeValid, this);
36
+ const isValid = !isElementInvalid(element);
37
+ return {
38
+ pass: isValid,
39
+ message: () => {
40
+ const is = isValid ? "is" : "is not";
41
+ return [
42
+ this.utils.matcherHint(`${this.isNot ? ".not" : ""}.toBeValid`, "element", ""),
43
+ "",
44
+ `Received element ${is} currently valid:`,
45
+ ` ${this.utils.printReceived(element.cloneNode(false))}`,
46
+ ].join("\n");
47
+ },
48
+ };
49
+ }
50
+ //# sourceMappingURL=to-be-invalid.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"to-be-invalid.js","sourceRoot":"","sources":["../../src/matchers/to-be-invalid.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,gBAAgB,EAAE,MAAM,EAAE,MAAM,YAAY,CAAC;AAEtD,MAAM,SAAS,GAAG,CAAC,MAAM,EAAE,OAAO,EAAE,QAAQ,EAAE,UAAU,CAAC,CAAC;AAE1D,SAAS,0BAA0B,CAAC,OAAO;IACvC,OAAO,OAAO,CAAC,YAAY,CAAC,cAAc,CAAC,IAAI,OAAO,CAAC,YAAY,CAAC,cAAc,CAAC,KAAK,OAAO,CAAC;AACpG,CAAC;AAED,SAAS,wBAAwB,CAAC,OAAO;IACrC,OAAO,SAAS,CAAC,QAAQ,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,CAAC;AAC/C,CAAC;AAED,SAAS,gBAAgB,CAAC,OAAO;IAC7B,MAAM,iBAAiB,GAAG,0BAA0B,CAAC,OAAO,CAAC,CAAC;IAC9D,IAAI,wBAAwB,CAAC,OAAO,CAAC,EAAE,CAAC;QACpC,OAAO,iBAAiB,IAAI,CAAC,OAAO,CAAC,aAAa,EAAE,CAAC;IACzD,CAAC;SAAM,CAAC;QACJ,OAAO,iBAAiB,CAAC;IAC7B,CAAC;AACL,CAAC;AAED,MAAM,UAAU,WAAW,CAAC,OAAgB;IACxC,gBAAgB,CAAC,OAAO,EAAE,WAAW,EAAE,IAAI,CAAC,CAAC;IAE7C,MAAM,SAAS,GAAG,gBAAgB,CAAC,OAAO,CAAC,CAAC;IAE5C,OAAO;QACH,IAAI,EAAE,SAAS;QACf,OAAO,EAAE,GAAG,EAAE;YACV,MAAM,EAAE,GAAG,SAAS,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,QAAQ,CAAC;YACvC,OAAO;gBACH,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,cAAc,EAAE,SAAS,EAAE,EAAE,CAAC;gBAChF,EAAE;gBACF,oBAAoB,EAAE,qBAAqB;gBAC3C,KAAK,IAAI,CAAC,KAAK,CAAC,aAAa,CAAC,OAAO,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC,EAAE;aAC5D,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACjB,CAAC;KACJ,CAAC;AACN,CAAC;AAED,MAAM,UAAU,SAAS,CAAC,OAAgB;IACtC,gBAAgB,CAAC,OAAO,EAAE,SAAS,EAAE,IAAI,CAAC,CAAC;IAE3C,MAAM,OAAO,GAAG,CAAC,gBAAgB,CAAC,OAAO,CAAC,CAAC;IAE3C,OAAO;QACH,IAAI,EAAE,OAAO;QACb,OAAO,EAAE,GAAG,EAAE;YACV,MAAM,EAAE,GAAG,OAAO,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,QAAQ,CAAC;YACrC,OAAO;gBACH,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,YAAY,EAAE,SAAS,EAAE,EAAE,CAAC;gBAC9E,EAAE;gBACF,oBAAoB,EAAE,mBAAmB;gBACzC,KAAK,IAAI,CAAC,KAAK,CAAC,aAAa,CAAC,OAAO,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC,EAAE;aAC5D,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACjB,CAAC;KACJ,CAAC;AACN,CAAC"}
@@ -0,0 +1,2 @@
1
+ import type { MatcherResult } from "./types.js";
2
+ export declare function toBePartiallyChecked(element: Element): MatcherResult;
@@ -0,0 +1,36 @@
1
+ import { checkHtmlElement } from "./utils.js";
2
+ export function toBePartiallyChecked(element) {
3
+ checkHtmlElement(element, toBePartiallyChecked, this);
4
+ const isValidInput = () => {
5
+ return element.tagName.toLowerCase() === "input" && element.type === "checkbox";
6
+ };
7
+ const isValidAriaElement = () => {
8
+ return element.getAttribute("role") === "checkbox";
9
+ };
10
+ if (!isValidInput() && !isValidAriaElement()) {
11
+ return {
12
+ pass: false,
13
+ message: () => 'only inputs with type="checkbox" or elements with role="checkbox" and a valid aria-checked attribute can be used with .toBePartiallyChecked(). Use .toHaveValue() instead',
14
+ };
15
+ }
16
+ const isPartiallyChecked = () => {
17
+ const isAriaMixed = element.getAttribute("aria-checked") === "mixed";
18
+ if (isValidInput()) {
19
+ return element.indeterminate || isAriaMixed;
20
+ }
21
+ return isAriaMixed;
22
+ };
23
+ return {
24
+ pass: isPartiallyChecked(),
25
+ message: () => {
26
+ const is = isPartiallyChecked() ? "is" : "is not";
27
+ return [
28
+ this.utils.matcherHint(`${this.isNot ? ".not" : ""}.toBePartiallyChecked`, "element", ""),
29
+ "",
30
+ `Received element ${is} partially checked:`,
31
+ ` ${this.utils.printReceived(element.cloneNode(false))}`,
32
+ ].join("\n");
33
+ },
34
+ };
35
+ }
36
+ //# sourceMappingURL=to-be-partially-checked.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"to-be-partially-checked.js","sourceRoot":"","sources":["../../src/matchers/to-be-partially-checked.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,gBAAgB,EAAE,MAAM,YAAY,CAAC;AAE9C,MAAM,UAAU,oBAAoB,CAAC,OAAgB;IACjD,gBAAgB,CAAC,OAAO,EAAE,oBAAoB,EAAE,IAAI,CAAC,CAAC;IAEtD,MAAM,YAAY,GAAG,GAAG,EAAE;QACtB,OAAO,OAAO,CAAC,OAAO,CAAC,WAAW,EAAE,KAAK,OAAO,IAAI,OAAO,CAAC,IAAI,KAAK,UAAU,CAAC;IACpF,CAAC,CAAC;IAEF,MAAM,kBAAkB,GAAG,GAAG,EAAE;QAC5B,OAAO,OAAO,CAAC,YAAY,CAAC,MAAM,CAAC,KAAK,UAAU,CAAC;IACvD,CAAC,CAAC;IAEF,IAAI,CAAC,YAAY,EAAE,IAAI,CAAC,kBAAkB,EAAE,EAAE,CAAC;QAC3C,OAAO;YACH,IAAI,EAAE,KAAK;YACX,OAAO,EAAE,GAAG,EAAE,CACV,2KAA2K;SAClL,CAAC;IACN,CAAC;IAED,MAAM,kBAAkB,GAAG,GAAG,EAAE;QAC5B,MAAM,WAAW,GAAG,OAAO,CAAC,YAAY,CAAC,cAAc,CAAC,KAAK,OAAO,CAAC;QAErE,IAAI,YAAY,EAAE,EAAE,CAAC;YACjB,OAAO,OAAO,CAAC,aAAa,IAAI,WAAW,CAAC;QAChD,CAAC;QAED,OAAO,WAAW,CAAC;IACvB,CAAC,CAAC;IAEF,OAAO;QACH,IAAI,EAAE,kBAAkB,EAAE;QAC1B,OAAO,EAAE,GAAG,EAAE;YACV,MAAM,EAAE,GAAG,kBAAkB,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,QAAQ,CAAC;YAClD,OAAO;gBACH,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,uBAAuB,EAAE,SAAS,EAAE,EAAE,CAAC;gBACzF,EAAE;gBACF,oBAAoB,EAAE,qBAAqB;gBAC3C,KAAK,IAAI,CAAC,KAAK,CAAC,aAAa,CAAC,OAAO,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC,EAAE;aAC5D,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACjB,CAAC;KACJ,CAAC;AACN,CAAC"}
@@ -0,0 +1,2 @@
1
+ import type { MatcherResult } from "./types.js";
2
+ export declare function toBeRequired(element: Element): MatcherResult;
@@ -0,0 +1,40 @@
1
+ import { checkHtmlElement, getTag } from "./utils.js";
2
+ // form elements that support 'required'
3
+ const FORM_TAGS = ["select", "textarea"];
4
+ const ARIA_FORM_TAGS = ["input", "select", "textarea"];
5
+ const UNSUPPORTED_INPUT_TYPES = ["color", "hidden", "range", "submit", "image", "reset"];
6
+ const SUPPORTED_ARIA_ROLES = ["combobox", "gridcell", "radiogroup", "spinbutton", "tree"];
7
+ function isRequiredOnFormTagsExceptInput(element) {
8
+ return FORM_TAGS.includes(getTag(element)) && element.hasAttribute("required");
9
+ }
10
+ function isRequiredOnSupportedInput(element) {
11
+ return (getTag(element) === "input" &&
12
+ element.hasAttribute("required") &&
13
+ ((element.hasAttribute("type") && !UNSUPPORTED_INPUT_TYPES.includes(element.getAttribute("type"))) ||
14
+ !element.hasAttribute("type")));
15
+ }
16
+ function isElementRequiredByARIA(element) {
17
+ return (element.hasAttribute("aria-required") &&
18
+ element.getAttribute("aria-required") === "true" &&
19
+ (ARIA_FORM_TAGS.includes(getTag(element)) ||
20
+ (element.hasAttribute("role") && SUPPORTED_ARIA_ROLES.includes(element.getAttribute("role")))));
21
+ }
22
+ export function toBeRequired(element) {
23
+ checkHtmlElement(element, toBeRequired, this);
24
+ const isRequired = isRequiredOnFormTagsExceptInput(element) ||
25
+ isRequiredOnSupportedInput(element) ||
26
+ isElementRequiredByARIA(element);
27
+ return {
28
+ pass: isRequired,
29
+ message: () => {
30
+ const is = isRequired ? "is" : "is not";
31
+ return [
32
+ this.utils.matcherHint(`${this.isNot ? ".not" : ""}.toBeRequired`, "element", ""),
33
+ "",
34
+ `Received element ${is} required:`,
35
+ ` ${this.utils.printReceived(element.cloneNode(false))}`,
36
+ ].join("\n");
37
+ },
38
+ };
39
+ }
40
+ //# sourceMappingURL=to-be-required.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"to-be-required.js","sourceRoot":"","sources":["../../src/matchers/to-be-required.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,gBAAgB,EAAE,MAAM,EAAE,MAAM,YAAY,CAAC;AAEtD,wCAAwC;AACxC,MAAM,SAAS,GAAG,CAAC,QAAQ,EAAE,UAAU,CAAC,CAAC;AAEzC,MAAM,cAAc,GAAG,CAAC,OAAO,EAAE,QAAQ,EAAE,UAAU,CAAC,CAAC;AAEvD,MAAM,uBAAuB,GAAG,CAAC,OAAO,EAAE,QAAQ,EAAE,OAAO,EAAE,QAAQ,EAAE,OAAO,EAAE,OAAO,CAAC,CAAC;AAEzF,MAAM,oBAAoB,GAAG,CAAC,UAAU,EAAE,UAAU,EAAE,YAAY,EAAE,YAAY,EAAE,MAAM,CAAC,CAAC;AAE1F,SAAS,+BAA+B,CAAC,OAAO;IAC5C,OAAO,SAAS,CAAC,QAAQ,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,IAAI,OAAO,CAAC,YAAY,CAAC,UAAU,CAAC,CAAC;AACnF,CAAC;AAED,SAAS,0BAA0B,CAAC,OAAO;IACvC,OAAO,CACH,MAAM,CAAC,OAAO,CAAC,KAAK,OAAO;QAC3B,OAAO,CAAC,YAAY,CAAC,UAAU,CAAC;QAChC,CAAC,CAAC,OAAO,CAAC,YAAY,CAAC,MAAM,CAAC,IAAI,CAAC,uBAAuB,CAAC,QAAQ,CAAC,OAAO,CAAC,YAAY,CAAC,MAAM,CAAC,CAAC,CAAC;YAC9F,CAAC,OAAO,CAAC,YAAY,CAAC,MAAM,CAAC,CAAC,CACrC,CAAC;AACN,CAAC;AAED,SAAS,uBAAuB,CAAC,OAAO;IACpC,OAAO,CACH,OAAO,CAAC,YAAY,CAAC,eAAe,CAAC;QACrC,OAAO,CAAC,YAAY,CAAC,eAAe,CAAC,KAAK,MAAM;QAChD,CAAC,cAAc,CAAC,QAAQ,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC;YACrC,CAAC,OAAO,CAAC,YAAY,CAAC,MAAM,CAAC,IAAI,oBAAoB,CAAC,QAAQ,CAAC,OAAO,CAAC,YAAY,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,CACrG,CAAC;AACN,CAAC;AAED,MAAM,UAAU,YAAY,CAAC,OAAgB;IACzC,gBAAgB,CAAC,OAAO,EAAE,YAAY,EAAE,IAAI,CAAC,CAAC;IAE9C,MAAM,UAAU,GACZ,+BAA+B,CAAC,OAAO,CAAC;QACxC,0BAA0B,CAAC,OAAO,CAAC;QACnC,uBAAuB,CAAC,OAAO,CAAC,CAAC;IAErC,OAAO;QACH,IAAI,EAAE,UAAU;QAChB,OAAO,EAAE,GAAG,EAAE;YACV,MAAM,EAAE,GAAG,UAAU,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,QAAQ,CAAC;YACxC,OAAO;gBACH,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,eAAe,EAAE,SAAS,EAAE,EAAE,CAAC;gBACjF,EAAE;gBACF,oBAAoB,EAAE,YAAY;gBAClC,KAAK,IAAI,CAAC,KAAK,CAAC,aAAa,CAAC,OAAO,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC,EAAE;aAC5D,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACjB,CAAC;KACJ,CAAC;AACN,CAAC"}
@@ -0,0 +1,2 @@
1
+ import type { MatcherResult } from "./types.js";
2
+ export declare function toBeVisible(element: Element): MatcherResult;
@@ -0,0 +1,46 @@
1
+ import { checkHtmlElement } from "./utils.js";
2
+ function isStyleVisible(element) {
3
+ const { getComputedStyle } = element.ownerDocument.defaultView;
4
+ const { display, visibility, opacity } = getComputedStyle(element);
5
+ return (display !== "none" &&
6
+ visibility !== "hidden" &&
7
+ visibility !== "collapse" &&
8
+ opacity !== "0" &&
9
+ opacity !== 0);
10
+ }
11
+ function isAttributeVisible(element, previousElement) {
12
+ let detailsVisibility;
13
+ if (previousElement) {
14
+ detailsVisibility =
15
+ element.nodeName === "DETAILS" && previousElement.nodeName !== "SUMMARY"
16
+ ? element.hasAttribute("open")
17
+ : true;
18
+ }
19
+ else {
20
+ detailsVisibility = element.nodeName === "DETAILS" ? element.hasAttribute("open") : true;
21
+ }
22
+ return !element.hasAttribute("hidden") && detailsVisibility;
23
+ }
24
+ function isElementVisible(element, previousElement) {
25
+ return (isStyleVisible(element) &&
26
+ isAttributeVisible(element, previousElement) &&
27
+ (!element.parentElement || isElementVisible(element.parentElement, element)));
28
+ }
29
+ export function toBeVisible(element) {
30
+ checkHtmlElement(element, toBeVisible, this);
31
+ const isInDocument = element.ownerDocument === element.getRootNode({ composed: true });
32
+ const isVisible = isInDocument && isElementVisible(element);
33
+ return {
34
+ pass: isVisible,
35
+ message: () => {
36
+ const is = isVisible ? "is" : "is not";
37
+ return [
38
+ this.utils.matcherHint(`${this.isNot ? ".not" : ""}.toBeVisible`, "element", ""),
39
+ "",
40
+ `Received element ${is} visible${isInDocument ? "" : " (element is not in the document)"}:`,
41
+ ` ${this.utils.printReceived(element.cloneNode(false))}`,
42
+ ].join("\n");
43
+ },
44
+ };
45
+ }
46
+ //# sourceMappingURL=to-be-visible.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"to-be-visible.js","sourceRoot":"","sources":["../../src/matchers/to-be-visible.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,gBAAgB,EAAE,MAAM,YAAY,CAAC;AAE9C,SAAS,cAAc,CAAC,OAAO;IAC3B,MAAM,EAAE,gBAAgB,EAAE,GAAG,OAAO,CAAC,aAAa,CAAC,WAAW,CAAC;IAE/D,MAAM,EAAE,OAAO,EAAE,UAAU,EAAE,OAAO,EAAE,GAAG,gBAAgB,CAAC,OAAO,CAAC,CAAC;IACnE,OAAO,CACH,OAAO,KAAK,MAAM;QAClB,UAAU,KAAK,QAAQ;QACvB,UAAU,KAAK,UAAU;QACzB,OAAO,KAAK,GAAG;QACf,OAAO,KAAK,CAAC,CAChB,CAAC;AACN,CAAC;AAED,SAAS,kBAAkB,CAAC,OAAO,EAAE,eAAe;IAChD,IAAI,iBAAiB,CAAC;IAEtB,IAAI,eAAe,EAAE,CAAC;QAClB,iBAAiB;YACb,OAAO,CAAC,QAAQ,KAAK,SAAS,IAAI,eAAe,CAAC,QAAQ,KAAK,SAAS;gBACpE,CAAC,CAAC,OAAO,CAAC,YAAY,CAAC,MAAM,CAAC;gBAC9B,CAAC,CAAC,IAAI,CAAC;IACnB,CAAC;SAAM,CAAC;QACJ,iBAAiB,GAAG,OAAO,CAAC,QAAQ,KAAK,SAAS,CAAC,CAAC,CAAC,OAAO,CAAC,YAAY,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC;IAC7F,CAAC;IAED,OAAO,CAAC,OAAO,CAAC,YAAY,CAAC,QAAQ,CAAC,IAAI,iBAAiB,CAAC;AAChE,CAAC;AAED,SAAS,gBAAgB,CAAC,OAAO,EAAE,eAAe;IAC9C,OAAO,CACH,cAAc,CAAC,OAAO,CAAC;QACvB,kBAAkB,CAAC,OAAO,EAAE,eAAe,CAAC;QAC5C,CAAC,CAAC,OAAO,CAAC,aAAa,IAAI,gBAAgB,CAAC,OAAO,CAAC,aAAa,EAAE,OAAO,CAAC,CAAC,CAC/E,CAAC;AACN,CAAC;AAED,MAAM,UAAU,WAAW,CAAC,OAAgB;IACxC,gBAAgB,CAAC,OAAO,EAAE,WAAW,EAAE,IAAI,CAAC,CAAC;IAC7C,MAAM,YAAY,GAAG,OAAO,CAAC,aAAa,KAAK,OAAO,CAAC,WAAW,CAAC,EAAE,QAAQ,EAAE,IAAI,EAAE,CAAC,CAAC;IACvF,MAAM,SAAS,GAAG,YAAY,IAAI,gBAAgB,CAAC,OAAO,CAAC,CAAC;IAC5D,OAAO;QACH,IAAI,EAAE,SAAS;QACf,OAAO,EAAE,GAAG,EAAE;YACV,MAAM,EAAE,GAAG,SAAS,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,QAAQ,CAAC;YACvC,OAAO;gBACH,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,cAAc,EAAE,SAAS,EAAE,EAAE,CAAC;gBAChF,EAAE;gBACF,oBAAoB,EAAE,WAAW,YAAY,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,mCAAmC,GAAG;gBAC3F,KAAK,IAAI,CAAC,KAAK,CAAC,aAAa,CAAC,OAAO,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC,EAAE;aAC5D,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACjB,CAAC;KACJ,CAAC;AACN,CAAC"}
@@ -0,0 +1,2 @@
1
+ import type { MatcherResult } from "./types.js";
2
+ export declare function toContainElement(container: Element, element: HTMLElement | SVGElement | null): MatcherResult;
@@ -0,0 +1,19 @@
1
+ import { checkHtmlElement } from "./utils.js";
2
+ export function toContainElement(container, element) {
3
+ checkHtmlElement(container, toContainElement, this);
4
+ if (element !== null) {
5
+ checkHtmlElement(element, toContainElement, this);
6
+ }
7
+ return {
8
+ pass: container.contains(element),
9
+ message: () => {
10
+ return [
11
+ this.utils.matcherHint(`${this.isNot ? ".not" : ""}.toContainElement`, "element", "element"),
12
+ "",
13
+ this.utils.RECEIVED_COLOR(`${this.utils.stringify(container.cloneNode(false))} ${this.isNot ? "contains:" : "does not contain:"} ${this.utils.stringify(element ? element.cloneNode(false) : element)}
14
+ `),
15
+ ].join("\n");
16
+ },
17
+ };
18
+ }
19
+ //# sourceMappingURL=to-contain-element.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"to-contain-element.js","sourceRoot":"","sources":["../../src/matchers/to-contain-element.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,gBAAgB,EAAE,MAAM,YAAY,CAAC;AAE9C,MAAM,UAAU,gBAAgB,CAC5B,SAAkB,EAClB,OAAwC;IAExC,gBAAgB,CAAC,SAAS,EAAE,gBAAgB,EAAE,IAAI,CAAC,CAAC;IAEpD,IAAI,OAAO,KAAK,IAAI,EAAE,CAAC;QACnB,gBAAgB,CAAC,OAAO,EAAE,gBAAgB,EAAE,IAAI,CAAC,CAAC;IACtD,CAAC;IAED,OAAO;QACH,IAAI,EAAE,SAAS,CAAC,QAAQ,CAAC,OAAO,CAAC;QACjC,OAAO,EAAE,GAAG,EAAE;YACV,OAAO;gBACH,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,mBAAmB,EAAE,SAAS,EAAE,SAAS,CAAC;gBAC5F,EAAE;gBACF,IAAI,CAAC,KAAK,CAAC,cAAc,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,SAAS,CAAC,SAAS,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC,IACzE,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC,CAAC,mBAC/B,IAAI,IAAI,CAAC,KAAK,CAAC,SAAS,CAAC,OAAO,CAAC,CAAC,CAAC,OAAO,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC;SAC7E,CAAC;aACG,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACjB,CAAC;KACJ,CAAC;AACN,CAAC"}
@@ -0,0 +1,2 @@
1
+ import type { MatcherResult } from "./types.js";
2
+ export declare function toContainHTML(container: Element, htmlText: string): MatcherResult;
@@ -0,0 +1,25 @@
1
+ import { checkHtmlElement } from "./utils.js";
2
+ function getNormalizedHtml(container, htmlText) {
3
+ const div = container.ownerDocument.createElement("div");
4
+ div.innerHTML = htmlText;
5
+ return div.innerHTML;
6
+ }
7
+ export function toContainHTML(container, htmlText) {
8
+ checkHtmlElement(container, toContainHTML, this);
9
+ if (typeof htmlText !== "string") {
10
+ throw new Error(`.toContainHTML() expects a string value, got ${htmlText}`);
11
+ }
12
+ return {
13
+ pass: container.outerHTML.includes(getNormalizedHtml(container, htmlText)),
14
+ message: () => {
15
+ return [
16
+ this.utils.matcherHint(`${this.isNot ? ".not" : ""}.toContainHTML`, "element", ""),
17
+ "Expected:",
18
+ ` ${this.utils.EXPECTED_COLOR(htmlText)}`,
19
+ "Received:",
20
+ ` ${this.utils.printReceived(container.cloneNode(true))}`,
21
+ ].join("\n");
22
+ },
23
+ };
24
+ }
25
+ //# sourceMappingURL=to-contain-html.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"to-contain-html.js","sourceRoot":"","sources":["../../src/matchers/to-contain-html.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,gBAAgB,EAAE,MAAM,YAAY,CAAC;AAE9C,SAAS,iBAAiB,CAAC,SAAS,EAAE,QAAQ;IAC1C,MAAM,GAAG,GAAG,SAAS,CAAC,aAAa,CAAC,aAAa,CAAC,KAAK,CAAC,CAAC;IACzD,GAAG,CAAC,SAAS,GAAG,QAAQ,CAAC;IACzB,OAAO,GAAG,CAAC,SAAS,CAAC;AACzB,CAAC;AAED,MAAM,UAAU,aAAa,CAAC,SAAkB,EAAE,QAAgB;IAC9D,gBAAgB,CAAC,SAAS,EAAE,aAAa,EAAE,IAAI,CAAC,CAAC;IAEjD,IAAI,OAAO,QAAQ,KAAK,QAAQ,EAAE,CAAC;QAC/B,MAAM,IAAI,KAAK,CAAC,gDAAgD,QAAQ,EAAE,CAAC,CAAC;IAChF,CAAC;IAED,OAAO;QACH,IAAI,EAAE,SAAS,CAAC,SAAS,CAAC,QAAQ,CAAC,iBAAiB,CAAC,SAAS,EAAE,QAAQ,CAAC,CAAC;QAC1E,OAAO,EAAE,GAAG,EAAE;YACV,OAAO;gBACH,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,gBAAgB,EAAE,SAAS,EAAE,EAAE,CAAC;gBAClF,WAAW;gBACX,KAAK,IAAI,CAAC,KAAK,CAAC,cAAc,CAAC,QAAQ,CAAC,EAAE;gBAC1C,WAAW;gBACX,KAAK,IAAI,CAAC,KAAK,CAAC,aAAa,CAAC,SAAS,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC,EAAE;aAC7D,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACjB,CAAC;KACJ,CAAC;AACN,CAAC"}
@@ -0,0 +1,4 @@
1
+ import type { expect } from "vitest";
2
+ import type { MatcherResult } from "./types.js";
3
+ /** @deprecated */
4
+ export declare function toHaveAccessibleDescription(htmlElement: Element, expectedAccessibleDescription?: string | RegExp | typeof expect.stringContaining): MatcherResult;
@@ -0,0 +1,28 @@
1
+ import { computeAccessibleDescription } from "dom-accessibility-api";
2
+ import { checkHtmlElement, getMessage } from "./utils.js";
3
+ /** @deprecated */
4
+ export function toHaveAccessibleDescription(htmlElement, expectedAccessibleDescription) {
5
+ checkHtmlElement(htmlElement, toHaveAccessibleDescription, this);
6
+ const actualAccessibleDescription = computeAccessibleDescription(htmlElement);
7
+ const missingExpectedValue = arguments.length === 1;
8
+ let pass = false;
9
+ if (missingExpectedValue) {
10
+ // When called without an expected value we only want to validate that the element has an
11
+ // accessible description, whatever it may be.
12
+ pass = actualAccessibleDescription !== "";
13
+ }
14
+ else {
15
+ pass =
16
+ expectedAccessibleDescription instanceof RegExp
17
+ ? expectedAccessibleDescription.test(actualAccessibleDescription)
18
+ : this.equals(actualAccessibleDescription, expectedAccessibleDescription);
19
+ }
20
+ return {
21
+ pass,
22
+ message: () => {
23
+ const to = this.isNot ? "not to" : "to";
24
+ return getMessage(this, this.utils.matcherHint(`${this.isNot ? ".not" : ""}.${toHaveAccessibleDescription.name}`, "element", ""), `Expected element ${to} have accessible description`, expectedAccessibleDescription, "Received", actualAccessibleDescription);
25
+ },
26
+ };
27
+ }
28
+ //# sourceMappingURL=to-have-accessible-description.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"to-have-accessible-description.js","sourceRoot":"","sources":["../../src/matchers/to-have-accessible-description.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,4BAA4B,EAAE,MAAM,uBAAuB,CAAC;AAIrE,OAAO,EAAE,gBAAgB,EAAE,UAAU,EAAE,MAAM,YAAY,CAAC;AAE1D,kBAAkB;AAClB,MAAM,UAAU,2BAA2B,CACvC,WAAoB,EACpB,6BAAgF;IAEhF,gBAAgB,CAAC,WAAW,EAAE,2BAA2B,EAAE,IAAI,CAAC,CAAC;IACjE,MAAM,2BAA2B,GAAG,4BAA4B,CAAC,WAAW,CAAC,CAAC;IAC9E,MAAM,oBAAoB,GAAG,SAAS,CAAC,MAAM,KAAK,CAAC,CAAC;IAEpD,IAAI,IAAI,GAAG,KAAK,CAAC;IACjB,IAAI,oBAAoB,EAAE,CAAC;QACvB,yFAAyF;QACzF,8CAA8C;QAC9C,IAAI,GAAG,2BAA2B,KAAK,EAAE,CAAC;IAC9C,CAAC;SAAM,CAAC;QACJ,IAAI;YACA,6BAA6B,YAAY,MAAM;gBAC3C,CAAC,CAAC,6BAA6B,CAAC,IAAI,CAAC,2BAA2B,CAAC;gBACjE,CAAC,CAAC,IAAI,CAAC,MAAM,CAAC,2BAA2B,EAAE,6BAA6B,CAAC,CAAC;IACtF,CAAC;IAED,OAAO;QACH,IAAI;QAEJ,OAAO,EAAE,GAAG,EAAE;YACV,MAAM,EAAE,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC;YACxC,OAAO,UAAU,CACb,IAAI,EACJ,IAAI,CAAC,KAAK,CAAC,WAAW,CAClB,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,IAAI,2BAA2B,CAAC,IAAI,EAAE,EACjE,SAAS,EACT,EAAE,CACL,EACD,oBAAoB,EAAE,8BAA8B,EACpD,6BAA6B,EAC7B,UAAU,EACV,2BAA2B,CAC9B,CAAC;QACN,CAAC;KACJ,CAAC;AACN,CAAC"}
@@ -0,0 +1,2 @@
1
+ import type { MatcherResult, MatcherState } from "./types.js";
2
+ export declare function toHaveAccessibleErrorMessage<State extends MatcherState>(this: State, htmlElement: HTMLElement, expectedAccessibleErrorMessage?: string | RegExp | State): MatcherResult;
@@ -0,0 +1,48 @@
1
+ import { checkHtmlElement, getMessage, normalize } from "./utils.js";
2
+ const ariaInvalidName = "aria-invalid";
3
+ const validStates = ["false"];
4
+ // See `aria-errormessage` spec at https://www.w3.org/TR/wai-aria-1.2/#aria-errormessage
5
+ export function toHaveAccessibleErrorMessage(htmlElement, expectedAccessibleErrorMessage) {
6
+ checkHtmlElement(htmlElement, toHaveAccessibleErrorMessage, this);
7
+ const to = this.isNot ? "not to" : "to";
8
+ const method = this.isNot ? ".not.toHaveAccessibleErrorMessage" : ".toHaveAccessibleErrorMessage";
9
+ // Enforce Valid Id
10
+ const errormessageId = htmlElement.getAttribute("aria-errormessage");
11
+ const errormessageIdInvalid = !!errormessageId && /\s+/.test(errormessageId);
12
+ if (errormessageIdInvalid) {
13
+ return {
14
+ pass: false,
15
+ message: () => {
16
+ return getMessage(this, this.utils.matcherHint(method, "element"), "Expected element's `aria-errormessage` attribute to be empty or a single, valid ID", "", "Received", `aria-errormessage="${errormessageId}"`);
17
+ },
18
+ };
19
+ }
20
+ // See `aria-invalid` spec at https://www.w3.org/TR/wai-aria-1.2/#aria-invalid
21
+ const ariaInvalidVal = htmlElement.getAttribute(ariaInvalidName);
22
+ const fieldValid = !htmlElement.hasAttribute(ariaInvalidName) || validStates.includes(ariaInvalidVal);
23
+ // Enforce Valid `aria-invalid` Attribute
24
+ if (fieldValid) {
25
+ return {
26
+ pass: false,
27
+ message: () => {
28
+ return getMessage(this, this.utils.matcherHint(method, "element"), "Expected element to be marked as invalid with attribute", `${ariaInvalidName}="${String(true)}"`, "Received", htmlElement.hasAttribute("aria-invalid")
29
+ ? `${ariaInvalidName}="${htmlElement.getAttribute(ariaInvalidName)}`
30
+ : null);
31
+ },
32
+ };
33
+ }
34
+ const error = normalize(errormessageId != null
35
+ ? (htmlElement.ownerDocument.getElementById(errormessageId)?.textContent ?? "")
36
+ : "");
37
+ return {
38
+ pass: expectedAccessibleErrorMessage === undefined
39
+ ? Boolean(error)
40
+ : expectedAccessibleErrorMessage instanceof RegExp
41
+ ? expectedAccessibleErrorMessage.test(error)
42
+ : this.equals(error, expectedAccessibleErrorMessage),
43
+ message: () => {
44
+ return getMessage(this, this.utils.matcherHint(method, "element"), `Expected element ${to} have accessible error message`, expectedAccessibleErrorMessage ?? "", "Received", error);
45
+ },
46
+ };
47
+ }
48
+ //# sourceMappingURL=to-have-accessible-errormessage.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"to-have-accessible-errormessage.js","sourceRoot":"","sources":["../../src/matchers/to-have-accessible-errormessage.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,gBAAgB,EAAE,UAAU,EAAE,SAAS,EAAE,MAAM,YAAY,CAAC;AAErE,MAAM,eAAe,GAAG,cAAc,CAAC;AACvC,MAAM,WAAW,GAAG,CAAC,OAAO,CAAC,CAAC;AAE9B,wFAAwF;AACxF,MAAM,UAAU,4BAA4B,CAExC,WAAwB,EACxB,8BAAwD;IAExD,gBAAgB,CAAC,WAAW,EAAE,4BAA4B,EAAE,IAAI,CAAC,CAAC;IAClE,MAAM,EAAE,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC;IACxC,MAAM,MAAM,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,mCAAmC,CAAC,CAAC,CAAC,+BAA+B,CAAC;IAElG,mBAAmB;IACnB,MAAM,cAAc,GAAG,WAAW,CAAC,YAAY,CAAC,mBAAmB,CAAC,CAAC;IACrE,MAAM,qBAAqB,GAAG,CAAC,CAAC,cAAc,IAAI,KAAK,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;IAE7E,IAAI,qBAAqB,EAAE,CAAC;QACxB,OAAO;YACH,IAAI,EAAE,KAAK;YACX,OAAO,EAAE,GAAG,EAAE;gBACV,OAAO,UAAU,CACb,IAAI,EACJ,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,MAAM,EAAE,SAAS,CAAC,EACzC,oFAAoF,EACpF,EAAE,EACF,UAAU,EACV,sBAAsB,cAAc,GAAG,CAC1C,CAAC;YACN,CAAC;SACJ,CAAC;IACN,CAAC;IAED,8EAA8E;IAC9E,MAAM,cAAc,GAAG,WAAW,CAAC,YAAY,CAAC,eAAe,CAAC,CAAC;IACjE,MAAM,UAAU,GAAG,CAAC,WAAW,CAAC,YAAY,CAAC,eAAe,CAAC,IAAI,WAAW,CAAC,QAAQ,CAAC,cAAe,CAAC,CAAC;IAEvG,yCAAyC;IACzC,IAAI,UAAU,EAAE,CAAC;QACb,OAAO;YACH,IAAI,EAAE,KAAK;YACX,OAAO,EAAE,GAAG,EAAE;gBACV,OAAO,UAAU,CACb,IAAI,EACJ,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,MAAM,EAAE,SAAS,CAAC,EACzC,yDAAyD,EACzD,GAAG,eAAe,KAAK,MAAM,CAAC,IAAI,CAAC,GAAG,EACtC,UAAU,EACV,WAAW,CAAC,YAAY,CAAC,cAAc,CAAC;oBACpC,CAAC,CAAC,GAAG,eAAe,KAAK,WAAW,CAAC,YAAY,CAAC,eAAe,CAAC,EAAE;oBACpE,CAAC,CAAC,IAAI,CACb,CAAC;YACN,CAAC;SACJ,CAAC;IACN,CAAC;IAED,MAAM,KAAK,GAAG,SAAS,CACnB,cAAc,IAAI,IAAI;QAClB,CAAC,CAAC,CAAC,WAAW,CAAC,aAAa,CAAC,cAAc,CAAC,cAAc,CAAC,EAAE,WAAW,IAAI,EAAE,CAAC;QAC/E,CAAC,CAAC,EAAE,CACX,CAAC;IAEF,OAAO;QACH,IAAI,EACA,8BAA8B,KAAK,SAAS;YACxC,CAAC,CAAC,OAAO,CAAC,KAAK,CAAC;YAChB,CAAC,CAAC,8BAA8B,YAAY,MAAM;gBAChD,CAAC,CAAC,8BAA8B,CAAC,IAAI,CAAC,KAAK,CAAC;gBAC5C,CAAC,CAAC,IAAI,CAAC,MAAM,CAAC,KAAK,EAAE,8BAA8B,CAAC;QAE9D,OAAO,EAAE,GAAG,EAAE;YACV,OAAO,UAAU,CACb,IAAI,EACJ,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,MAAM,EAAE,SAAS,CAAC,EACzC,oBAAoB,EAAE,gCAAgC,EACtD,8BAA8B,IAAI,EAAE,EACpC,UAAU,EACV,KAAK,CACR,CAAC;QACN,CAAC;KACJ,CAAC;AACN,CAAC"}
@@ -0,0 +1,3 @@
1
+ import type { expect } from "vitest";
2
+ import type { MatcherResult } from "./types.js";
3
+ export declare function toHaveAccessibleName(htmlElement: Element, expectedAccessibleName?: string | RegExp | typeof expect.stringContaining): MatcherResult;