-
Notifications
You must be signed in to change notification settings - Fork 33
/
Copy pathtransform-include-atrule.js
65 lines (55 loc) · 1.82 KB
/
transform-include-atrule.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
// tooling
import { list } from 'postcss';
import getClosestVariable from './get-closest-variable';
import getReplacedString from './get-replaced-string';
import manageUnresolved from './manage-unresolved';
import setVariable from './set-variable';
import transformNode from './transform-node';
// transform @include at-rules
export default function transformIncludeAtrule(rule, opts) {
// if @include is supported
if (opts.transform.includes('@include')) {
// @include options
const { name, args } = getIncludeOpts(rule);
// the closest @mixin variable
const mixin = getClosestVariable(`@mixin ${name}`, rule.parent, opts);
// if the @mixin variable exists
if (mixin) {
// set @mixin variables on the @include at-rule
mixin.params.forEach(
(param, index) => {
const arg = index in args
? getReplacedString(args[index], rule, opts)
: param.value;
setVariable(rule, param.name, arg, opts);
}
);
// clone the @mixin at-rule
const clone = mixin.rule.clone({
original: rule,
parent: rule.parent,
variables: rule.variables
});
// transform the clone children
return transformNode(clone, opts).then(() => {
// replace the @include at-rule with the clone children
rule.parent.insertBefore(rule, clone.nodes);
rule.remove();
})
} else {
// otherwise, if the @mixin variable does not exist
manageUnresolved(rule, opts, name, `Could not resolve the mixin for "${name}"`);
}
}
}
// return the @include statement options (@include NAME, @include NAME(ARGS))
const getIncludeOpts = node => {
// @include name and args
const [ name, sourceArgs ] = node.params.split(matchOpeningParen, 2);
const args = sourceArgs
? list.comma(sourceArgs.slice(0, -1))
: [];
return { name, args };
};
// match an opening parenthesis
const matchOpeningParen = /(?<!var)\(/;