Electron App API 知识点总结
目录
- [1. App 模块概述](#1. App 模块概述 "#1-app-%E6%A8%A1%E5%9D%97%E6%A6%82%E8%BF%B0")
- [2. 应用程序生命周期事件](#2. 应用程序生命周期事件 "#2-%E5%BA%94%E7%94%A8%E7%A8%8B%E5%BA%8F%E7%94%9F%E5%91%BD%E5%91%A8%E6%9C%9F%E4%BA%8B%E4%BB%B6")
- [3. macOS 特有事件](#3. macOS 特有事件 "#3-macos-%E7%89%B9%E6%9C%89%E4%BA%8B%E4%BB%B6")
- [4. 窗口相关事件](#4. 窗口相关事件 "#4-%E7%AA%97%E5%8F%A3%E7%9B%B8%E5%85%B3%E4%BA%8B%E4%BB%B6")
- [5. 安全与认证事件](#5. 安全与认证事件 "#5-%E5%AE%89%E5%85%A8%E4%B8%8E%E8%AE%A4%E8%AF%81%E4%BA%8B%E4%BB%B6")
- [6. 进程相关事件](#6. 进程相关事件 "#6-%E8%BF%9B%E7%A8%8B%E7%9B%B8%E5%85%B3%E4%BA%8B%E4%BB%B6")
- [7. 应用方法](#7. 应用方法 "#7-%E5%BA%94%E7%94%A8%E6%96%B9%E6%B3%95")
- [8. 应用信息管理](#8. 应用信息管理 "#8-%E5%BA%94%E7%94%A8%E4%BF%A1%E6%81%AF%E7%AE%A1%E7%90%86")
1. App 模块概述
app 模块用于控制应用程序的事件生命周期 。它是主进程模块。
基本使用
javascript
const { app } = require('electron')
app.on('window-all-closed', () => {
app.quit()
})
2. 应用程序生命周期事件
事件触发顺序
scss
┌─────────────────────────────────────────────┐
│ will-finish-launching │
│ ↓ │
│ ready ← 最重要的!应用入口 │
│ ↓ │
│ [应用运行中] │
│ ↓ │
│ window-all-closed (可选) │
│ ↓ │
│ before-quit │
│ ↓ │
│ will-quit │
│ ↓ │
│ quit ← 应用退出 │
└─────────────────────────────────────────────┘
2.1 will-finish-launching
应用程序完成基础启动时触发。
- Windows/Linux :与
ready事件相同 - macOS :相当于
applicationWillFinishLaunching - 建议 :大部分逻辑应在
ready事件中处理
2.2 ready ⭐最重要
Electron 完成初始化时触发一次。
javascript
app.on('ready', (event, launchInfo) => {
console.log('应用已就绪')
// 创建窗口、初始化应用等
})
// 替代写法:返回 Promise
app.whenReady().then(() => {
// 应用已就绪
})
2.3 window-all-closed
所有窗口关闭时触发。
javascript
app.on('window-all-closed', () => {
// macOS 外,退出应用
if (process.platform !== 'darwin') {
app.quit()
}
})
2.4 before-quit
关闭窗口前触发。调用 event.preventDefault() 可阻止退出。
2.5 will-quit
所有窗口关闭后、应用程序退出前触发。
2.6 quit
应用程序退出时触发。
⚠️ Windows 注意 :如果应用程序因系统关机/重启而关闭,
before-quit、will-quit、quit事件不会触发。
3. macOS 特有事件
3.1 activate
应用被激活时触发。
触发场景:
- 首次启动应用
- 点击 Dock 或任务栏图标
- 应用已在运行时尝试重新激活
javascript
app.on('activate', (event, hasVisibleWindows) => {
if (!hasVisibleWindows) {
// 创建新窗口
createWindow()
}
})
3.2 did-become-active
每次程序被激活前触发(不仅限于 Dock 点击)。
3.3 open-file ⭐重要
用户想要在应用中打开文件时触发。
javascript
// 必须在 ready 事件前监听!
app.on('open-file', (event, path) => {
event.preventDefault()
console.log('打开文件:', path)
})
3.4 open-url
用户通过 URL scheme 打开应用时触发。
javascript
app.on('open-url', (event, url) => {
event.preventDefault()
console.log('打开 URL:', url)
})
⚠️ 重要 :必须在
ready事件前注册监听器!
3.5 Handoff 相关事件(macOS)
| 事件名 | 说明 |
|---|---|
will-continue-activity |
跨设备活动恢复前 |
continue-activity |
跨设备活动恢复时 |
continue-activity-error |
跨设备活动恢复失败 |
activity-was-continued |
本设备活动在其他设备恢复 |
update-activity-state |
活动状态更新 |
3.6 其他 macOS 事件
| 事件名 | 说明 |
|---|---|
new-window-for-tab |
点击原生新标签按钮 |
did-rele-active |
应用长时间非激活状态 |
4. 窗口相关事件
4.1 browser-window-created
当新的 BrowserWindow 被创建时触发。
javascript
app.on('browser-window-created', (event, window) => {
console.log('新窗口创建')
})
4.2 browser-window-focus
窗口获得焦点时触发。
4.3 browser-window-blur
窗口失去焦点时触发。
4.4 web-contents-created
当新的 WebContents 被创建时触发。
5. 安全与认证事件
5.1 certificate-error
证书验证失败时触发。可用于信任自签名证书。
javascript
app.on('certificate-error', (event, webContents, url, error, certificate, callback) => {
if (url === 'https://example.com') {
event.preventDefault()
callback(true) // 信任该证书
} else {
callback(false)
}
})
5.2 select-client-certificate
客户端证书请求时触发。
javascript
app.on('select-client-certificate', (event, webContents, url, list, callback) => {
event.preventDefault()
callback(list[0]) // 选择第一个证书
})
5.3 login
基本认证时触发。
javascript
app.on('login', (event, webContents, details, authInfo, callback) => {
event.preventDefault()
callback('username', 'password')
})
6. 进程相关事件
6.1 render-process-gone
渲染器进程意外消失时触发。
javascript
app.on('render-process-gone', (event, webContents, details) => {
if (details.reason === 'crashed') {
console.log('渲染进程崩溃')
}
})
6.2 child-process-gone
子进程意外消失时触发。
| reason 值 | 说明 |
|---|---|
clean-exit |
正常退出(退出码 0) |
abnormal-exit |
非零退出码退出 |
killed |
被 SIGTERM 或外部杀死 |
crashed |
进程崩溃 |
oom |
内存不足 |
launch-failed |
启动失败 |
integrity-failure |
代码完整性检查失败 |
6.3 second-instance
第二个应用实例启动时触发。
javascript
const gotTheLock = app.requestSingleInstanceLock()
if (!gotTheLock) {
app.quit()
} else {
app.on('second-instance', (event, argv, workingDirectory, additionalData) => {
// 将第二个实例的窗口聚焦
if (mainWindow) {
if (mainWindow.isMinimized()) mainWindow.restore()
mainWindow.focus()
}
})
}
6.4 session-created
创建新 session 时触发。
javascript
app.on('session-created', (session) => {
console.log('新 session 创建')
})
7. 应用方法
7.1 退出应用
| 方法 | 说明 | 触发事件 |
|---|---|---|
app.quit() |
尝试关闭所有窗口并退出 | before-quit → will-quit → quit |
app.exit(exitCode) |
立即退出 | 不触发任何退出事件 |
javascript
// 优雅退出
app.quit()
// 强制退出(不触发 before-quit)
app.exit(1)
7.2 重启应用
javascript
app.relaunch({ args: process.argv.slice(1).concat(['--relaunch']) })
app.exit(0)
7.3 应用状态检查
javascript
app.isReady() // 是否已就绪
app.whenReady() // 返回 Promise
7.4 macOS 应用激活
javascript
app.hide() // 隐藏所有窗口
app.show() // 显示隐藏的窗口
app.isHidden() // 检查是否隐藏
app.focus() // 聚焦应用
8. 应用信息管理
8.1 获取应用路径
javascript
app.getAppPath() // 当前应用程序目录
app.getPath('home') // 用户主目录
app.getPath('appData') // 应用数据目录
app.getPath('userData') // 用户配置目录
app.getPath('logs') // 日志目录
app.getPath('desktop') // 桌面目录
app.getPath('documents') // 文档目录
app.getPath('downloads') // 下载目录
app.getPath('temp') // 临时目录
8.2 设置日志路径
javascript
app.setAppLogsPath('/custom/path') // 自定义日志路径
8.3 应用信息
javascript
app.getName() // 应用名称
app.getVersion() // 应用版本
app.getLocale() // 当前语言
app.getLocaleCountryCode() // 国家代码
最佳实践总结
✅ 推荐写法
javascript
const { app, BrowserWindow } = require('electron')
let mainWindow
function createWindow() {
mainWindow = new BrowserWindow({ width: 1200, height: 800 })
mainWindow.loadURL('https://example.com')
}
// 等待应用就绪
app.whenReady().then(() => {
createWindow()
// macOS:点击 Dock 图标时如果没有窗口则创建
app.on('activate', () => {
if (BrowserWindow.getAllWindows().length === 0) {
createWindow()
}
})
})
// 关闭所有窗口时退出(非 macOS)
app.on('window-all-closed', () => {
if (process.platform !== 'darwin') {
app.quit()
}
})
// 确保单实例
const gotLock = app.requestSingleInstanceLock()
if (!gotLock) {
app.quit()
} else {
app.on('second-instance', () => {
if (mainWindow) {
if (mainWindow.isMinimized()) mainWindow.restore()
mainWindow.focus()
}
})
}
❌ 避免做法
- 不要在
ready事件前使用需要初始化的 API - macOS 应用不要在
window-all-closed中直接 quit - 处理文件打开要在应用启动前注册监听器
- Windows 下注意关机不会触发退出事件
事件速查表
| 事件 | 跨平台 | macOS | 说明 |
|---|---|---|---|
will-finish-launching |
✅ | ✅ | 基础启动完成 |
ready |
✅ | ✅ | 应用就绪(最重要) |
window-all-closed |
✅ | 所有窗口关闭 | |
before-quit |
✅ | ✅ | 退出前 |
will-quit |
✅ | ✅ | 即将退出 |
quit |
✅ | 应用退出 | |
activate |
✅ | 应用激活 | |
open-file |
✅ | 打开文件 | |
open-url |
✅ | 通过 URL 打开 | |
browser-window-created |
✅ | 窗口创建 | |
certificate-error |
✅ | 证书错误 | |
login |
✅ | 认证 | |
render-process-gone |
✅ | 渲染进程消失 | |
second-instance |
✅ | 第二个实例 | |
session-created |
✅ | Session 创建 |
文档基于 Electron v28+ App API 编写