effect 3.3.5 → 3.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (98) hide show
  1. package/Micro/package.json +6 -0
  2. package/dist/cjs/Array.js +18 -3
  3. package/dist/cjs/Array.js.map +1 -1
  4. package/dist/cjs/Chunk.js +13 -2
  5. package/dist/cjs/Chunk.js.map +1 -1
  6. package/dist/cjs/Effect.js +110 -8
  7. package/dist/cjs/Effect.js.map +1 -1
  8. package/dist/cjs/Either.js +31 -1
  9. package/dist/cjs/Either.js.map +1 -1
  10. package/dist/cjs/ManagedRuntime.js.map +1 -1
  11. package/dist/cjs/Micro.js +2383 -0
  12. package/dist/cjs/Micro.js.map +1 -0
  13. package/dist/cjs/Option.js +1 -2
  14. package/dist/cjs/Option.js.map +1 -1
  15. package/dist/cjs/Schedule.js +2 -2
  16. package/dist/cjs/Stream.js.map +1 -1
  17. package/dist/cjs/Tuple.js +16 -9
  18. package/dist/cjs/Tuple.js.map +1 -1
  19. package/dist/cjs/index.js +4 -2
  20. package/dist/cjs/index.js.map +1 -1
  21. package/dist/cjs/internal/core-effect.js +4 -2
  22. package/dist/cjs/internal/core-effect.js.map +1 -1
  23. package/dist/cjs/internal/core.js +12 -2
  24. package/dist/cjs/internal/core.js.map +1 -1
  25. package/dist/cjs/internal/fiberRuntime.js +32 -0
  26. package/dist/cjs/internal/fiberRuntime.js.map +1 -1
  27. package/dist/cjs/internal/stream.js.map +1 -1
  28. package/dist/cjs/internal/version.js +1 -1
  29. package/dist/dts/Array.d.ts +14 -0
  30. package/dist/dts/Array.d.ts.map +1 -1
  31. package/dist/dts/Cause.d.ts +1 -1
  32. package/dist/dts/Chunk.d.ts +11 -0
  33. package/dist/dts/Chunk.d.ts.map +1 -1
  34. package/dist/dts/Effect.d.ts +109 -5
  35. package/dist/dts/Effect.d.ts.map +1 -1
  36. package/dist/dts/Either.d.ts +35 -0
  37. package/dist/dts/Either.d.ts.map +1 -1
  38. package/dist/dts/ManagedRuntime.d.ts +15 -0
  39. package/dist/dts/ManagedRuntime.d.ts.map +1 -1
  40. package/dist/dts/Micro.d.ts +2002 -0
  41. package/dist/dts/Micro.d.ts.map +1 -0
  42. package/dist/dts/Option.d.ts +2 -0
  43. package/dist/dts/Option.d.ts.map +1 -1
  44. package/dist/dts/Schedule.d.ts +2 -2
  45. package/dist/dts/Stream.d.ts +45 -6
  46. package/dist/dts/Stream.d.ts.map +1 -1
  47. package/dist/dts/Tuple.d.ts +18 -0
  48. package/dist/dts/Tuple.d.ts.map +1 -1
  49. package/dist/dts/index.d.ts +7 -0
  50. package/dist/dts/index.d.ts.map +1 -1
  51. package/dist/dts/internal/core-effect.d.ts.map +1 -1
  52. package/dist/dts/internal/core.d.ts.map +1 -1
  53. package/dist/dts/internal/fiberRuntime.d.ts.map +1 -1
  54. package/dist/esm/Array.js +14 -0
  55. package/dist/esm/Array.js.map +1 -1
  56. package/dist/esm/Chunk.js +11 -0
  57. package/dist/esm/Chunk.js.map +1 -1
  58. package/dist/esm/Effect.js +107 -5
  59. package/dist/esm/Effect.js.map +1 -1
  60. package/dist/esm/Either.js +30 -0
  61. package/dist/esm/Either.js.map +1 -1
  62. package/dist/esm/ManagedRuntime.js.map +1 -1
  63. package/dist/esm/Micro.js +2307 -0
  64. package/dist/esm/Micro.js.map +1 -0
  65. package/dist/esm/Option.js +1 -1
  66. package/dist/esm/Option.js.map +1 -1
  67. package/dist/esm/Schedule.js +2 -2
  68. package/dist/esm/Stream.js.map +1 -1
  69. package/dist/esm/Tuple.js +15 -8
  70. package/dist/esm/Tuple.js.map +1 -1
  71. package/dist/esm/index.js +7 -0
  72. package/dist/esm/index.js.map +1 -1
  73. package/dist/esm/internal/core-effect.js +2 -0
  74. package/dist/esm/internal/core-effect.js.map +1 -1
  75. package/dist/esm/internal/core.js +10 -1
  76. package/dist/esm/internal/core.js.map +1 -1
  77. package/dist/esm/internal/fiberRuntime.js +32 -0
  78. package/dist/esm/internal/fiberRuntime.js.map +1 -1
  79. package/dist/esm/internal/stream.js.map +1 -1
  80. package/dist/esm/internal/version.js +1 -1
  81. package/package.json +9 -1
  82. package/src/Array.ts +15 -0
  83. package/src/Cause.ts +1 -1
  84. package/src/Chunk.ts +12 -0
  85. package/src/Effect.ts +117 -5
  86. package/src/Either.ts +51 -0
  87. package/src/ManagedRuntime.ts +16 -0
  88. package/src/Micro.ts +3826 -0
  89. package/src/Option.ts +12 -1
  90. package/src/Schedule.ts +2 -2
  91. package/src/Stream.ts +60 -8
  92. package/src/Tuple.ts +18 -8
  93. package/src/index.ts +8 -0
  94. package/src/internal/core-effect.ts +33 -0
  95. package/src/internal/core.ts +18 -1
  96. package/src/internal/fiberRuntime.ts +32 -0
  97. package/src/internal/stream.ts +8 -4
  98. package/src/internal/version.ts +1 -1
@@ -0,0 +1,2383 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.matchFailureMicro = exports.matchFailure = exports.match = exports.mapFailure = exports.mapError = exports.map = exports.make = exports.locally = exports.let = exports.isMicro = exports.isHandle = exports.interruptible = exports.ignoreLogged = exports.ignore = exports.getEnvRef = exports.gen = exports.fromResultSync = exports.fromResult = exports.fromOption = exports.fromEither = exports.forkScoped = exports.forkIn = exports.forkDaemon = exports.fork = exports.forever = exports.forEach = exports.flip = exports.flatten = exports.flatMap = exports.filterOrFailWith = exports.filterOrFail = exports.filterMap = exports.filter = exports.failureWithTrace = exports.failureSquash = exports.failureIsUnexpected = exports.failureIsExpected = exports.failureIsAborted = exports.failWithSync = exports.failWith = exports.failSync = exports.fail = exports.envUnsafeMakeEmpty = exports.envSet = exports.envRefMake = exports.envMutate = exports.envMake = exports.envGet = exports.ensuring = exports.either = exports.die = exports.delayWithRecurs = exports.delayWithMaxElapsed = exports.delayWithMax = exports.delaySpaced = exports.delayExponential = exports.delay = exports.currentMaxDepthBeforeYield = exports.currentContext = exports.currentConcurrency = exports.currentAbortSignal = exports.currentAbortController = exports.context = exports.catchUnexpected = exports.catchTag = exports.catchIf = exports.catchFailureIf = exports.catchFailure = exports.catchExpected = exports.bindTo = exports.bind = exports.async = exports.asVoid = exports.asSome = exports.asResult = exports.as = exports.andThen = exports.all = exports.addFinalizer = exports.acquireUseRelease = exports.acquireRelease = exports.abort = exports.TypeId = exports.TaggedError = exports.ResultSuccess = exports.ResultFailWith = exports.ResultFailUnexpected = exports.ResultFail = exports.ResultAborted = exports.MicroScopeTypeId = exports.MicroScope = exports.HandleTypeId = exports.FailureUnexpected = exports.FailureTypeId = exports.FailureExpected = exports.FailureAborted = exports.Error = exports.EnvTypeId = exports.EnvRefTypeId = exports.Do = void 0;
7
+ exports.zip = exports.yieldNow = exports.yieldFlush = exports.withTrace = exports.withConcurrency = exports.when = exports.void = exports.uninterruptibleMask = exports.uninterruptible = exports.tryPromise = exports.try = exports.timeoutOrElse = exports.timeout = exports.tapUnexpected = exports.tapFailureIf = exports.tapFailure = exports.tapExpected = exports.tap = exports.sync = exports.suspend = exports.succeedSome = exports.succeedNone = exports.succeed = exports.sleep = exports.serviceOption = exports.service = exports.scoped = exports.scopeUnsafeMake = exports.scopeMake = exports.scope = exports.sandbox = exports.runSyncResult = exports.runSync = exports.runSymbol = exports.runPromiseResult = exports.runPromise = exports.runFork = exports.retry = exports.resultVoid = exports.resultIsSuccess = exports.resultIsFailureUnexpected = exports.resultIsFailureExpected = exports.resultIsFailure = exports.resultIsAborted = exports.repeatResult = exports.repeat = exports.raceFirst = exports.raceAllFirst = exports.raceAll = exports.race = exports.provideServiceMicro = exports.provideService = exports.provideScope = exports.provideContext = exports.promise = exports.orElseSucceed = exports.orDie = exports.option = exports.onResultIf = exports.onResult = exports.onFailure = exports.onAbort = exports.never = exports.matchMicro = void 0;
8
+ var Context = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("./Context.js"));
9
+ var Effectable = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("./Effectable.js"));
10
+ var Either = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("./Either.js"));
11
+ var _Function = /*#__PURE__*/require("./Function.js");
12
+ var _GlobalValue = /*#__PURE__*/require("./GlobalValue.js");
13
+ var _Inspectable = /*#__PURE__*/require("./Inspectable.js");
14
+ var _effectable = /*#__PURE__*/require("./internal/effectable.js");
15
+ var _singleShotGen = /*#__PURE__*/require("./internal/singleShotGen.js");
16
+ var Option = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("./Option.js"));
17
+ var _Pipeable = /*#__PURE__*/require("./Pipeable.js");
18
+ var _Predicate = /*#__PURE__*/require("./Predicate.js");
19
+ var _Utils = /*#__PURE__*/require("./Utils.js");
20
+ function _getRequireWildcardCache(e) {
21
+ if ("function" != typeof WeakMap) return null;
22
+ var r = new WeakMap(),
23
+ t = new WeakMap();
24
+ return (_getRequireWildcardCache = function (e) {
25
+ return e ? t : r;
26
+ })(e);
27
+ }
28
+ function _interopRequireWildcard(e, r) {
29
+ if (!r && e && e.__esModule) return e;
30
+ if (null === e || "object" != typeof e && "function" != typeof e) return {
31
+ default: e
32
+ };
33
+ var t = _getRequireWildcardCache(r);
34
+ if (t && t.has(e)) return t.get(e);
35
+ var n = {
36
+ __proto__: null
37
+ },
38
+ a = Object.defineProperty && Object.getOwnPropertyDescriptor;
39
+ for (var u in e) if ("default" !== u && {}.hasOwnProperty.call(e, u)) {
40
+ var i = a ? Object.getOwnPropertyDescriptor(e, u) : null;
41
+ i && (i.get || i.set) ? Object.defineProperty(n, u, i) : n[u] = e[u];
42
+ }
43
+ return n.default = e, t && t.set(e, n), n;
44
+ }
45
+ /**
46
+ * @since 3.4.0
47
+ * @experimental
48
+ * @category type ids
49
+ */
50
+ const TypeId = exports.TypeId = /*#__PURE__*/Symbol.for("effect/Micro");
51
+ /**
52
+ * @since 3.4.0
53
+ * @experimental
54
+ * @category symbols
55
+ */
56
+ const runSymbol = exports.runSymbol = /*#__PURE__*/Symbol.for("effect/Micro/runSymbol");
57
+ /**
58
+ * @since 3.4.0
59
+ * @experimental
60
+ * @category guards
61
+ */
62
+ const isMicro = u => typeof u === "object" && u !== null && TypeId in u;
63
+ // ----------------------------------------------------------------------------
64
+ // Failures
65
+ // ----------------------------------------------------------------------------
66
+ /**
67
+ * @since 3.4.0
68
+ * @experimental
69
+ * @category failure
70
+ */
71
+ exports.isMicro = isMicro;
72
+ const FailureTypeId = exports.FailureTypeId = /*#__PURE__*/Symbol.for("effect/Micro/Failure");
73
+ const failureVariance = {
74
+ _E: _Function.identity
75
+ };
76
+ class FailureImpl extends globalThis.Error {
77
+ _tag;
78
+ traces;
79
+ [FailureTypeId];
80
+ constructor(_tag, originalError, traces) {
81
+ const failureName = `Failure${_tag}`;
82
+ let name;
83
+ let message;
84
+ let stack;
85
+ if (originalError instanceof globalThis.Error) {
86
+ name = `(${failureName}) ${originalError.name}`;
87
+ message = originalError.message;
88
+ const messageLines = message.split("\n").length;
89
+ stack = originalError.stack ? `(${failureName}) ${originalError.stack.split("\n").slice(0, messageLines + 3).join("\n")}` : `${name}: ${message}`;
90
+ } else {
91
+ name = failureName;
92
+ message = (0, _Inspectable.toStringUnknown)(originalError, 0);
93
+ stack = `${name}: ${message}`;
94
+ }
95
+ if (traces.length > 0) {
96
+ stack += `\n ${traces.join("\n ")}`;
97
+ }
98
+ super(message);
99
+ this._tag = _tag;
100
+ this.traces = traces;
101
+ this[FailureTypeId] = failureVariance;
102
+ this.name = name;
103
+ this.stack = stack;
104
+ }
105
+ pipe() {
106
+ return (0, _Pipeable.pipeArguments)(this, arguments);
107
+ }
108
+ toString() {
109
+ return this.stack;
110
+ }
111
+ [_Inspectable.NodeInspectSymbol]() {
112
+ return this.stack;
113
+ }
114
+ }
115
+ class FailureExpectedImpl extends FailureImpl {
116
+ error;
117
+ constructor(error, traces = []) {
118
+ super("Expected", error, traces);
119
+ this.error = error;
120
+ }
121
+ }
122
+ /**
123
+ * @since 3.4.0
124
+ * @experimental
125
+ * @category failure
126
+ */
127
+ const FailureExpected = (error, traces = []) => new FailureExpectedImpl(error, traces);
128
+ exports.FailureExpected = FailureExpected;
129
+ class FailureUnexpectedImpl extends FailureImpl {
130
+ defect;
131
+ constructor(defect, traces = []) {
132
+ super("Unexpected", defect, traces);
133
+ this.defect = defect;
134
+ }
135
+ }
136
+ /**
137
+ * @since 3.4.0
138
+ * @experimental
139
+ * @category failure
140
+ */
141
+ const FailureUnexpected = (defect, traces = []) => new FailureUnexpectedImpl(defect, traces);
142
+ exports.FailureUnexpected = FailureUnexpected;
143
+ class FailureAbortedImpl extends FailureImpl {
144
+ constructor(traces = []) {
145
+ super("Aborted", "aborted", traces);
146
+ }
147
+ }
148
+ /**
149
+ * @since 3.4.0
150
+ * @experimental
151
+ * @category failure
152
+ */
153
+ const FailureAborted = (traces = []) => new FailureAbortedImpl(traces);
154
+ /**
155
+ * @since 3.4.0
156
+ * @experimental
157
+ * @category failure
158
+ */
159
+ exports.FailureAborted = FailureAborted;
160
+ const failureIsExpected = self => self._tag === "Expected";
161
+ /**
162
+ * @since 3.4.0
163
+ * @experimental
164
+ * @category failure
165
+ */
166
+ exports.failureIsExpected = failureIsExpected;
167
+ const failureIsUnexpected = self => self._tag === "Unexpected";
168
+ /**
169
+ * @since 3.4.0
170
+ * @experimental
171
+ * @category failure
172
+ */
173
+ exports.failureIsUnexpected = failureIsUnexpected;
174
+ const failureIsAborted = self => self._tag === "Aborted";
175
+ /**
176
+ * @since 3.4.0
177
+ * @experimental
178
+ * @category failure
179
+ */
180
+ exports.failureIsAborted = failureIsAborted;
181
+ const failureSquash = self => self._tag === "Expected" ? self.error : self._tag === "Unexpected" ? self.defect : self;
182
+ /**
183
+ * @since 3.4.0
184
+ * @experimental
185
+ * @category failure
186
+ */
187
+ exports.failureSquash = failureSquash;
188
+ const failureWithTrace = exports.failureWithTrace = /*#__PURE__*/(0, _Function.dual)(2, (self, trace) => {
189
+ if (self._tag === "Expected") {
190
+ return FailureExpected(self.error, [...self.traces, trace]);
191
+ } else if (self._tag === "Unexpected") {
192
+ return FailureUnexpected(self.defect, [...self.traces, trace]);
193
+ }
194
+ return FailureAborted([...self.traces, trace]);
195
+ });
196
+ /**
197
+ * @since 3.4.0
198
+ * @experimental
199
+ * @category result
200
+ */
201
+ const ResultAborted = exports.ResultAborted = /*#__PURE__*/Either.left( /*#__PURE__*/FailureAborted());
202
+ /**
203
+ * @since 3.4.0
204
+ * @experimental
205
+ * @category result
206
+ */
207
+ const ResultSuccess = exports.ResultSuccess = Either.right;
208
+ /**
209
+ * @since 3.4.0
210
+ * @experimental
211
+ * @category result
212
+ */
213
+ const ResultFail = e => Either.left(FailureExpected(e));
214
+ /**
215
+ * @since 3.4.0
216
+ * @experimental
217
+ * @category result
218
+ */
219
+ exports.ResultFail = ResultFail;
220
+ const ResultFailUnexpected = defect => Either.left(FailureUnexpected(defect));
221
+ /**
222
+ * @since 3.4.0
223
+ * @experimental
224
+ * @category result
225
+ */
226
+ exports.ResultFailUnexpected = ResultFailUnexpected;
227
+ const ResultFailWith = exports.ResultFailWith = Either.left;
228
+ /**
229
+ * @since 3.4.0
230
+ * @experimental
231
+ * @category result
232
+ */
233
+ const resultIsSuccess = exports.resultIsSuccess = Either.isRight;
234
+ /**
235
+ * @since 3.4.0
236
+ * @experimental
237
+ * @category result
238
+ */
239
+ const resultIsFailure = exports.resultIsFailure = Either.isLeft;
240
+ /**
241
+ * @since 3.4.0
242
+ * @experimental
243
+ * @category result
244
+ */
245
+ const resultIsAborted = self => resultIsFailure(self) && self.left._tag === "Aborted";
246
+ /**
247
+ * @since 3.4.0
248
+ * @experimental
249
+ * @category result
250
+ */
251
+ exports.resultIsAborted = resultIsAborted;
252
+ const resultIsFailureExpected = self => resultIsFailure(self) && self.left._tag === "Expected";
253
+ /**
254
+ * @since 3.4.0
255
+ * @experimental
256
+ * @category result
257
+ */
258
+ exports.resultIsFailureExpected = resultIsFailureExpected;
259
+ const resultIsFailureUnexpected = self => resultIsFailure(self) && self.left._tag === "Unexpected";
260
+ /**
261
+ * @since 3.4.0
262
+ * @experimental
263
+ * @category result
264
+ */
265
+ exports.resultIsFailureUnexpected = resultIsFailureUnexpected;
266
+ const resultVoid = exports.resultVoid = /*#__PURE__*/ResultSuccess(void 0);
267
+ // ----------------------------------------------------------------------------
268
+ // env
269
+ // ----------------------------------------------------------------------------
270
+ /**
271
+ * @since 3.4.0
272
+ * @experimental
273
+ * @category environment
274
+ */
275
+ const EnvTypeId = exports.EnvTypeId = /*#__PURE__*/Symbol.for("effect/Micro/Env");
276
+ /**
277
+ * @since 3.4.0
278
+ * @experimental
279
+ * @category environment
280
+ */
281
+ const EnvRefTypeId = exports.EnvRefTypeId = /*#__PURE__*/Symbol.for("effect/Micro/EnvRef");
282
+ const EnvProto = {
283
+ [EnvTypeId]: {
284
+ _R: _Function.identity
285
+ },
286
+ pipe() {
287
+ return (0, _Pipeable.pipeArguments)(this, arguments);
288
+ }
289
+ };
290
+ /**
291
+ * @since 3.4.0
292
+ * @experimental
293
+ * @category environment
294
+ */
295
+ const envMake = refs => {
296
+ const self = Object.create(EnvProto);
297
+ self.refs = refs;
298
+ return self;
299
+ };
300
+ /**
301
+ * @since 3.4.0
302
+ * @experimental
303
+ * @category environment
304
+ */
305
+ exports.envMake = envMake;
306
+ const envUnsafeMakeEmpty = () => {
307
+ const controller = new AbortController();
308
+ const refs = Object.create(null);
309
+ refs[currentAbortController.key] = controller;
310
+ refs[currentAbortSignal.key] = controller.signal;
311
+ return envMake(refs);
312
+ };
313
+ /**
314
+ * @since 3.4.0
315
+ * @experimental
316
+ * @category environment
317
+ */
318
+ exports.envUnsafeMakeEmpty = envUnsafeMakeEmpty;
319
+ const envGet = exports.envGet = /*#__PURE__*/(0, _Function.dual)(2, (self, ref) => ref.key in self.refs ? self.refs[ref.key] : ref.initial);
320
+ /**
321
+ * @since 3.4.0
322
+ * @experimental
323
+ * @category environment
324
+ */
325
+ const envSet = exports.envSet = /*#__PURE__*/(0, _Function.dual)(3, (self, ref, value) => {
326
+ const refs = Object.assign(Object.create(null), self.refs);
327
+ refs[ref.key] = value;
328
+ return envMake(refs);
329
+ });
330
+ /**
331
+ * @since 3.4.0
332
+ * @experimental
333
+ * @category environment
334
+ */
335
+ const envMutate = exports.envMutate = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => envMake(f(Object.assign(Object.create(null), self.refs))));
336
+ /**
337
+ * Access the given `Context.Tag` from the environment.
338
+ *
339
+ * @since 3.4.0
340
+ * @experimental
341
+ * @category environment
342
+ */
343
+ const service = tag => make(function (env, onResult) {
344
+ onResult(ResultSuccess(Context.get(envGet(env, currentContext), tag)));
345
+ });
346
+ /**
347
+ * Access the given `Context.Tag` from the environment, without tracking the
348
+ * dependency at the type level.
349
+ *
350
+ * It will return an `Option` of the service, depending on whether it is
351
+ * available in the environment or not.
352
+ *
353
+ * @since 3.4.0
354
+ * @experimental
355
+ * @category environment
356
+ */
357
+ exports.service = service;
358
+ const serviceOption = tag => make(function (env, onResult) {
359
+ onResult(ResultSuccess(Context.getOption(envGet(env, currentContext), tag)));
360
+ });
361
+ /**
362
+ * Retrieve the current value of the given `EnvRef`.
363
+ *
364
+ * @since 3.4.0
365
+ * @experimental
366
+ * @category environment
367
+ */
368
+ exports.serviceOption = serviceOption;
369
+ const getEnvRef = envRef => make((env, onResult) => onResult(Either.right(envGet(env, envRef))));
370
+ /**
371
+ * Set the value of the given `EnvRef` for the duration of the effect.
372
+ *
373
+ * @since 3.4.0
374
+ * @experimental
375
+ * @category environment
376
+ */
377
+ exports.getEnvRef = getEnvRef;
378
+ const locally = exports.locally = /*#__PURE__*/(0, _Function.dual)(3, (self, fiberRef, value) => make((env, onResult) => self[runSymbol](envSet(env, fiberRef, value), onResult)));
379
+ /**
380
+ * Access the current `Context` from the environment.
381
+ *
382
+ * @since 3.4.0
383
+ * @experimental
384
+ * @category environment
385
+ */
386
+ const context = () => getEnvRef(currentContext);
387
+ /**
388
+ * Merge the given `Context` with the current context.
389
+ *
390
+ * @since 3.4.0
391
+ * @experimental
392
+ * @category environment
393
+ */
394
+ exports.context = context;
395
+ const provideContext = exports.provideContext = /*#__PURE__*/(0, _Function.dual)(2, (self, provided) => make(function (env, onResult) {
396
+ const context = envGet(env, currentContext);
397
+ const nextEnv = envSet(env, currentContext, Context.merge(context, provided));
398
+ self[runSymbol](nextEnv, onResult);
399
+ }));
400
+ /**
401
+ * Add the provided service to the current context.
402
+ *
403
+ * @since 3.4.0
404
+ * @experimental
405
+ * @category environment
406
+ */
407
+ const provideService = exports.provideService = /*#__PURE__*/(0, _Function.dual)(3, (self, tag, service) => make(function (env, onResult) {
408
+ const context = envGet(env, currentContext);
409
+ const nextEnv = envSet(env, currentContext, Context.add(context, tag, service));
410
+ self[runSymbol](nextEnv, onResult);
411
+ }));
412
+ /**
413
+ * Create a service using the provided `Micro` effect, and add it to the
414
+ * current context.
415
+ *
416
+ * @since 3.4.0
417
+ * @experimental
418
+ * @category environment
419
+ */
420
+ const provideServiceMicro = exports.provideServiceMicro = /*#__PURE__*/(0, _Function.dual)(3, (self, tag, acquire) => flatMap(acquire, service => provideService(self, tag, service)));
421
+ // ========================================================================
422
+ // Env refs
423
+ // ========================================================================
424
+ const EnvRefProto = {
425
+ [EnvRefTypeId]: EnvRefTypeId
426
+ };
427
+ /**
428
+ * @since 3.4.0
429
+ * @experimental
430
+ * @category environment refs
431
+ */
432
+ const envRefMake = (key, initial) => (0, _GlobalValue.globalValue)(key, () => {
433
+ const self = Object.create(EnvRefProto);
434
+ self.key = key;
435
+ self.initial = initial();
436
+ return self;
437
+ });
438
+ /**
439
+ * @since 3.4.0
440
+ * @experimental
441
+ * @category environment refs
442
+ */
443
+ exports.envRefMake = envRefMake;
444
+ const currentAbortController = exports.currentAbortController = /*#__PURE__*/envRefMake("effect/Micro/currentAbortController", () => new AbortController());
445
+ /**
446
+ * @since 3.4.0
447
+ * @experimental
448
+ * @category environment refs
449
+ */
450
+ const currentAbortSignal = exports.currentAbortSignal = /*#__PURE__*/envRefMake("effect/Micro/currentAbortSignal", () => currentAbortController.initial.signal);
451
+ /**
452
+ * @since 3.4.0
453
+ * @experimental
454
+ * @category environment refs
455
+ */
456
+ const currentContext = exports.currentContext = /*#__PURE__*/envRefMake("effect/Micro/currentContext", () => Context.empty());
457
+ /**
458
+ * @since 3.4.0
459
+ * @experimental
460
+ * @category environment refs
461
+ */
462
+ const currentConcurrency = exports.currentConcurrency = /*#__PURE__*/envRefMake("effect/Micro/currentConcurrency", () => "unbounded");
463
+ /**
464
+ * @since 3.4.0
465
+ * @experimental
466
+ * @category environment refs
467
+ */
468
+ const currentMaxDepthBeforeYield = exports.currentMaxDepthBeforeYield = /*#__PURE__*/envRefMake("effect/Micro/currentMaxDepthBeforeYield", () => 2048);
469
+ const currentInterruptible = /*#__PURE__*/envRefMake("effect/Micro/currentInterruptible", () => true);
470
+ /**
471
+ * If you have a `Micro` that uses `concurrency: "inherit"`, you can use this
472
+ * api to control the concurrency of that `Micro` when it is run.
473
+ *
474
+ * @since 3.4.0
475
+ * @experimental
476
+ * @category environment refs
477
+ * @example
478
+ * import * as Micro from "effect/Micro"
479
+ *
480
+ * Micro.forEach([1, 2, 3], (n) => Micro.succeed(n), {
481
+ * concurrency: "inherit"
482
+ * }).pipe(
483
+ * Micro.withConcurrency(2) // use a concurrency of 2
484
+ * )
485
+ */
486
+ const withConcurrency = exports.withConcurrency = /*#__PURE__*/(0, _Function.dual)(2, (self, concurrency) => locally(self, currentConcurrency, concurrency));
487
+ // ----------------------------------------------------------------------------
488
+ // constructors
489
+ // ----------------------------------------------------------------------------
490
+ const MicroProto = {
491
+ ...Effectable.EffectPrototype,
492
+ _op: "Micro",
493
+ [TypeId]: {
494
+ _A: _Function.identity,
495
+ _E: _Function.identity,
496
+ _R: _Function.identity
497
+ },
498
+ [Symbol.iterator]() {
499
+ return new _singleShotGen.SingleShotGen(new _Utils.YieldWrap(this));
500
+ }
501
+ };
502
+ const microDepthState = /*#__PURE__*/(0, _GlobalValue.globalValue)("effect/Micro/microDepthState", () => ({
503
+ depth: 0,
504
+ maxDepthBeforeYield: currentMaxDepthBeforeYield.initial
505
+ }));
506
+ const unsafeMake = run => {
507
+ const self = Object.create(MicroProto);
508
+ self[runSymbol] = run;
509
+ return self;
510
+ };
511
+ const unsafeMakeOptions = (run, checkAbort) => unsafeMake(function execute(env, onResult) {
512
+ if (checkAbort && env.refs[currentInterruptible.key] !== false && env.refs[currentAbortSignal.key].aborted) {
513
+ return onResult(ResultAborted);
514
+ }
515
+ microDepthState.depth++;
516
+ if (microDepthState.depth === 1) {
517
+ microDepthState.maxDepthBeforeYield = envGet(env, currentMaxDepthBeforeYield);
518
+ }
519
+ if (microDepthState.depth >= microDepthState.maxDepthBeforeYield) {
520
+ yieldAdd(() => execute(env, onResult));
521
+ } else {
522
+ try {
523
+ run(env, onResult);
524
+ } catch (err) {
525
+ onResult(ResultFailUnexpected(err));
526
+ }
527
+ }
528
+ microDepthState.depth--;
529
+ });
530
+ /**
531
+ * A low-level constructor for creating a `Micro` effect. It takes a function
532
+ * that receives an environment and a callback which should be called with the
533
+ * result of the effect.
534
+ *
535
+ * @since 3.4.0
536
+ * @experimental
537
+ * @category constructors
538
+ */
539
+ const make = run => unsafeMakeOptions(run, true);
540
+ /**
541
+ * Converts a `Result` into a `Micro` effect.
542
+ *
543
+ * @since 3.4.0
544
+ * @experimental
545
+ * @category constructors
546
+ */
547
+ exports.make = make;
548
+ const fromResult = self => make(function (_env, onResult) {
549
+ onResult(self);
550
+ });
551
+ /**
552
+ * Converts a lazy `Result` into a `Micro` effect.
553
+ *
554
+ * @since 3.4.0
555
+ * @experimental
556
+ * @category constructors
557
+ */
558
+ exports.fromResult = fromResult;
559
+ const fromResultSync = self => make(function (_env, onResult) {
560
+ onResult(self());
561
+ });
562
+ /**
563
+ * Creates a `Micro` effect that will succeed with the specified constant value.
564
+ *
565
+ * @since 3.4.0
566
+ * @experimental
567
+ * @category constructors
568
+ */
569
+ exports.fromResultSync = fromResultSync;
570
+ const succeed = a => fromResult(ResultSuccess(a));
571
+ /**
572
+ * Creates a `Micro` effect that will succeed with `Option.Some` of the value.
573
+ *
574
+ * @since 3.4.0
575
+ * @experimental
576
+ * @category constructors
577
+ */
578
+ exports.succeed = succeed;
579
+ const succeedSome = a => succeed(Option.some(a));
580
+ /**
581
+ * Creates a `Micro` effect that will succeed with `Option.None`.
582
+ *
583
+ * @since 3.4.0
584
+ * @experimental
585
+ * @category constructors
586
+ */
587
+ exports.succeedSome = succeedSome;
588
+ const succeedNone = exports.succeedNone = /*#__PURE__*/succeed( /*#__PURE__*/Option.none());
589
+ /**
590
+ * Creates a `Micro` effect that will fail with the specified error.
591
+ *
592
+ * This will result in a `FailureExpected`, where the error is tracked at the
593
+ * type level.
594
+ *
595
+ * @since 3.4.0
596
+ * @experimental
597
+ * @category constructors
598
+ */
599
+ const fail = e => fromResult(ResultFail(e));
600
+ /**
601
+ * Creates a `Micro` effect that will fail with the lazily evaluated error.
602
+ *
603
+ * This will result in a `FailureExpected`, where the error is tracked at the
604
+ * type level.
605
+ *
606
+ * @since 3.4.0
607
+ * @experimental
608
+ * @category constructors
609
+ */
610
+ exports.fail = fail;
611
+ const failSync = e => make(function (_env, onResult) {
612
+ onResult(ResultFail(e()));
613
+ });
614
+ /**
615
+ * Creates a `Micro` effect that will die with the specified error.
616
+ *
617
+ * This will result in a `FailureUnexpected`, where the error is not tracked at
618
+ * the type level.
619
+ *
620
+ * @since 3.4.0
621
+ * @experimental
622
+ * @category constructors
623
+ */
624
+ exports.failSync = failSync;
625
+ const die = defect => fromResult(ResultFailUnexpected(defect));
626
+ /**
627
+ * Creates a `Micro` effect that will fail with the specified `Failure`.
628
+ *
629
+ * @since 3.4.0
630
+ * @experimental
631
+ * @category constructors
632
+ */
633
+ exports.die = die;
634
+ const failWith = failure => fromResult(ResultFailWith(failure));
635
+ /**
636
+ * Creates a `Micro` effect that will fail with the lazily evaluated `Failure`.
637
+ *
638
+ * @since 3.4.0
639
+ * @experimental
640
+ * @category constructors
641
+ */
642
+ exports.failWith = failWith;
643
+ const failWithSync = failure => fromResultSync(() => ResultFailWith(failure()));
644
+ /**
645
+ * Creates a `Micro` effect that will succeed with the lazily evaluated value.
646
+ *
647
+ * If the evaluation of the value throws an error, the effect will fail with
648
+ * `FailureUnexpected`.
649
+ *
650
+ * @since 3.4.0
651
+ * @experimental
652
+ * @category constructors
653
+ */
654
+ exports.failWithSync = failWithSync;
655
+ const sync = evaluate => make(function (_env, onResult) {
656
+ onResult(ResultSuccess(evaluate()));
657
+ });
658
+ /**
659
+ * Converts an `Option` into a `Micro` effect, that will fail with a
660
+ * `Option.None` if the option is `None`. Otherwise, it will succeed with the
661
+ * value of the option.
662
+ *
663
+ * @since 3.4.0
664
+ * @experimental
665
+ * @category constructors
666
+ */
667
+ exports.sync = sync;
668
+ const fromOption = option => make(function (_env, onResult) {
669
+ onResult(option._tag === "Some" ? ResultSuccess(option.value) : ResultFail(Option.none()));
670
+ });
671
+ /**
672
+ * Converts an `Either` into a `Micro` effect, that will fail with the left side
673
+ * of the either if it is a `Left`. Otherwise, it will succeed with the right
674
+ * side of the either.
675
+ *
676
+ * @since 3.4.0
677
+ * @experimental
678
+ * @category constructors
679
+ */
680
+ exports.fromOption = fromOption;
681
+ const fromEither = either => make(function (_env, onResult) {
682
+ onResult(either._tag === "Right" ? either : ResultFail(either.left));
683
+ });
684
+ /**
685
+ * Lazily creates a `Micro` effect from the given side-effect.
686
+ *
687
+ * @since 3.4.0
688
+ * @experimental
689
+ * @category constructors
690
+ */
691
+ exports.fromEither = fromEither;
692
+ const suspend = evaluate => make(function (env, onResult) {
693
+ evaluate()[runSymbol](env, onResult);
694
+ });
695
+ exports.suspend = suspend;
696
+ const void_ = exports.void = /*#__PURE__*/succeed(void 0);
697
+ /**
698
+ * Create a `Micro` effect from an asynchronous computation.
699
+ *
700
+ * You can return a cleanup effect that will be run when the effect is aborted.
701
+ * It is also passed an `AbortSignal` that is triggered when the effect is
702
+ * aborted.
703
+ *
704
+ * @since 3.4.0
705
+ * @experimental
706
+ * @category constructors
707
+ */
708
+ const async = register => make(function (env, onResult) {
709
+ let resumed = false;
710
+ const controller = register.length > 1 ? new AbortController() : undefined;
711
+ const signal = envGet(env, currentAbortSignal);
712
+ let cleanup = undefined;
713
+ function onAbort() {
714
+ if (cleanup) {
715
+ resume(uninterruptible(andThen(cleanup, fromResult(ResultAborted))));
716
+ } else {
717
+ resume(fromResult(ResultAborted));
718
+ }
719
+ if (controller !== undefined) {
720
+ controller.abort();
721
+ }
722
+ }
723
+ function resume(effect) {
724
+ if (resumed) {
725
+ return;
726
+ }
727
+ resumed = true;
728
+ signal.removeEventListener("abort", onAbort);
729
+ effect[runSymbol](env, onResult);
730
+ }
731
+ cleanup = controller === undefined ? register(resume) : register(resume, controller.signal);
732
+ if (resumed) return;
733
+ signal.addEventListener("abort", onAbort);
734
+ });
735
+ exports.async = async;
736
+ const try_ = options => make(function (_env, onResult) {
737
+ try {
738
+ onResult(ResultSuccess(options.try()));
739
+ } catch (err) {
740
+ onResult(ResultFail(options.catch(err)));
741
+ }
742
+ });
743
+ exports.try = try_;
744
+ /**
745
+ * Wrap a `Promise` into a `Micro` effect. Any errors will result in a
746
+ * `FailureUnexpected`.
747
+ *
748
+ * @since 3.4.0
749
+ * @experimental
750
+ * @category constructors
751
+ */
752
+ const promise = evaluate => async(function (resume, signal) {
753
+ evaluate(signal).then(a => resume(succeed(a)), e => resume(die(e)));
754
+ });
755
+ /**
756
+ * Wrap a `Promise` into a `Micro` effect. Any errors will be caught and
757
+ * converted into a specific error type.
758
+ *
759
+ * @since 3.4.0
760
+ * @experimental
761
+ * @category constructors
762
+ * @example
763
+ * import { Micro } from "effect"
764
+ *
765
+ * Micro.tryPromise({
766
+ * try: () => Promise.resolve("success"),
767
+ * catch: (cause) => new Error("caught", { cause })
768
+ * })
769
+ */
770
+ exports.promise = promise;
771
+ const tryPromise = options => async(function (resume, signal) {
772
+ try {
773
+ options.try(signal).then(a => resume(succeed(a)), e => resume(fail(options.catch(e))));
774
+ } catch (err) {
775
+ resume(fail(options.catch(err)));
776
+ }
777
+ });
778
+ exports.tryPromise = tryPromise;
779
+ const yieldState = /*#__PURE__*/(0, _GlobalValue.globalValue)("effect/Micro/yieldState", () => ({
780
+ tasks: [],
781
+ working: false
782
+ }));
783
+ const yieldRunTasks = () => {
784
+ const tasks = yieldState.tasks;
785
+ yieldState.tasks = [];
786
+ for (let i = 0, len = tasks.length; i < len; i++) {
787
+ tasks[i]();
788
+ }
789
+ };
790
+ const setImmediate = "setImmediate" in globalThis ? globalThis.setImmediate : f => setTimeout(f, 0);
791
+ const yieldAdd = task => {
792
+ yieldState.tasks.push(task);
793
+ if (!yieldState.working) {
794
+ yieldState.working = true;
795
+ setImmediate(() => {
796
+ yieldState.working = false;
797
+ yieldRunTasks();
798
+ });
799
+ }
800
+ };
801
+ /**
802
+ * Pause the execution of the current `Micro` effect, and resume it on the next
803
+ * iteration of the event loop.
804
+ *
805
+ * @since 3.4.0
806
+ * @experimental
807
+ * @category constructors
808
+ */
809
+ const yieldNow = exports.yieldNow = /*#__PURE__*/make(function (_env, onResult) {
810
+ yieldAdd(() => onResult(resultVoid));
811
+ });
812
+ /**
813
+ * Flush any yielded effects that are waiting to be executed.
814
+ *
815
+ * @since 3.4.0
816
+ * @experimental
817
+ * @category constructors
818
+ */
819
+ const yieldFlush = exports.yieldFlush = /*#__PURE__*/sync(function () {
820
+ while (yieldState.tasks.length > 0) {
821
+ yieldRunTasks();
822
+ }
823
+ });
824
+ /**
825
+ * A `Micro` that will never succeed or fail. It wraps `setInterval` to prevent
826
+ * the Javascript runtime from exiting.
827
+ *
828
+ * @since 3.4.0
829
+ * @experimental
830
+ * @category constructors
831
+ */
832
+ const never = exports.never = /*#__PURE__*/async(function () {
833
+ const interval = setInterval(_Function.constVoid, 2147483646);
834
+ return sync(() => clearInterval(interval));
835
+ });
836
+ /**
837
+ * @since 3.4.0
838
+ * @experimental
839
+ * @category constructors
840
+ */
841
+ const gen = f => make(function (env, onResult) {
842
+ const iterator = f();
843
+ let running = false;
844
+ let value = undefined;
845
+ function run() {
846
+ running = true;
847
+ try {
848
+ let shouldContinue = true;
849
+ while (shouldContinue) {
850
+ const result = iterator.next(value);
851
+ if (result.done) {
852
+ return onResult(ResultSuccess(result.value));
853
+ }
854
+ shouldContinue = false;
855
+ (0, _Utils.yieldWrapGet)(result.value)[runSymbol](env, function (result) {
856
+ if (result._tag === "Left") {
857
+ onResult(result);
858
+ } else {
859
+ shouldContinue = true;
860
+ value = result.right;
861
+ if (!running) run();
862
+ }
863
+ });
864
+ }
865
+ } catch (err) {
866
+ onResult(ResultFailUnexpected(err));
867
+ }
868
+ running = false;
869
+ }
870
+ run();
871
+ });
872
+ // ----------------------------------------------------------------------------
873
+ // mapping & sequencing
874
+ // ----------------------------------------------------------------------------
875
+ /**
876
+ * Flattens any nested `Micro` effects, merging the error and requirement types.
877
+ *
878
+ * @since 3.4.0
879
+ * @experimental
880
+ * @category mapping & sequencing
881
+ */
882
+ exports.gen = gen;
883
+ const flatten = self => make(function (env, onResult) {
884
+ self[runSymbol](env, result => result._tag === "Left" ? onResult(result) : result.right[runSymbol](env, onResult));
885
+ });
886
+ /**
887
+ * Transforms the success value of the `Micro` effect with the specified
888
+ * function.
889
+ *
890
+ * @since 3.4.0
891
+ * @experimental
892
+ * @category mapping & sequencing
893
+ */
894
+ exports.flatten = flatten;
895
+ const map = exports.map = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => make(function (env, onResult) {
896
+ self[runSymbol](env, function (result) {
897
+ onResult(result._tag === "Left" ? result : ResultSuccess(f(result.right)));
898
+ });
899
+ }));
900
+ /**
901
+ * Create a `Micro` effect that will replace the success value of the given
902
+ * effect.
903
+ *
904
+ * @since 3.4.0
905
+ * @experimental
906
+ * @category mapping & sequencing
907
+ */
908
+ const as = exports.as = /*#__PURE__*/(0, _Function.dual)(2, (self, value) => map(self, _ => value));
909
+ /**
910
+ * Wrap the success value of this `Micro` effect in an `Option.Some`.
911
+ *
912
+ * @since 3.4.0
913
+ * @experimental
914
+ * @category mapping & sequencing
915
+ */
916
+ const asSome = self => map(self, Option.some);
917
+ /**
918
+ * Map the success value of this `Micro` effect to another `Micro` effect, then
919
+ * flatten the result.
920
+ *
921
+ * @since 3.4.0
922
+ * @experimental
923
+ * @category mapping & sequencing
924
+ */
925
+ exports.asSome = asSome;
926
+ const flatMap = exports.flatMap = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => make(function (env, onResult) {
927
+ self[runSymbol](env, function (result) {
928
+ if (result._tag === "Left") {
929
+ return onResult(result);
930
+ }
931
+ f(result.right)[runSymbol](env, onResult);
932
+ });
933
+ }));
934
+ /**
935
+ * Swap the error and success types of the `Micro` effect.
936
+ *
937
+ * @since 3.4.0
938
+ * @experimental
939
+ * @category mapping & sequencing
940
+ */
941
+ const flip = self => matchMicro(self, {
942
+ onFailure: succeed,
943
+ onSuccess: fail
944
+ });
945
+ /**
946
+ * A more flexible version of `flatMap`, that combines `map` and `flatMap` into
947
+ * a single api.
948
+ *
949
+ * It also allows you to pass in a `Micro` effect directly, which will be
950
+ * executed after the current effect.
951
+ *
952
+ * @since 3.4.0
953
+ * @experimental
954
+ * @category mapping & sequencing
955
+ */
956
+ exports.flip = flip;
957
+ const andThen = exports.andThen = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => make(function (env, onResult) {
958
+ self[runSymbol](env, function (result) {
959
+ if (result._tag === "Left") {
960
+ return onResult(result);
961
+ } else if (envGet(env, currentAbortSignal).aborted) {
962
+ return onResult(ResultAborted);
963
+ }
964
+ const value = isMicro(f) ? f : typeof f === "function" ? f(result.right) : f;
965
+ if (isMicro(value)) {
966
+ value[runSymbol](env, onResult);
967
+ } else {
968
+ onResult(ResultSuccess(value));
969
+ }
970
+ });
971
+ }));
972
+ /**
973
+ * Execute a side effect from the success value of the `Micro` effect.
974
+ *
975
+ * It is similar to the `andThen` api, but the success value is ignored.
976
+ *
977
+ * @since 3.4.0
978
+ * @experimental
979
+ * @category mapping & sequencing
980
+ */
981
+ const tap = exports.tap = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => make(function (env, onResult) {
982
+ self[runSymbol](env, function (selfResult) {
983
+ if (selfResult._tag === "Left") {
984
+ return onResult(selfResult);
985
+ } else if (envGet(env, currentAbortSignal).aborted) {
986
+ return onResult(ResultAborted);
987
+ }
988
+ const value = isMicro(f) ? f : typeof f === "function" ? f(selfResult.right) : f;
989
+ if (isMicro(value)) {
990
+ value[runSymbol](env, function (tapResult) {
991
+ if (tapResult._tag === "Left") {
992
+ return onResult(tapResult);
993
+ }
994
+ onResult(selfResult);
995
+ });
996
+ } else {
997
+ onResult(selfResult);
998
+ }
999
+ });
1000
+ }));
1001
+ /**
1002
+ * Replace the success value of the `Micro` effect with `void`.
1003
+ *
1004
+ * @since 3.4.0
1005
+ * @experimental
1006
+ * @category mapping & sequencing
1007
+ */
1008
+ const asVoid = self => map(self, _ => void 0);
1009
+ /**
1010
+ * Access the `Result` of the given `Micro` effect.
1011
+ *
1012
+ * @since 3.4.0
1013
+ * @experimental
1014
+ * @category mapping & sequencing
1015
+ */
1016
+ exports.asVoid = asVoid;
1017
+ const asResult = self => make(function (env, onResult) {
1018
+ self[runSymbol](env, function (result) {
1019
+ onResult(ResultSuccess(result));
1020
+ });
1021
+ });
1022
+ /**
1023
+ * Replace the error type of the given `Micro` with the full `Failure` object.
1024
+ *
1025
+ * @since 3.4.0
1026
+ * @experimental
1027
+ * @category mapping & sequencing
1028
+ */
1029
+ exports.asResult = asResult;
1030
+ const sandbox = self => catchFailure(self, failure => fail(failure));
1031
+ exports.sandbox = sandbox;
1032
+ function forkSignal(env) {
1033
+ const controller = new AbortController();
1034
+ const parentSignal = envGet(env, currentAbortSignal);
1035
+ function onAbort() {
1036
+ controller.abort();
1037
+ parentSignal.removeEventListener("abort", onAbort);
1038
+ }
1039
+ parentSignal.addEventListener("abort", onAbort);
1040
+ const envWithSignal = envMutate(env, function (refs) {
1041
+ refs[currentAbortController.key] = controller;
1042
+ refs[currentAbortSignal.key] = controller.signal;
1043
+ return refs;
1044
+ });
1045
+ return [envWithSignal, onAbort];
1046
+ }
1047
+ /**
1048
+ * Returns an effect that races all the specified effects,
1049
+ * yielding the value of the first effect to succeed with a value. Losers of
1050
+ * the race will be interrupted immediately
1051
+ *
1052
+ * @since 3.4.0
1053
+ * @experimental
1054
+ * @category sequencing
1055
+ */
1056
+ const raceAll = all => make(function (env, onResult) {
1057
+ const [envWithSignal, onAbort] = forkSignal(env);
1058
+ const effects = Array.from(all);
1059
+ let len = effects.length;
1060
+ let index = 0;
1061
+ let done = 0;
1062
+ let result = undefined;
1063
+ const failures = [];
1064
+ function onDone(result_) {
1065
+ done++;
1066
+ if (result_._tag === "Right" && result === undefined) {
1067
+ len = index;
1068
+ result = result_;
1069
+ onAbort();
1070
+ } else if (result_._tag === "Left") {
1071
+ failures.push(result_.left);
1072
+ }
1073
+ if (done >= len) {
1074
+ onResult(result ?? Either.left(failures[0]));
1075
+ }
1076
+ }
1077
+ for (; index < len; index++) {
1078
+ effects[index][runSymbol](envWithSignal, onDone);
1079
+ }
1080
+ });
1081
+ /**
1082
+ * Returns an effect that races all the specified effects,
1083
+ * yielding the value of the first effect to succeed or fail. Losers of
1084
+ * the race will be interrupted immediately
1085
+ *
1086
+ * @since 3.4.0
1087
+ * @experimental
1088
+ * @category sequencing
1089
+ */
1090
+ exports.raceAll = raceAll;
1091
+ const raceAllFirst = all => make(function (env, onResult) {
1092
+ const [envWithSignal, onAbort] = forkSignal(env);
1093
+ const effects = Array.from(all);
1094
+ let len = effects.length;
1095
+ let index = 0;
1096
+ let done = 0;
1097
+ let result = undefined;
1098
+ const failures = [];
1099
+ function onDone(result_) {
1100
+ done++;
1101
+ if (result === undefined) {
1102
+ len = index;
1103
+ result = result_;
1104
+ onAbort();
1105
+ }
1106
+ if (done >= len) {
1107
+ onResult(result ?? Either.left(failures[0]));
1108
+ }
1109
+ }
1110
+ for (; index < len; index++) {
1111
+ effects[index][runSymbol](envWithSignal, onDone);
1112
+ }
1113
+ });
1114
+ /**
1115
+ * Returns an effect that races two effects, yielding the value of the first
1116
+ * effect to succeed. Losers of the race will be interrupted immediately
1117
+ *
1118
+ * @since 3.4.0
1119
+ * @experimental
1120
+ * @category sequencing
1121
+ */
1122
+ exports.raceAllFirst = raceAllFirst;
1123
+ const race = exports.race = /*#__PURE__*/(0, _Function.dual)(2, (self, that) => raceAll([self, that]));
1124
+ /**
1125
+ * Returns an effect that races two effects, yielding the value of the first
1126
+ * effect to succeed *or* fail. Losers of the race will be interrupted immediately
1127
+ *
1128
+ * @since 3.4.0
1129
+ * @experimental
1130
+ * @category sequencing
1131
+ */
1132
+ const raceFirst = exports.raceFirst = /*#__PURE__*/(0, _Function.dual)(2, (self, that) => raceAllFirst([self, that]));
1133
+ // ----------------------------------------------------------------------------
1134
+ // zipping
1135
+ // ----------------------------------------------------------------------------
1136
+ /**
1137
+ * Combine two `Micro` effects into a single effect that produces a tuple of
1138
+ * their results.
1139
+ *
1140
+ * @since 3.4.0
1141
+ * @experimental
1142
+ * @category zipping
1143
+ */
1144
+ const zip = exports.zip = /*#__PURE__*/(0, _Function.dual)(args => isMicro(args[1]), (self, that, options) => {
1145
+ if (options?.concurrent) {
1146
+ return all([self, that], {
1147
+ concurrency: "unbounded"
1148
+ });
1149
+ }
1150
+ return flatMap(self, a => map(that, a2 => [a, a2]));
1151
+ });
1152
+ // ----------------------------------------------------------------------------
1153
+ // filtering & conditionals
1154
+ // ----------------------------------------------------------------------------
1155
+ /**
1156
+ * Filter the specified effect with the provided function, failing with specified
1157
+ * `Failure` if the predicate fails.
1158
+ *
1159
+ * In addition to the filtering capabilities discussed earlier, you have the option to further
1160
+ * refine and narrow down the type of the success channel by providing a
1161
+ *
1162
+ * @since 3.4.0
1163
+ * @experimental
1164
+ * @category filtering & conditionals
1165
+ */
1166
+ const filterOrFailWith = exports.filterOrFailWith = /*#__PURE__*/(0, _Function.dual)(args => isMicro(args[0]), (self, refinement, orFailWith) => flatMap(self, a => refinement(a) ? succeed(a) : failWith(orFailWith(a))));
1167
+ /**
1168
+ * Filter the specified effect with the provided function, failing with specified
1169
+ * error if the predicate fails.
1170
+ *
1171
+ * In addition to the filtering capabilities discussed earlier, you have the option to further
1172
+ * refine and narrow down the type of the success channel by providing a
1173
+ *
1174
+ * @since 3.4.0
1175
+ * @experimental
1176
+ * @category filtering & conditionals
1177
+ */
1178
+ const filterOrFail = exports.filterOrFail = /*#__PURE__*/(0, _Function.dual)(args => isMicro(args[0]), (self, refinement, orFailWith) => flatMap(self, a => refinement(a) ? succeed(a) : fail(orFailWith(a))));
1179
+ /**
1180
+ * The moral equivalent of `if (p) exp`.
1181
+ *
1182
+ * @since 3.4.0
1183
+ * @experimental
1184
+ * @category filtering & conditionals
1185
+ */
1186
+ const when = exports.when = /*#__PURE__*/(0, _Function.dual)(2, (self, condition) => flatMap(isMicro(condition) ? condition : sync(condition), pass => pass ? asSome(self) : succeed(Option.none())));
1187
+ // ----------------------------------------------------------------------------
1188
+ // repetition
1189
+ // ----------------------------------------------------------------------------
1190
+ /**
1191
+ * Repeat the given `Micro` using the provided options.
1192
+ *
1193
+ * The `while` predicate will be checked after each iteration, and can use the
1194
+ * fall `Result` of the effect to determine if the repetition should continue.
1195
+ *
1196
+ * @since 3.4.0
1197
+ * @experimental
1198
+ * @category repetition
1199
+ */
1200
+ const repeatResult = exports.repeatResult = /*#__PURE__*/(0, _Function.dual)(2, (self, options) => make(function (env, onResult) {
1201
+ const startedAt = options.delay ? Date.now() : 0;
1202
+ let attempt = 0;
1203
+ self[runSymbol](env, function loop(result) {
1204
+ if (options.while !== undefined && !options.while(result)) {
1205
+ return onResult(result);
1206
+ } else if (options.times !== undefined && attempt >= options.times) {
1207
+ return onResult(result);
1208
+ }
1209
+ attempt++;
1210
+ let delayEffect = yieldNow;
1211
+ if (options.delay !== undefined) {
1212
+ const elapsed = Date.now() - startedAt;
1213
+ const duration = options.delay(attempt, elapsed);
1214
+ if (Option.isNone(duration)) {
1215
+ return onResult(result);
1216
+ }
1217
+ delayEffect = sleep(duration.value);
1218
+ }
1219
+ delayEffect[runSymbol](env, function (result) {
1220
+ if (result._tag === "Left") {
1221
+ return onResult(result);
1222
+ }
1223
+ self[runSymbol](env, loop);
1224
+ });
1225
+ });
1226
+ }));
1227
+ /**
1228
+ * Repeat the given `Micro` effect using the provided options. Only successful
1229
+ * results will be repeated.
1230
+ *
1231
+ * @since 3.4.0
1232
+ * @experimental
1233
+ * @category repetition
1234
+ */
1235
+ const repeat = exports.repeat = /*#__PURE__*/(0, _Function.dual)(args => isMicro(args[0]), (self, options) => repeatResult(self, {
1236
+ ...options,
1237
+ while: result => result._tag === "Right" && (options?.while === undefined || options.while(result.right))
1238
+ }));
1239
+ /**
1240
+ * Repeat the given `Micro` effect forever, only stopping if the effect fails.
1241
+ *
1242
+ * @since 3.4.0
1243
+ * @experimental
1244
+ * @category repetition
1245
+ */
1246
+ const forever = self => repeat(self);
1247
+ /**
1248
+ * Create a `DelayFn` that will generate a duration with an exponential backoff.
1249
+ *
1250
+ * @since 3.4.0
1251
+ * @experimental
1252
+ * @category delay fn
1253
+ */
1254
+ exports.forever = forever;
1255
+ const delayExponential = (baseMillis, factor = 2) => attempt => Option.some(attempt ** factor * baseMillis);
1256
+ /**
1257
+ * Create a `DelayFn` that will generate a duration with fixed intervals.
1258
+ *
1259
+ * @since 3.4.0
1260
+ * @experimental
1261
+ * @category delay fn
1262
+ */
1263
+ exports.delayExponential = delayExponential;
1264
+ const delaySpaced = millis => _ => Option.some(millis);
1265
+ /**
1266
+ * Transform a `DelayFn` to one that will have a duration that will never exceed
1267
+ * the specified maximum.
1268
+ *
1269
+ * @since 3.4.0
1270
+ * @experimental
1271
+ * @category delay fn
1272
+ */
1273
+ exports.delaySpaced = delaySpaced;
1274
+ const delayWithMax = exports.delayWithMax = /*#__PURE__*/(0, _Function.dual)(2, (self, max) => (attempt, elapsed) => Option.map(self(attempt, elapsed), duration => Math.min(duration, max)));
1275
+ /**
1276
+ * Transform a `DelayFn` to one that will stop repeating after the specified
1277
+ * amount of time.
1278
+ *
1279
+ * @since 3.4.0
1280
+ * @experimental
1281
+ * @category delay fn
1282
+ */
1283
+ const delayWithMaxElapsed = exports.delayWithMaxElapsed = /*#__PURE__*/(0, _Function.dual)(2, (self, max) => (attempt, elapsed) => elapsed < max ? self(attempt, elapsed) : Option.none());
1284
+ /**
1285
+ * Transform a `DelayFn` to one that will stop repeating after the specified
1286
+ * number of attempts.
1287
+ *
1288
+ * @since 3.4.0
1289
+ * @experimental
1290
+ * @category delay fn
1291
+ */
1292
+ const delayWithRecurs = exports.delayWithRecurs = /*#__PURE__*/(0, _Function.dual)(2, (self, n) => (attempt, elapsed) => Option.filter(self(attempt, elapsed), () => attempt <= n));
1293
+ // ----------------------------------------------------------------------------
1294
+ // error handling
1295
+ // ----------------------------------------------------------------------------
1296
+ /**
1297
+ * Catch the full `Failure` object of the given `Micro` effect, allowing you to
1298
+ * recover from any kind of failure.
1299
+ *
1300
+ * @since 3.4.0
1301
+ * @experimental
1302
+ * @category error handling
1303
+ */
1304
+ const catchFailure = exports.catchFailure = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => catchFailureIf(self, _Function.constTrue, f));
1305
+ /**
1306
+ * Selectively catch a `Failure` object of the given `Micro` effect,
1307
+ * using the provided predicate to determine if the failure should be caught.
1308
+ *
1309
+ * @since 3.4.0
1310
+ * @experimental
1311
+ * @category error handling
1312
+ */
1313
+ const catchFailureIf = exports.catchFailureIf = /*#__PURE__*/(0, _Function.dual)(3, (self, refinement, f) => make(function (env, onResult) {
1314
+ self[runSymbol](env, function (result) {
1315
+ if (result._tag === "Right" || !refinement(result.left)) {
1316
+ return onResult(result);
1317
+ }
1318
+ f(result.left)[runSymbol](env, onResult);
1319
+ });
1320
+ }));
1321
+ /**
1322
+ * Catch the error of the given `Micro` effect, allowing you to recover from it.
1323
+ *
1324
+ * It only catches expected (`FailureExpected`) errors.
1325
+ *
1326
+ * @since 3.4.0
1327
+ * @experimental
1328
+ * @category error handling
1329
+ */
1330
+ const catchExpected = exports.catchExpected = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => catchFailureIf(self, failureIsExpected, failure => f(failure.error)));
1331
+ /**
1332
+ * Catch any unexpected errors of the given `Micro` effect, allowing you to recover from them.
1333
+ *
1334
+ * @since 3.4.0
1335
+ * @experimental
1336
+ * @category error handling
1337
+ */
1338
+ const catchUnexpected = exports.catchUnexpected = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => catchFailureIf(self, failureIsUnexpected, failure => f(failure.defect)));
1339
+ /**
1340
+ * Perform a side effect using the full `Failure` object of the given `Micro`.
1341
+ *
1342
+ * @since 3.4.0
1343
+ * @experimental
1344
+ * @category error handling
1345
+ */
1346
+ const tapFailure = exports.tapFailure = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => tapFailureIf(self, _Function.constTrue, f));
1347
+ /**
1348
+ * Perform a side effect using if a `Failure` object matches the specified
1349
+ * predicate.
1350
+ *
1351
+ * @since 3.4.0
1352
+ * @experimental
1353
+ * @category error handling
1354
+ */
1355
+ const tapFailureIf = exports.tapFailureIf = /*#__PURE__*/(0, _Function.dual)(3, (self, refinement, f) => catchFailureIf(self, refinement, failure => andThen(f(failure), failWith(failure))));
1356
+ /**
1357
+ * Perform a side effect from expected errors of the given `Micro`.
1358
+ *
1359
+ * @since 3.4.0
1360
+ * @experimental
1361
+ * @category error handling
1362
+ */
1363
+ const tapExpected = exports.tapExpected = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => tapFailureIf(self, failureIsExpected, failure => f(failure.error)));
1364
+ /**
1365
+ * Perform a side effect from unexpected errors of the given `Micro`.
1366
+ *
1367
+ * @since 3.4.0
1368
+ * @experimental
1369
+ * @category error handling
1370
+ */
1371
+ const tapUnexpected = exports.tapUnexpected = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => tapFailureIf(self, failureIsUnexpected, failure => f(failure.defect)));
1372
+ /**
1373
+ * Catch any expected errors that match the specified predicate.
1374
+ *
1375
+ * @since 3.4.0
1376
+ * @experimental
1377
+ * @category error handling
1378
+ */
1379
+ const catchIf = exports.catchIf = /*#__PURE__*/(0, _Function.dual)(3, (self, pred, f) => catchFailureIf(self, f => failureIsExpected(f) && pred(f.error), failure => f(failure.error)));
1380
+ /**
1381
+ * Recovers from the specified tagged error.
1382
+ *
1383
+ * @since 3.4.0
1384
+ * @experimental
1385
+ * @category error handling
1386
+ */
1387
+ const catchTag = exports.catchTag = /*#__PURE__*/(0, _Function.dual)(3, (self, k, f) => catchIf(self, error => (0, _Predicate.isTagged)(error, k), f));
1388
+ /**
1389
+ * Transform the full `Failure` object of the given `Micro` effect.
1390
+ *
1391
+ * @since 3.4.0
1392
+ * @experimental
1393
+ * @category error handling
1394
+ */
1395
+ const mapFailure = exports.mapFailure = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => catchFailure(self, failure => failWith(f(failure))));
1396
+ /**
1397
+ * Transform any expected errors of the given `Micro` effect.
1398
+ *
1399
+ * @since 3.4.0
1400
+ * @experimental
1401
+ * @category error handling
1402
+ */
1403
+ const mapError = exports.mapError = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => catchExpected(self, error => fail(f(error))));
1404
+ /**
1405
+ * Elevate any expected errors of the given `Micro` effect to unexpected errors,
1406
+ * resulting in an error type of `never`.
1407
+ *
1408
+ * @since 3.4.0
1409
+ * @experimental
1410
+ * @category error handling
1411
+ */
1412
+ const orDie = self => catchExpected(self, die);
1413
+ /**
1414
+ * Recover from all errors by succeeding with the given value.
1415
+ *
1416
+ * @since 3.4.0
1417
+ * @experimental
1418
+ * @category error handling
1419
+ */
1420
+ exports.orDie = orDie;
1421
+ const orElseSucceed = exports.orElseSucceed = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => catchExpected(self, _ => sync(f)));
1422
+ /**
1423
+ * Ignore any expected errors of the given `Micro` effect, returning `void`.
1424
+ *
1425
+ * @since 3.4.0
1426
+ * @experimental
1427
+ * @category error handling
1428
+ */
1429
+ const ignore = self => matchMicro(self, {
1430
+ onFailure: _ => void_,
1431
+ onSuccess: _ => void_
1432
+ });
1433
+ /**
1434
+ * Ignore any expected errors of the given `Micro` effect, returning `void`.
1435
+ *
1436
+ * @since 3.4.0
1437
+ * @experimental
1438
+ * @category error handling
1439
+ */
1440
+ exports.ignore = ignore;
1441
+ const ignoreLogged = self => matchMicro(self, {
1442
+ onFailure: failure => sync(() => console.error(failure)),
1443
+ onSuccess: _ => void_
1444
+ });
1445
+ /**
1446
+ * Replace the success value of the given `Micro` effect with an `Option`,
1447
+ * wrapping the success value in `Some` and returning `None` if the effect fails
1448
+ * with an expected error.
1449
+ *
1450
+ * @since 3.4.0
1451
+ * @experimental
1452
+ * @category error handling
1453
+ */
1454
+ exports.ignoreLogged = ignoreLogged;
1455
+ const option = self => match(self, {
1456
+ onFailure: _ => Option.none(),
1457
+ onSuccess: Option.some
1458
+ });
1459
+ /**
1460
+ * Replace the success value of the given `Micro` effect with an `Either`,
1461
+ * wrapping the success value in `Right` and wrapping any expected errors with
1462
+ * a `Left`.
1463
+ *
1464
+ * @since 3.4.0
1465
+ * @experimental
1466
+ * @category error handling
1467
+ */
1468
+ exports.option = option;
1469
+ const either = self => match(self, {
1470
+ onFailure: Either.left,
1471
+ onSuccess: Either.right
1472
+ });
1473
+ /**
1474
+ * Retry the given `Micro` effect using the provided options.
1475
+ *
1476
+ * @since 3.4.0
1477
+ * @experimental
1478
+ * @category error handling
1479
+ */
1480
+ exports.either = either;
1481
+ const retry = exports.retry = /*#__PURE__*/(0, _Function.dual)(args => isMicro(args[0]), (self, options) => repeatResult(self, {
1482
+ ...options,
1483
+ while: result => result._tag === "Left" && result.left._tag === "Expected" && (options?.while === undefined || options.while(result.left.error))
1484
+ }));
1485
+ /**
1486
+ * Add a stack trace to any failures that occur in the effect. The trace will be
1487
+ * added to the `traces` field of the `Failure` object.
1488
+ *
1489
+ * @since 3.4.0
1490
+ * @experimental
1491
+ * @category error handling
1492
+ */
1493
+ const withTrace = function () {
1494
+ const prevLimit = globalThis.Error.stackTraceLimit;
1495
+ globalThis.Error.stackTraceLimit = 2;
1496
+ const error = new globalThis.Error();
1497
+ globalThis.Error.stackTraceLimit = prevLimit;
1498
+ function generate(name, failure) {
1499
+ const stack = error.stack;
1500
+ if (!stack) {
1501
+ return failure;
1502
+ }
1503
+ const line = stack.split("\n")[2]?.trim().replace(/^at /, "");
1504
+ if (!line) {
1505
+ return failure;
1506
+ }
1507
+ const lineMatch = line.match(/\((.*)\)$/);
1508
+ return failureWithTrace(failure, `at ${name} (${lineMatch ? lineMatch[1] : line})`);
1509
+ }
1510
+ const f = name => self => unsafeMakeOptions(function (env, onResult) {
1511
+ self[runSymbol](env, function (result) {
1512
+ onResult(result._tag === "Left" ? Either.left(generate(name, result.left)) : result);
1513
+ });
1514
+ }, false);
1515
+ if (arguments.length === 2) {
1516
+ return f(arguments[1])(arguments[0]);
1517
+ }
1518
+ return f(arguments[0]);
1519
+ };
1520
+ // ----------------------------------------------------------------------------
1521
+ // pattern matching
1522
+ // ----------------------------------------------------------------------------
1523
+ /**
1524
+ * @since 3.4.0
1525
+ * @experimental
1526
+ * @category pattern matching
1527
+ */
1528
+ exports.withTrace = withTrace;
1529
+ const matchFailureMicro = exports.matchFailureMicro = /*#__PURE__*/(0, _Function.dual)(2, (self, options) => make(function (env, onResult) {
1530
+ self[runSymbol](env, function (result) {
1531
+ try {
1532
+ const next = result._tag === "Left" ? options.onFailure(result.left) : options.onSuccess(result.right);
1533
+ next[runSymbol](env, onResult);
1534
+ } catch (err) {
1535
+ onResult(ResultFailUnexpected(err));
1536
+ }
1537
+ });
1538
+ }));
1539
+ /**
1540
+ * @since 3.4.0
1541
+ * @experimental
1542
+ * @category pattern matching
1543
+ */
1544
+ const matchFailure = exports.matchFailure = /*#__PURE__*/(0, _Function.dual)(2, (self, options) => matchFailureMicro(self, {
1545
+ onFailure: failure => sync(() => options.onFailure(failure)),
1546
+ onSuccess: value => sync(() => options.onSuccess(value))
1547
+ }));
1548
+ /**
1549
+ * @since 3.4.0
1550
+ * @experimental
1551
+ * @category pattern matching
1552
+ */
1553
+ const matchMicro = exports.matchMicro = /*#__PURE__*/(0, _Function.dual)(2, (self, options) => matchFailureMicro(self, {
1554
+ onFailure: failure => failure._tag === "Expected" ? options.onFailure(failure.error) : failWith(failure),
1555
+ onSuccess: options.onSuccess
1556
+ }));
1557
+ /**
1558
+ * @since 3.4.0
1559
+ * @experimental
1560
+ * @category pattern matching
1561
+ */
1562
+ const match = exports.match = /*#__PURE__*/(0, _Function.dual)(2, (self, options) => matchMicro(self, {
1563
+ onFailure: error => sync(() => options.onFailure(error)),
1564
+ onSuccess: value => sync(() => options.onSuccess(value))
1565
+ }));
1566
+ // ----------------------------------------------------------------------------
1567
+ // delays & timeouts
1568
+ // ----------------------------------------------------------------------------
1569
+ /**
1570
+ * Create a `Micro` effect that will sleep for the specified duration.
1571
+ *
1572
+ * @since 3.4.0
1573
+ * @experimental
1574
+ * @category delays & timeouts
1575
+ */
1576
+ const sleep = millis => async(function (resume) {
1577
+ const timeout = setTimeout(function () {
1578
+ resume(void_);
1579
+ }, millis);
1580
+ return sync(() => {
1581
+ return clearTimeout(timeout);
1582
+ });
1583
+ });
1584
+ /**
1585
+ * Returns an effect that will delay the execution of this effect by the
1586
+ * specified duration.
1587
+ *
1588
+ * @since 3.4.0
1589
+ * @experimental
1590
+ * @category delays & timeouts
1591
+ */
1592
+ exports.sleep = sleep;
1593
+ const delay = exports.delay = /*#__PURE__*/(0, _Function.dual)(2, (self, millis) => andThen(sleep(millis), self));
1594
+ /**
1595
+ * Returns an effect that will timeout this effect, that will execute the
1596
+ * fallback effect if the timeout elapses before the effect has produced a value.
1597
+ *
1598
+ * If the timeout elapses, the running effect will be safely interrupted.
1599
+ *
1600
+ * @since 3.4.0
1601
+ * @experimental
1602
+ * @category delays & timeouts
1603
+ */
1604
+ const timeoutOrElse = exports.timeoutOrElse = /*#__PURE__*/(0, _Function.dual)(2, (self, options) => raceFirst(self, andThen(interruptible(sleep(options.duration)), options.onTimeout)));
1605
+ /**
1606
+ * Returns an effect that will timeout this effect, succeeding with a `None`
1607
+ * if the timeout elapses before the effect has produced a value; and `Some` of
1608
+ * the produced value otherwise.
1609
+ *
1610
+ * If the timeout elapses, the running effect will be safely interrupted.
1611
+ *
1612
+ * @since 3.4.0
1613
+ * @experimental
1614
+ * @category delays & timeouts
1615
+ */
1616
+ const timeout = exports.timeout = /*#__PURE__*/(0, _Function.dual)(2, (self, millis) => raceFirst(asSome(self), as(interruptible(sleep(millis)), Option.none())));
1617
+ // ----------------------------------------------------------------------------
1618
+ // resources & finalization
1619
+ // ----------------------------------------------------------------------------
1620
+ /**
1621
+ * @since 3.4.0
1622
+ * @experimental
1623
+ * @category resources & finalization
1624
+ */
1625
+ const MicroScopeTypeId = exports.MicroScopeTypeId = /*#__PURE__*/Symbol.for("effect/Micro/MicroScope");
1626
+ /**
1627
+ * @since 3.4.0
1628
+ * @experimental
1629
+ * @category resources & finalization
1630
+ */
1631
+ const MicroScope = exports.MicroScope = /*#__PURE__*/Context.GenericTag("effect/Micro/MicroScope");
1632
+ class ScopeImpl {
1633
+ [MicroScopeTypeId];
1634
+ state = {
1635
+ _tag: "Open",
1636
+ finalizers: new Set()
1637
+ };
1638
+ constructor() {
1639
+ this[MicroScopeTypeId] = MicroScopeTypeId;
1640
+ }
1641
+ unsafeAddFinalizer(finalizer) {
1642
+ if (this.state._tag === "Open") {
1643
+ this.state.finalizers.add(finalizer);
1644
+ }
1645
+ }
1646
+ addFinalizer(finalizer) {
1647
+ return suspend(() => {
1648
+ if (this.state._tag === "Open") {
1649
+ this.state.finalizers.add(finalizer);
1650
+ return void_;
1651
+ }
1652
+ return finalizer(this.state.result);
1653
+ });
1654
+ }
1655
+ unsafeRemoveFinalizer(finalizer) {
1656
+ if (this.state._tag === "Open") {
1657
+ this.state.finalizers.delete(finalizer);
1658
+ }
1659
+ }
1660
+ close(result) {
1661
+ return suspend(() => {
1662
+ if (this.state._tag === "Open") {
1663
+ const finalizers = Array.from(this.state.finalizers).reverse();
1664
+ this.state = {
1665
+ _tag: "Closed",
1666
+ result
1667
+ };
1668
+ return flatMap(forEach(finalizers, finalizer => asResult(finalizer(result))), results => asVoid(fromResult(Either.all(results))));
1669
+ }
1670
+ return void_;
1671
+ });
1672
+ }
1673
+ get fork() {
1674
+ return sync(() => {
1675
+ const newScope = new ScopeImpl();
1676
+ if (this.state._tag === "Closed") {
1677
+ newScope.state = this.state;
1678
+ return newScope;
1679
+ }
1680
+ function fin(result) {
1681
+ return newScope.close(result);
1682
+ }
1683
+ this.state.finalizers.add(fin);
1684
+ newScope.unsafeAddFinalizer(_ => sync(() => this.unsafeRemoveFinalizer(fin)));
1685
+ return newScope;
1686
+ });
1687
+ }
1688
+ }
1689
+ /**
1690
+ * @since 3.4.0
1691
+ * @experimental
1692
+ * @category resources & finalization
1693
+ */
1694
+ const scopeMake = exports.scopeMake = /*#__PURE__*/sync(() => new ScopeImpl());
1695
+ /**
1696
+ * @since 3.4.0
1697
+ * @experimental
1698
+ * @category resources & finalization
1699
+ */
1700
+ const scopeUnsafeMake = () => new ScopeImpl();
1701
+ /**
1702
+ * Access the current `MicroScope`.
1703
+ *
1704
+ * @since 3.4.0
1705
+ * @experimental
1706
+ * @category resources & finalization
1707
+ */
1708
+ exports.scopeUnsafeMake = scopeUnsafeMake;
1709
+ const scope = exports.scope = /*#__PURE__*/service(MicroScope);
1710
+ /**
1711
+ * Provide a `MicroScope` to an effect.
1712
+ *
1713
+ * @since 3.4.0
1714
+ * @experimental
1715
+ * @category resources & finalization
1716
+ */
1717
+ const provideScope = exports.provideScope = /*#__PURE__*/(0, _Function.dual)(2, (self, scope) => provideService(self, MicroScope, scope));
1718
+ /**
1719
+ * Provide a `MicroScope` to the given effect, closing it after the effect has
1720
+ * finished executing.
1721
+ *
1722
+ * @since 3.4.0
1723
+ * @experimental
1724
+ * @category resources & finalization
1725
+ */
1726
+ const scoped = self => suspend(function () {
1727
+ const scope = new ScopeImpl();
1728
+ return onResult(provideService(self, MicroScope, scope), result => scope.close(result));
1729
+ });
1730
+ /**
1731
+ * Create a resource with a cleanup `Micro` effect, ensuring the cleanup is
1732
+ * executed when the `MicroScope` is closed.
1733
+ *
1734
+ * @since 3.4.0
1735
+ * @experimental
1736
+ * @category resources & finalization
1737
+ */
1738
+ exports.scoped = scoped;
1739
+ const acquireRelease = (acquire, release) => uninterruptible(flatMap(scope, scope => tap(acquire, a => scope.addFinalizer(result => release(a, result)))));
1740
+ /**
1741
+ * Add a finalizer to the current `MicroScope`.
1742
+ *
1743
+ * @since 3.4.0
1744
+ * @experimental
1745
+ * @category resources & finalization
1746
+ */
1747
+ exports.acquireRelease = acquireRelease;
1748
+ const addFinalizer = finalizer => flatMap(scope, scope => scope.addFinalizer(finalizer));
1749
+ /**
1750
+ * When the `Micro` effect is completed, run the given finalizer effect with the
1751
+ * `Result` of the executed effect.
1752
+ *
1753
+ * @since 3.4.0
1754
+ * @experimental
1755
+ * @category resources & finalization
1756
+ */
1757
+ exports.addFinalizer = addFinalizer;
1758
+ const onResult = exports.onResult = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => onResultIf(self, _Function.constTrue, f));
1759
+ /**
1760
+ * When the `Micro` effect is completed, run the given finalizer effect if it
1761
+ * matches the specified predicate.
1762
+ *
1763
+ * @since 3.4.0
1764
+ * @experimental
1765
+ * @category resources & finalization
1766
+ */
1767
+ const onResultIf = exports.onResultIf = /*#__PURE__*/(0, _Function.dual)(3, (self, refinement, f) => uninterruptibleMask(restore => make(function (env, onResult) {
1768
+ restore(self)[runSymbol](env, function (result) {
1769
+ if (!refinement(result)) {
1770
+ return onResult(result);
1771
+ }
1772
+ f(result)[runSymbol](env, function (finalizerResult) {
1773
+ if (finalizerResult._tag === "Left") {
1774
+ return onResult(finalizerResult);
1775
+ }
1776
+ onResult(result);
1777
+ });
1778
+ });
1779
+ })));
1780
+ /**
1781
+ * Regardless of the result of the this `Micro` effect, run the finalizer effect.
1782
+ *
1783
+ * @since 3.4.0
1784
+ * @experimental
1785
+ * @category resources & finalization
1786
+ */
1787
+ const ensuring = exports.ensuring = /*#__PURE__*/(0, _Function.dual)(2, (self, finalizer) => onResult(self, _ => finalizer));
1788
+ /**
1789
+ * When the `Micro` effect fails, run the given finalizer effect with the
1790
+ * `Failure` of the executed effect.
1791
+ *
1792
+ * @since 3.4.0
1793
+ * @experimental
1794
+ * @category resources & finalization
1795
+ */
1796
+ const onFailure = exports.onFailure = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => onResultIf(self, resultIsFailure, result => f(result.left)));
1797
+ /**
1798
+ * If this `Micro` effect is aborted, run the finalizer effect.
1799
+ *
1800
+ * @since 3.4.0
1801
+ * @experimental
1802
+ * @category resources & finalization
1803
+ */
1804
+ const onAbort = exports.onAbort = /*#__PURE__*/(0, _Function.dual)(2, (self, finalizer) => onResultIf(self, resultIsAborted, _ => finalizer));
1805
+ /**
1806
+ * Acquire a resource, use it, and then release the resource when the `use`
1807
+ * effect has completed.
1808
+ *
1809
+ * @since 3.4.0
1810
+ * @experimental
1811
+ * @category resources & finalization
1812
+ */
1813
+ const acquireUseRelease = (acquire, use, release) => uninterruptibleMask(restore => flatMap(acquire, a => flatMap(asResult(restore(use(a))), result => andThen(release(a, result), fromResult(result)))));
1814
+ // ----------------------------------------------------------------------------
1815
+ // interruption
1816
+ // ----------------------------------------------------------------------------
1817
+ /**
1818
+ * Abort the current `Micro` effect.
1819
+ *
1820
+ * @since 3.4.0
1821
+ * @experimental
1822
+ * @category interruption
1823
+ */
1824
+ exports.acquireUseRelease = acquireUseRelease;
1825
+ const abort = exports.abort = /*#__PURE__*/make(function (env, onResult) {
1826
+ const controller = envGet(env, currentAbortController);
1827
+ controller.abort();
1828
+ onResult(ResultAborted);
1829
+ });
1830
+ /**
1831
+ * Wrap the given `Micro` effect in an uninterruptible region, preventing the
1832
+ * effect from being aborted.
1833
+ *
1834
+ * @since 3.4.0
1835
+ * @experimental
1836
+ * @category interruption
1837
+ */
1838
+ const uninterruptible = self => unsafeMakeOptions(function (env, onResult) {
1839
+ const nextEnv = envMutate(env, function (env) {
1840
+ env[currentInterruptible.key] = false;
1841
+ env[currentAbortSignal.key] = new AbortController().signal;
1842
+ return env;
1843
+ });
1844
+ self[runSymbol](nextEnv, onResult);
1845
+ }, false);
1846
+ /**
1847
+ * Wrap the given `Micro` effect in an uninterruptible region, preventing the
1848
+ * effect from being aborted.
1849
+ *
1850
+ * You can use the `restore` function to restore a `Micro` effect to the
1851
+ * interruptibility state before the `uninterruptibleMask` was applied.
1852
+ *
1853
+ * @since 3.4.0
1854
+ * @experimental
1855
+ * @category interruption
1856
+ * @example
1857
+ * import * as Micro from "effect/Micro"
1858
+ *
1859
+ * Micro.uninterruptibleMask((restore) =>
1860
+ * Micro.sleep(1000).pipe( // uninterruptible
1861
+ * Micro.andThen(restore(Micro.sleep(1000))) // interruptible
1862
+ * )
1863
+ * )
1864
+ */
1865
+ exports.uninterruptible = uninterruptible;
1866
+ const uninterruptibleMask = f => unsafeMakeOptions((env, onResult) => {
1867
+ const isInterruptible = envGet(env, currentInterruptible);
1868
+ const effect = isInterruptible ? f(interruptible) : f(_Function.identity);
1869
+ const nextEnv = isInterruptible ? envMutate(env, function (env) {
1870
+ env[currentInterruptible.key] = false;
1871
+ env[currentAbortSignal.key] = new AbortController().signal;
1872
+ return env;
1873
+ }) : env;
1874
+ effect[runSymbol](nextEnv, onResult);
1875
+ }, false);
1876
+ /**
1877
+ * Wrap the given `Micro` effect in an interruptible region, allowing the effect
1878
+ * to be aborted.
1879
+ *
1880
+ * @since 3.4.0
1881
+ * @experimental
1882
+ * @category interruption
1883
+ */
1884
+ exports.uninterruptibleMask = uninterruptibleMask;
1885
+ const interruptible = self => make((env, onResult) => {
1886
+ const isInterruptible = envGet(env, currentInterruptible);
1887
+ let newEnv = env;
1888
+ if (!isInterruptible) {
1889
+ const controller = envGet(env, currentAbortController);
1890
+ newEnv = envMutate(env, function (env) {
1891
+ env[currentInterruptible.key] = true;
1892
+ env[currentAbortSignal.key] = controller.signal;
1893
+ return env;
1894
+ });
1895
+ }
1896
+ self[runSymbol](newEnv, onResult);
1897
+ });
1898
+ /**
1899
+ * Runs all the provided effects in sequence respecting the structure provided in input.
1900
+ *
1901
+ * Supports multiple arguments, a single argument tuple / array or record / struct.
1902
+ *
1903
+ * @since 3.4.0
1904
+ * @experimental
1905
+ * @category collecting & elements
1906
+ */
1907
+ exports.interruptible = interruptible;
1908
+ const all = (arg, options) => {
1909
+ if (Array.isArray(arg) || (0, _Predicate.isIterable)(arg)) {
1910
+ return forEach(arg, _Function.identity, options);
1911
+ } else if (options?.discard) {
1912
+ return forEach(Object.values(arg), _Function.identity, options);
1913
+ }
1914
+ return suspend(() => {
1915
+ const out = {};
1916
+ return as(forEach(Object.entries(arg), ([key, effect]) => map(effect, value => {
1917
+ out[key] = value;
1918
+ }), {
1919
+ discard: true,
1920
+ concurrency: options?.concurrency
1921
+ }), out);
1922
+ });
1923
+ };
1924
+ /**
1925
+ * For each element of the provided iterable, run the effect and collect the results.
1926
+ *
1927
+ * If the `discard` option is set to `true`, the results will be discarded and
1928
+ * the effect will return `void`.
1929
+ *
1930
+ * The `concurrency` option can be set to control how many effects are run in
1931
+ * parallel. By default, the effects are run sequentially.
1932
+ *
1933
+ * @since 3.4.0
1934
+ * @experimental
1935
+ * @category collecting & elements
1936
+ */
1937
+ exports.all = all;
1938
+ const forEach = (iterable, f, options) => make(function (env, onResult) {
1939
+ const concurrencyOption = options?.concurrency === "inherit" ? envGet(env, currentConcurrency) : options?.concurrency ?? 1;
1940
+ const concurrency = concurrencyOption === "unbounded" ? Number.POSITIVE_INFINITY : Math.max(1, concurrencyOption);
1941
+ // abort
1942
+ const [envWithSignal, onAbort] = forkSignal(env);
1943
+ // iterate
1944
+ let failure = undefined;
1945
+ const items = Array.from(iterable);
1946
+ let length = items.length;
1947
+ const out = options?.discard ? undefined : new Array(length);
1948
+ let index = 0;
1949
+ let inProgress = 0;
1950
+ let doneCount = 0;
1951
+ let pumping = false;
1952
+ function pump() {
1953
+ pumping = true;
1954
+ while (inProgress < concurrency && index < length) {
1955
+ const currentIndex = index;
1956
+ const item = items[currentIndex];
1957
+ index++;
1958
+ inProgress++;
1959
+ try {
1960
+ f(item, currentIndex)[runSymbol](envWithSignal, function (result) {
1961
+ if (result._tag === "Left") {
1962
+ if (failure === undefined) {
1963
+ failure = result;
1964
+ length = index;
1965
+ onAbort();
1966
+ }
1967
+ } else if (out !== undefined) {
1968
+ out[currentIndex] = result.right;
1969
+ }
1970
+ doneCount++;
1971
+ inProgress--;
1972
+ if (doneCount === length) {
1973
+ onResult(failure ?? Either.right(out));
1974
+ } else if (!pumping && inProgress < concurrency) {
1975
+ pump();
1976
+ }
1977
+ });
1978
+ } catch (err) {
1979
+ failure = ResultFailUnexpected(err);
1980
+ length = index;
1981
+ onAbort();
1982
+ }
1983
+ }
1984
+ pumping = false;
1985
+ }
1986
+ pump();
1987
+ });
1988
+ /**
1989
+ * Effectfully filter the elements of the provided iterable.
1990
+ *
1991
+ * Use the `concurrency` option to control how many elements are processed in parallel.
1992
+ *
1993
+ * @since 3.4.0
1994
+ * @experimental
1995
+ * @category collecting & elements
1996
+ */
1997
+ exports.forEach = forEach;
1998
+ const filter = (iterable, f, options) => filterMap(iterable, a => map(f(a), pass => {
1999
+ pass = options?.negate ? !pass : pass;
2000
+ return pass ? Option.some(a) : Option.none();
2001
+ }));
2002
+ /**
2003
+ * Effectfully filter the elements of the provided iterable.
2004
+ *
2005
+ * Use the `concurrency` option to control how many elements are processed in parallel.
2006
+ *
2007
+ * @since 3.4.0
2008
+ * @experimental
2009
+ * @category collecting & elements
2010
+ */
2011
+ exports.filter = filter;
2012
+ const filterMap = (iterable, f, options) => suspend(() => {
2013
+ const out = [];
2014
+ return as(forEach(iterable, a => map(f(a), o => {
2015
+ if (o._tag === "Some") {
2016
+ out.push(o.value);
2017
+ }
2018
+ }), {
2019
+ discard: true,
2020
+ concurrency: options?.concurrency
2021
+ }), out);
2022
+ });
2023
+ // ----------------------------------------------------------------------------
2024
+ // do notation
2025
+ // ----------------------------------------------------------------------------
2026
+ /**
2027
+ * Start a do notation block.
2028
+ *
2029
+ * @since 3.4.0
2030
+ * @experimental
2031
+ * @category do notation
2032
+ */
2033
+ exports.filterMap = filterMap;
2034
+ const Do = exports.Do = /*#__PURE__*/succeed({});
2035
+ /**
2036
+ * Bind the success value of this `Micro` effect to the provided name.
2037
+ *
2038
+ * @since 3.4.0
2039
+ * @experimental
2040
+ * @category do notation
2041
+ */
2042
+ const bindTo = exports.bindTo = /*#__PURE__*/(0, _Function.dual)(2, (self, name) => map(self, f => ({
2043
+ [name]: f
2044
+ })));
2045
+ /**
2046
+ * Bind the success value of this `Micro` effect to the provided name.
2047
+ *
2048
+ * @since 3.4.0
2049
+ * @experimental
2050
+ * @category do notation
2051
+ */
2052
+ const bind = exports.bind = /*#__PURE__*/(0, _Function.dual)(3, (self, name, f) => flatMap(self, a => map(f(a), b => ({
2053
+ ...a,
2054
+ [name]: b
2055
+ }))));
2056
+ const let_ = exports.let = /*#__PURE__*/(0, _Function.dual)(3, (self, name, f) => map(self, a => ({
2057
+ ...a,
2058
+ [name]: f(a)
2059
+ })));
2060
+ // ----------------------------------------------------------------------------
2061
+ // handle & forking
2062
+ // ----------------------------------------------------------------------------
2063
+ /**
2064
+ * @since 3.4.0
2065
+ * @experimental
2066
+ * @category handle & forking
2067
+ */
2068
+ const HandleTypeId = exports.HandleTypeId = /*#__PURE__*/Symbol.for("effect/Micro/Handle");
2069
+ /**
2070
+ * @since 3.4.0
2071
+ * @experimental
2072
+ * @category handle & forking
2073
+ */
2074
+ const isHandle = u => typeof u === "object" && u !== null && HandleTypeId in u;
2075
+ exports.isHandle = isHandle;
2076
+ class HandleImpl {
2077
+ parentSignal;
2078
+ [HandleTypeId];
2079
+ observers = new Set();
2080
+ _result = undefined;
2081
+ _controller;
2082
+ isRoot;
2083
+ constructor(parentSignal, controller) {
2084
+ this.parentSignal = parentSignal;
2085
+ this[HandleTypeId] = HandleTypeId;
2086
+ this.isRoot = controller !== undefined;
2087
+ this._controller = controller ?? new AbortController();
2088
+ if (!this.isRoot) {
2089
+ parentSignal.addEventListener("abort", this.unsafeAbort);
2090
+ }
2091
+ }
2092
+ unsafePoll() {
2093
+ return this._result ?? null;
2094
+ }
2095
+ unsafeAbort = () => {
2096
+ this._controller.abort();
2097
+ };
2098
+ emit(result) {
2099
+ if (this._result) {
2100
+ return;
2101
+ }
2102
+ this._result = result;
2103
+ if (!this.isRoot) {
2104
+ this.parentSignal.removeEventListener("abort", this.unsafeAbort);
2105
+ }
2106
+ this.observers.forEach(observer => observer(result));
2107
+ this.observers.clear();
2108
+ }
2109
+ addObserver(observer) {
2110
+ if (this._result) {
2111
+ return observer(this._result);
2112
+ }
2113
+ this.observers.add(observer);
2114
+ }
2115
+ removeObserver(observer) {
2116
+ this.observers.delete(observer);
2117
+ }
2118
+ get await() {
2119
+ return suspend(() => {
2120
+ if (this._result) {
2121
+ return succeed(this._result);
2122
+ }
2123
+ return async(resume => {
2124
+ function observer(result) {
2125
+ resume(succeed(result));
2126
+ }
2127
+ this.addObserver(observer);
2128
+ return sync(() => {
2129
+ this.removeObserver(observer);
2130
+ });
2131
+ });
2132
+ });
2133
+ }
2134
+ get join() {
2135
+ return flatMap(this.await, fromResult);
2136
+ }
2137
+ get abort() {
2138
+ return suspend(() => {
2139
+ this.unsafeAbort();
2140
+ return this.await;
2141
+ });
2142
+ }
2143
+ }
2144
+ /**
2145
+ * Run the `Micro` effect in a new `Handle` that can be awaited, joined, or
2146
+ * aborted.
2147
+ *
2148
+ * When the parent `Micro` finishes, this `Micro` will be aborted.
2149
+ *
2150
+ * @since 3.4.0
2151
+ * @experimental
2152
+ * @category handle & forking
2153
+ */
2154
+ const fork = self => make(function (env, onResult) {
2155
+ const signal = envGet(env, currentAbortSignal);
2156
+ const handle = new HandleImpl(signal);
2157
+ const nextEnv = envMutate(env, map => {
2158
+ map[currentAbortController.key] = handle._controller;
2159
+ map[currentAbortSignal.key] = handle._controller.signal;
2160
+ return map;
2161
+ });
2162
+ yieldAdd(() => {
2163
+ self[runSymbol](nextEnv, result => {
2164
+ handle.emit(result);
2165
+ });
2166
+ });
2167
+ onResult(Either.right(handle));
2168
+ });
2169
+ /**
2170
+ * Run the `Micro` effect in a new `Handle` that can be awaited, joined, or
2171
+ * aborted.
2172
+ *
2173
+ * It will not be aborted when the parent `Micro` finishes.
2174
+ *
2175
+ * @since 3.4.0
2176
+ * @experimental
2177
+ * @category handle & forking
2178
+ */
2179
+ exports.fork = fork;
2180
+ const forkDaemon = self => make(function (env, onResult) {
2181
+ const controller = new AbortController();
2182
+ const handle = new HandleImpl(controller.signal, controller);
2183
+ const nextEnv = envMutate(env, map => {
2184
+ map[currentAbortController.key] = controller;
2185
+ map[currentAbortSignal.key] = controller.signal;
2186
+ return map;
2187
+ });
2188
+ yieldAdd(() => {
2189
+ self[runSymbol](nextEnv, result => {
2190
+ handle.emit(result);
2191
+ });
2192
+ });
2193
+ onResult(Either.right(handle));
2194
+ });
2195
+ /**
2196
+ * Run the `Micro` effect in a new `Handle` that can be awaited, joined, or
2197
+ * aborted.
2198
+ *
2199
+ * The lifetime of the handle will be attached to the provided `MicroScope`.
2200
+ *
2201
+ * @since 3.4.0
2202
+ * @experimental
2203
+ * @category handle & forking
2204
+ */
2205
+ exports.forkDaemon = forkDaemon;
2206
+ const forkIn = exports.forkIn = /*#__PURE__*/(0, _Function.dual)(2, (self, scope) => uninterruptibleMask(restore => flatMap(scope.fork, scope => tap(restore(forkDaemon(onResult(self, result => scope.close(result)))), fiber => scope.addFinalizer(_ => asVoid(fiber.abort))))));
2207
+ /**
2208
+ * Run the `Micro` effect in a new `Handle` that can be awaited, joined, or
2209
+ * aborted.
2210
+ *
2211
+ * The lifetime of the handle will be attached to the current `MicroScope`.
2212
+ *
2213
+ * @since 3.4.0
2214
+ * @experimental
2215
+ * @category handle & forking
2216
+ */
2217
+ const forkScoped = self => flatMap(scope, scope => forkIn(self, scope));
2218
+ // ----------------------------------------------------------------------------
2219
+ // execution
2220
+ // ----------------------------------------------------------------------------
2221
+ /**
2222
+ * Execute the `Micro` effect and return a `Handle` that can be awaited, joined,
2223
+ * or aborted.
2224
+ *
2225
+ * You can listen for the result by adding an observer using the handle's
2226
+ * `addObserver` method.
2227
+ *
2228
+ * @since 3.4.0
2229
+ * @experimental
2230
+ * @category execution
2231
+ * @example
2232
+ * import * as Micro from "effect/Micro"
2233
+ *
2234
+ * const handle = Micro.succeed(42).pipe(
2235
+ * Micro.delay(1000),
2236
+ * Micro.runFork
2237
+ * )
2238
+ *
2239
+ * handle.addObserver((result) => {
2240
+ * console.log(result)
2241
+ * })
2242
+ */
2243
+ exports.forkScoped = forkScoped;
2244
+ const runFork = (effect, options) => {
2245
+ const controller = new AbortController();
2246
+ const refs = Object.create(null);
2247
+ refs[currentAbortController.key] = controller;
2248
+ refs[currentAbortSignal.key] = controller.signal;
2249
+ const env = envMake(refs);
2250
+ const handle = new HandleImpl(controller.signal, controller);
2251
+ effect[runSymbol](envSet(env, currentAbortSignal, handle._controller.signal), result => {
2252
+ handle.emit(result);
2253
+ });
2254
+ if (options?.signal) {
2255
+ if (options.signal.aborted) {
2256
+ handle.unsafeAbort();
2257
+ } else {
2258
+ options.signal.addEventListener("abort", () => handle.unsafeAbort());
2259
+ }
2260
+ }
2261
+ return handle;
2262
+ };
2263
+ /**
2264
+ * Execute the `Micro` effect and return a `Promise` that resolves with the
2265
+ * `Result` of the computation.
2266
+ *
2267
+ * @since 3.4.0
2268
+ * @experimental
2269
+ * @category execution
2270
+ */
2271
+ exports.runFork = runFork;
2272
+ const runPromiseResult = (effect, options) => new Promise((resolve, _reject) => {
2273
+ const handle = runFork(effect, options);
2274
+ handle.addObserver(resolve);
2275
+ });
2276
+ /**
2277
+ * Execute the `Micro` effect and return a `Promise` that resolves with the
2278
+ * successful value of the computation.
2279
+ *
2280
+ * @since 3.4.0
2281
+ * @experimental
2282
+ * @category execution
2283
+ */
2284
+ exports.runPromiseResult = runPromiseResult;
2285
+ const runPromise = (effect, options) => runPromiseResult(effect, options).then(result => {
2286
+ if (result._tag === "Left") {
2287
+ throw result.left;
2288
+ }
2289
+ return result.right;
2290
+ });
2291
+ /**
2292
+ * Attempt to execute the `Micro` effect synchronously and return the `Result`.
2293
+ *
2294
+ * If any asynchronous effects are encountered, the function will return a
2295
+ * FailureUnexpected containing the `Handle`.
2296
+ *
2297
+ * @since 3.4.0
2298
+ * @experimental
2299
+ * @category execution
2300
+ */
2301
+ exports.runPromise = runPromise;
2302
+ const runSyncResult = effect => {
2303
+ const handle = runFork(effect);
2304
+ while (yieldState.tasks.length > 0) {
2305
+ yieldRunTasks();
2306
+ }
2307
+ const result = handle.unsafePoll();
2308
+ if (result === null) {
2309
+ return ResultFailUnexpected(handle);
2310
+ }
2311
+ return result;
2312
+ };
2313
+ /**
2314
+ * Attempt to execute the `Micro` effect synchronously and return the success
2315
+ * value.
2316
+ *
2317
+ * @since 3.4.0
2318
+ * @experimental
2319
+ * @category execution
2320
+ */
2321
+ exports.runSyncResult = runSyncResult;
2322
+ const runSync = effect => {
2323
+ const result = runSyncResult(effect);
2324
+ if (result._tag === "Left") {
2325
+ throw result.left;
2326
+ }
2327
+ return result.right;
2328
+ };
2329
+ exports.runSync = runSync;
2330
+ const YieldableError = /*#__PURE__*/function () {
2331
+ class YieldableError extends globalThis.Error {
2332
+ [runSymbol](_env, onResult) {
2333
+ onResult(ResultFail(this));
2334
+ }
2335
+ toString() {
2336
+ return this.message ? `${this.name}: ${this.message}` : this.name;
2337
+ }
2338
+ toJSON() {
2339
+ return {
2340
+ ...this
2341
+ };
2342
+ }
2343
+ [_Inspectable.NodeInspectSymbol]() {
2344
+ const stack = this.stack;
2345
+ if (stack) {
2346
+ return `${this.toString()}\n${stack.split("\n").slice(1).join("\n")}`;
2347
+ }
2348
+ return this.toString();
2349
+ }
2350
+ }
2351
+ Object.assign(YieldableError.prototype, MicroProto, _effectable.StructuralPrototype);
2352
+ return YieldableError;
2353
+ }();
2354
+ /**
2355
+ * @since 3.4.0
2356
+ * @experimental
2357
+ * @category errors
2358
+ */
2359
+ const Error = exports.Error = /*#__PURE__*/function () {
2360
+ return class extends YieldableError {
2361
+ constructor(args) {
2362
+ super();
2363
+ if (args) {
2364
+ Object.assign(this, args);
2365
+ }
2366
+ }
2367
+ };
2368
+ }();
2369
+ /**
2370
+ * @since 3.4.0
2371
+ * @experimental
2372
+ * @category errors
2373
+ */
2374
+ const TaggedError = tag => {
2375
+ class Base extends Error {
2376
+ _tag = tag;
2377
+ }
2378
+ ;
2379
+ Base.prototype.name = tag;
2380
+ return Base;
2381
+ };
2382
+ exports.TaggedError = TaggedError;
2383
+ //# sourceMappingURL=Micro.js.map