Skip to content
4 changes: 1 addition & 3 deletions packages/@tailwindcss-node/src/urls.ts
Original file line number Diff line number Diff line change
Expand Up @@ -86,9 +86,7 @@ export async function rewriteUrls({
await Promise.all(promises)
}

return toCss(ast, {
printUtilitiesNode: true,
})
return toCss(ast)
}

function rewriteCssUrls(css: string, replacer: CssUrlReplacer): Promise<string> {
Expand Down
15 changes: 2 additions & 13 deletions packages/tailwindcss/src/ast.ts
Original file line number Diff line number Diff line change
Expand Up @@ -202,7 +202,7 @@ export function walkDepth(
}
}

export function toCss(ast: AstNode[], { printUtilitiesNode = false } = {}) {
export function toCss(ast: AstNode[]) {
let atRoots: string = ''
let seenAtProperties = new Set<string>()
let propertyFallbacksRoot: Declaration[] = []
Expand All @@ -223,25 +223,14 @@ export function toCss(ast: AstNode[], { printUtilitiesNode = false } = {}) {

// AtRule
else if (node.kind === 'at-rule') {
if (
!printUtilitiesNode &&
node.name === '@tailwind' &&
(node.params === 'utilities' || node.params.startsWith('utilities'))
) {
for (let child of node.nodes) {
css += stringify(child, depth)
}
return css
}

// Print at-rules without nodes with a `;` instead of an empty block.
//
// E.g.:
//
// ```css
// @layer base, components, utilities;
// ```
else if (node.nodes.length === 0) {
if (node.nodes.length === 0) {
return `${indent}${node.name} ${node.params};\n`
}

Expand Down
18 changes: 18 additions & 0 deletions packages/tailwindcss/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ import {
WalkAction,
type AstNode,
type AtRule,
type Context,
type StyleRule,
} from './ast'
import { substituteAtImports } from './at-import'
Expand Down Expand Up @@ -452,6 +453,23 @@ async function parseCss(
firstThemeRule.nodes = nodes
}

// Replace the `@tailwind utilities` node with a conext since it prints
// children directly.
if (utilitiesNode) {
let node = utilitiesNode as AstNode as Context
node.kind = 'context'
node.context = {}

// Remove additional `@tailwind utilities` nodes
walk(ast, (node, { replaceWith }) => {
if (node.kind !== 'at-rule') return
if (node.name !== '@tailwind') return
if (!node.params.startsWith('utilities')) return

replaceWith([])
})
}

// Replace `@apply` rules with the actual utility classes.
substituteAtApply(ast, designSystem)

Expand Down