1
1
/**
2
- * @typedef {import('unist').Parent } Parent
3
2
* @typedef {import('hast').Element } Element
3
+ * @typedef {import('unist').Parent } Parent
4
4
*/
5
5
6
6
/**
7
- * @typedef {null | undefined | string | TestFunctionAnything | Array< string | TestFunctionAnything> } Test
7
+ * @typedef {Array<TestFunctionAnything | string> | TestFunctionAnything | string | null | undefined } Test
8
8
* Check for an arbitrary element, unaware of TypeScript inferral.
9
9
*
10
10
* @callback TestFunctionAnything
11
11
* Check if an element passes a test, unaware of TypeScript inferral.
12
12
* @param {Element } element
13
13
* An element.
14
14
* @param {number | null | undefined } [index]
15
- * The element’s position in its parent.
15
+ * Position of `node` in ` parent` .
16
16
* @param {Parent | null | undefined } [parent]
17
- * The element’s parent .
18
- * @returns {boolean | void }
17
+ * Parent of `node` .
18
+ * @returns {boolean | undefined | void }
19
19
* Whether this element passes the test.
20
20
*/
21
21
22
22
/**
23
23
* @template {Element} T
24
24
* Element type.
25
- * @typedef {T ['tagName'] | TestFunctionPredicate<T> | Array< T['tagName'] | TestFunctionPredicate<T>> } PredicateTest
25
+ * @typedef {Array<TestFunctionPredicate<T> | T ['tagName']> | TestFunctionPredicate<T> | T['tagName'] } PredicateTest
26
26
* Check for an element that can be inferred by TypeScript.
27
27
*/
28
28
36
36
* @param {Element } element
37
37
* An element.
38
38
* @param {number | null | undefined } [index]
39
- * The element’s position in its parent.
39
+ * Position of `node` in ` parent` .
40
40
* @param {Parent | null | undefined } [parent]
41
- * The element’s parent .
41
+ * Parent of `node` .
42
42
* @returns {element is T }
43
43
* Whether this element passes the test.
44
44
*/
49
49
* @param {unknown } [node]
50
50
* Anything (typically a node).
51
51
* @param {number | null | undefined } [index]
52
- * The node’s position in its parent.
52
+ * Position of ` node` in ` parent` .
53
53
* @param {Parent | null | undefined } [parent]
54
- * The node’s parent .
54
+ * Parent of `node` .
55
55
* @returns {boolean }
56
56
* Whether this is an element and passes a test.
57
57
*/
66
66
* @param {unknown } [node]
67
67
* Anything (typically a node).
68
68
* @param {number | null | undefined } [index]
69
- * The node’s position in its parent.
69
+ * Position of ` node` in ` parent` .
70
70
* @param {Parent | null | undefined } [parent]
71
- * The node’s parent .
71
+ * Parent of `node` .
72
72
* @returns {node is T }
73
73
* Whether this is an element and passes a test.
74
74
*/
79
79
* @param node
80
80
* Thing to check, typically `Node`.
81
81
* @param test
82
- * A check for a specific element.
82
+ * Check for a specific element.
83
83
* @param index
84
- * The node’s position in its parent.
84
+ * Position of ` node` in ` parent` .
85
85
* @param parent
86
- * The node’s parent.
86
+ * Parent of `node`.
87
+ * @param context
88
+ * Context to call `test` with.
87
89
* @returns
88
90
* Whether `node` is an element and passes a test.
89
91
*/
90
92
export const isElement =
93
+ // Note: JSDoc overloads don’t support optional type parameters.
91
94
/**
92
95
* @type {(
93
96
* (() => false) &
@@ -109,8 +112,8 @@ export const isElement =
109
112
const check = convertElement ( test )
110
113
111
114
if (
112
- index !== undefined &&
113
115
index !== null &&
116
+ index !== undefined &&
114
117
( typeof index !== 'number' ||
115
118
index < 0 ||
116
119
index === Number . POSITIVE_INFINITY )
@@ -119,21 +122,21 @@ export const isElement =
119
122
}
120
123
121
124
if (
122
- parent !== undefined &&
123
125
parent !== null &&
126
+ parent !== undefined &&
124
127
( ! parent . type || ! parent . children )
125
128
) {
126
129
throw new Error ( 'Expected parent node' )
127
130
}
128
131
129
- // @ts -expect-error Looks like a node.
132
+ // @ts -expect-error: looks like a node.
130
133
if ( ! node || ! node . type || typeof node . type !== 'string' ) {
131
134
return false
132
135
}
133
136
134
137
if (
135
- ( parent === undefined || parent === null ) !==
136
- ( index === undefined || index === null )
138
+ ( parent === null || parent === undefined ) !==
139
+ ( index === null || index === undefined )
137
140
) {
138
141
throw new Error ( 'Expected both parent and index' )
139
142
}
@@ -172,7 +175,7 @@ export const convertElement =
172
175
* @returns {AssertAnything }
173
176
*/
174
177
function ( test ) {
175
- if ( test === undefined || test === null ) {
178
+ if ( test === null || test === undefined ) {
176
179
return element
177
180
}
178
181
@@ -195,7 +198,7 @@ export const convertElement =
195
198
/**
196
199
* Handle multiple tests.
197
200
*
198
- * @param {Array<string | TestFunctionAnything > } tests
201
+ * @param {Array<TestFunctionAnything | string > } tests
199
202
* @returns {AssertAnything }
200
203
*/
201
204
function anyFactory ( tests ) {
@@ -261,7 +264,7 @@ function castFactory(check) {
261
264
* @returns {boolean }
262
265
*/
263
266
function assertion ( node , ...parameters ) {
264
- // @ts -expect-error: fine .
267
+ // @ts -expect-error: assume valid parameters .
265
268
return element ( node ) && Boolean ( check . call ( this , node , ...parameters ) )
266
269
}
267
270
}
@@ -276,9 +279,9 @@ function element(node) {
276
279
return Boolean (
277
280
node &&
278
281
typeof node === 'object' &&
279
- // @ts -expect-error Looks like a node.
282
+ 'type' in node &&
280
283
node . type === 'element' &&
281
- // @ts -expect-error Looks like an element.
284
+ 'tagName' in node &&
282
285
typeof node . tagName === 'string'
283
286
)
284
287
}
0 commit comments