主题
安全配置
Electron 的安全重点是限制渲染进程能力。渲染进程越像普通浏览器页面,风险越低。
BrowserWindow 配置
ts
const win = new BrowserWindow({
webPreferences: {
preload: preloadPath,
contextIsolation: true,
nodeIntegration: false,
sandbox: true,
},
})关键配置:
contextIsolation: true:隔离 preload 和页面运行上下文。nodeIntegration: false:页面中不能直接使用 Node.js。sandbox: true:进一步限制渲染进程权限。preload:只暴露经过封装的最小 API。
不直接加载远程页面
桌面应用优先加载本地构建产物:
ts
void win.loadFile(indexHtml)开发环境可以加载本地开发服务器:
ts
void win.loadURL(process.env.ELECTRON_RENDERER_URL)如果必须加载远程页面,需要额外处理 CSP、导航限制、权限控制和外链打开策略。
限制导航
阻止应用窗口被导航到非预期地址:
ts
win.webContents.on('will-navigate', (event, url) => {
if (!url.startsWith('file://')) {
event.preventDefault()
}
})外部链接交给系统浏览器:
ts
import { shell } from 'electron'
win.webContents.setWindowOpenHandler(({ url }) => {
void shell.openExternal(url)
return { action: 'deny' }
})打开外部链接前应校验协议,只允许 https: 等安全协议。
Preload 最小暴露
不要暴露底层对象:
ts
// 避免
contextBridge.exposeInMainWorld('ipcRenderer', ipcRenderer)只暴露业务 API:
ts
contextBridge.exposeInMainWorld('settingsApi', {
get: (key: string) => ipcRenderer.invoke('settings:get', key),
set: (key: string, value: string) => ipcRenderer.invoke('settings:set', key, value),
})权限控制
按需处理权限请求:
ts
session.defaultSession.setPermissionRequestHandler((_webContents, permission, callback) => {
const allowed = permission === 'clipboard-read'
callback(allowed)
})默认策略应偏保守:不明确需要的权限直接拒绝。
Checklist
- [ ]
contextIsolation: true - [ ]
nodeIntegration: false - [ ]
sandbox: true - [ ] preload 不暴露
ipcRenderer、require、process - [ ] IPC 参数做类型和范围校验
- [ ] 禁止窗口导航到非预期地址
- [ ] 外链使用系统浏览器打开
- [ ] 不在生产环境加载不受控远程页面
