1
1
export default function transformValueAST ( root , customProperties ) {
2
2
if ( root . nodes && root . nodes . length ) {
3
- root . nodes . slice ( ) . forEach ( child => {
3
+ root . nodes . slice ( ) . forEach ( ( child ) => {
4
4
if ( isVarFunction ( child ) ) {
5
- // eslint-disable-next-line no-unused-vars
6
- const [ propertyNode , comma , ...fallbacks ] = child . nodes ;
5
+ const [ propertyNode , ...fallbacks ] = child . nodes . filter ( ( node ) => node . type !== 'div' ) ;
7
6
const { value : name } = propertyNode ;
7
+ const index = root . nodes . indexOf ( child ) ;
8
8
9
9
if ( name in Object ( customProperties ) ) {
10
- // conditionally replace a known custom property
11
- const nodes = asClonedArrayWithBeforeSpacing ( customProperties [ name ] , child . raws . before ) ;
12
-
13
- /**
14
- * https://github.com/postcss/postcss-custom-properties/issues/221
15
- * https://github.com/postcss/postcss-custom-properties/issues/218
16
- *
17
- * replaceWith loses node.raws values, so we need to save it and restore
18
- */
19
- const raws = nodes . map ( node => ( { ...node . raws } ) ) ;
20
-
21
- child . replaceWith ( ...nodes ) ;
22
-
23
- nodes . forEach ( ( node , index ) => {
24
- node . raws = raws [ index ] ;
25
- } ) ;
10
+ // Direct match of a custom property to a parsed value
11
+ const nodes = customProperties [ name ] . nodes ;
26
12
13
+ // Re-transform nested properties without given one to avoid circular from keeping this forever
27
14
retransformValueAST ( { nodes } , customProperties , name ) ;
28
- } else if ( fallbacks . length ) {
29
- // conditionally replace a custom property with a fallback
30
- const index = root . nodes . indexOf ( child ) ;
31
15
32
- if ( index !== - 1 ) {
33
- root . nodes . splice ( index , 1 , ...asClonedArrayWithBeforeSpacing ( fallbacks , child . raws . before ) ) ;
16
+ if ( index > - 1 ) {
17
+ root . nodes . splice ( index , 1 , ...nodes ) ;
18
+ }
19
+ } else if ( fallbacks . length ) {
20
+ // No match, but fallback available
21
+ if ( index > - 1 ) {
22
+ root . nodes . splice ( index , 1 , ...fallbacks ) ;
34
23
}
35
24
36
25
transformValueAST ( root , customProperties ) ;
37
26
}
38
27
} else {
28
+ // Transform child nodes of current child
39
29
transformValueAST ( child , customProperties ) ;
40
30
}
41
31
} ) ;
42
32
}
43
33
44
- return root ;
34
+ return root . toString ( ) ;
45
35
}
46
36
47
37
// retransform the current ast without a custom property (to prevent recursion)
@@ -57,35 +47,4 @@ function retransformValueAST(root, customProperties, withoutProperty) {
57
47
const varRegExp = / ^ v a r $ / i;
58
48
59
49
// whether the node is a var() function
60
- const isVarFunction = node => node . type === 'func' && varRegExp . test ( node . name ) && Object ( node . nodes ) . length > 0 ;
61
-
62
- // return an array with its nodes cloned, preserving the raw
63
- const asClonedArrayWithBeforeSpacing = ( array , beforeSpacing ) => {
64
- const clonedArray = asClonedArray ( array , null ) ;
65
-
66
- if ( clonedArray [ 0 ] ) {
67
- clonedArray [ 0 ] . raws . before = beforeSpacing ;
68
- }
69
-
70
- return clonedArray ;
71
- } ;
72
-
73
- // return an array with its nodes cloned
74
- const asClonedArray = ( array , parent ) => array . map ( node => asClonedNode ( node , parent ) ) ;
75
-
76
- // return a cloned node
77
- const asClonedNode = ( node , parent ) => {
78
- const cloneNode = new node . constructor ( node ) ;
79
-
80
- for ( const key in node ) {
81
- if ( key === 'parent' ) {
82
- cloneNode . parent = parent ;
83
- } else if ( Object ( node [ key ] ) . constructor === Array ) {
84
- cloneNode [ key ] = asClonedArray ( node . nodes , cloneNode ) ;
85
- } else if ( Object ( node [ key ] ) . constructor === Object ) {
86
- cloneNode [ key ] = Object . assign ( { } , node [ key ] ) ;
87
- }
88
- }
89
-
90
- return cloneNode ;
91
- } ;
50
+ const isVarFunction = node => node . type === 'function' && varRegExp . test ( node . value ) && Object ( node . nodes ) . length > 0 ;
0 commit comments