在浏览器端的交互机制中,`alert`、`confirm` 和 `prompt` 这三个方法非常特殊:它们并非开发者可自由选择的工具,而是浏览器强制执行的同步阻塞入口。一旦调用,JavaScript 执行流会完全卡住,页面彻底冻结,直到用户点击按钮。开发者无法绕过这一机制,只能顺应其特性来设计交互逻辑。
confirm 返回布尔值,但 null 不会出现
`confirm` 的返回值只有两种:用户点“确定”返回 `true`,点“取消”或按
Esc 返回 `false`。这一点与 `prompt` 有本质区别,若混淆两者,逻辑分支容易出错。
- 用户点“确定” → 返回 `true`
- 用户点“取消”或按 Esc → 返回 `false`
- 不要写 `if (result === null)` 这样的判断——它永远不成立,只会增加代码阅读负担
- 隐藏细节:移动端 Safari 在部分 iOS 版本中会把“取消”按钮的文字本地化为“取消”,但返回值始终是 `false`,不受影响
prompt 的第二个参数不能省略,IE 和旧版 Edge 会把它当 undefined 渲染
`prompt(title, default)` 中的 `default` 参数必须显式传入,即使传空字符串 `''` 也行。否则在 IE 或旧版 Edge 中,输入框内会直接显示 `undefined` 字样——这并非留空,而是字面上的“undefined”文本。
- 正确写法:`prompt('用户名', '')` 或 `prompt('用户名', 'guest')`
- 错误写法:`prompt('用户名')` → IE 里显示“undefined”,用户容易误以为是默认提示
- 返回值只有两种:用户输入的字符串(包括空格),或者 `null`(点取消或按 Esc)
- 空字符串 `''` 和 `null` 是完全不同的值:`if (input)` 会把 `''` 当作假值,必须用 `input !== null` 显式判断
alert 没有返回值,但滥用会导致页面卡死
`alert` 返回 `undefined`,但最关键的并非返回值,而是其不可中断性。连续弹出多个 `alert`,用户必须逐一点击,没有“全部关闭”或“跳过”选项。
- 调试时慎用:`alert` 会打断异步流程,放在 `setTimeout` 或 Promise 回调中,容易掩盖真实的执行顺序
- 循环里绝对不能调用:`for (let i = 0; i < 10; i++) alert(i)` 会弹出 10 次,且无法批量关闭
- 移动端行为不一致:部分 Android 浏览器会将连续的 `alert` 合并或静默丢弃
- 实际建议:开发阶段使用 `console.log` 替代,上线前删除所有 `alert`。真正需要提示的地方,使用 DOM 自定义弹层
总结:真正难处理的不是语法,是执行流的绝对控制
这几个方法最棘手的问题不在于语法复杂,而在于它们对执行流的绝对控制——无法监听关闭事件,无法添加 loading,无法阻止重复触发。一旦进入 `prompt`,连 `beforeunload` 事件都会被挂起。因此不要试图去“增强”它们:该用的时候就用,该换的时候果断换成 DOM 自定义弹层。