人人都会AI编程

生命周期钩子:启动、窗口创建、退出

更新时间:2026-07-11

在 Tauri 应用中,生命周期钩子让你能在应用启动、窗口创建和退出等关键节点执行自定义逻辑,例如初始化配置、打开调试工具或清理资源。这些钩子都在 Rust 端通过 tauri::Builder 提供的方法进行注册,写法简洁且可靠。


启动钩子:setup

应用核心初始化完成后、前端页面加载之前触发。这是做一次性准备工作最合适的时机:

  • 读取本地配置文件
  • 初始化日志系统
  • 启动后台服务(如本地服务器、守护线程)
  • 预加载数据到状态管理

示例:

fn main() {
    tauri::Builder::default()
        .setup(|app| {
            // 这里可以访问 app 实例,管理状态、注册资源
            println!("应用启动,执行初始化任务");
            Ok(())
        })
        .run(tauri::generate_context!())
        .expect("启动失败");
}

注意:setup 闭包必须返回 Ok(()),否则应用会终止启动。它运行在 Rust 的异步上下文中,但本身是同步的;如果需要异步初始化,可以使用 tauri::async_runtime::spawn 另行安排。


窗口创建钩子:on_window_eventon_page_load

Tauri 没有直接的“窗口创建时”全局钩子,但可以通过窗口的事件监听实现。创建窗口后,可以在 setup 阶段拿到窗口实例并监听其事件,或者使用 tauri::WindowBuilderon_navigation 等。

  • on_window_event:监听窗口大小变化、聚焦、关闭请求等。可以在窗口首次 ResizedFocused 时执行逻辑,模拟窗口创建完成。
  • on_page_loadWebviewBuilder 提供的事件,当 WebView 开始加载或加载完成时触发,适合注入初始脚本或显示加载动画。

示例(在 setup 中获取已有窗口并监听):

.setup(|app| {
    let window = app.get_window("main").unwrap();
    window.on_window_event(|event| {
        if let tauri::WindowEvent::Focused(focused) = event {
            if *focused {
                // 窗口获得焦点,可视为用户可见后的首次交互准备
            }
        }
    });
    Ok(())
})

更常见的做法是在创建窗口时直接用 WindowBuilder 指定事件:

tauri::WindowBuilder::new(app, "main", tauri::WindowUrl::App("index.html".into()))
    .on_page_load(|window, _| {
        // 页面加载完成,DOM 就绪
    })
    .build()?;

退出钩子:on_exit(或直接使用 Rust 的 Drop

Tauri 提供了 on_exit 方法来注册一个在应用完全退出前执行的函数,适合做清理工作:

  • 保存用户界面状态(窗口位置、尺寸)
  • 关闭数据库连接、停止后台进程
  • 写入日志尾部信息
  • 清理临时文件

示例:

fn main() {
    tauri::Builder::default()
        .on_exit(|_app_handle| {
            println!("应用即将退出,执行清理");
            // 这里 _app_handle 无法保证完全可用(资源可能已释放),仅做轻量级操作
        })
        .run(tauri::generate_context!())
        .expect("启动失败");
}

重要说明on_exit 是同步的,且调用时 Tauri 运行时可能已部分销毁,不能依赖窗口或状态管理器。如需更可靠的资源释放,应利用 Rust 的 Drop 特性管理自定义结构体,或使用 setup 中注册的全局资源。

此外,窗口关闭事件(close_requested)允许你阻止关闭或弹出确认对话框:

window.on_window_event(|event| {
    if let tauri::WindowEvent::CloseRequested { api, .. } = event {
        api.prevent_close();
        // 显示确认对话框,然后手动关闭窗口
    }
});

通过这三个核心钩子,你可以精确控制应用从生到死的完整流程,代码量少且逻辑清晰,没有 Electron 中多个进程事件交织的复杂情况。