tailwindcss-patch 9.0.1 → 9.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/cli.js +2 -2
- package/dist/cli.mjs +2 -2
- package/dist/commands/cli-runtime.js +1 -1
- package/dist/commands/cli-runtime.mjs +1 -1
- package/dist/index.bundle-BQ_yKkd8.js +239 -0
- package/dist/index.bundle-dp_pw5fq.mjs +201 -0
- package/dist/index.d.mts +73 -1
- package/dist/index.d.ts +73 -1
- package/dist/index.js +7 -2
- package/dist/index.mjs +3 -3
- package/dist/{validate-B8H-8rWO.js → validate-749MHvAC.js} +284 -38
- package/dist/{validate-BI8356RT.mjs → validate-D5elFZMj.mjs} +260 -38
- package/package.json +2 -2
- package/src/extraction/candidate-extractor.ts +14 -69
- package/src/index.bundle.ts +21 -0
- package/src/index.ts +16 -0
- package/src/v4/candidates.ts +224 -0
- package/src/v4/engine.ts +93 -0
- package/src/v4/index.ts +25 -0
- package/src/v4/node-adapter.ts +209 -0
- package/src/v4/source.ts +193 -0
- package/src/v4/types.ts +64 -0
- package/dist/index.bundle-BGBMTX9A.js +0 -35
- package/dist/index.bundle-ByrTqrr3.mjs +0 -18
|
@@ -9,14 +9,14 @@ import { createConsola } from "consola";
|
|
|
9
9
|
import path$1 from "node:path";
|
|
10
10
|
import { fileURLToPath, pathToFileURL } from "node:url";
|
|
11
11
|
import { promises } from "node:fs";
|
|
12
|
+
import postcss from "postcss";
|
|
12
13
|
import * as t from "@babel/types";
|
|
13
14
|
import generate from "@babel/generator";
|
|
14
15
|
import _babelTraverse from "@babel/traverse";
|
|
15
16
|
import { parse, parse as parse$1 } from "@babel/parser";
|
|
16
|
-
import postcss from "postcss";
|
|
17
17
|
import { loadConfig } from "tailwindcss-config";
|
|
18
18
|
//#region package.json
|
|
19
|
-
var version = "9.0
|
|
19
|
+
var version = "9.2.0";
|
|
20
20
|
//#endregion
|
|
21
21
|
//#region src/constants.ts
|
|
22
22
|
const pkgName = "tailwindcss-patch";
|
|
@@ -1445,57 +1445,275 @@ async function loadPatchOptionsForWorkspace(cwd, overrides) {
|
|
|
1445
1445
|
return merge(overrides ?? {}, base, { projectRoot: cwd });
|
|
1446
1446
|
}
|
|
1447
1447
|
//#endregion
|
|
1448
|
-
//#region src/
|
|
1449
|
-
|
|
1450
|
-
|
|
1448
|
+
//#region src/v4/candidates.ts
|
|
1449
|
+
function resolveValidTailwindV4Candidates(designSystem, candidates) {
|
|
1450
|
+
const validCandidates = /* @__PURE__ */ new Set();
|
|
1451
|
+
const parsedCandidates = [];
|
|
1452
|
+
for (const candidate of candidates) {
|
|
1453
|
+
if (!candidate || parsedCandidates.includes(candidate)) continue;
|
|
1454
|
+
if (designSystem.parseCandidate(candidate).length > 0) parsedCandidates.push(candidate);
|
|
1455
|
+
}
|
|
1456
|
+
if (parsedCandidates.length === 0) return validCandidates;
|
|
1457
|
+
const cssByCandidate = designSystem.candidatesToCss(parsedCandidates);
|
|
1458
|
+
for (let index = 0; index < parsedCandidates.length; index++) {
|
|
1459
|
+
const candidate = parsedCandidates[index];
|
|
1460
|
+
const candidateCss = cssByCandidate[index];
|
|
1461
|
+
if (candidate && typeof candidateCss === "string" && candidateCss.trim().length > 0) validCandidates.add(candidate);
|
|
1462
|
+
}
|
|
1463
|
+
return validCandidates;
|
|
1464
|
+
}
|
|
1465
|
+
function splitTopLevel(value, separator) {
|
|
1466
|
+
const result = [];
|
|
1467
|
+
let start = 0;
|
|
1468
|
+
let depth = 0;
|
|
1469
|
+
let quote;
|
|
1470
|
+
for (let index = 0; index < value.length; index++) {
|
|
1471
|
+
const character = value[index];
|
|
1472
|
+
if (character === "\\") {
|
|
1473
|
+
index++;
|
|
1474
|
+
continue;
|
|
1475
|
+
}
|
|
1476
|
+
if (quote) {
|
|
1477
|
+
if (character === quote) quote = void 0;
|
|
1478
|
+
continue;
|
|
1479
|
+
}
|
|
1480
|
+
if (character === "\"" || character === "'") {
|
|
1481
|
+
quote = character;
|
|
1482
|
+
continue;
|
|
1483
|
+
}
|
|
1484
|
+
if (character === "(" || character === "[" || character === "{") {
|
|
1485
|
+
depth++;
|
|
1486
|
+
continue;
|
|
1487
|
+
}
|
|
1488
|
+
if (character === ")" || character === "]" || character === "}") {
|
|
1489
|
+
depth = Math.max(0, depth - 1);
|
|
1490
|
+
continue;
|
|
1491
|
+
}
|
|
1492
|
+
if (depth === 0 && character === separator) {
|
|
1493
|
+
const item = value.slice(start, index).trim();
|
|
1494
|
+
if (item) result.push(item);
|
|
1495
|
+
start = index + 1;
|
|
1496
|
+
}
|
|
1497
|
+
}
|
|
1498
|
+
const item = value.slice(start).trim();
|
|
1499
|
+
if (item) result.push(item);
|
|
1500
|
+
return result;
|
|
1501
|
+
}
|
|
1502
|
+
const sequencePattern = /^(-?\d+)\.\.(-?\d+)(?:\.\.(-?\d+))?$/;
|
|
1503
|
+
function expandSequence(value) {
|
|
1504
|
+
const match = value.match(sequencePattern);
|
|
1505
|
+
if (!match) return [value];
|
|
1506
|
+
const [, startValue, endValue, stepValue] = match;
|
|
1507
|
+
if (startValue === void 0 || endValue === void 0) return [value];
|
|
1508
|
+
const start = Number.parseInt(startValue, 10);
|
|
1509
|
+
const end = Number.parseInt(endValue, 10);
|
|
1510
|
+
let step = stepValue === void 0 ? start <= end ? 1 : -1 : Number.parseInt(stepValue, 10);
|
|
1511
|
+
if (step === 0) throw new Error("Step cannot be zero in Tailwind CSS v4 inline source sequence.");
|
|
1512
|
+
const ascending = start < end;
|
|
1513
|
+
if (ascending && step < 0) step = -step;
|
|
1514
|
+
if (!ascending && step > 0) step = -step;
|
|
1515
|
+
const result = [];
|
|
1516
|
+
for (let current = start; ascending ? current <= end : current >= end; current += step) result.push(current.toString());
|
|
1517
|
+
return result;
|
|
1518
|
+
}
|
|
1519
|
+
function expandInlinePattern(pattern) {
|
|
1520
|
+
const openIndex = pattern.indexOf("{");
|
|
1521
|
+
if (openIndex === -1) return [pattern];
|
|
1522
|
+
const prefix = pattern.slice(0, openIndex);
|
|
1523
|
+
const rest = pattern.slice(openIndex);
|
|
1524
|
+
let depth = 0;
|
|
1525
|
+
let closeIndex = -1;
|
|
1526
|
+
for (let index = 0; index < rest.length; index++) {
|
|
1527
|
+
const character = rest[index];
|
|
1528
|
+
if (character === "{") depth++;
|
|
1529
|
+
else if (character === "}") {
|
|
1530
|
+
depth--;
|
|
1531
|
+
if (depth === 0) {
|
|
1532
|
+
closeIndex = index;
|
|
1533
|
+
break;
|
|
1534
|
+
}
|
|
1535
|
+
}
|
|
1536
|
+
}
|
|
1537
|
+
if (closeIndex === -1) throw new Error(`The Tailwind CSS v4 inline source pattern "${pattern}" is not balanced.`);
|
|
1538
|
+
const body = rest.slice(1, closeIndex);
|
|
1539
|
+
const suffix = rest.slice(closeIndex + 1);
|
|
1540
|
+
const parts = sequencePattern.test(body) ? expandSequence(body) : splitTopLevel(body, ",").flatMap((part) => expandInlinePattern(part));
|
|
1541
|
+
const suffixes = expandInlinePattern(suffix);
|
|
1542
|
+
const result = [];
|
|
1543
|
+
for (const part of parts) for (const expandedSuffix of suffixes) result.push(`${prefix}${part}${expandedSuffix}`);
|
|
1544
|
+
return result;
|
|
1545
|
+
}
|
|
1546
|
+
function unquoteCssString(value) {
|
|
1547
|
+
const quote = value[0];
|
|
1548
|
+
if (quote !== "\"" && quote !== "'" || value[value.length - 1] !== quote) return;
|
|
1549
|
+
let result = "";
|
|
1550
|
+
for (let index = 1; index < value.length - 1; index++) {
|
|
1551
|
+
const character = value[index];
|
|
1552
|
+
if (character === "\\") {
|
|
1553
|
+
index++;
|
|
1554
|
+
result += value[index] ?? "";
|
|
1555
|
+
continue;
|
|
1556
|
+
}
|
|
1557
|
+
result += character;
|
|
1558
|
+
}
|
|
1559
|
+
return result;
|
|
1560
|
+
}
|
|
1561
|
+
function extractTailwindV4InlineSourceCandidates(css) {
|
|
1562
|
+
const included = /* @__PURE__ */ new Set();
|
|
1563
|
+
const excluded = /* @__PURE__ */ new Set();
|
|
1564
|
+
postcss.parse(css).walkAtRules("source", (rule) => {
|
|
1565
|
+
let params = rule.params.trim();
|
|
1566
|
+
if (!params) return;
|
|
1567
|
+
let negated = false;
|
|
1568
|
+
if (params.startsWith("not ")) {
|
|
1569
|
+
negated = true;
|
|
1570
|
+
params = params.slice(4).trim();
|
|
1571
|
+
}
|
|
1572
|
+
if (!params.startsWith("inline(") || !params.endsWith(")")) return;
|
|
1573
|
+
const inlineValue = unquoteCssString(params.slice(7, -1).trim());
|
|
1574
|
+
if (inlineValue === void 0) return;
|
|
1575
|
+
const target = negated ? excluded : included;
|
|
1576
|
+
for (const part of splitTopLevel(inlineValue, " ")) for (const candidate of expandInlinePattern(part)) target.add(candidate);
|
|
1577
|
+
});
|
|
1578
|
+
return {
|
|
1579
|
+
included,
|
|
1580
|
+
excluded
|
|
1581
|
+
};
|
|
1582
|
+
}
|
|
1583
|
+
//#endregion
|
|
1584
|
+
//#region src/v4/node-adapter.ts
|
|
1585
|
+
const nodeModulePromiseCache = /* @__PURE__ */ new Map();
|
|
1451
1586
|
const designSystemPromiseCache = /* @__PURE__ */ new Map();
|
|
1452
|
-
|
|
1453
|
-
|
|
1454
|
-
return import("@tailwindcss/node");
|
|
1587
|
+
function unique(values) {
|
|
1588
|
+
return Array.from(new Set(Array.from(values).filter(Boolean).map((value) => path.resolve(value))));
|
|
1455
1589
|
}
|
|
1456
|
-
|
|
1457
|
-
return
|
|
1590
|
+
function createRequireBase(base) {
|
|
1591
|
+
return path.join(base, "package.json");
|
|
1458
1592
|
}
|
|
1459
|
-
function
|
|
1460
|
-
|
|
1461
|
-
return nodeImportPromise;
|
|
1593
|
+
function isRelativeSpecifier(id) {
|
|
1594
|
+
return id.startsWith("./") || id.startsWith("../") || id === "." || id === "..";
|
|
1462
1595
|
}
|
|
1463
|
-
function
|
|
1464
|
-
|
|
1465
|
-
|
|
1596
|
+
function isAbsoluteSpecifier(id) {
|
|
1597
|
+
return path.isAbsolute(id);
|
|
1598
|
+
}
|
|
1599
|
+
function isCssSpecifier(id) {
|
|
1600
|
+
return path.extname(id) === ".css";
|
|
1601
|
+
}
|
|
1602
|
+
function createCssResolutionCandidates(id) {
|
|
1603
|
+
if (isCssSpecifier(id)) return [id];
|
|
1604
|
+
return [`${id}/index.css`, id];
|
|
1605
|
+
}
|
|
1606
|
+
function createFallbackCssResolver(baseCandidates) {
|
|
1607
|
+
const bases = unique(baseCandidates);
|
|
1608
|
+
return async (id) => {
|
|
1609
|
+
if (isRelativeSpecifier(id) || isAbsoluteSpecifier(id)) return;
|
|
1610
|
+
for (const base of bases) {
|
|
1611
|
+
const requireFromBase = createRequire(createRequireBase(base));
|
|
1612
|
+
for (const candidate of createCssResolutionCandidates(id)) try {
|
|
1613
|
+
return requireFromBase.resolve(candidate);
|
|
1614
|
+
} catch {}
|
|
1615
|
+
}
|
|
1616
|
+
};
|
|
1617
|
+
}
|
|
1618
|
+
async function importResolvedModule(resolved) {
|
|
1619
|
+
return import(pathToFileURL(resolved).href);
|
|
1620
|
+
}
|
|
1621
|
+
async function importTailwindNodeFromBase(base) {
|
|
1622
|
+
try {
|
|
1623
|
+
return await importResolvedModule(createRequire(createRequireBase(base)).resolve("@tailwindcss/node"));
|
|
1624
|
+
} catch {
|
|
1625
|
+
return;
|
|
1626
|
+
}
|
|
1627
|
+
}
|
|
1628
|
+
async function importFallbackTailwindNode() {
|
|
1629
|
+
return import("@tailwindcss/node");
|
|
1630
|
+
}
|
|
1631
|
+
async function loadTailwindV4NodeModule(baseCandidates) {
|
|
1632
|
+
const bases = unique(baseCandidates);
|
|
1633
|
+
const cacheKey = JSON.stringify(bases);
|
|
1634
|
+
const cached = nodeModulePromiseCache.get(cacheKey);
|
|
1635
|
+
if (cached) return cached;
|
|
1636
|
+
const promise = (async () => {
|
|
1637
|
+
for (const base of bases) {
|
|
1638
|
+
const loaded = await importTailwindNodeFromBase(base);
|
|
1639
|
+
if (loaded) return loaded;
|
|
1640
|
+
}
|
|
1641
|
+
return importFallbackTailwindNode();
|
|
1642
|
+
})();
|
|
1643
|
+
nodeModulePromiseCache.set(cacheKey, promise);
|
|
1644
|
+
promise.catch(() => {
|
|
1645
|
+
if (nodeModulePromiseCache.get(cacheKey) === promise) nodeModulePromiseCache.delete(cacheKey);
|
|
1646
|
+
});
|
|
1647
|
+
return promise;
|
|
1466
1648
|
}
|
|
1467
1649
|
function createDesignSystemCacheKey(css, bases) {
|
|
1468
1650
|
return JSON.stringify({
|
|
1469
1651
|
css,
|
|
1470
|
-
bases:
|
|
1652
|
+
bases: unique(bases)
|
|
1471
1653
|
});
|
|
1472
1654
|
}
|
|
1473
|
-
|
|
1474
|
-
|
|
1475
|
-
|
|
1476
|
-
|
|
1655
|
+
function getTailwindV4DesignSystemCacheKey(source) {
|
|
1656
|
+
return createDesignSystemCacheKey(source.css, [source.base, ...source.baseFallbacks]);
|
|
1657
|
+
}
|
|
1658
|
+
async function loadTailwindV4DesignSystem(source) {
|
|
1659
|
+
const bases = unique([source.base, ...source.baseFallbacks]);
|
|
1660
|
+
if (bases.length === 0) throw new Error("No base directories provided for Tailwind CSS v4 design system.");
|
|
1661
|
+
const cacheKey = createDesignSystemCacheKey(source.css, bases);
|
|
1477
1662
|
const cached = designSystemPromiseCache.get(cacheKey);
|
|
1478
1663
|
if (cached) return cached;
|
|
1479
1664
|
const promise = (async () => {
|
|
1480
|
-
const
|
|
1665
|
+
const node = await loadTailwindV4NodeModule([source.projectRoot, ...bases]);
|
|
1481
1666
|
let lastError;
|
|
1482
|
-
for (const base of
|
|
1483
|
-
return await __unstable__loadDesignSystem(css, { base });
|
|
1667
|
+
for (const base of bases) try {
|
|
1668
|
+
return await node.__unstable__loadDesignSystem(source.css, { base });
|
|
1484
1669
|
} catch (error) {
|
|
1485
1670
|
lastError = error;
|
|
1486
1671
|
}
|
|
1487
1672
|
if (lastError instanceof Error) throw lastError;
|
|
1488
|
-
throw new Error("Failed to load Tailwind CSS design system.");
|
|
1673
|
+
throw new Error("Failed to load Tailwind CSS v4 design system.");
|
|
1489
1674
|
})();
|
|
1490
1675
|
designSystemPromiseCache.set(cacheKey, promise);
|
|
1491
1676
|
promise.catch(() => {
|
|
1492
|
-
if (designSystemPromiseCache.get(cacheKey) === promise)
|
|
1493
|
-
designSystemPromiseCache.delete(cacheKey);
|
|
1494
|
-
designSystemCandidateCache.delete(cacheKey);
|
|
1495
|
-
}
|
|
1677
|
+
if (designSystemPromiseCache.get(cacheKey) === promise) designSystemPromiseCache.delete(cacheKey);
|
|
1496
1678
|
});
|
|
1497
1679
|
return promise;
|
|
1498
1680
|
}
|
|
1681
|
+
async function compileTailwindV4Source(source) {
|
|
1682
|
+
const bases = unique([source.base, ...source.baseFallbacks]);
|
|
1683
|
+
if (bases.length === 0) throw new Error("No base directories provided for Tailwind CSS v4 compiler.");
|
|
1684
|
+
const node = await loadTailwindV4NodeModule([source.projectRoot, ...bases]);
|
|
1685
|
+
let lastError;
|
|
1686
|
+
for (const base of bases) {
|
|
1687
|
+
const dependencies = new Set(source.dependencies);
|
|
1688
|
+
try {
|
|
1689
|
+
return {
|
|
1690
|
+
compiled: await node.compile(source.css, {
|
|
1691
|
+
base,
|
|
1692
|
+
customCssResolver: createFallbackCssResolver([source.projectRoot, ...bases]),
|
|
1693
|
+
onDependency(dependency) {
|
|
1694
|
+
dependencies.add(path.resolve(dependency));
|
|
1695
|
+
}
|
|
1696
|
+
}),
|
|
1697
|
+
dependencies
|
|
1698
|
+
};
|
|
1699
|
+
} catch (error) {
|
|
1700
|
+
lastError = error;
|
|
1701
|
+
}
|
|
1702
|
+
}
|
|
1703
|
+
if (lastError instanceof Error) throw lastError;
|
|
1704
|
+
throw new Error("Failed to compile Tailwind CSS v4 source.");
|
|
1705
|
+
}
|
|
1706
|
+
//#endregion
|
|
1707
|
+
//#region src/extraction/candidate-extractor.ts
|
|
1708
|
+
let oxideImportPromise;
|
|
1709
|
+
const designSystemCandidateCache = /* @__PURE__ */ new Map();
|
|
1710
|
+
async function importOxide() {
|
|
1711
|
+
return import("@tailwindcss/oxide");
|
|
1712
|
+
}
|
|
1713
|
+
function getOxideModule() {
|
|
1714
|
+
oxideImportPromise ??= importOxide();
|
|
1715
|
+
return oxideImportPromise;
|
|
1716
|
+
}
|
|
1499
1717
|
async function extractRawCandidatesWithPositions(content, extension = "html") {
|
|
1500
1718
|
const { Scanner } = await getOxideModule();
|
|
1501
1719
|
return new Scanner({}).getCandidatesWithPositions({
|
|
@@ -1526,8 +1744,15 @@ async function extractValidCandidates(options) {
|
|
|
1526
1744
|
pattern: source.pattern,
|
|
1527
1745
|
negated: source.negated
|
|
1528
1746
|
}));
|
|
1529
|
-
const
|
|
1530
|
-
|
|
1747
|
+
const source = {
|
|
1748
|
+
projectRoot: defaultCwd,
|
|
1749
|
+
base,
|
|
1750
|
+
baseFallbacks,
|
|
1751
|
+
css,
|
|
1752
|
+
dependencies: []
|
|
1753
|
+
};
|
|
1754
|
+
const designSystemKey = getTailwindV4DesignSystemCacheKey(source);
|
|
1755
|
+
const designSystem = await loadTailwindV4DesignSystem(source);
|
|
1531
1756
|
const candidateCache = designSystemCandidateCache.get(designSystemKey) ?? /* @__PURE__ */ new Map();
|
|
1532
1757
|
designSystemCandidateCache.set(designSystemKey, candidateCache);
|
|
1533
1758
|
const candidates = await extractRawCandidates(sources);
|
|
@@ -1547,12 +1772,9 @@ async function extractValidCandidates(options) {
|
|
|
1547
1772
|
candidateCache.set(rawCandidate, false);
|
|
1548
1773
|
}
|
|
1549
1774
|
if (uncachedCandidates.length === 0) return validCandidates;
|
|
1550
|
-
const
|
|
1551
|
-
for (
|
|
1552
|
-
const
|
|
1553
|
-
if (candidate === void 0) continue;
|
|
1554
|
-
const candidateCss = cssByCandidate[index];
|
|
1555
|
-
const isValid = typeof candidateCss === "string" && candidateCss.trim().length > 0;
|
|
1775
|
+
const validUncachedCandidates = resolveValidTailwindV4Candidates(designSystem, uncachedCandidates);
|
|
1776
|
+
for (const candidate of uncachedCandidates) {
|
|
1777
|
+
const isValid = validUncachedCandidates.has(candidate);
|
|
1556
1778
|
candidateCache.set(candidate, isValid);
|
|
1557
1779
|
if (!isValid) continue;
|
|
1558
1780
|
validCandidates.push(candidate);
|
|
@@ -3333,4 +3555,4 @@ var ValidateCommandError = class extends Error {
|
|
|
3333
3555
|
}
|
|
3334
3556
|
};
|
|
3335
3557
|
//#endregion
|
|
3336
|
-
export {
|
|
3558
|
+
export { extractTailwindV4InlineSourceCandidates as C, normalizeOptions as D, loadWorkspaceConfigModule as E, CacheStore as O, loadTailwindV4DesignSystem as S, loadPatchOptionsForWorkspace as T, extractRawCandidates as _, tailwindcssPatchCommands as a, groupTokensByFile as b, MIGRATION_REPORT_KIND as c, getPatchStatusReport as d, runTailwindBuild as f, extractProjectCandidatesWithPositions as g, collectClassesFromTailwindV4 as h, classifyValidateError as i, logger as k, MIGRATION_REPORT_SCHEMA_VERSION as l, collectClassesFromContexts as m, VALIDATE_FAILURE_REASONS as n, migrateConfigFiles as o, loadRuntimeContexts as p, ValidateCommandError as r, restoreConfigFiles as s, VALIDATE_EXIT_CODES as t, TailwindcssPatcher as u, extractRawCandidatesWithPositions as v, resolveValidTailwindV4Candidates as w, compileTailwindV4Source as x, extractValidCandidates as y };
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "tailwindcss-patch",
|
|
3
|
-
"version": "9.0
|
|
3
|
+
"version": "9.2.0",
|
|
4
4
|
"description": "patch tailwindcss for exposing context and extract classes",
|
|
5
5
|
"author": "ice breaker <1324318532@qq.com>",
|
|
6
6
|
"license": "MIT",
|
|
@@ -71,7 +71,7 @@
|
|
|
71
71
|
"fs-extra": "^11.3.4",
|
|
72
72
|
"local-pkg": "^1.1.2",
|
|
73
73
|
"pathe": "^2.0.3",
|
|
74
|
-
"postcss": "^8.5.
|
|
74
|
+
"postcss": "^8.5.14",
|
|
75
75
|
"semver": "^7.7.4",
|
|
76
76
|
"tailwindcss-config": "^1.1.5",
|
|
77
77
|
"@tailwindcss-mangle/config": "7.0.1"
|
|
@@ -8,78 +8,21 @@ import type {
|
|
|
8
8
|
import { promises as fs } from 'node:fs'
|
|
9
9
|
import process from 'node:process'
|
|
10
10
|
import path from 'pathe'
|
|
11
|
+
import { resolveValidTailwindV4Candidates } from '../v4/candidates'
|
|
12
|
+
import { getTailwindV4DesignSystemCacheKey, loadTailwindV4DesignSystem } from '../v4/node-adapter'
|
|
11
13
|
|
|
12
|
-
let nodeImportPromise: ReturnType<typeof importNode> | undefined
|
|
13
14
|
let oxideImportPromise: ReturnType<typeof importOxide> | undefined
|
|
14
|
-
const designSystemPromiseCache = new Map<string, Promise<any>>()
|
|
15
15
|
const designSystemCandidateCache = new Map<string, Map<string, boolean>>()
|
|
16
16
|
|
|
17
|
-
async function importNode() {
|
|
18
|
-
return import('@tailwindcss/node')
|
|
19
|
-
}
|
|
20
|
-
|
|
21
17
|
async function importOxide() {
|
|
22
18
|
return import('@tailwindcss/oxide')
|
|
23
19
|
}
|
|
24
20
|
|
|
25
|
-
function getNodeModule() {
|
|
26
|
-
nodeImportPromise ??= importNode()
|
|
27
|
-
return nodeImportPromise
|
|
28
|
-
}
|
|
29
|
-
|
|
30
21
|
function getOxideModule() {
|
|
31
22
|
oxideImportPromise ??= importOxide()
|
|
32
23
|
return oxideImportPromise
|
|
33
24
|
}
|
|
34
25
|
|
|
35
|
-
function createDesignSystemCacheKey(css: string, bases: string[]) {
|
|
36
|
-
return JSON.stringify({
|
|
37
|
-
css,
|
|
38
|
-
bases: Array.from(new Set(bases.filter(Boolean))),
|
|
39
|
-
})
|
|
40
|
-
}
|
|
41
|
-
|
|
42
|
-
async function loadDesignSystem(css: string, bases: string[]) {
|
|
43
|
-
const uniqueBases = Array.from(new Set(bases.filter(Boolean)))
|
|
44
|
-
if (uniqueBases.length === 0) {
|
|
45
|
-
throw new Error('No base directories provided for Tailwind CSS design system.')
|
|
46
|
-
}
|
|
47
|
-
|
|
48
|
-
const cacheKey = createDesignSystemCacheKey(css, uniqueBases)
|
|
49
|
-
const cached = designSystemPromiseCache.get(cacheKey)
|
|
50
|
-
if (cached) {
|
|
51
|
-
return cached
|
|
52
|
-
}
|
|
53
|
-
|
|
54
|
-
const promise = (async () => {
|
|
55
|
-
const { __unstable__loadDesignSystem } = await getNodeModule()
|
|
56
|
-
let lastError: unknown
|
|
57
|
-
|
|
58
|
-
for (const base of uniqueBases) {
|
|
59
|
-
try {
|
|
60
|
-
return await __unstable__loadDesignSystem(css, { base })
|
|
61
|
-
}
|
|
62
|
-
catch (error) {
|
|
63
|
-
lastError = error
|
|
64
|
-
}
|
|
65
|
-
}
|
|
66
|
-
|
|
67
|
-
if (lastError instanceof Error) {
|
|
68
|
-
throw lastError
|
|
69
|
-
}
|
|
70
|
-
throw new Error('Failed to load Tailwind CSS design system.')
|
|
71
|
-
})()
|
|
72
|
-
|
|
73
|
-
designSystemPromiseCache.set(cacheKey, promise)
|
|
74
|
-
promise.catch(() => {
|
|
75
|
-
if (designSystemPromiseCache.get(cacheKey) === promise) {
|
|
76
|
-
designSystemPromiseCache.delete(cacheKey)
|
|
77
|
-
designSystemCandidateCache.delete(cacheKey)
|
|
78
|
-
}
|
|
79
|
-
})
|
|
80
|
-
return promise
|
|
81
|
-
}
|
|
82
|
-
|
|
83
26
|
export interface ExtractValidCandidatesOption {
|
|
84
27
|
sources?: SourceEntry[]
|
|
85
28
|
base?: string
|
|
@@ -131,8 +74,15 @@ export async function extractValidCandidates(options?: ExtractValidCandidatesOpt
|
|
|
131
74
|
negated: source.negated,
|
|
132
75
|
}))
|
|
133
76
|
|
|
134
|
-
const
|
|
135
|
-
|
|
77
|
+
const source = {
|
|
78
|
+
projectRoot: defaultCwd,
|
|
79
|
+
base,
|
|
80
|
+
baseFallbacks,
|
|
81
|
+
css,
|
|
82
|
+
dependencies: [],
|
|
83
|
+
}
|
|
84
|
+
const designSystemKey = getTailwindV4DesignSystemCacheKey(source)
|
|
85
|
+
const designSystem = await loadTailwindV4DesignSystem(source)
|
|
136
86
|
const candidateCache = designSystemCandidateCache.get(designSystemKey) ?? new Map<string, boolean>()
|
|
137
87
|
designSystemCandidateCache.set(designSystemKey, candidateCache)
|
|
138
88
|
|
|
@@ -163,15 +113,10 @@ export async function extractValidCandidates(options?: ExtractValidCandidatesOpt
|
|
|
163
113
|
return validCandidates
|
|
164
114
|
}
|
|
165
115
|
|
|
166
|
-
const
|
|
116
|
+
const validUncachedCandidates = resolveValidTailwindV4Candidates(designSystem, uncachedCandidates)
|
|
167
117
|
|
|
168
|
-
for (
|
|
169
|
-
const
|
|
170
|
-
if (candidate === undefined) {
|
|
171
|
-
continue
|
|
172
|
-
}
|
|
173
|
-
const candidateCss = cssByCandidate[index]
|
|
174
|
-
const isValid = typeof candidateCss === 'string' && candidateCss.trim().length > 0
|
|
118
|
+
for (const candidate of uncachedCandidates) {
|
|
119
|
+
const isValid = validUncachedCandidates.has(candidate)
|
|
175
120
|
candidateCache.set(candidate, isValid)
|
|
176
121
|
if (!isValid) {
|
|
177
122
|
continue
|
package/src/index.bundle.ts
CHANGED
|
@@ -33,6 +33,13 @@ import {
|
|
|
33
33
|
runTailwindBuild,
|
|
34
34
|
} from './install'
|
|
35
35
|
import logger from './logger'
|
|
36
|
+
import {
|
|
37
|
+
createTailwindV4Engine,
|
|
38
|
+
loadTailwindV4DesignSystem,
|
|
39
|
+
resolveTailwindV4Source,
|
|
40
|
+
resolveTailwindV4SourceFromPatchOptions,
|
|
41
|
+
resolveValidTailwindV4Candidates,
|
|
42
|
+
} from './v4'
|
|
36
43
|
|
|
37
44
|
const require = createRequire(import.meta.url)
|
|
38
45
|
|
|
@@ -46,6 +53,7 @@ export {
|
|
|
46
53
|
CacheStore,
|
|
47
54
|
collectClassesFromContexts,
|
|
48
55
|
collectClassesFromTailwindV4,
|
|
56
|
+
createTailwindV4Engine,
|
|
49
57
|
extractProjectCandidatesWithPositions,
|
|
50
58
|
extractRawCandidates,
|
|
51
59
|
extractRawCandidatesWithPositions,
|
|
@@ -53,11 +61,15 @@ export {
|
|
|
53
61
|
getPatchStatusReport,
|
|
54
62
|
groupTokensByFile,
|
|
55
63
|
loadRuntimeContexts,
|
|
64
|
+
loadTailwindV4DesignSystem,
|
|
56
65
|
logger,
|
|
57
66
|
migrateConfigFiles,
|
|
58
67
|
MIGRATION_REPORT_KIND,
|
|
59
68
|
MIGRATION_REPORT_SCHEMA_VERSION,
|
|
60
69
|
normalizeOptions,
|
|
70
|
+
resolveTailwindV4Source,
|
|
71
|
+
resolveTailwindV4SourceFromPatchOptions,
|
|
72
|
+
resolveValidTailwindV4Candidates,
|
|
61
73
|
restoreConfigFiles,
|
|
62
74
|
runTailwindBuild,
|
|
63
75
|
tailwindcssPatchCommands,
|
|
@@ -91,6 +103,15 @@ export type {
|
|
|
91
103
|
} from './commands/validate'
|
|
92
104
|
export type { TailwindCssPatchOptions } from './config'
|
|
93
105
|
export * from './types'
|
|
106
|
+
export type {
|
|
107
|
+
TailwindV4CandidateSource,
|
|
108
|
+
TailwindV4DesignSystem,
|
|
109
|
+
TailwindV4Engine,
|
|
110
|
+
TailwindV4GenerateOptions,
|
|
111
|
+
TailwindV4GenerateResult,
|
|
112
|
+
TailwindV4ResolvedSource,
|
|
113
|
+
TailwindV4SourceOptions,
|
|
114
|
+
} from './v4'
|
|
94
115
|
|
|
95
116
|
export function mountTailwindcssPatchCommands(cli: CAC, options: TailwindcssPatchCliMountOptions = {}) {
|
|
96
117
|
return loadCliModule().mountTailwindcssPatchCommands(cli, options)
|
package/src/index.ts
CHANGED
|
@@ -51,6 +51,22 @@ export {
|
|
|
51
51
|
} from './install'
|
|
52
52
|
export { default as logger } from './logger'
|
|
53
53
|
export * from './types'
|
|
54
|
+
export {
|
|
55
|
+
createTailwindV4Engine,
|
|
56
|
+
loadTailwindV4DesignSystem,
|
|
57
|
+
resolveTailwindV4Source,
|
|
58
|
+
resolveTailwindV4SourceFromPatchOptions,
|
|
59
|
+
resolveValidTailwindV4Candidates,
|
|
60
|
+
} from './v4'
|
|
61
|
+
export type {
|
|
62
|
+
TailwindV4CandidateSource,
|
|
63
|
+
TailwindV4DesignSystem,
|
|
64
|
+
TailwindV4Engine,
|
|
65
|
+
TailwindV4GenerateOptions,
|
|
66
|
+
TailwindV4GenerateResult,
|
|
67
|
+
TailwindV4ResolvedSource,
|
|
68
|
+
TailwindV4SourceOptions,
|
|
69
|
+
} from './v4'
|
|
54
70
|
|
|
55
71
|
export function defineConfig<T extends TailwindcssMangleConfig>(config: T): T {
|
|
56
72
|
return config
|