| ... | @@ -1944,7 +1944,8 @@ it.layer(Layer.mergeAll(NodeServices.layer, ServerSettingsModule.layerTest(), Te | ... | @@ -1944,7 +1944,8 @@ it.layer(Layer.mergeAll(NodeServices.layer, ServerSettingsModule.layerTest(), Te |
| 1944 | const firstMissing = `t3code_codex_first_`; | 1944 | const firstMissing = `t3code_codex_first_`; |
| 1945 | const secondMissing = `t3code_codex_second_`; | 1945 | const secondMissing = `t3code_codex_second_`; |
| 1946 | const spawnedCommands: Array<string> = []; | 1946 | const spawnedCommands: Array<string> = []; |
| 1947 | const serverSettings = yield* makeMutableServerSettingsService( | 1947 | const allowLazySettingsStream = yield* Deferred.make<void>(); |
| | 1948 | const mutableServerSettings = yield* makeMutableServerSettingsService( |
| 1948 | decodeServerSettings( | 1949 | decodeServerSettings( |
| 1949 | deepMerge(encodedDefaultServerSettings, { | 1950 | deepMerge(encodedDefaultServerSettings, { |
| 1950 | providers: { | 1951 | providers: { |
| ... | @@ -1957,6 +1958,14 @@ it.layer(Layer.mergeAll(NodeServices.layer, ServerSettingsModule.layerTest(), Te | ... | @@ -1957,6 +1958,14 @@ it.layer(Layer.mergeAll(NodeServices.layer, ServerSettingsModule.layerTest(), Te |
| 1957 | }), | 1958 | }), |
| 1958 | ), | 1959 | ), |
| 1959 | ); | 1960 | ); |
| | 1961 | const serverSettings = { |
| | 1962 | ...mutableServerSettings, |
| | 1963 | streamChanges: Stream.unwrap( |
| | 1964 | Deferred.await(allowLazySettingsStream).pipe( |
| | 1965 | Effect.as(mutableServerSettings.streamChanges), |
| | 1966 | ), |
| | 1967 | ), |
| | 1968 | } satisfies ServerSettingsModule.ServerSettingsService["Service"]; |
| 1960 | const scope = yield* Scope.make(); | 1969 | const scope = yield* Scope.make(); |
| 1961 | yield* Effect.addFinalizer(() => Scope.close(scope, Exit.void)); | 1970 | yield* Effect.addFinalizer(() => Scope.close(scope, Exit.void)); |
| 1962 | const providerRegistryLayer = ProviderRegistryLive.pipe( | 1971 | const providerRegistryLayer = ProviderRegistryLive.pipe( |
| ... | @@ -2016,7 +2025,7 @@ it.layer(Layer.mergeAll(NodeServices.layer, ServerSettingsModule.layerTest(), Te | ... | @@ -2016,7 +2025,7 @@ it.layer(Layer.mergeAll(NodeServices.layer, ServerSettingsModule.layerTest(), Te |
| 2016 | assert.deepStrictEqual(spawnedCommands, [firstMissing]); | 2025 | assert.deepStrictEqual(spawnedCommands, [firstMissing]); |
| 2017 | | 2026 | |
| 2018 | // Drive a settings change. The Hydration layer's | 2027 | // Drive a settings change. The Hydration layer's |
| 2019 | // `SettingsWatcherLive` consumes this via `streamChanges`, | 2028 | // `SettingsWatcherLive` consumes this via `subscribeChanges`, |
| 2020 | // calls `reconcile`, which rebuilds the codex instance (the | 2029 | // calls `reconcile`, which rebuilds the codex instance (the |
| 2021 | // envelope changed because `binaryPath` differs → `entryEqual` | 2030 | // envelope changed because `binaryPath` differs → `entryEqual` |
| 2022 | // is false). The registry's `Stream.runForEach( | 2031 | // is false). The registry's `Stream.runForEach( |
| ... | @@ -2028,6 +2037,9 @@ it.layer(Layer.mergeAll(NodeServices.layer, ServerSettingsModule.layerTest(), Te | ... | @@ -2028,6 +2037,9 @@ it.layer(Layer.mergeAll(NodeServices.layer, ServerSettingsModule.layerTest(), Te |
| 2028 | codex: { enabled: true, binaryPath: secondMissing }, | 2037 | codex: { enabled: true, binaryPath: secondMissing }, |
| 2029 | }, | 2038 | }, |
| 2030 | }); | 2039 | }); |
| | 2040 | // Start the lazy stream only after publishing. A watcher that did |
| | 2041 | // not subscribe before forking has already lost this update. |
| | 2042 | yield* Deferred.succeed(allowLazySettingsStream, undefined); |
| 2031 | | 2043 | |
| 2032 | // Poll until the injected process boundary observes the new | 2044 | // Poll until the injected process boundary observes the new |
| 2033 | // executable. This verifies the public settings-to-probe behavior | 2045 | // executable. This verifies the public settings-to-probe behavior |