工程上最危险的不是完全不可用,而是在理想环境里正常、进入真实网络和真实数据量后悄悄失去边界。 一个全局 showModal 与 currentRequest 在第二个请求到来时会覆盖第一个,用户点同意却批准错误对象。请求必须是实体队列,弹窗只是当前队首的视图。
前端架构的核心不是目录层级,而是状态由谁拥有、事件能否重复执行、旧异步结果如何失效,以及卸载后监听器和资源是否真正归零。
工程边界与取舍
实现之前先列出不可违反的不变量,再为性能与体验留出调节参数。参数可以灰度,身份、权限和终态规则不能在运行时随意漂移。
- 每个请求有稳定 ID、类型、来源、创建时间、过期和独立终态。
- 安全敏感首次连接高于普通文件请求,但任何队列都有公平与防骚扰上限。
- 确认动作携带当前请求 ID,响应回来前只锁该项,不冻结整个应用。
弹窗不是状态容器。把请求建模为有身份、有终态的队列实体,才能保证用户的每次同意都作用于眼前那一个对象。
生产环境会怎样出错
失败路径需要与成功路径共享同一套状态模型。只弹一个错误提示却不释放资源、不传播终态,下一次恢复就会继承脏状态。
- 关闭弹窗被解释为拒绝所有待处理请求,其他合法任务一起消失。
- 请求过期后仍显示,同意动作发送给服务端却永远无法完成。
- 新弹窗抢走焦点却不恢复,屏幕阅读器用户迷失在背景页面。
把测试跑成闭环
测试不能以“最后成功了”结束。还要测量经历了多少次副作用、等待多久、是否泄露内容,以及失败后再次执行能否从干净基线开始。
- 同时注入不同来源与类型的十个请求,逐项同意、拒绝、过期和关闭。
- 延迟第一项响应并继续收到新请求,确认实体不覆盖且队列仍可操作。
- 用键盘遍历、Esc 关闭和屏幕阅读器检查焦点陷阱与恢复位置。
当实现能够安全降级、重复执行不产生额外副作用、故障指标早于投诉出现时,这项能力才算具备长期维护价值。