22
33module . exports = match
44
5- var zwitch = require ( 'zwitch ' )
5+ var commas = require ( 'comma-separated-tokens ' )
66var has = require ( 'hast-util-has-property' )
77var find = require ( 'property-information/find' )
8- var spaceSeparated = require ( 'space-separated-tokens' ) . stringify
9- var commaSeparated = require ( 'comma-separated-tokens' ) . stringify
10-
11- var handle = zwitch ( 'operator' )
12- var handlers = handle . handlers
8+ var spaces = require ( 'space-separated-tokens' )
9+ var zwitch = require ( 'zwitch' )
1310
14- handle . unknown = unknownOperator
15- handle . invalid = exists
16- handlers [ '=' ] = exact
17- handlers [ '~=' ] = spaceSeparatedList
18- handlers [ '|=' ] = exactOrPrefix
19- handlers [ '^=' ] = begins
20- handlers [ '$=' ] = ends
21- handlers [ '*=' ] = contains
11+ var handle = zwitch ( 'operator' , {
12+ unknown : unknownOperator ,
13+ invalid : exists ,
14+ handlers : {
15+ '=' : exact ,
16+ '~=' : spaceSeparatedList ,
17+ '|=' : exactOrPrefix ,
18+ '^=' : begins ,
19+ '$=' : ends ,
20+ '*=' : contains
21+ }
22+ } )
2223
2324function match ( query , node , schema ) {
2425 var attrs = query . attrs
25- var length = attrs . length
2626 var index = - 1
27- var info
28- var attr
29-
30- while ( ++ index < length ) {
31- attr = attrs [ index ]
32- info = find ( schema , attr . name )
3327
34- if ( ! handle ( attr , node , info ) ) {
35- return false
36- }
28+ while ( ++ index < attrs . length ) {
29+ if ( ! handle ( attrs [ index ] , node , find ( schema , attrs [ index ] . name ) ) ) return
3730 }
3831
3932 return true
@@ -46,75 +39,56 @@ function exists(query, node, info) {
4639
4740// `[attr=value]`
4841function exact ( query , node , info ) {
49- if ( ! has ( node , info . property ) ) {
50- return false
51- }
52-
53- return normalizeValue ( node . properties [ info . property ] , info ) === query . value
42+ return (
43+ has ( node , info . property ) &&
44+ normalizeValue ( node . properties [ info . property ] , info ) === query . value
45+ )
5446}
5547
5648// `[attr~=value]`
5749function spaceSeparatedList ( query , node , info ) {
58- var value
50+ var value = node . properties [ info . property ]
5951
60- if ( ! has ( node , info . property ) ) {
61- return false
62- }
63-
64- value = node . properties [ info . property ]
65-
66- // If this is a comma-separated list, and the query is contained in it, return
67- // true.
68- if (
69- typeof value === 'object' &&
70- ! info . commaSeparated &&
71- value . indexOf ( query . value ) !== - 1
72- ) {
73- return true
74- }
75-
76- // For all other values (including comma-separated lists), return whether this
77- // is an exact match.
78- return normalizeValue ( value , info ) === query . value
52+ return (
53+ // If this is a comma-separated list, and the query is contained in it, return
54+ // true.
55+ ( ! info . commaSeparated &&
56+ value &&
57+ typeof value === 'object' &&
58+ value . indexOf ( query . value ) > - 1 ) ||
59+ // For all other values (including comma-separated lists), return whether this
60+ // is an exact match.
61+ ( has ( node , info . property ) && normalizeValue ( value , info ) === query . value )
62+ )
7963}
8064
8165// `[attr|=value]`
8266function exactOrPrefix ( query , node , info ) {
83- var value
84-
85- if ( ! has ( node , info . property ) ) {
86- return false
87- }
67+ var value = normalizeValue ( node . properties [ info . property ] , info )
8868
89- value = normalizeValue ( node . properties [ info . property ] , info )
90-
91- return Boolean (
92- value === query . value ||
69+ return (
70+ has ( node , info . property ) &&
71+ ( value === query . value ||
9372 ( value . slice ( 0 , query . value . length ) === query . value &&
94- value . charAt ( query . value . length ) === '-' )
73+ value . charAt ( query . value . length ) === '-' ) )
9574 )
9675}
9776
9877// `[attr^=value]`
9978function begins ( query , node , info ) {
100- var value
101-
102- if ( ! has ( node , info . property ) ) {
103- return false
104- }
105-
106- value = normalizeValue ( node . properties [ info . property ] , info )
107-
108- return value . slice ( 0 , query . value . length ) === query . value
79+ return (
80+ has ( node , info . property ) &&
81+ normalizeValue ( node . properties [ info . property ] , info ) . slice (
82+ 0 ,
83+ query . value . length
84+ ) === query . value
85+ )
10986}
11087
11188// `[attr$=value]`
11289function ends ( query , node , info ) {
113- if ( ! has ( node , info . property ) ) {
114- return false
115- }
116-
11790 return (
91+ has ( node , info . property ) &&
11892 normalizeValue ( node . properties [ info . property ] , info ) . slice (
11993 - query . value . length
12094 ) === query . value
@@ -123,14 +97,10 @@ function ends(query, node, info) {
12397
12498// `[attr*=value]`
12599function contains ( query , node , info ) {
126- if ( ! has ( node , info . property ) ) {
127- return false
128- }
129-
130100 return (
131- normalizeValue ( node . properties [ info . property ] , info ) . indexOf (
132- query . value
133- ) !== - 1
101+ has ( node , info . property ) &&
102+ normalizeValue ( node . properties [ info . property ] , info ) . indexOf ( query . value ) >
103+ - 1
134104 )
135105}
136106
@@ -142,11 +112,15 @@ function unknownOperator(query) {
142112// Stringify a hast value back to its HTML form.
143113function normalizeValue ( value , info ) {
144114 if ( typeof value === 'number' ) {
145- value = String ( value )
146- } else if ( typeof value === 'boolean' ) {
147- value = info . attribute
148- } else if ( typeof value === 'object' && 'length' in value ) {
149- value = ( info . commaSeparated ? commaSeparated : spaceSeparated ) ( value )
115+ return String ( value )
116+ }
117+
118+ if ( typeof value === 'boolean' ) {
119+ return info . attribute
120+ }
121+
122+ if ( typeof value === 'object' && 'length' in value ) {
123+ return ( info . commaSeparated ? commas . stringify : spaces . stringify ) ( value )
150124 }
151125
152126 return value
0 commit comments