dart sass 1.77+ 的 css 输出顺序变化是 ast 深度优先遍历更严格所致,由嵌套展开、@mixin 插入点和 @import 合并时机共同决定;应统一使用 @use、避免混用 @import、将 mixin 收口至注入点或改用 @function。

dart-sass 1.77+ 版本起,CSS 输出顺序变化不是 bug,而是编译器 AST 遍历逻辑更严格体现的结果——嵌套展开、@mixin 插入点、@import 合并时机 这三者共同决定了最终 CSS 行序,不再“看起来像源码顺序”。
为什么 @mixin 展开位置突然变了?
@mixin 定义本身不产生 CSS;只有 @include 处才插入规则节点。Dart Sass 1.77+ 对 AST 的深度优先遍历更忠实,导致:
-
@include出现在父选择器内部时,生成的 CSS 规则会紧贴该父节点输出,而非按 mixin 定义位置归类 - 若多个组件文件都
@include同一个通用 mixin(如reset-text),它们的输出位置取决于各自@include在 AST 中的插入点,可能分散在不同区块
常见现象:_typography.scss 里定义了 @mixin font-sm,但在 components/_card.scss 和 layout/_header.scss 中分别 @include,结果编译后两条 font-size 规则被拆开,中间插进了其他样式。
解决建议:
- 把高频复用的
@mixin改为@function+ 内联值(例如font-size: typography.font-sm();),避免生成独立规则 - 若必须保留
@mixin,统一收口到一个“注入点”:比如在base/_mixins.scss末尾集中@include所有全局基础 mixin,并确保它被@import在所有样式之前 - 禁用自动排序干扰:不要在
@mixin内部再嵌套@media或&:hover—— 拆成独立@mixin更可控
@import 和 @use 混用导致顺序断裂
@import 是扁平合并,@use 是作用域隔离 —— 两者混用会让编译器无法确定变量/混合器依赖链,间接打乱 CSS 输出顺序。
典型误用:main.scss 里先 @use 'base/variables',又 @import 'components/button',而 button.scss 内部又 @import 'base/mixins'。此时 button 的 CSS 可能被提前注入,因为它通过 @import 直接拿到了依赖,绕过了 @use 的声明时序。
如果你了解HTML,CSS和JavaScript,您已经拥有所需的工具开发Android应用程序。本动手本书展示了如何使用这些开源web标准设计和建造,可适应任何Android设备的应用程序 - 无需使用Java。您将学习如何创建一个在您选择的平台的Android友好的网络应用程序,然后转换与自由PhoneGap框架到一个原生的Android应用程序。了解为什么设备无关的移动应用是未来的潮流,并开始构建应用程序,提供更
解决建议:
- 全项目统一用
@use,彻底弃用@import(Dart Sass 1.77+ 已标记@import为 deprecated) - 所有
@use必须放在文件顶部,且按依赖层级排序:基础层(variables,functions)→ 工具层(mixins,placeholders)→ 组件层 - 如果某组件需要覆盖基础变量,用
@use 'base/variables' with ($spacing-unit: 12px),别在组件内部重定义同名变量
嵌套中 & 多次展开导致选择器“跳位”
带 & 的嵌套(如 .btn { &--primary {}, &.is-loading {} })会生成多个同级节点,它们在 AST 中的兄弟顺序严格对应源码书写顺序 —— 但一旦混入条件指令(@if, @for),顺序就不可预测。
例子:.card { @each $type in (info, warn, error) { &--#{$type} { color: map-get($colors, $type); } } },这段代码在 1.77 前可能稳定输出 info/warn/error 顺序,但新版因循环节点插入时机变化,可能错乱。
解决建议:
- 避免在嵌套块内使用动态指令生成多条规则;改用
@forward+@use拆分为静态模块 - 如需保持顺序,显式写出每个变体(
&--info,&--warn),放弃@each - 用
/* stylelint-disable no-duplicate-selectors */注释临时压制警告,但仅限过渡期
真正影响交付的不是“顺序变了”,而是你原本靠 CSS 顺序做样式覆盖(比如用后写的 .btn.is-active 覆盖前面的 .btn)的写法,在新编译逻辑下失效了。这时候该检查的不是 Sass 版本,而是你的 CSS 架构是否还依赖“写在后面就赢”的隐式约定。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!










