Baike.dev
All toolsAI codingTrendingOpen sourceNewsSubmit
Log in
Back to tool/Back to issues
#1222·lightningcss

`@layer` ordering declaration is silently dropped when followed by `@layer` blocks

Author: madogiwa0124Created Apr 19, 2026Updated Sep 14, 2026
Labelspending triage

Description

When a CSS file contains a standalone @layer ordering declaration followed by @layer blocks for the same layer names, transform() (and bundle()) silently drops the ordering declaration from the output — regardless of the minify option.

Environment

  • lightningcss: 1.32.0
  • Reproduced on:
    • macOS 26.3.1, arm64, Node.js v24.13.0
    • Linux (Alpine), x86_64, Node.js v24.15.0
    • Linux (Alpine), arm64, Node.js v24.15.0

Reproduction

javascript
// repro.mjs
import { transform } from "lightningcss";

const input = `
@layer base, layout, components, utils;

@layer base { body { margin: 0; } }
@layer layout { .container { max-width: 1200px; } }
@layer components { .btn { padding: 8px 16px; } }
@layer utils { .hidden { display: none; } }
`.trim();

for (const minify of [false, true]) {
  const { code } = transform({
    filename: "test.css",
    code: Buffer.from(input),
    minify,
  });
  const output = code.toString();
  const needle = minify
    ? "@layer base,layout,components,utils;"
    : "@layer base, layout, components, utils;";
  console.log(
    `minify: ${minify} → ordering preserved: ${output.includes(needle) ? "✓ OK" : "✗ BUG"}`,
  );
  console.log(output);
  console.log("---");
}
bash
$ node repro.mjs
minify: false → ordering preserved: ✗ BUG
@layer base {
  body {
    margin: 0;
  }
}

@layer layout {
  .container {
    max-width: 1200px;
  }
}

@layer components {
  .btn {
    padding: 8px 16px;
  }
}

@layer utils {
  .hidden {
    display: none;
  }
}

---
minify: true → ordering preserved: ✗ BUG
@layer base{body{margin:0}}@layer layout{.container{max-width:1200px}}@layer components{.btn{padding:8px 16px}}@layer utils{.hidden{display:none}}
---

Expected

The ordering declaration @layer base, layout, components, utils; should be preserved in the output in both minify: false and minify: true modes.

Actual

The ordering declaration is completely absent from the output. The @layer blocks themselves are preserved, so the layers exist but their explicit ordering is gone.

Additional findings

Testing two variations narrows down the trigger:

Input minify: false minify: true
ordering declaration only (no blocks) ✓ preserved ✓ preserved
ordering declaration + blocks (original repro) ✗ dropped ✗ dropped

The drop only occurs when the same layer names appear in both the ordering declaration and subsequent @layer blocks. When the ordering declaration appears alone (no blocks), it is preserved as expected.

bundle() is also affected:

javascript
import { bundle } from "lightningcss";

// with the same input written to a file:
bundle({ filename: "test.css", minify: false });
// → ordering declaration is also dropped

Notes

Per MDN:

"the initial order in which layers are declared indicates which layer has precedence"

A standalone @layer ordering declaration is explicitly described as a mechanism to establish layer precedence order. This indicates it carries semantic meaning and should be preserved in the output.

Source: parcel-bundler/lightningcss

View original on GitHubView discussion on GitHub