11/**
22 * @since 1.0.0
33 */
4+ import * as Context from "effect/Context"
45import * as Duration from "effect/Duration"
56import * as Effect from "effect/Effect"
67import { identity } from "effect/Function"
@@ -31,6 +32,19 @@ export interface EntityResource<out A, out E = never> {
3132 readonly close : Effect . Effect < void >
3233}
3334
35+ /**
36+ * A `Scope` that is only closed when the resource is explicitly closed.
37+ *
38+ * It is not closed during restarts, due to shard movement or node shutdowns.
39+ *
40+ * @since 1.0.0
41+ * @category Scope
42+ */
43+ export class CloseScope extends Context . Tag ( "@effect/cluster/EntityResource/CloseScope" ) <
44+ CloseScope ,
45+ Scope . Scope
46+ > ( ) { }
47+
3448/**
3549 * A `EntityResource` is a resource that can be acquired inside a cluster
3650 * entity, which will keep the entity alive even across restarts.
@@ -47,55 +61,32 @@ export interface EntityResource<out A, out E = never> {
4761export const make : < A , E , R > ( options : {
4862 readonly acquire : Effect . Effect < A , E , R >
4963 readonly idleTimeToLive ?: Duration . DurationInput | undefined
50- /**
51- * When to close the resource Scope.
52- *
53- * If set to "explicit", the resource will only be cleaned up when either the
54- * `idleTimeToLive` is reached, or the .close effect is called.
55- *
56- * Defaults to "always", which means the resource will be cleaned up when the
57- * the parent Scope is closed.
58- */
59- readonly shutdownMode ?: "explicit" | "always" | undefined
6064} ) => Effect . Effect <
6165 EntityResource < A , E > ,
6266 E ,
63- Scope . Scope | R | Sharding | Entity . CurrentAddress
67+ Scope . Scope | Exclude < R , CloseScope > | Sharding | Entity . CurrentAddress
6468> = Effect . fnUntraced ( function * < A , E , R > ( options : {
6569 readonly acquire : Effect . Effect < A , E , R >
6670 readonly idleTimeToLive ?: Duration . DurationInput | undefined
67- readonly shutdownMode ?: "explicit" | "always" | undefined
6871} ) {
69- const shutdownMode = options . shutdownMode ?? "always"
7072 let shuttingDown = false
7173
7274 const ref = yield * RcRef . make ( {
7375 acquire : Effect . gen ( function * ( ) {
74- let scope = yield * Effect . scope
76+ const closeable = yield * Scope . make ( )
7577
76- if ( shutdownMode === "explicit" ) {
77- const closeable = yield * Scope . make ( )
78- const context = yield * Effect . context < Sharding | Entity . CurrentAddress > ( )
79- yield * Scope . addFinalizerExit (
80- scope ,
81- Effect . fnUntraced ( function * ( exit ) {
82- if ( shuttingDown ) return
83- yield * Scope . close ( closeable , exit )
84- yield * Entity . keepAlive ( false )
85- } , Effect . provide ( context ) )
86- )
87- scope = closeable
88- } else {
89- yield * Effect . addFinalizer ( ( ) => {
90- if ( shuttingDown ) return Effect . void
91- return Entity . keepAlive ( false )
78+ yield * Effect . addFinalizer (
79+ Effect . fnUntraced ( function * ( exit ) {
80+ if ( shuttingDown ) return
81+ yield * Scope . close ( closeable , exit )
82+ yield * Entity . keepAlive ( false )
9283 } )
93- }
84+ )
9485
9586 yield * Entity . keepAlive ( true )
9687
9788 return yield * options . acquire . pipe (
98- Scope . extend ( scope )
89+ Effect . provideService ( CloseScope , closeable )
9990 )
10091 } ) ,
10192 idleTimeToLive : options . idleTimeToLive ?? Duration . infinity
0 commit comments