@@ -3,7 +3,7 @@ import { WorkspaceContext } from "@/control-plane/workspace-context"
33import { disposeInstance } from "@/effect/instance-registry"
44import { makeRuntime } from "@/effect/run-service"
55import { AppFileSystem } from "@opencode-ai/core/filesystem"
6- import { Context , Deferred , Effect , Exit , Layer , Scope } from "effect"
6+ import { Context , Deferred , Duration , Effect , Exit , Layer , Scope } from "effect"
77import { context , type InstanceContext } from "./instance-context"
88import * as Project from "./project"
99
@@ -33,9 +33,6 @@ export const layer: Layer.Layer<Service, never, Project.Service> = Layer.effect(
3333 const project = yield * Project . Service
3434 const scope = yield * Scope . Scope
3535 const cache = new Map < string , Entry > ( )
36- const disposal = {
37- all : undefined as Deferred . Deferred < void > | undefined ,
38- }
3936
4037 const boot = Effect . fn ( "InstanceStore.boot" ) ( function * ( input : LoadInput & { directory : string } ) {
4138 const ctx =
@@ -146,41 +143,29 @@ export const layer: Layer.Layer<Service, never, Project.Service> = Layer.effect(
146143 yield * disposeEntry ( ctx . directory , entry , ctx ) . pipe ( Effect . asVoid )
147144 } )
148145
149- const disposeAll = Effect . fn ( "InstanceStore.disposeAll" ) ( function * ( ) {
150- return yield * Effect . uninterruptibleMask ( ( restore ) =>
151- Effect . gen ( function * ( ) {
152- const existing = disposal . all
153- if ( existing ) return yield * restore ( Deferred . await ( existing ) )
154-
155- const done = Deferred . makeUnsafe < void > ( )
156- const entries = [ ...cache . entries ( ) ]
157- disposal . all = done
158- const exit = yield * Effect . gen ( function * ( ) {
159- yield * Effect . logInfo ( "disposing all instances" )
160- yield * Effect . forEach (
161- entries ,
162- ( item ) =>
163- Effect . gen ( function * ( ) {
164- const exit = yield * Deferred . await ( item [ 1 ] . deferred ) . pipe ( Effect . exit )
165- if ( Exit . isFailure ( exit ) ) {
166- yield * Effect . logWarning ( "instance dispose failed" , { key : item [ 0 ] , cause : exit . cause } )
167- yield * removeEntry ( item [ 0 ] , item [ 1 ] )
168- return
169- }
170- yield * disposeEntry ( item [ 0 ] , item [ 1 ] , exit . value )
171- } ) ,
172- { discard : true } ,
173- )
174- } ) . pipe ( Effect . exit )
175- yield * Deferred . done ( done , exit ) . pipe ( Effect . asVoid )
176- if ( disposal . all === done ) {
177- disposal . all = undefined
178- }
179- return yield * restore ( Deferred . await ( done ) )
180- } ) ,
146+ const disposeAllOnce = Effect . fnUntraced ( function * ( ) {
147+ yield * Effect . logInfo ( "disposing all instances" )
148+ yield * Effect . forEach (
149+ [ ...cache . entries ( ) ] ,
150+ ( item ) =>
151+ Effect . gen ( function * ( ) {
152+ const exit = yield * Deferred . await ( item [ 1 ] . deferred ) . pipe ( Effect . exit )
153+ if ( Exit . isFailure ( exit ) ) {
154+ yield * Effect . logWarning ( "instance dispose failed" , { key : item [ 0 ] , cause : exit . cause } )
155+ yield * removeEntry ( item [ 0 ] , item [ 1 ] )
156+ return
157+ }
158+ yield * disposeEntry ( item [ 0 ] , item [ 1 ] , exit . value )
159+ } ) ,
160+ { discard : true } ,
181161 )
182162 } )
183163
164+ const cachedDisposeAll = yield * Effect . cachedWithTTL ( disposeAllOnce ( ) , Duration . zero )
165+ const disposeAll = Effect . fn ( "InstanceStore.disposeAll" ) ( function * ( ) {
166+ return yield * cachedDisposeAll
167+ } )
168+
184169 yield * Effect . addFinalizer ( ( ) => disposeAll ( ) . pipe ( Effect . ignore ) )
185170
186171 return Service . of ( {
0 commit comments