bem 通过类名编码组件归属、结构和状态,使新人30秒内理解样式职责;user-card__avatar--loading 比 .avatar 更具语义;块名须为业务词、文件名与块名严格一致、禁止跨文件定义、需工具链校验与约束。

因为 BEM 把组件归属、结构和状态直接编码进类名,新成员打开一个 CSS 文件,30 秒内就能判断出它负责什么、能怎么用、有哪些合法状态——不需要查 HTML、不翻 Git 历史、不靠同事口述。
看到 user-card__avatar--loading 就比看到 .avatar 更快理解
人脑处理无上下文字符串成本很高。.avatar 出现在审查元素里,得跳转 HTML 才知道它属于哪个模块;而 user-card__avatar--loading 自带三重语义:归属(user-card)、角色(avatar)、状态(loading)。这种信息密度让新人不用猜。
- 常见错误现象:
card-title和product-card__title并存,新人改了前者却发现购物车页没生效——因为实际生效的是后者,但没人告诉过他“title”到底属于哪个块 - 块名必须是业务词,禁用
big-box、left-panel这类视觉描述 - 元素名不能脱离块独立存在:
__avatar合法,.avatar或__image都不行 - 修饰符只表达可预期的状态:
--large可收敛,--lg容易失控
每个 BEM 块对应一个独立 CSS 文件,且文件名与块名严格一致
这是让新人快速建立心智模型的关键约束。不是靠文档教,而是靠文件系统本身提供导航。
- 示例注释必须出现在文件开头:
/*<br>* @block user-card<br>* @description 用户资料卡片,支持头像尺寸/信息折叠/操作按钮显隐<br>* @modifiers: --compact, --with-actions, --loading<br>*/
- IDE 按
user-card.css搜索,ctrl+click 跳转即见全部样式逻辑 - 禁止跨文件定义同一块的样式:比如
form.css里写user-card__footer是违规的 - 子组件仍需独立块名:
dropdown里的菜单不是dropdown__menu,而是menu,除非它绝不出现在dropdown外
stylelint-selector-bem-pattern 必须接入开发流程
靠 Code Review 拦不住拼写错误,必须让违规在保存时就报错。
- 配置示例:
{"componentName": "[a-z][a-zA-Z0-9]+", "styleType": "bem"},自动拦截.header .logo或btn-primary - VS Code 安装 “BEM Helper”,输入
user-card回车自动补全user-card__和user-card-- - CI 流程中跑
npx stylelint "**/*.css",把命名校验变成门禁 - 禁止在 JS 里硬编码 BEM 字符串,比如
el.classList.add('card__body')—— 应该抽成常量或工具函数
真正难的不是写对第一个 button__icon--disabled,而是坚持不让临时需求破坏这个映射关系。当产品经理说“首页按钮加个脉冲动画”,正确做法是去 button.css 补 button--pulsing,哪怕只被用一次——这个动作本身就在训练边界意识,也是新人最容易忽略的长期成本点。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











