import { ScopedRefURI } from "@effect/core/io/ScopedRef/definition"
export class ScopedRefInternal implements ScopedRef {
constructor(readonly ref: Ref.Synchronized) {}
readonly [ScopedRefURI] = {
_A: (_: never) => _
}
get get(): Effect {
return this.ref.get.map((tuple) => tuple[1])
}
get close(): Effect {
return this.ref.get.flatMap(([scope, _]) => scope.close(Exit.unit))
}
set(this: this, acquire: Effect): Effect {
return this.ref.modifyEffect(([oldScope, a]) =>
Effect.uninterruptibleMask(({ restore }) =>
Do(($) => {
const newScope = $(Scope.make)
const exit = $(
restore(
acquire.provideSomeEnvironment((env: Env) => env.add(Scope.Tag, newScope))
).exit
)
return $(exit.fold(
(cause) =>
newScope.close(Exit.unit).ignore.as(
[
Effect.failCause(cause) as unknown as Effect,
[oldScope, a] as const
] as const
),
(a) =>
oldScope.close(Exit.unit).ignore.as([Effect.unit, [newScope, a] as const] as const)
))
})
)
).flatten
}
setAsync(this: this, acquire: Effect): Effect {
return this.set(acquire).forkDaemon.unit
}
}