保护 Electron 应用:实用指南
在现代桌面应用中安全处理秘密与 IPC。
为什么 Electron 需要谨慎使用
Electron 应用将浏览器和 Node.js 运行时结合在一起。如果加载远程内容或受攻击者影响内容的渲染进程能够访问 Node,一次 XSS 就能成为用户设备上的远程代码执行。保护 Electron 的重点是把这两个世界隔开。GitSwitch 是基于 Electron 和 React 19 的 Git 客户端,持有 GitHub 令牌和 Gemini API 密钥,必须正确落实这条边界。
隔离契约
| 设置 | 值 | 原因 |
|---|---|---|
contextIsolation | 开启 | preload 与页面运行在不同 JS 上下文中,页面无法篡改具有权限的全局对象 |
sandbox | 开启 | 渲染进程不能直接使用 Node.js、require、fs 或 child_process |
nodeIntegration | 关闭 | 页面无法看到 Node 内置功能 |
| 暴露的 API | contextBridge 允许列表 | preload 只暴露少量具名函数,而非原始 ipcRenderer |
IPC 是信任边界
每项特权操作都经由 ipcMain.handle / ipcRenderer.invoke,并使用明确的通道允许列表。主进程将每条消息视为不可信输入:验证通道、清理参数,并为长时间调用设置超时,避免卡住的 Git 操作冻结应用。不存在执行任意命令的桥接,每个通道只完成一个有限任务。
处理秘密
令牌不会进入 localStorage,也不会长期留在渲染进程:
- 静态存储,GitHub 个人访问令牌和 Gemini 密钥保存在操作系统密钥库:macOS 的 Keychain、Windows 的 Credential Manager、Linux 的 libsecret,而非明文配置文件。
- 使用期间,日志中的密钥被隐去,使用后从内存清除,避免崩溃转储或共享日志泄漏。
- 传输期间,Gemini API 是唯一出站路径,用于生成提交消息的 diff 仅包含用户此次提交的内容。
结论
让 Electron 方便的默认方式,例如渲染进程中的 Node、旧版 remote 模块和宽泛 IPC,也会带来风险。GitSwitch 反向设置它们:开启隔离与 sandbox,使用最小且可审计的桥接,并将秘密保存在系统密钥库。最终得到的是带 Web 界面的桌面应用,无法被诱导执行它未设计执行的代码。