diff --git a/apps/desktop-shell/scripts/check-config.mjs b/apps/desktop-shell/scripts/check-config.mjs index 78478214f..84e626415 100644 --- a/apps/desktop-shell/scripts/check-config.mjs +++ b/apps/desktop-shell/scripts/check-config.mjs @@ -2288,6 +2288,7 @@ const requiredRustHostSnippets = [ 'window.history.replaceState', "window.addEventListener('popstate'", '__genarrativeDesktopHistoryIndex', + "console.warn('desktop navigation state sync failed', error)", 'file.imageDropped', 'emit_desktop_image_drop_event(&drop_window, paths, drop_position)', 'app.notification().builder()', @@ -2801,6 +2802,8 @@ for (const blockedLifecycleSnippet of [ 'let _ = open_normalized_desktop_external_url(', 'let _ = emit_desktop_lifecycle_event(&close_window', 'let _ = close_window.hide()', + 'catch (_error) {}', + 'catch (error) {}', ]) { if (rustHostSource.includes(blockedLifecycleSnippet)) { throw new Error( diff --git a/apps/desktop-shell/src-tauri/src/shell/navigation.rs b/apps/desktop-shell/src-tauri/src/shell/navigation.rs index f154d9888..d02e7d306 100644 --- a/apps/desktop-shell/src-tauri/src/shell/navigation.rs +++ b/apps/desktop-shell/src-tauri/src/shell/navigation.rs @@ -78,7 +78,9 @@ pub(crate) fn desktop_navigation_state_script() -> Result {{ try {{ originalReplaceState(stateWithIndex(window.history.state, currentIndex), '', window.location.href); - }} catch (_error) {{}} + }} catch (error) {{ + console.warn('desktop navigation state sync failed', error); + }} }}; window.__GENARRATIVE_DESKTOP_EMIT_NAVIGATION_STATE__ = emitNavigationState; @@ -365,6 +367,7 @@ mod tests { assert!(script.contains("(currentIndex > 0)")); assert!(script.contains("\\\"canGoBack\\\":true")); assert!(script.contains("\\\"canGoBack\\\":false")); + assert!(script.contains("console.warn('desktop navigation state sync failed', error)")); assert!(script.contains("window.__GENARRATIVE_DESKTOP_NAVIGATION_STATE_INSTALLED__")); } } diff --git a/docs/project-memory/shared-memory/decision-log.md b/docs/project-memory/shared-memory/decision-log.md index 459772a6a..cf303baae 100644 --- a/docs/project-memory/shared-memory/decision-log.md +++ b/docs/project-memory/shared-memory/decision-log.md @@ -2909,6 +2909,13 @@ - 影响范围:`apps/desktop-shell/src-tauri/src/shell/lifecycle.rs`、`apps/desktop-shell/scripts/check-config.mjs`。 - 验证方式:`cargo test --manifest-path apps/desktop-shell/src-tauri/Cargo.toml shell::lifecycle`、`npm run desktop-shell:typecheck`、`npm run check:native-shells`、`npm run check:encoding`、`git diff --check`。 +## 2026-06-20 桌面壳返回栈状态同步失败不可静默 + +- 背景:Tauri 桌面壳 `navigation.canGoBack` 注入脚本会把当前 H5 history index 写入 `window.history.state`;如果 `replaceState(...)` 因页面状态异常或浏览器限制失败后静默吞掉,H5 返回栈事件可能漂移且无排查线索。 +- 决策:`desktop_navigation_state_script()` 的 `replaceCurrentState()` catch 路径必须输出 `desktop navigation state sync failed` 浏览器 console 警告;配置检查拒绝该注入脚本重新出现空 catch。 +- 影响范围:`apps/desktop-shell/src-tauri/src/shell/navigation.rs`、`apps/desktop-shell/scripts/check-config.mjs`。 +- 验证方式:`cargo test --manifest-path apps/desktop-shell/src-tauri/Cargo.toml shell::navigation`、`npm run desktop-shell:typecheck`、`npm run check:native-shells`、`npm run check:encoding`、`git diff --check`。 + ## 2026-06-20 移动壳 EAS 原生包构建 profile - 背景:移动壳已能通过 Expo managed config 和 Metro production bundle smoke,但缺少原生安装包构建 profile;如果只保留 `expo export`,无法证明 Android / iOS 壳有进入原生分发链路的配置。