# CSS 日常开发规范 ## 1. 适用范围 本规范适用于新增、修改、迁移和审查前端 CSS。它是日常开发的强制规则;`global.css` 的存量拆分步骤另见 `global-css-modularization-plan-20260904.md`。 原则只有两条:每条样式必须有唯一所有者;样式的生效范围必须和所有者范围一致。 ## 2. 先判断归属 按以下顺序判断,命中后停止: | 问题 | 归属 | |---|---| | 是否只是颜色、间距、字号、圆角、阴影等设计变量? | `src/styles/tokens.css`,只定义自定义属性 | | 是否是浏览器重置或标签字体继承? | `src/styles/reset.css`,不得包含业务类名 | | 是否属于 AppShell、侧栏、顶栏、导航、登录框架或页面容器? | `src/styles/shell.css` | | 是否被多个业务域复用,且所有状态和视觉语义一致? | `src/styles/components/` 中对应公共组件文件 | | 是否只在同一业务域的多个页面复用? | 业务域目录中的共享 CSS,并使用业务域根前缀 | | 是否只服务一个页面、弹窗或局部组件? | 与所有者同目录的 CSS,由所有者直接 import | | 是否无法确认用途的历史规则? | 暂留 `global.css`,先记录和查证,不得复制或新增 | “看起来相似”不等于公共组件。只有 API、交互状态和视觉语义都一致,才能上移到公共层。 ## 3. 命名和作用域 - 页面必须有唯一根类名,例如 `.admin-report-materials-page`。 - 页面样式必须位于页面根类名下,避免路由切换后已加载 CSS 污染其他页面。 - 业务域共享样式使用稳定的业务域前缀;公共组件使用组件名,不使用 `item`、`title`、`card` 等无上下文短类名。 - 状态类使用所属组件限定,例如 `.report-field-card.is-selected`,不得单独定义全局 `.selected`。 - 不新增无根节点限定的 `div`、`button`、`table` 等业务样式。 - 新代码不使用 ID 选择器控制样式。 ## 4. Import 和级联 固定层级为: ```text tokens → reset → shell → shared components → business shared → page styles ``` - 基础层和全局共享层只能由应用入口或明确的公共组件入口加载。 - 页面 CSS 由页面或其业务域入口直接 import,不得通过 `global.css` 间接加载。 - 公共组件不得依赖业务页面样式;业务页面可以覆盖公共组件,但必须位于页面根节点下。 - 相同 specificity 下的覆盖如果依赖加载顺序,必须在代码中保持稳定,并验证首次进入、刷新和跨路由跳转。 - 伪类、子选择器、动画和媒体查询跟随其所有者,不集中到新的全局文件。 ## 5. 修改规则 - 优先复用 `tokens.css` 中已有变量;新增 token 必须具有跨页面意义。 - 不新增 `!important`。确有第三方样式等不可控原因时,需说明原因、影响范围和移除条件。 - 不通过不断嵌套或重复类名提高 specificity;应修正所有权、根节点或加载层级。 - 不在纯样式修复中顺手重排整个文件、改色、改字号或重做布局。 - 不复制已有规则来快速覆盖问题;先搜索同名选择器和全部消费者。 - 动态数值可使用 React `style` 或 CSS 自定义属性;稳定视觉规则仍应归入 CSS 所有者文件。 ## 6. `global.css` 过渡规则 - 在完成自动门禁和相关脚本适配前,文件继续保留 `global.css` 名称,行为上视为只减不增的 legacy 文件。 - 允许:迁出选择器、删除已验证无用规则、为保持迁移前计算样式而做的最小修正。 - 禁止:新页面选择器、新业务组件、单页补丁、无根节点覆盖以及新的 `!important`。 - 例外必须在变更说明中记录原因、影响页面、验证证据和后续清理条件;不能只写“临时处理”。 - 禁止整文件 Prettier;迁出的新文件应单独格式化。 ## 7. 开发和审查清单 提交前至少确认: 1. 样式文件和选择器有明确所有者。 2. 页面及业务样式具有根节点命名空间。 3. 没有向 `global.css` 增加页面或业务规则。 4. 没有新的无说明 `!important`、宽泛标签选择器或跨层依赖。 5. 修改共享样式时已列出并检查所有消费者。 6. hover、focus、disabled、loading、selected、danger、空数据和错误状态没有遗漏。 7. 1600×1000、1366×768、390×844 下没有新增溢出、遮挡和层级错误。 8. 首次进入、刷新和跨路由切换后的计算样式一致。 9. 已运行 CSS 格式与样式门禁、相关测试、TypeScript、生产构建和 `git diff --check`。 10. staged diff 没有整文件重排或其他会话的修改。 在自动门禁正式落地前,第 3、4、5、8 项必须人工检查,不能因工具尚未覆盖而跳过。