forked from tailwindlabs/tailwindcss
-
Notifications
You must be signed in to change notification settings - Fork 0
/
plugin.js
133 lines (116 loc) · 4.33 KB
/
plugin.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
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
import postcss from 'postcss'
import lightningcss, { Features } from 'lightningcss'
import browserslist from 'browserslist'
import setupTrackingContext from './lib/setupTrackingContext'
import processTailwindFeatures from './processTailwindFeatures'
import { env } from './lib/sharedState'
import { findAtConfigPath } from './lib/findAtConfigPath'
import { handleImportAtRules } from './lib/handleImportAtRules'
import { version as tailwindVersion } from '../package.json'
function license() {
return `/* ! tailwindcss v${tailwindVersion} | MIT License | https://tailwindcss.com */\n`
}
module.exports = function tailwindcss(configOrPath) {
return {
postcssPlugin: 'tailwindcss',
plugins: [
env.DEBUG &&
function (root) {
console.log('\n')
console.time('JIT TOTAL')
return root
},
...handleImportAtRules(),
async function (root, result) {
// Use the path for the `@config` directive if it exists, otherwise use the
// path for the file being processed
configOrPath = findAtConfigPath(root, result) ?? configOrPath
let context = setupTrackingContext(configOrPath)
if (root.type === 'document') {
let roots = root.nodes.filter((node) => node.type === 'root')
for (const root of roots) {
if (root.type === 'root') {
await processTailwindFeatures(context)(root, result)
}
}
return
}
await processTailwindFeatures(context)(root, result)
},
function lightningCssPlugin(_root, result) {
let map = result.map ?? result.opts.map
let intermediateResult = result.root.toResult({
map: map ? { inline: true } : false,
})
let intermediateMap = intermediateResult.map?.toJSON?.() ?? map
try {
let resolvedBrowsersListConfig = browserslist.findConfig(
result.opts.from ?? process.cwd()
)?.defaults
let defaultBrowsersListConfig = require('../package.json').browserslist
let browsersListConfig = resolvedBrowsersListConfig ?? defaultBrowsersListConfig
let transformed = lightningcss.transform({
filename: result.opts.from,
code: Buffer.from(intermediateResult.css),
minify: false,
sourceMap: !!intermediateMap,
targets: lightningcss.browserslistToTargets(browserslist(browsersListConfig)),
errorRecovery: true,
drafts: {
customMedia: true,
},
nonStandard: {
deepSelectorCombinator: true,
},
include: Features.Nesting,
exclude: Features.LogicalProperties,
})
let code = transformed.code.toString()
// https://postcss.org/api/#sourcemapoptions
if (intermediateMap && transformed.map != null) {
let prev = transformed.map.toString()
if (typeof intermediateMap === 'object') {
intermediateMap.prev = prev
} else {
code = `${code}\n/*# sourceMappingURL=data:application/json;base64,${Buffer.from(
prev
).toString('base64')} */`
}
}
result.root = postcss.parse(license() + code, {
...result.opts,
map: intermediateMap,
})
} catch (err) {
if (err.source && typeof process !== 'undefined' && process.env.JEST_WORKER_ID) {
let lines = err.source.split('\n')
err = new Error(
[
'Error formatting using Lightning CSS:',
'',
...[
'```css',
...lines.slice(Math.max(err.loc.line - 3, 0), err.loc.line),
' '.repeat(err.loc.column - 1) + '^-- ' + err.toString(),
...lines.slice(err.loc.line, err.loc.line + 2),
'```',
],
].join('\n')
)
}
if (Error.captureStackTrace) {
Error.captureStackTrace(err, lightningCssPlugin)
}
throw err
}
},
env.DEBUG &&
function (root) {
console.timeEnd('JIT TOTAL')
console.log('\n')
return root
},
].filter(Boolean),
}
}
module.exports.postcss = true