
安全告警里最容易被滥用的按钮往往不是“忽略”。而是这个漏洞还在 但我们有其他控制措施 所以先关掉。GitHub 8 月 20 日给 Code Scanning 新增了一个专门的 dismissal reasonMitigated适用场景是漏洞仍然存在于代码中 但外部补偿控制已经降低了风险官方给出的例子包括Web Application Firewall Network Policy这个能力本身很合理。真正危险的是如果企业把Mitigated当成一个新的“关闭按钮”很快就会形成另一种安全债漏洞没修 告警关了 补偿控制后来失效 没人知道所以Mitigated不能只是一列状态。它应该是一份有证据、有Owner、有期限、可复审的风险接受记录。Mitigated和Won’t Fix不是一回事这两个状态经常被混。Wont Fix的意思更接近我们决定不修原因可能是风险很低代码即将下线修复成本不合理误报边缘场景接受业务风险。Mitigated则不同风险原本存在 但另一个控制把它压下去了例如代码里仍有 SQL Injection 路径 ↓ 外层 API Gateway 强制参数白名单 ↓ 攻击路径被阻断如果白名单策略被删掉风险重新暴露这就是补偿控制。Mitigated至少要保存6个字段我不会只保存reason MITIGATED至少publicrecordMitigationRecord(StringalertId,StringcontrolType,StringevidenceRef,Stringowner,InstanteffectiveAt,InstantexpiresAt){}再加review_frequency更完整一点publicrecordMitigationRecord(StringmitigationId,StringalertId,Stringrepository,StringcontrolType,StringcontrolId,StringevidenceRef,Stringowner,Stringapprover,InstanteffectiveAt,InstantexpiresAt,DurationreviewInterval,MitigationStatusstatus){}没有expiresAt的补偿控制我会默认认为风险很高。为什么一定要Expiry DateWAF Rule 今天存在。三个月后可能规则被合并迁了网关服务改了域名Network Policy 改了 Namespace新路径绕开控制业务接口重构。如果安全告警已经关掉代码扫描也不会每天提醒你“你那个补偿措施还在吗”所以必须自己建立到期机制。例如mitigation:max_validity:WAF_RULE:90dNETWORK_POLICY:90dFEATURE_FLAG:30dRATE_LIMIT:60d到期前14天提醒 7天提醒 当天自动进入REVIEW_REQUIREDOwner不能写“安全团队”必须是具体责任主体。差owner Security好owner platform-security-oncall或者owner team-payment-api更关键的是谁负责保证补偿控制持续有效不一定就是发现漏洞的人。例如 WAF 由平台团队管理应用团队负责代码两个Owner可能不同。Evidence不能是一句备注差“有WAF挡着”这不叫证据。至少要能定位到WAF Rule ID Policy Version Namespace Rule Hash Dashboard Test Result例如{control_type:WAF,control_id:rule-8821,policy_version:v17,evidence:security-test/run-1842}这样复审时不是靠回忆。最好做一次“补偿控制验证测试”例如漏洞是/path?qpayloadWAF 声称会拦。那就应该有一个安全测试请求恶意Payload ↓ 确认返回403 ↓ 确认后端没有收到请求每次 WAF Policy 更新后自动再跑。补偿控制不是配置存在就算有效。必须验证它真的拦住了对应攻击路径Mitigation状态机我会定义publicenumMitigationStatus{PROPOSED,APPROVED,ACTIVE,REVIEW_REQUIRED,EXPIRED,INVALID,SUPERSEDED}流程Alert Open ↓ Propose Mitigation ↓ Security Review ↓ ACTIVE ↓ Periodic Verification ↓ 继续 ACTIVE 或 INVALID / EXPIRED如果INVALID原漏洞自动重新进入OPEN“外部控制失效”必须能反向打开漏洞这是最关键的一步。否则系统只有Alert → Mitigated没有Mitigation Failed → Alert Reopened真正的闭环应该是Vulnerability ↔ Mitigation补偿控制失效风险状态立即恢复。一个简单的数据模型createtablevulnerability_mitigation(mitigation_idvarchar(128)primarykey,alert_idvarchar(128)notnull,control_typevarchar(64)notnull,control_idvarchar(256)notnull,ownervarchar(128)notnull,evidence_refvarchar(512)notnull,statusvarchar(32)notnull,effective_at timestamptznotnull,expires_at timestamptznotnull,last_verified_at timestamptz,next_review_at timestamptznotnull);索引createindexidx_mitigation_reviewonvulnerability_mitigation(status,next_review_at);每天扫next_review_at now()生成 Review Task。Mitigated告警仍然要算Security Debt很多 Dashboard 一旦告警被关闭Open Findings ↓看起来质量变好了。但实际上只是Code Fix Debt 转成了 Control Maintenance Debt所以我建议单独统计Open Vulnerability Mitigated Vulnerability Fixed Vulnerability不要把 Mitigated 从风险面板彻底消失。一个很实用的指标Mitigation Age今天 - effective_at例如 30d 30—90d 90—180d 180d如果大量漏洞长期处于Mitigated 180d说明补偿控制正在变成永久替代修复。这通常不是好信号。另一个指标Mitigation Dependency Concentration假设83 个漏洞 都依赖同一套WAF Policy这个 Policy 就成为高价值单点控制一旦配置失效83 个风险一起恢复。可以计算control_id → linked_alert_count超过阈值进入关键控制清单WAF不是万能MitigationWAF 适合HTTP入口 已知Payload模式 可观察请求不适合内部服务调用非HTTP路径业务逻辑漏洞权限绕过后台任务消息队列本地文件处理。所以安全 Review 必须检查攻击路径是否真的经过这层控制不能只因为“我们有WAF”就判 Mitigated。Network Policy也有边界例如漏洞需要应用访问 metadata endpointNetwork Policy 阻断某些 Egress可能有效。但如果新Pod没套Policy Namespace Label变了 Sidecar绕过补偿就失效。所以 Evidence 应该包含Policy Selector Namespace Pod Label Egress TestMitigated不应该绕过修复SLA我更建议漏洞SLA继续存在 但可以暂停升级例如 Critical正常修复 7天 Mitigated后 30天内完成永久修复计划而不是Mitigated 永久关闭具体期限按企业风险制度定。一个审批策略mitigation-policy:critical:security-approval:requiredbusiness-owner:requiredmax-validity:30dhigh:security-approval:requiredmax-validity:60dmedium:team-lead-approval:requiredmax-validity:90d越高风险补偿控制有效期越短。哪些漏洞我不会接受Mitigated明确涉及认证绕过 跨租户读取 密钥泄漏 远程代码执行 支付篡改即使有外部控制我也会要求非常高的批准级别并优先永久修复。因为这些漏洞一旦补偿层失效损失上限太高。GitHub新增这个reason真正解决了一个治理问题过去安全团队经常被迫二选一Fixed Wont Fix现实里却存在第三种情况代码还没修 但风险已经被外层控制有效降低把它单独建模是好事。问题在于Mitigated不是漏洞生命周期的终点而是另一个需要持续维护的安全对象。如果系统只记录一个 dismissal reason却不记录证据、Owner、Expiry 和复审Mitigated 很容易从“补偿控制”退化成一个更好听的“以后再修”。我会把它理解成风险暂时转移到了另一层控制既然风险转移了责任、证据和有效期也必须一起转移。