diff --git a/src/lib/exporter/backendPolicy.test.ts b/src/lib/exporter/backendPolicy.test.ts index 9a33701c..e2c3827f 100644 --- a/src/lib/exporter/backendPolicy.test.ts +++ b/src/lib/exporter/backendPolicy.test.ts @@ -76,4 +76,121 @@ describe("backendPolicy", () => { ], }); }); + + it("documents the native static layout path when Breeze is selected explicitly", () => { + expect( + planLightningExportRoutes({ + backendPreference: "breeze", + platform: "win32", + nativeStaticLayoutAvailable: true, + }), + ).toEqual({ + selectedRoute: "native-static-layout", + decisions: [ + { + route: "native-static-layout", + status: "selected", + reasons: ["visually-compatible"], + }, + { + route: "breeze-stream", + status: "fallback", + reasons: ["user-selected-breeze"], + }, + { + route: "webcodecs", + status: "fallback", + reasons: ["breeze-unavailable-fallback"], + }, + ], + }); + }); + + it("keeps explicit Breeze selected when native static layout is unavailable", () => { + expect( + planLightningExportRoutes({ + backendPreference: "breeze", + platform: "win32", + nativeStaticLayoutAvailable: false, + }), + ).toEqual({ + selectedRoute: "breeze-stream", + decisions: [ + { + route: "native-static-layout", + status: "rejected", + reasons: ["native-static-unavailable"], + }, + { + route: "breeze-stream", + status: "selected", + reasons: ["user-selected-breeze"], + }, + { + route: "webcodecs", + status: "fallback", + reasons: ["breeze-unavailable-fallback"], + }, + ], + }); + }); + + it("records explicit Breeze native static layout skip reasons", () => { + expect( + planLightningExportRoutes({ + backendPreference: "breeze", + platform: "win32", + nativeStaticLayoutAvailable: true, + nativeStaticLayoutSkipReasons: ["unsupported-audio-mix"], + }), + ).toEqual({ + selectedRoute: "breeze-stream", + decisions: [ + { + route: "native-static-layout", + status: "rejected", + reasons: ["unsupported-audio-mix"], + }, + { + route: "breeze-stream", + status: "selected", + reasons: ["user-selected-breeze"], + }, + { + route: "webcodecs", + status: "fallback", + reasons: ["breeze-unavailable-fallback"], + }, + ], + }); + }); + + it("documents why macOS auto skips native static layout", () => { + expect( + planLightningExportRoutes({ + backendPreference: "auto", + platform: "darwin", + nativeStaticLayoutAvailable: true, + }), + ).toEqual({ + selectedRoute: "breeze-stream", + decisions: [ + { + route: "native-static-layout", + status: "rejected", + reasons: ["platform-does-not-use-native-static-layout"], + }, + { + route: "breeze-stream", + status: "selected", + reasons: ["platform-prefers-native-streaming"], + }, + { + route: "webcodecs", + status: "fallback", + reasons: ["breeze-unavailable-fallback"], + }, + ], + }); + }); }); diff --git a/src/lib/exporter/backendPolicy.ts b/src/lib/exporter/backendPolicy.ts index 85be5209..ecfaa11d 100644 --- a/src/lib/exporter/backendPolicy.ts +++ b/src/lib/exporter/backendPolicy.ts @@ -107,6 +107,11 @@ export function planLightningExportRoutes(options: { } if (options.backendPreference === "auto" && shouldPreferNativeAutoBackend(options.platform)) { + decisions.push({ + route: "native-static-layout", + status: "rejected", + reasons: ["platform-does-not-use-native-static-layout"], + }); decisions.push({ route: "breeze-stream", status: "selected",