@use 下以 $_ 或 $- 开头的成员默认不导出,故“看似私有”;但私有性仅由模块系统控制,非命名规则决定,混用 @import 或不当 @forward 会彻底失效。

@use + $_ 前缀变量是唯一可行组合,但私有性不来自下划线,而来自模块系统默认不导出以 $_ 开头的成员。
为什么 $_ 变量在 @use 下“看起来”私有?
SCSS 编译器对 @use 加载的模块做了硬性约定:所有以 $_ 或 $- 开头的变量、mixin、function 默认不对外暴露。这不是语法限制,而是模块系统的默认行为。
- 你写
$_spacing-xs: 4px;在_vars.scss里,@use "vars" as v;后,v.$_spacing-xs会报错 —— 它根本不在导出列表中 - 但若用
@import "vars";,$_spacing-xs立刻变成全局可读、可覆盖,前缀毫无约束力 - 这个规则只对
@use有效;混用@import会让整条依赖链退化为 legacy 模式,私有性彻底失效
哪些写法会让私有性当场失效?
私有不是靠命名自动生效的,几个典型翻车点:
- 在变量文件里写
@forward "colors" as *;—— 解构导入会绕过$_过滤,把本该隐藏的项也带进来 - 用
@forward "vars" show $primary-color, $_private-token;显式列出$_private-token→ 它就不再是私有 - 入口文件里漏掉
as别名:@use "theme";后直接写$primary-color会失败,但有人误以为是变量名错了,其实是命名空间没建立 - 路径写成
@use "src/styles/_vars.scss";(带下划线和扩展名)→ 编译直接报错File not found,根本走不到私有逻辑
真正安全的私有变量实践方式
别依赖下划线“自动私有”,要靠结构+命名+约束三重保障:
- 变量文件必须命名为
_vars.scss(下划线开头),确保它不会被构建工具单独编译成 CSS - 内部定义统一用
$_前缀:$_z-index-drawer: 900;,但同时明确:这只是团队约定,不是语法锁 - 对外只暴露必要项,用
@forward "vars" hide $_z-index-drawer;显式屏蔽 - 调用方必须
@use "vars" as theme;,所有访问带前缀:theme.$primary-color,$_z-index-drawer根本不可见 - 如果某处真需要“跨模块传参”,改用 CSS 自定义属性:
--_drawer-z-index: 900;,配合var(--_drawer-z-index),这才是运行时可控的“私有”
最容易被忽略的是:私有性只存在于 @use 边界内。一旦变量通过 @forward 或解构 as * 流出模块,它就和普通变量没区别了 —— 此时再加 $_ 也拦不住别人读取。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











