1/**
2 * Describes workflows that run only when executed by the Effect runtime.
3 *
4 * An `Effect<A, E, R>` can succeed with an `A`, fail with an `E`, and require
5 * services `R`. Creating an effect does not perform the work; it builds a value
6 * that can be composed, provided with services, retried, interrupted, run
7 * concurrently, or inspected by the runtime. This module is the main API for
8 * creating effects, combining them, handling failures, managing resources, and
9 * running effect programs.
10 *
11 * @since 2.0.0
12 */
13import type * as Arr from "./Array.ts"
14import type * as Cause from "./Cause.ts"
15import type { Clock } from "./Clock.ts"
16import * as Context from "./Context.ts"
17import * as Duration from "./Duration.ts"
18import type * as ExecutionPlan from "./ExecutionPlan.ts"
19import * as Exit from "./Exit.ts"
20import type { Fiber } from "./Fiber.ts"
21import type * as Filter from "./Filter.ts"
22import { constant, dual, type LazyArg } from "./Function.ts"
23import type { TypeLambda } from "./HKT.ts"
24import type { Inspectable } from "./Inspectable.ts"
25import * as core from "./internal/core.ts"
26import * as internal from "./internal/effect.ts"
27import * as internalExecutionPlan from "./internal/executionPlan.ts"
28import * as internalLayer from "./internal/layer.ts"
29import * as InternalRecord from "./internal/record.ts"
30import * as internalRequest from "./internal/request.ts"
31import * as internalSchedule from "./internal/schedule.ts"
32import type * as Layer from "./Layer.ts"
33import type { Logger } from "./Logger.ts"
34import type { Severity } from "./LogLevel.ts"
35import * as Metric from "./Metric.ts"
36import type { Option } from "./Option.ts"
37import type { Pipeable } from "./Pipeable.ts"
38import type * as Predicate from "./Predicate.ts"
39import { CurrentLogAnnotations, CurrentLogSpans } from "./References.ts"
40import type * as Request from "./Request.ts"
41import type { RequestResolver } from "./RequestResolver.ts"
42import type * as Result from "./Result.ts"
43import type { Metadata as ScheduleMetadata, Schedule } from "./Schedule.ts"
44import type { Scheduler } from "./Scheduler.ts"
45import type { Scope } from "./Scope.ts"
46import type {
47 AnySpan,
48 ParentSpan,
49 Span,
50 SpanLink,
51 SpanOptions,
52 SpanOptionsNoTrace,
53 TraceOptions,
54 Tracer
55} from "./Tracer.ts"
56import type { TxRef } from "./TxRef.ts"
57import type {
58 Concurrency,
59 Covariant,
60 EqualsWith,
61 ExcludeReason,
62 ExcludeTag,
63 ExtractReason,
64 ExtractTag,
65 NarrowReason,
66 NoInfer,
67 OmitReason,
68 ReasonOf,
69 ReasonTags,
70 Simplify,
71 Tags,
72 unassigned
73} from "./Types.ts"
74import type * as Unify from "./Unify.ts"
75
76/**
77 * Type-level identifier for `Effect` values.
78 *
79 * @category type IDs
80 * @since 4.0.0
81 */
82export type TypeId = "~effect/Effect"
83
84/**
85 * Runtime identifier used to recognize `Effect` values.
86 *
87 * @category type IDs
88 * @since 4.0.0
89 */
90export const TypeId: TypeId = core.EffectTypeId
91
92/**
93 * The `Effect` interface defines a value that lazily describes a workflow or
94 * job. The workflow requires some context `R`, and may fail with an error of
95 * type `E`, or succeed with a value of type `A`.
96 *
97 * **When to use**
98 *
99 * Use when you need to represent a lazy, composable workflow that can require
100 * services, fail with a typed error, or succeed with a typed value.
101 *
102 * **Details**
103 *
104 * `Effect` values model resourceful interaction with the outside world,
105 * including synchronous, asynchronous, concurrent, and parallel interaction.
106 * They use a fiber-based concurrency model, with built-in support for
107 * scheduling, fine-grained interruption, structured concurrency, and high
108 * scalability.
109 *
110 * To run an `Effect` value, you need a `Runtime`, which is a type that is
111 * capable of executing `Effect` values.
112 *
113 * @category models
114 * @since 2.0.0
115 */
116export interface Effect<out A, out E = never, out R = never> extends Pipeable, Inspectable {
117 readonly [TypeId]: Variance<A, E, R>
118 [Symbol.iterator](): EffectIterator<Effect<A, E, R>>
119 [Unify.typeSymbol]?: unknown
120 [Unify.unifySymbol]?: EffectUnify<this>
121 [Unify.ignoreSymbol]?: {}
122}
123
124/**
125 * Type-level unification support for `Effect` values.
126 *
127 * @category models
128 * @since 2.0.0
129 */
130export interface EffectUnify<A extends { [Unify.typeSymbol]?: any }> {
131 Effect?: () => A[Unify.typeSymbol] extends
132 | Effect<infer A0, infer E0, infer R0>
133 | infer _ ? Effect<A0, E0, R0>
134 : never
135}
136
137/**
138 * Type lambda used to represent `Effect` in higher-kinded APIs.
139 *
140 * @category utility types
141 * @since 2.0.0
142 */
143export interface EffectTypeLambda extends TypeLambda {
144 readonly type: Effect<this["Target"], this["Out1"], this["Out2"]>
145}
146
147/**
148 * Variance interface for Effect, encoding the type parameters' variance.
149 *
150 * @category models
151 * @since 2.0.0
152 */
153export interface Variance<A, E, R> {
154 _A: Covariant<A>
155 _E: Covariant<E>
156 _R: Covariant<R>
157}
158
159/**
160 * Extracts the success type from an `Effect`.
161 *
162 * **When to use**
163 *
164 * Use to derive the value produced by an existing effect when declaring
165 * reusable type aliases, service interfaces, or function signatures.
166 *
167 * @see {@link Error} for extracting the failure type from the same `Effect`
168 * @see {@link Services} for extracting the required services from the same `Effect`
169 *
170 * @category utility types
171 * @since 2.0.0
172 */
173export type Success<T> = T extends Effect<infer _A, infer _E, infer _R> ? _A
174 : never
175
176/**
177 * Extracts the error type from an `Effect`.
178 *
179 * **When to use**
180 *
181 * Use to derive the error type from an existing `Effect` type when declaring
182 * helper types, wrappers, or APIs that preserve the effect's failure channel.
183 *
184 * **Details**
185 *
186 * Non-`Effect` inputs resolve to `never`.
187 *
188 * @see {@link Success} for extracting the success value type instead
189 * @see {@link Services} for extracting the required services type instead
190 *
191 * @category utility types
192 * @since 2.0.0
193 */
194export type Error<T> = T extends Effect<infer _A, infer _E, infer _R> ? _E
195 : never
196
197/**
198 * Extracts the required services type from an `Effect`.
199 *
200 * **When to use**
201 *
202 * Use to derive the context requirements of a generic or inferred `Effect`
203 * without restating its `R` type parameter.
204 *
205 * @see {@link Success} for extracting the success value type instead
206 * @see {@link Error} for extracting the failure type instead
207 *
208 * @category utility types
209 * @since 4.0.0
210 */
211export type Services<T> = T extends Effect<infer _A, infer _E, infer _R> ? _R
212 : never
213
214/**
215 * Checks whether a value is an `Effect`.
216 *
217 * **Example** (Checking whether a value is an Effect)
218 *
219 * ```ts import.meta.vitest
220 * import { Effect } from "effect"
221 *
222 * Effect.isEffect(Effect.succeed(1)) // => true
223 * Effect.isEffect("hello") // => false
224 * ```
225 *
226 * @category guards
227 * @since 2.0.0
228 */
229export const isEffect: (u: unknown) => u is Effect<unknown, unknown, unknown> = core.isEffect
230
231/**
232 * Iterator interface for Effect generators, enabling Effect values to work with generator functions.
233 *
234 * **When to use**
235 *
236 * Use when defining or typing `[Symbol.iterator]()` for values typed as
237 * `Effect`s so `yield*` can pass their success type back into `Effect.gen`.
238 *
239 * @see {@link gen} for writing generator-based `Effect` programs that consume this iterator protocol
240 *
241 * @category models
242 * @since 4.0.0
243 */
244export interface EffectIterator<T extends Effect<any, any, any>> {
245 next(
246 ...args: ReadonlyArray<any>
247 ): IteratorResult<T, Success<T>>
248}
249
250// ========================================================================
251// Collecting
252// ========================================================================
253
254/**
255 * Namespace containing type utilities for the `Effect.all` function, which handles
256 * collecting multiple effects into various output structures.
257 *
258 * @category collecting
259 * @since 2.0.0
260 */
261export declare namespace All {
262 /**
263 * Alias for any `Effect` value accepted by `Effect.all`.
264 *
265 * @category utility types
266 * @since 2.0.0
267 */
268 export type EffectAny = Effect<any, any, any>
269
270 /**
271 * Computes the return type for `Effect.all` when collecting an iterable.
272 *
273 * @category utility types
274 * @since 2.0.0
275 */
276 export type ReturnIterable<
277 T extends Iterable<EffectAny>,
278 Discard extends boolean,
279 Mode extends boolean = false
280 > = [T] extends [Iterable<Effect<infer A, infer E, infer R>>] ? Effect<
281 Discard extends true ? void : Array<Mode extends true ? Result.Result<A, E> : A>,
282 Mode extends true ? never : E,
283 R
284 >
285 : never
286
287 /**
288 * Computes the return type for `Effect.all` when collecting a tuple.
289 *
290 * @category utility types
291 * @since 2.0.0
292 */
293 export type ReturnTuple<
294 T extends ReadonlyArray<unknown>,
295 Discard extends boolean,
296 Mode extends boolean = false
297 > = Effect<
298 Discard extends true ? void
299 : T[number] extends never ? []
300 : {
301 -readonly [K in keyof T]: T[K] extends Effect<
302 infer _A,
303 infer _E,
304 infer _R
305 > ? Mode extends true ? Result.Result<_A, _E> : _A
306 : never
307 },
308 Mode extends true ? never
309 : T[number] extends never ? never
310 : T[number] extends Effect<infer _A, infer _E, infer _R> ? _E
311 : never,
312 T[number] extends never ? never
313 : T[number] extends Effect<infer _A, infer _E, infer _R> ? _R
314 : never
315 > extends infer X ? X
316 : never
317
318 /**
319 * Computes the return type for `Effect.all` when collecting a record.
320 *
321 * @category utility types
322 * @since 2.0.0
323 */
324 export type ReturnObject<T, Discard extends boolean, Mode extends boolean = false> = [T] extends [
325 Record<string, EffectAny>
326 ] ? Effect<
327 Discard extends true ? void
328 : {
329 -readonly [K in keyof T]: [T[K]] extends [
330 Effect<infer _A, infer _E, infer _R>
331 ] ? Mode extends true ? Result.Result<_A, _E> : _A
332 : never
333 },
334 Mode extends true ? never : Error<ObjectValues<T>>,
335 Services<ObjectValues<T>>
336 >
337 : never
338
339 /**
340 * Detects whether `Effect.all` should discard collected values.
341 *
342 * @category utility types
343 * @since 2.0.0
344 */
345 export type IsDiscard<A> = [Extract<A, { readonly discard: true }>] extends [
346 never
347 ] ? false
348 : true
349
350 /**
351 * Detects whether `Effect.all` should collect results in `Result` mode.
352 *
353 * @category utility types
354 * @since 4.0.0
355 */
356 export type IsResult<A> = [Extract<A, { readonly mode: "result" }>] extends [never] ? false : true
357
358 /**
359 * Computes the return type for `Effect.all` from its input and options.
360 *
361 * @category utility types
362 * @since 2.0.0
363 */
364 export type Return<
365 Arg extends Iterable<EffectAny> | Record<string, EffectAny>,
366 O extends {
367 readonly concurrency?: Concurrency | undefined
368 readonly discard?: boolean | undefined
369 readonly mode?: "default" | "result" | undefined
370 }
371 > = [Arg] extends [ReadonlyArray<EffectAny>] ? ReturnTuple<Arg, IsDiscard<O>, IsResult<O>>
372 : [Arg] extends [Iterable<EffectAny>] ? ReturnIterable<Arg, IsDiscard<O>, IsResult<O>>
373 : [Arg] extends [Record<string, EffectAny>] ? ReturnObject<Arg, IsDiscard<O>, IsResult<O>>
374 : never
375
376 type ObjectValues<T> = T extends unknown ? T[keyof T] : never
377}
378
379/**
380 * Combines an iterable or record of effects into one effect whose success shape
381 * follows the input.
382 *
383 * **When to use**
384 *
385 * Use to run a known collection of effects and collect results in the same
386 * tuple, iterable, or record shape.
387 *
388 * **Details**
389 *
390 * Tuple and iterable inputs collect results in order. Record inputs collect
391 * results under the same keys. By default, the combined effect fails on the
392 * first failure; with concurrent execution, effects that have already started
393 * may be interrupted, while effects not yet started are skipped.
394 *
395 * Options:
396 *
397 * Use `concurrency` to control sequential or concurrent execution. Use
398 * `mode: "result"` to run every effect and collect each success or failure as a
399 * `Result` in the same output shape. Use `discard: true` to ignore successful
400 * values and return `void`.
401 *
402 * **Example** (Collecting tuple results in order)
403 *
404 * ```ts import.meta.vitest
405 * import { Effect } from "effect"
406 *
407 * const tupleOfEffects = [
408 * Effect.succeed(42),
409 * Effect.succeed("Hello")
410 * ] as const
411 *
412 * // ┌─── Effect<[number, string], never, never>
413 * // ▼
414 * const resultsAsTuple = Effect.all(tupleOfEffects)
415 *
416 * await Effect.runPromise(resultsAsTuple) // => [42, "Hello"]
417 * ```
418 *
419 * **Example** (Collecting iterable results in order)
420 *
421 * ```ts import.meta.vitest
422 * import { Effect } from "effect"
423 *
424 * const iterableOfEffects: Iterable<Effect.Effect<number>> = [1, 2, 3].map(
425 * Effect.succeed
426 * )
427 *
428 * // ┌─── Effect<number[], never, never>
429 * // ▼
430 * const resultsAsArray = Effect.all(iterableOfEffects)
431 *
432 * await Effect.runPromise(resultsAsArray) // => [1, 2, 3]
433 * ```
434 *
435 * **Example** (Collecting struct results by key)
436 *
437 * ```ts import.meta.vitest
438 * import { Effect } from "effect"
439 *
440 * const structOfEffects = {
441 * a: Effect.succeed(42),
442 * b: Effect.succeed("Hello")
443 * }
444 *
445 * // ┌─── Effect<{ a: number; b: string; }, never, never>
446 * // ▼
447 * const resultsAsStruct = Effect.all(structOfEffects)
448 *
449 * await Effect.runPromise(resultsAsStruct) // => { a: 42, b: "Hello" }
450 * ```
451 *
452 * **Example** (Collecting record results by key)
453 *
454 * ```ts import.meta.vitest
455 * import { Effect } from "effect"
456 *
457 * const recordOfEffects: Record<string, Effect.Effect<number>> = {
458 * key1: Effect.succeed(1),
459 * key2: Effect.succeed(2)
460 * }
461 *
462 * // ┌─── Effect<{ [x: string]: number; }, never, never>
463 * // ▼
464 * const resultsAsRecord = Effect.all(recordOfEffects)
465 *
466 * await Effect.runPromise(resultsAsRecord) // => { key1: 1, key2: 2 }
467 * ```
468 *
469 * **Example** (Stopping on the first failure)
470 *
471 * ```ts import.meta.vitest
472 * import { Effect, Exit } from "effect"
473 * const output: Array<unknown> = []
474 * const record = (value: unknown) => Effect.sync(() => { output.push(value) })
475 *
476 * const program = Effect.all([
477 * Effect.succeed("Task1").pipe(Effect.tap(record)),
478 * Effect.fail("Task2: Oh no!").pipe(Effect.tap(record)),
479 * // Won't execute due to earlier failure
480 * Effect.succeed("Task3").pipe(Effect.tap(record))
481 * ])
482 *
483 * const outcome = await Effect.runPromiseExit(program)
484 * const observation = [output, outcome] // => [["Task1"], Exit.fail("Task2: Oh no!")]
485 * ```
486 *
487 * @see {@link forEach} for iterating over elements and applying an effect.
488 * @category collecting
489 * @since 2.0.0
490 */
491export const all: <
492 const Arg extends
493 | Iterable<Effect<any, any, any>>
494 | Record<string, Effect<any, any, any>>,
495 O extends {
496 readonly concurrency?: Concurrency | undefined
497 readonly discard?: boolean | undefined
498 readonly mode?: "default" | "result" | undefined
499 }
500>(
501 arg: Arg,
502 options?: O
503) => All.Return<Arg, O> = internal.all
504
505/**
506 * Applies an effectful function to each element and partitions successes and
507 * failures.
508 *
509 * **Details**
510 *
511 * The returned tuple is `[passes, fails]`, where `passes` contains all
512 * successes and `fails` contains all failures.
513 *
514 * This function runs every effect and never fails. Use `concurrency` to control
515 * parallelism.
516 *
517 * **Example** (Separating successes and failures)
518 *
519 * ```ts import.meta.vitest
520 * import { Effect } from "effect"
521 *
522 * const program = Effect.partition([0, 1, 2, 3], (n) =>
523 * n % 2 === 0 ? Effect.fail(`${n} is even`) : Effect.succeed(n)
524 * )
525 *
526 * await Effect.runPromise(program) // => [[1, 3], ['0 is even', '2 is even']]
527 * ```
528 *
529 * @category collecting
530 * @since 2.0.0
531 */
532export const partition: {
533 <A, B, E, R>(
534 f: (a: A, i: number) => Effect<B, E, R>,
535 options?: { readonly concurrency?: Concurrency | undefined }
536 ): (elements: Iterable<A>) => Effect<[passes: Array<B>, fails: Array<E>], never, R>
537 <A, B, E, R>(
538 elements: Iterable<A>,
539 f: (a: A, i: number) => Effect<B, E, R>,
540 options?: { readonly concurrency?: Concurrency | undefined }
541 ): Effect<[passes: Array<B>, fails: Array<E>], never, R>
542} = internal.partition
543
544/**
545 * Reduces elements from left to right with an effectful accumulator function.
546 *
547 * **When to use**
548 *
549 * Use when each accumulation step is effectful and must run sequentially in
550 * iteration order.
551 *
552 * **Details**
553 *
554 * The accumulator function receives the current accumulator, the current
555 * element, and its zero-based index. The `zero` function is evaluated each
556 * time the effect runs. An empty iterable succeeds with its result. If a step
557 * fails, remaining elements are not processed.
558 *
559 * **Example** (Summing values sequentially)
560 *
561 * ```ts import.meta.vitest
562 * import { Effect } from "effect"
563 * const output: Array<unknown> = []
564 *
565 * const program = Effect.reduce(
566 * [1, 2, 3],
567 * () => 0,
568 * (total, value, index) =>
569 * Effect.sync(() => { output.push(`Adding ${value} at index ${index}`) }).pipe(
570 * Effect.as(total + value)
571 * )
572 * )
573 *
574 * void output.push(await Effect.runPromise(program))
575 * output // => ["Adding 1 at index 0", "Adding 2 at index 1", "Adding 3 at index 2", 6]
576 * ```
577 *
578 * @category collecting
579 * @since 2.0.0
580 */
581export const reduce: {
582 <Z, A, E, R>(
583 zero: LazyArg<Z>,
584 f: (z: Z, a: A, i: number) => Effect<Z, E, R>
585 ): (elements: Iterable<A>) => Effect<Z, E, R>
586 <A, Z, E, R>(
587 elements: Iterable<A>,
588 zero: LazyArg<Z>,
589 f: (z: Z, a: A, i: number) => Effect<Z, E, R>
590 ): Effect<Z, E, R>
591} = internal.reduce
592
593/**
594 * Applies an effectful function to each element and accumulates all failures.
595 *
596 * **Details**
597 *
598 * This function always evaluates every element. If at least one effect fails,
599 * all failures are returned as a non-empty array and successes are discarded.
600 * If all effects succeed, it returns all collected successes.
601 *
602 * Use `discard: true` to ignore successful values while still validating all
603 * elements.
604 *
605 * **Example** (Validating every element)
606 *
607 * ```ts import.meta.vitest
608 * import { Effect, Exit } from "effect"
609 *
610 * const program = Effect.validate([0, 1, 2, 3], (n) =>
611 * n % 2 === 0 ? Effect.fail(`${n} is even`) : Effect.succeed(n)
612 * )
613 *
614 * await Effect.runPromiseExit(program) // => Exit.fail(["0 is even", "2 is even"])
615 * ```
616 *
617 * @category collecting
618 * @since 2.0.0
619 */
620export const validate: {
621 <A, B, E, R>(
622 f: (a: A, i: number) => Effect<B, E, R>,
623 options?: {
624 readonly concurrency?: Concurrency | undefined
625 readonly discard?: false | undefined
626 } | undefined
627 ): (elements: Iterable<A>) => Effect<Array<B>, Arr.NonEmptyArray<E>, R>
628 <A, B, E, R>(
629 f: (a: A, i: number) => Effect<B, E, R>,
630 options: {
631 readonly concurrency?: Concurrency | undefined
632 readonly discard: true
633 }
634 ): (elements: Iterable<A>) => Effect<void, Arr.NonEmptyArray<E>, R>
635 <A, B, E, R>(
636 elements: Iterable<A>,
637 f: (a: A, i: number) => Effect<B, E, R>,
638 options?: {
639 readonly concurrency?: Concurrency | undefined
640 readonly discard?: false | undefined
641 } | undefined
642 ): Effect<Array<B>, Arr.NonEmptyArray<E>, R>
643 <A, B, E, R>(
644 elements: Iterable<A>,
645 f: (a: A, i: number) => Effect<B, E, R>,
646 options: {
647 readonly concurrency?: Concurrency | undefined
648 readonly discard: true
649 }
650 ): Effect<void, Arr.NonEmptyArray<E>, R>
651} = internal.validate
652
653/**
654 * Returns the first element that satisfies an effectful predicate.
655 *
656 * **Details**
657 *
658 * The predicate receives the element and its index. Evaluation short-circuits
659 * as soon as an element matches.
660 *
661 * **Example** (Finding the first successful match)
662 *
663 * ```ts import.meta.vitest
664 * import { Effect, Option } from "effect"
665 *
666 * const program = Effect.findFirst([1, 2, 3, 4], (n) => Effect.succeed(n > 2))
667 *
668 * await Effect.runPromise(program) // => Option.some(3)
669 * ```
670 *
671 * @category collecting
672 * @since 2.0.0
673 */
674export const findFirst: {
675 <A, E, R>(
676 predicate: (a: NoInfer<A>, i: number) => Effect<boolean, E, R>
677 ): (elements: Iterable<A>) => Effect<Option<A>, E, R>
678 <A, E, R>(
679 elements: Iterable<A>,
680 predicate: (a: NoInfer<A>, i: number) => Effect<boolean, E, R>
681 ): Effect<Option<A>, E, R>
682} = internal.findFirst
683
684/**
685 * Returns the first value that passes an effectful `FilterEffect`.
686 *
687 * **When to use**
688 *
689 * Use when you need to find the first element that satisfies an effectful
690 * filter returning a `Result`, which also transforms the matching element.
691 *
692 * **Details**
693 *
694 * The filter receives the element and index. Evaluation short-circuits on the
695 * first `Result.succeed` and returns the transformed value in `Option.some`.
696 *
697 * @see {@link findFirst} for the simpler effectful predicate-based variant
698 *
699 * @category collecting
700 * @since 4.0.0
701 */
702export const findFirstFilter: {
703 <A, B, X, E, R>(
704 filter: (input: NoInfer<A>, i: number) => Effect<Result.Result<B, X>, E, R>
705 ): (elements: Iterable<A>) => Effect<Option<B>, E, R>
706 <A, B, X, E, R>(
707 elements: Iterable<A>,
708 filter: (input: NoInfer<A>, i: number) => Effect<Result.Result<B, X>, E, R>
709 ): Effect<Option<B>, E, R>
710} = internal.findFirstFilter
711
712/**
713 * Executes an effectful operation for each element in an `Iterable`.
714 *
715 * **When to use**
716 *
717 * Use to traverse an iterable with an effectful function while preserving
718 * element order in the collected results.
719 *
720 * **Details**
721 *
722 * The `forEach` function applies a provided operation to each element in the
723 * iterable, producing a new effect that returns an array of results.
724 *
725 * If any effect fails, the iteration stops immediately (short-circuiting), and
726 * the error is propagated.
727 *
728 * Concurrency:
729 *
730 * The `concurrency` option controls how many operations are performed
731 * concurrently. By default, the operations are performed sequentially.
732 *
733 * Discarding Results:
734 *
735 * If the `discard` option is set to `true`, the intermediate results are not
736 * collected, and the final result of the operation is `void`.
737 *
738 * **Example** (Mapping over an iterable with effects)
739 *
740 * ```ts import.meta.vitest
741 * import { Effect } from "effect"
742 * const output: Array<unknown> = []
743 *
744 * const result = Effect.forEach(
745 * [1, 2, 3, 4, 5],
746 * (n, index) =>
747 * Effect.sync(() => { output.push(`Currently at index ${index}`) }).pipe(Effect.as(n * 2))
748 * )
749 *
750 * void output.push(await Effect.runPromise(result))
751 * output // => ["Currently at index 0", "Currently at index 1", "Currently at index 2", "Currently at index 3", "Currently at index 4", [2, 4, 6, 8, 10]]
752 * ```
753 *
754 * **Example** (Running effects without collecting results)
755 *
756 * ```ts import.meta.vitest
757 * import { Effect } from "effect"
758 * const output: Array<unknown> = []
759 *
760 * // Apply effects but discard the results
761 * const result = Effect.forEach(
762 * [1, 2, 3, 4, 5],
763 * (n, index) =>
764 * Effect.sync(() => { output.push(`Currently at index ${index}`) }).pipe(Effect.as(n * 2)),
765 * { discard: true }
766 * )
767 *
768 * void output.push(await Effect.runPromise(result))
769 * output // => ["Currently at index 0", "Currently at index 1", "Currently at index 2", "Currently at index 3", "Currently at index 4", undefined]
770 * ```
771 *
772 * @see {@link all} for combining multiple effects into one.
773 * @category collecting
774 * @since 2.0.0
775 */
776export const forEach: {
777 <A, B, E, R, S extends Iterable<A> = Iterable<A>, const Discard extends boolean = false>(
778 f: (a: A, i: number) => Effect<B, E, R>,
779 options?: { readonly concurrency?: Concurrency | undefined; readonly discard?: Discard | undefined } | undefined
780 ): (
781 self: [S] extends [never] ? Iterable<A> : S
782 ) => Effect<Discard extends false ? Arr.ReadonlyArray.With<S, B> : void, E, R>
783 <B, E, R, S extends Iterable<any>, const Discard extends boolean = false>(
784 self: S,
785 f: (a: Arr.ReadonlyArray.Infer<S>, i: number) => Effect<B, E, R>,
786 options?: { readonly concurrency?: Concurrency | undefined; readonly discard?: Discard | undefined } | undefined
787 ): Effect<Discard extends false ? Arr.ReadonlyArray.With<S, B> : void, E, R>
788} = internal.forEach
789
790/**
791 * Returns the first element of the iterable produced by an effect, or fails
792 * with `NoSuchElementError` if the iterable is empty.
793 *
794 * **When to use**
795 *
796 * Use when an effect produces a collection that must contain at least one
797 * element and absence should be represented in the typed error channel.
798 *
799 * **Example** (Getting the first element)
800 *
801 * ```ts import.meta.vitest
802 * import { Effect, Option } from "effect"
803 *
804 * const first = await Effect.runPromise(Effect.head(Effect.succeed([1, 2, 3])))
805 * first // => 1
806 *
807 * const empty = Effect.head(Effect.succeed([] as Array<number>)).pipe(Effect.catchNoSuchElement)
808 * await Effect.runPromise(empty) // => Option.none()
809 * ```
810 *
811 * @category collecting
812 * @since 2.0.0
813 */
814export const head: <A, E, R>(
815 self: Effect<Iterable<A>, E, R>
816) => Effect<A, E | Cause.NoSuchElementError, R> = internal.head
817
818/**
819 * Executes a body effect repeatedly while a condition holds true.
820 *
821 * **Example** (Repeating an effectful loop)
822 *
823 * ```ts import.meta.vitest
824 * import { Effect } from "effect"
825 * const output: Array<unknown> = []
826 *
827 * let counter = 0
828 *
829 * const program = Effect.whileLoop({
830 * while: () => counter < 5,
831 * body: () => Effect.sync(() => ++counter),
832 * step: (n) => void output.push(`Current count: ${n}`)
833 * })
834 *
835 * await Effect.runPromise(program)
836 * output // => ["Current count: 1", "Current count: 2", "Current count: 3", "Current count: 4", "Current count: 5"]
837 * ```
838 *
839 * @category repetition
840 * @since 2.0.0
841 */
842export const whileLoop: <A, E, R>(options: {
843 readonly while: LazyArg<boolean>
844 readonly body: LazyArg<Effect<A, E, R>>
845 readonly step: (a: A) => void
846}) => Effect<void, E, R> = internal.whileLoop
847
848// -----------------------------------------------------------------------------
849// Creating Effects
850// -----------------------------------------------------------------------------
851
852/**
853 * Creates an `Effect` that represents an asynchronous computation guaranteed to
854 * succeed.
855 *
856 * **When to use**
857 *
858 * Use to convert a `Promise` into an `Effect` when the async operation is
859 * guaranteed to succeed and will not reject.
860 *
861 * **Details**
862 *
863 * An optional `AbortSignal` can be provided to allow for interruption of the
864 * wrapped `Promise` API.
865 *
866 * **Gotchas**
867 *
868 * The `Promise` must not reject. If it rejects, the rejection is treated as a
869 * defect, not as a typed failure. Use `tryPromise` when rejection is expected.
870 *
871 * Interruption aborts the provided `AbortSignal`, but the underlying
872 * asynchronous operation only stops if it observes that signal.
873 *
874 * **Example** (Wrapping a non-rejecting Promise)
875 *
876 * ```ts import.meta.vitest
877 * import { Effect } from "effect"
878 *
879 * const succeedAsync = (message: string) =>
880 * Effect.promise<string>(() => Promise.resolve(message))
881 *
882 * // ┌─── Effect<string, never, never>
883 * // ▼
884 * const program = succeedAsync("Async operation completed successfully!")
885 * await Effect.runPromise(program) // => "Async operation completed successfully!"
886 * ```
887 *
888 * @see {@link tryPromise} for a version that can handle failures.
889 * @category constructors
890 * @since 2.0.0
891 */
892export const promise: <A>(
893 evaluate: (signal: AbortSignal) => PromiseLike<A>
894) => Effect<A> = internal.promise
895
896/**
897 * Creates an `Effect` from an asynchronous computation that may throw or
898 * reject, mapping failures into the error channel.
899 *
900 * **When to use**
901 *
902 * Use when you need to perform asynchronous operations that might fail, such
903 * as fetching data from an API, and want thrown exceptions or rejected promises
904 * captured as Effect errors.
905 *
906 * **Details**
907 *
908 * The promise thunk is evaluated when the effect runs. If it returns a promise
909 * that resolves, the resolved value becomes the success value. If the thunk
910 * throws before returning a promise, or if the returned promise rejects, the
911 * thrown or rejected value is mapped into the error channel.
912 *
913 * Passing the thunk directly maps failures to {@link Cause.UnknownError}.
914 * Passing `{ try, catch }` uses `catch` to map failures to an error of type
915 * `E`.
916 *
917 * The thunk receives an `AbortSignal` that is aborted if the effect is
918 * interrupted. The underlying asynchronous operation only stops if it observes
919 * that signal.
920 *
921 * **Gotchas**
922 *
923 * If `catch` throws while mapping the error, that thrown value is treated as a
924 * defect. Return the error value you want in the error channel instead of
925 * throwing it.
926 *
927 * **Example** (Wrapping a fetch request that may fail)
928 *
929 * ```ts import.meta.vitest
930 * import { Effect } from "effect"
931 *
932 * const getTodo = (id: number) =>
933 * Effect.tryPromise(() => Promise.resolve({ id, completed: false }))
934 *
935 * // ┌─── Effect<{ id: number; completed: boolean }, UnknownError, never>
936 * // ▼
937 * const program = getTodo(1)
938 * await Effect.runPromise(program) // => { id: 1, completed: false }
939 * ```
940 *
941 * **Example** (Mapping Promise rejections to a tagged error)
942 *
943 * ```ts import.meta.vitest
944 * import { Data, Effect } from "effect"
945 *
946 * class TodoFetchError extends Data.TaggedError("TodoFetchError")<{ readonly cause: unknown }> {}
947 *
948 * const getTodo = (id: number) =>
949 * Effect.tryPromise({
950 * try: () => Promise.reject(`Todo ${id} is unavailable`),
951 * // remap the error
952 * catch: (cause) => new TodoFetchError({ cause })
953 * })
954 *
955 * // ┌─── Effect<never, TodoFetchError, never>
956 * // ▼
957 * const program = Effect.flip(getTodo(1))
958 * const error = await Effect.runPromise(program)
959 * error._tag // => "TodoFetchError"
960 * ```
961 *
962 * @see {@link promise} if the effectful computation is asynchronous and does not throw errors.
963 * @category constructors
964 * @since 2.0.0
965 */
966export const tryPromise: {
967 <A>(options: (signal: AbortSignal) => PromiseLike<A>): Effect<A, Cause.UnknownError>
968 <A, E>(
969 options: { readonly try: (signal: AbortSignal) => PromiseLike<A>; readonly catch: (error: unknown) => E }
970 ): Effect<A, E>
971} = internal.tryPromise
972
973/**
974 * Creates an `Effect` that always succeeds with a given value.
975 *
976 * **When to use**
977 *
978 * Use when an effect should complete successfully with a specific value without any errors
979 * or external dependencies.
980 *
981 * **Example** (Creating a successful effect)
982 *
983 * ```ts import.meta.vitest
984 * import { Effect } from "effect"
985 *
986 * // Creating an effect that represents a successful scenario
987 * //
988 * // ┌─── Effect<number, never, never>
989 * // ▼
990 * const success = Effect.succeed(42)
991 * Effect.runSync(success) // => 42
992 * ```
993 *
994 * @see {@link fail} to create an effect that represents a failure.
995 * @category constructors
996 * @since 2.0.0
997 */
998export const succeed: <A>(value: A) => Effect<A> = internal.succeed
999
1000/**
1001 * Returns an effect which succeeds with `None`.
1002 *
1003 * **Example** (Succeeding with Option.none)
1004 *
1005 * ```ts import.meta.vitest
1006 * import { Effect, Option } from "effect"
1007 *
1008 * const program = Effect.succeedNone
1009 *
1010 * Effect.runSync(program) // => Option.none()
1011 * ```
1012 *
1013 * @category constructors
1014 * @since 2.0.0
1015 */
1016export const succeedNone: Effect<Option<never>> = internal.succeedNone
1017
1018/**
1019 * Returns an effect which succeeds with the value wrapped in a `Some`.
1020 *
1021 * **Example** (Succeeding with Option.some)
1022 *
1023 * ```ts import.meta.vitest
1024 * import { Effect, Option } from "effect"
1025 *
1026 * const program = Effect.succeedSome(42)
1027 *
1028 * Effect.runSync(program) // => Option.some(42)
1029 * ```
1030 *
1031 * @category constructors
1032 * @since 2.0.0
1033 */
1034export const succeedSome: <A>(value: A) => Effect<Option<A>> = internal.succeedSome
1035
1036/**
1037 * Creates an `Effect` lazily, delaying construction until it is needed.
1038 *
1039 * **When to use**
1040 *
1041 * Use when you need to defer the evaluation of an effect until it is required.
1042 *
1043 * **Details**
1044 *
1045 * `suspend` takes a thunk that represents an effect and delays creating it
1046 * until the suspended effect is evaluated. This is useful for optimizing
1047 * expensive computations, managing circular dependencies such as recursive
1048 * functions, and helping TypeScript unify return types when branches construct
1049 * different effects. Any side effects or scoped captures inside the thunk are
1050 * re-executed on each invocation.
1051 *
1052 * **Example** (Lazily evaluating side effects)
1053 *
1054 * ```ts import.meta.vitest
1055 * import { Effect } from "effect"
1056 *
1057 * let i = 0
1058 *
1059 * const bad = Effect.succeed(i++)
1060 *
1061 * const good = Effect.suspend(() => Effect.succeed(i++))
1062 *
1063 * Effect.runSync(bad) // => 0
1064 * Effect.runSync(bad) // => 0
1065 *
1066 * Effect.runSync(good) // => 1
1067 * Effect.runSync(good) // => 2
1068 * ```
1069 *
1070 * **Example** (Suspending recursive Fibonacci evaluation)
1071 *
1072 * ```ts import.meta.vitest
1073 * import { Effect } from "effect"
1074 *
1075 * const blowsUp = (n: number): Effect.Effect<number> =>
1076 * n < 2
1077 * ? Effect.succeed(1)
1078 * : Effect.zipWith(blowsUp(n - 1), blowsUp(n - 2), (a, b) => a + b)
1079 *
1080 * // console.log(Effect.runSync(blowsUp(32)))
1081 * // crash: JavaScript heap out of memory
1082 *
1083 * const allGood = (n: number): Effect.Effect<number> =>
1084 * n < 2
1085 * ? Effect.succeed(1)
1086 * : Effect.zipWith(
1087 * Effect.suspend(() => allGood(n - 1)),
1088 * Effect.suspend(() => allGood(n - 2)),
1089 * (a, b) => a + b
1090 * )
1091 *
1092 * Effect.runSync(allGood(16)) // => 1597
1093 * ```
1094 *
1095 * **Example** (Helping TypeScript infer recursive effect types)
1096 *
1097 * ```ts import.meta.vitest
1098 * import { Effect } from "effect"
1099 *
1100 * // Without suspend, TypeScript may struggle with type inference.
1101 * // Inferred type:
1102 * // (a: number, b: number) =>
1103 * // Effect<never, Error, never> | Effect<number, never, never>
1104 * const withoutSuspend = (a: number, b: number) =>
1105 * b === 0
1106 * ? Effect.fail(new Error("Cannot divide by zero"))
1107 * : Effect.succeed(a / b)
1108 *
1109 * // Using suspend to unify return types.
1110 * // Inferred type:
1111 * // (a: number, b: number) => Effect<number, Error, never>
1112 * const withSuspend = (a: number, b: number) =>
1113 * Effect.suspend(() =>
1114 * b === 0
1115 * ? Effect.fail(new Error("Cannot divide by zero"))
1116 * : Effect.succeed(a / b)
1117 * )
1118 *
1119 * Effect.runSync(withSuspend(6, 2)) // => 3
1120 * ```
1121 *
1122 * @category constructors
1123 * @since 2.0.0
1124 */
1125export const suspend: <A, E, R>(
1126 effect: LazyArg<Effect<A, E, R>>
1127) => Effect<A, E, R> = internal.suspend
1128
1129/**
1130 * Creates an `Effect` that represents a synchronous side-effectful computation.
1131 *
1132 * **When to use**
1133 *
1134 * Use when you need to wrap a synchronous side-effectful operation that is not
1135 * expected to throw.
1136 *
1137 * **Details**
1138 *
1139 * The provided function is evaluated lazily when the effect runs.
1140 *
1141 * **Gotchas**
1142 *
1143 * The function must not throw. If it throws, the thrown value is treated as a
1144 * defect, not as a typed failure. Use `try` when throwing is expected.
1145 *
1146 * **Example** (Capturing synchronous logging in an Effect)
1147 *
1148 * ```ts import.meta.vitest
1149 * import { Effect } from "effect"
1150 * const output: Array<unknown> = []
1151 *
1152 * const log = (message: string) =>
1153 * Effect.sync(() => {
1154 * void output.push(message) // side effect
1155 * })
1156 *
1157 * // ┌─── Effect<void, never, never>
1158 * // ▼
1159 * const program = log("Hello, World!")
1160 * Effect.runSync(program)
1161 * output // => ["Hello, World!"]
1162 * ```
1163 *
1164 * @see {@link try_ | try} for a version that can handle failures.
1165 * @category constructors
1166 * @since 2.0.0
1167 */
1168export const sync: <A>(thunk: LazyArg<A>) => Effect<A> = internal.sync
1169
1170const void_: Effect<void> = internal.void
1171export {
1172 /**
1173 * Returns an effect that succeeds with `void`.
1174 *
1175 * @category constructors
1176 * @since 2.0.0
1177 */
1178 void_ as void
1179}
1180
1181const undefined_: Effect<undefined> = internal.undefined
1182export {
1183 /**
1184 * Returns an effect that succeeds with `undefined`.
1185 *
1186 * @category constructors
1187 * @since 4.0.0
1188 */
1189 undefined_ as undefined
1190}
1191
1192/**
1193 * Creates an `Effect` from a callback-based asynchronous API.
1194 *
1195 * **When to use**
1196 *
1197 * Use when you need to integrate APIs that complete through callbacks instead
1198 * of returning a `Promise`.
1199 *
1200 * **Details**
1201 *
1202 * The registration function receives a `resume` callback and, when requested,
1203 * an `AbortSignal`. Call `resume` at most once with the effect that should
1204 * complete the fiber; later calls are ignored. Return an optional cleanup
1205 * effect from the registration function to run if the fiber is interrupted.
1206 *
1207 * **Example** (Integrating callback APIs)
1208 *
1209 * ```ts import.meta.vitest
1210 * import { Effect } from "effect"
1211 * const output: Array<unknown> = []
1212 *
1213 * const fromCallback = (message: string) =>
1214 * Effect.callback<void>((resume) => {
1215 * queueMicrotask(() => {
1216 * void output.push(message)
1217 * resume(Effect.void)
1218 * })
1219 * })
1220 *
1221 * await Effect.runPromise(fromCallback("callback completed"))
1222 * output // => ["callback completed"]
1223 * ```
1224 *
1225 * @category constructors
1226 * @since 4.0.0
1227 */
1228export const callback: <A, E = never, R = never>(
1229 register: (
1230 this: Scheduler,
1231 resume: (effect: Effect<A, E, R>) => void,
1232 signal: AbortSignal
1233 ) => void | Effect<void, never, R>
1234) => Effect<A, E, R> = internal.callback
1235
1236/**
1237 * Returns an effect that will never produce anything. The moral equivalent of
1238 * `while(true) {}`, only without the wasted CPU cycles.
1239 *
1240 * **Example** (Creating a never-ending effect)
1241 *
1242 * ```ts import.meta.vitest
1243 * import { Effect, Option } from "effect"
1244 *
1245 * const program = Effect.timeoutOption(Effect.never, 0)
1246 * await Effect.runPromise(program) // => Option.none()
1247 * ```
1248 *
1249 * @category constructors
1250 * @since 2.0.0
1251 */
1252export const never: Effect<never> = internal.never
1253
1254/**
1255 * Effect that succeeds with an empty record `{}`, used as the starting point
1256 * for do notation chains.
1257 *
1258 * **Example** (Starting do notation)
1259 *
1260 * ```ts import.meta.vitest
1261 * import { Effect, pipe } from "effect"
1262 *
1263 * const program = pipe(
1264 * Effect.Do,
1265 * Effect.bind("x", () => Effect.succeed(2)),
1266 * Effect.bind("y", ({ x }) => Effect.succeed(x + 1)),
1267 * Effect.let("sum", ({ x, y }) => x + y)
1268 * )
1269 *
1270 * Effect.runSync(program) // => { x: 2, y: 3, sum: 5 }
1271 * ```
1272 *
1273 * @category do notation
1274 * @since 2.0.0
1275 */
1276export const Do: Effect<{}> = internal.Do
1277
1278/**
1279 * Gives a name to the success value of an `Effect`, creating a single-key
1280 * record used in do notation pipelines.
1281 *
1282 * **When to use**
1283 *
1284 * Use to start a do-notation pipeline from an existing `Effect` when its
1285 * success value should become the first named field in the accumulated record.
1286 *
1287 * @see {@link Do} for starting from an empty accumulated record
1288 * @see {@link bind} for adding fields produced by effects
1289 *
1290 * @category do notation
1291 * @since 2.0.0
1292 */
1293export const bindTo: {
1294 <N extends string>(name: N): <A, E, R>(self: Effect<A, E, R>) => Effect<{ [K in N]: A }, E, R>
1295 <A, E, R, N extends string>(self: Effect<A, E, R>, name: N): Effect<{ [K in N]: A }, E, R>
1296} = internal.bindTo
1297
1298const let_: {
1299 <N extends string, A extends Record<string, any>, B>(
1300 name: N,
1301 f: (a: NoInfer<A>) => B
1302 ): <E, R>(
1303 self: Effect<A, E, R>
1304 ) => Effect<Simplify<Omit<A, N> & Record<N, B>>, E, R>
1305 <A extends Record<string, any>, E, R, B, N extends string>(
1306 self: Effect<A, E, R>,
1307 name: N,
1308 f: (a: NoInfer<A>) => B
1309 ): Effect<Simplify<Omit<A, N> & Record<N, B>>, E, R>
1310} = internal.let
1311
1312export {
1313 /**
1314 * Adds a computed plain value to the do notation record.
1315 *
1316 * **When to use**
1317 *
1318 * Use to add a derived, synchronous value to a do-notation pipeline when it
1319 * depends on fields already accumulated in the record and does not need to run
1320 * another `Effect`.
1321 *
1322 * **Details**
1323 *
1324 * The new field is added with object spreading. If the name already exists in
1325 * the record, the computed value replaces it in the returned type.
1326 *
1327 * @see {@link bind} for adding fields produced by effects
1328 * @see {@link bindTo} for naming an existing success value
1329 * @see {@link Do} for starting from an empty accumulated record
1330 * @see {@link gen} for sequencing without accumulating a record
1331 *
1332 * @category do notation
1333 * @since 2.0.0
1334 */
1335 let_ as let
1336}
1337
1338/**
1339 * Adds an `Effect` value to the do notation record under a given name.
1340 *
1341 * **When to use**
1342 *
1343 * Use to sequence an effectful step in a do-notation pipeline when that step
1344 * depends on fields already accumulated in the record and its success value
1345 * should be stored under a name.
1346 *
1347 * **Details**
1348 *
1349 * The function receives the current record, runs the returned effect after the
1350 * input effect succeeds, and inserts its success value under `name`. The
1351 * resulting effect combines the error and service requirements of both steps.
1352 *
1353 * **Gotchas**
1354 *
1355 * Binding a name that already exists replaces that field in the resulting
1356 * record.
1357 *
1358 * @see {@link Do} for starting from an empty do-notation record
1359 * @see {@link bindTo} for naming the success value of an existing effect
1360 * @see {@link gen} for generator-based sequencing without accumulating a record
1361 *
1362 * @category do notation
1363 * @since 2.0.0
1364 */
1365export const bind: {
1366 <N extends string, A extends Record<string, any>, B, E2, R2>(
1367 name: N,
1368 f: (a: NoInfer<A>) => Effect<B, E2, R2>
1369 ): <E, R>(
1370 self: Effect<A, E, R>
1371 ) => Effect<Simplify<Omit<A, N> & Record<N, B>>, E | E2, R | R2>
1372 <A extends Record<string, any>, E, R, B, E2, R2, N extends string>(
1373 self: Effect<A, E, R>,
1374 name: N,
1375 f: (a: NoInfer<A>) => Effect<B, E2, R2>
1376 ): Effect<Simplify<Omit<A, N> & Record<N, B>>, E | E2, R | R2>
1377} = internal.bind
1378
1379/**
1380 * Provides a way to write effectful code using generator functions, simplifying
1381 * control flow and error handling.
1382 *
1383 * **When to use**
1384 *
1385 * Use when you want to write effectful code that looks and behaves like
1386 * synchronous code, while still handling asynchronous tasks, errors, and complex
1387 * control flow such as loops and conditions.
1388 *
1389 * Generator functions work similarly to `async/await` but keep errors,
1390 * requirements, and interruption in the Effect type. You can `yield*` values
1391 * from effects and return the final result at the end.
1392 *
1393 * **Example** (Sequencing effects with generators)
1394 *
1395 * ```ts import.meta.vitest
1396 * import { Data, Effect } from "effect"
1397 *
1398 * class DiscountRateError extends Data.TaggedError("DiscountRateError")<{}> {}
1399 *
1400 * const addServiceCharge = (amount: number) => amount + 1
1401 *
1402 * const applyDiscount = (
1403 * total: number,
1404 * discountRate: number
1405 * ): Effect.Effect<number, DiscountRateError> =>
1406 * discountRate === 0
1407 * ? Effect.fail(new DiscountRateError())
1408 * : Effect.succeed(total - (total * discountRate) / 100)
1409 *
1410 * const fetchTransactionAmount = Effect.promise(() => Promise.resolve(100))
1411 *
1412 * const fetchDiscountRate = Effect.promise(() => Promise.resolve(5))
1413 *
1414 * export const program = Effect.gen(function*() {
1415 * const transactionAmount = yield* fetchTransactionAmount
1416 * const discountRate = yield* fetchDiscountRate
1417 * const discountedAmount = yield* applyDiscount(
1418 * transactionAmount,
1419 * discountRate
1420 * )
1421 * const finalAmount = addServiceCharge(discountedAmount)
1422 * return `Final amount to charge: ${finalAmount}`
1423 * })
1424 *
1425 * await Effect.runPromise(program) // => "Final amount to charge: 96"
1426 * ```
1427 *
1428 * @category constructors
1429 * @since 2.0.0
1430 */
1431export const gen: {
1432 <Eff extends Effect<any, any, any>, AEff>(
1433 f: () => Generator<Eff, AEff, never>
1434 ): Effect<
1435 AEff,
1436 [Eff] extends [never] ? never
1437 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
1438 : never,
1439 [Eff] extends [never] ? never
1440 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
1441 : never
1442 >
1443 <Self, Eff extends Effect<any, any, any>, AEff>(
1444 options: {
1445 readonly self: Self
1446 },
1447 f: (this: Self) => Generator<Eff, AEff, never>
1448 ): Effect<
1449 AEff,
1450 [Eff] extends [never] ? never
1451 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
1452 : never,
1453 [Eff] extends [never] ? never
1454 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
1455 : never
1456 >
1457} = internal.gen
1458
1459/**
1460 * Type helpers for `Effect.gen` generator return signatures.
1461 *
1462 * @category constructors
1463 * @since 2.0.0
1464 */
1465export declare namespace gen {
1466 /**
1467 * Generator return type accepted by `Effect.gen`.
1468 *
1469 * @category constructors
1470 * @since 4.0.0
1471 */
1472 export type Return<A, E = never, R = never> = Generator<Effect<any, E, R>, A, any>
1473}
1474
1475/**
1476 * Creates an `Effect` that represents a recoverable error.
1477 *
1478 * **When to use**
1479 *
1480 * Use to explicitly signal a recoverable error in an `Effect`.
1481 *
1482 * **Details**
1483 *
1484 * The error keeps propagating unless it is handled. You can handle tagged
1485 * errors with functions like {@link catchTag} or {@link catchTags}.
1486 *
1487 * **Example** (Creating a failed effect)
1488 *
1489 * ```ts import.meta.vitest
1490 * import { Data, Effect } from "effect"
1491 *
1492 * class OperationFailedError extends Data.TaggedError("OperationFailedError")<{}> {}
1493 *
1494 * // ┌─── Effect<never, OperationFailedError, never>
1495 * // ▼
1496 * const failure = Effect.fail(
1497 * new OperationFailedError()
1498 * )
1499 * Effect.runSync(Effect.flip(failure))._tag // => "OperationFailedError"
1500 * ```
1501 *
1502 * @see {@link succeed} to create an effect that represents a successful value.
1503 * @category constructors
1504 * @since 2.0.0
1505 */
1506export const fail: <E>(error: E) => Effect<never, E> = internal.fail
1507
1508/**
1509 * Creates an `Effect` that represents a recoverable error using a lazy evaluation.
1510 *
1511 * **When to use**
1512 *
1513 * Use to defer computing a recoverable error value until the effect is run.
1514 *
1515 * **Details**
1516 *
1517 * The error-producing function is evaluated each time the effect is executed.
1518 *
1519 * **Example** (Lazily creating failures)
1520 *
1521 * ```ts import.meta.vitest
1522 * import { Data, Effect } from "effect"
1523 *
1524 * class ProgramError extends Data.TaggedError("ProgramError")<{ readonly operation: string }> {}
1525 *
1526 * const program = Effect.failSync(() => new ProgramError({ operation: "sync" }))
1527 *
1528 * Effect.runSync(Effect.flip(program)).operation // => "sync"
1529 * ```
1530 *
1531 * @category constructors
1532 * @since 2.0.0
1533 */
1534export const failSync: <E>(evaluate: LazyArg<E>) => Effect<never, E> = internal.failSync
1535
1536/**
1537 * Creates an `Effect` that represents a failure with a specific `Cause`.
1538 *
1539 * **When to use**
1540 *
1541 * Use when you already have a full `Cause` and need to preserve defects,
1542 * interruptions, annotations, or combined failures in the effect's failure
1543 * channel.
1544 *
1545 * **Details**
1546 *
1547 * This function allows you to create effects that fail with complex error
1548 * structures, including multiple errors, defects, interruptions, and more.
1549 *
1550 * **Example** (Failing with a full Cause)
1551 *
1552 * ```ts import.meta.vitest
1553 * import { Cause, Effect } from "effect"
1554 *
1555 * const program = Effect.failCause(
1556 * Cause.fail("Network error")
1557 * )
1558 *
1559 * Effect.runSync(Effect.flip(program)) // => "Network error"
1560 * ```
1561 *
1562 * @category constructors
1563 * @since 2.0.0
1564 */
1565export const failCause: <E>(cause: Cause.Cause<E>) => Effect<never, E> = internal.failCause
1566
1567/**
1568 * Creates an `Effect` that represents a failure with a `Cause` computed lazily.
1569 *
1570 * **When to use**
1571 *
1572 * Use to defer computing a full `Cause` until the effect is run.
1573 *
1574 * **Details**
1575 *
1576 * The cause-producing function is evaluated each time the effect is executed.
1577 *
1578 * **Example** (Lazily creating a Cause)
1579 *
1580 * ```ts import.meta.vitest
1581 * import { Cause, Effect } from "effect"
1582 *
1583 * const program = Effect.failCauseSync(() =>
1584 * Cause.fail("Error computed at runtime")
1585 * )
1586 *
1587 * Effect.runSync(Effect.flip(program)) // => "Error computed at runtime"
1588 * ```
1589 *
1590 * @category constructors
1591 * @since 2.0.0
1592 */
1593export const failCauseSync: <E>(
1594 evaluate: LazyArg<Cause.Cause<E>>
1595) => Effect<never, E> = internal.failCauseSync
1596
1597/**
1598 * Creates an effect that terminates a fiber with a specified error.
1599 *
1600 * **When to use**
1601 *
1602 * Use when you need an `Effect` to report an unrecoverable defect instead of a
1603 * typed error.
1604 *
1605 * **Details**
1606 *
1607 * The `die` function is used to signal a defect, which represents a critical
1608 * and unexpected error in the code. When invoked, it produces an effect that
1609 * does not handle the error and instead terminates the fiber.
1610 *
1611 * The error channel of the resulting effect is of type `never`, indicating that
1612 * it cannot recover from this failure.
1613 *
1614 * **Example** (Failing on division by zero)
1615 *
1616 * ```ts import.meta.vitest
1617 * import { Effect, Exit } from "effect"
1618 *
1619 * const defect = new Error("Cannot divide by zero")
1620 * const divide = (a: number, b: number) =>
1621 * b === 0
1622 * ? Effect.die(defect)
1623 * : Effect.succeed(a / b)
1624 *
1625 * // ┌─── Effect<number, never, never>
1626 * // ▼
1627 * const program = divide(1, 0)
1628 *
1629 * Effect.runSyncExit(program) // => Exit.die(defect)
1630 * ```
1631 *
1632 * @category constructors
1633 * @since 2.0.0
1634 */
1635export const die: (defect: unknown) => Effect<never> = internal.die
1636
1637const try_: {
1638 <A>(options: LazyArg<A>): Effect<A, Cause.UnknownError>
1639 <A, E>(options: {
1640 readonly try: LazyArg<A>
1641 readonly catch: (error: unknown) => E
1642 }): Effect<A, E>
1643} = internal.try
1644
1645export {
1646 /**
1647 * Creates an `Effect` from a synchronous computation that may throw, mapping
1648 * thrown values into the error channel.
1649 *
1650 * **When to use**
1651 *
1652 * Use when you need to perform synchronous operations that might throw, such
1653 * as parsing JSON, and want thrown exceptions captured as Effect errors.
1654 *
1655 * **Details**
1656 *
1657 * The thunk is evaluated when the effect runs. If it returns normally, the
1658 * returned value becomes the success value. If it throws, the thrown value is
1659 * mapped into the error channel.
1660 *
1661 * Passing the thunk directly maps failures to {@link Cause.UnknownError}.
1662 * Passing `{ try, catch }` uses `catch` to map failures to an error of type
1663 * `E`.
1664 *
1665 * **Gotchas**
1666 *
1667 * If `catch` throws while mapping the error, that thrown value is treated as
1668 * a defect. Return the error value you want in the error channel instead of
1669 * throwing it.
1670 *
1671 * **Example** (Parsing JSON)
1672 *
1673 * ```ts import.meta.vitest
1674 * import { Effect } from "effect"
1675 *
1676 * const parseJSON = (input: string) =>
1677 * Effect.try(() => JSON.parse(input))
1678 *
1679 * // Success case
1680 * await Effect.runPromise(parseJSON("{\"name\": \"Alice\"}")) // => { name: 'Alice' }
1681 *
1682 * // Failure case maps the thrown value to UnknownError
1683 * const exit = await Effect.runPromiseExit(parseJSON("invalid json"))
1684 * exit._tag // => "Failure"
1685 * ```
1686 *
1687 * **Example** (Mapping exceptions to a tagged error)
1688 *
1689 * ```ts import.meta.vitest
1690 * import { Data, Effect } from "effect"
1691 *
1692 * class JsonParsingError extends Data.TaggedError("JsonParsingError")<{ readonly cause: unknown }> {}
1693 *
1694 * const parseJSON = (input: string) =>
1695 * Effect.try({
1696 * try: () => JSON.parse(input),
1697 * catch: (cause) => new JsonParsingError({ cause })
1698 * })
1699 *
1700 * const error = await Effect.runPromise(Effect.flip(parseJSON("invalid json")))
1701 * error._tag // => "JsonParsingError"
1702 * ```
1703 *
1704 * @see {@link sync} if the effectful computation is synchronous and does not
1705 * throw errors.
1706 * @category constructors
1707 * @since 2.0.0
1708 */
1709 try_ as try
1710}
1711
1712/**
1713 * Yields control back to the Effect runtime, allowing other fibers to execute.
1714 *
1715 * **Example** (Yielding to other fibers)
1716 *
1717 * ```ts import.meta.vitest
1718 * import { Effect } from "effect"
1719 * const output: Array<unknown> = []
1720 *
1721 * const program = Effect.gen(function*() {
1722 * void output.push("Before yield")
1723 * yield* Effect.yieldNow
1724 * void output.push("After yield")
1725 * })
1726 *
1727 * await Effect.runPromise(program)
1728 * output // => ["Before yield", "After yield"]
1729 * ```
1730 *
1731 * @category constructors
1732 * @since 2.0.0
1733 */
1734export const yieldNow: Effect<void> = internal.yieldNow
1735
1736/**
1737 * Yields control back to the Effect runtime with a specified priority, allowing other fibers to execute.
1738 *
1739 * **Example** (Yielding with priority)
1740 *
1741 * ```ts import.meta.vitest
1742 * import { Effect } from "effect"
1743 * const output: Array<unknown> = []
1744 *
1745 * const program = Effect.gen(function*() {
1746 * void output.push("High priority task")
1747 * yield* Effect.yieldNowWith(10) // Higher priority
1748 * void output.push("Continued after yield")
1749 * })
1750 *
1751 * await Effect.runPromise(program)
1752 * output // => ["High priority task", "Continued after yield"]
1753 * ```
1754 *
1755 * @category constructors
1756 * @since 4.0.0
1757 */
1758export const yieldNowWith: (priority?: number) => Effect<void> = internal.yieldNowWith
1759
1760/**
1761 * Provides access to the current fiber within an effect computation.
1762 *
1763 * **Example** (Reading the current fiber)
1764 *
1765 * ```ts import.meta.vitest
1766 * import { Effect } from "effect"
1767 *
1768 * const program = Effect.withFiber((fiber) => Effect.succeed(typeof fiber.id))
1769 *
1770 * Effect.runSync(program) // => "number"
1771 * ```
1772 *
1773 * @category constructors
1774 * @since 4.0.0
1775 */
1776export const withFiber: <A, E = never, R = never>(
1777 evaluate: (fiber: Fiber<unknown, unknown>) => Effect<A, E, R>
1778) => Effect<A, E, R> = core.withFiber
1779
1780/**
1781 * Accesses the current fiber to compute a successful value.
1782 *
1783 * **Example** (Computing a value from the current fiber)
1784 *
1785 * ```ts import.meta.vitest
1786 * import { Effect } from "effect"
1787 *
1788 * const program = Effect.withFiberSucceed((fiber) => typeof fiber.id)
1789 *
1790 * Effect.runSync(program) // => "number"
1791 * ```
1792 *
1793 * @category constructors
1794 * @since 4.0.0
1795 */
1796export const withFiberSucceed: <A, R = never>(
1797 evaluate: (fiber: Fiber<unknown, unknown>) => A
1798) => Effect<A, never, R> = core.withFiberSucceed
1799
1800// -----------------------------------------------------------------------------
1801// Conversions
1802// -----------------------------------------------------------------------------
1803
1804/**
1805 * Converts a `Result` to an `Effect`.
1806 *
1807 * **Example** (Converting a Result into an Effect)
1808 *
1809 * ```ts import.meta.vitest
1810 * import { Effect, Result } from "effect"
1811 * const output: Array<unknown> = []
1812 *
1813 * const success = Result.succeed(42)
1814 * const failure = Result.fail("Something went wrong")
1815 *
1816 * const effect1 = Effect.fromResult(success)
1817 * const effect2 = Effect.fromResult(failure)
1818 *
1819 * void output.push(Effect.runSync(effect1))
1820 * void output.push(Effect.runSync(Effect.flip(effect2)))
1821 * output // => [42, "Something went wrong"]
1822 * ```
1823 *
1824 * @category converting
1825 * @since 4.0.0
1826 */
1827export const fromResult: <A, E>(result: Result.Result<A, E>) => Effect<A, E> = internal.fromResult
1828
1829/**
1830 * Converts an `Option` into an `Effect`.
1831 *
1832 * **When to use**
1833 *
1834 * Use when absence should become a typed `NoSuchElementError` in the effect error
1835 * channel.
1836 *
1837 * **Details**
1838 *
1839 * `Option.some` becomes a successful effect with the contained value, while
1840 * `Option.none` becomes a failed effect. By default the failure is a
1841 * `NoSuchElementError`, but you can provide an `onNone` callback to customize
1842 * the error value.
1843 *
1844 * **Example** (Converting an Option into an Effect)
1845 *
1846 * ```ts import.meta.vitest
1847 * import { Effect, Option } from "effect"
1848 * const output: Array<unknown> = []
1849 *
1850 * const some = Option.some(42)
1851 * const none = Option.none()
1852 *
1853 * const effect1 = Effect.fromOption(some)
1854 * const effect2 = Effect.fromOption(none)
1855 * const effect3 = Effect.fromOption(none, () => new Error("missing"))
1856 *
1857 * void output.push(Effect.runSync(effect1))
1858 * void output.push(Effect.runSync(Effect.flip(effect2))._tag)
1859 * void output.push(Effect.runSync(Effect.flip(effect3)).message)
1860 * output // => [42, "NoSuchElementError", "missing"]
1861 * ```
1862 *
1863 * @category converting
1864 * @since 4.0.0
1865 */
1866export const fromOption: <
1867 Arg extends Option<unknown> | LazyArg<unknown>,
1868 Rest extends [] | [onNone: LazyArg<unknown> | undefined] = []
1869>(
1870 arg: Arg & (Rest extends [] ? unknown : Option<unknown>),
1871 ...rest: Rest
1872) => [Arg] extends [Option<infer A>] ? Effect<
1873 A,
1874 Rest extends [LazyArg<infer E>] ? E
1875 : Rest extends [undefined] ? Cause.NoSuchElementError
1876 : Rest extends [LazyArg<infer E> | undefined] ? E | Cause.NoSuchElementError
1877 : Cause.NoSuchElementError
1878 >
1879 : [Arg] extends [LazyArg<infer E>] ? <A>(option: Option<A>) => Effect<A, E>
1880 : never = internal.fromOption
1881
1882/**
1883 * Converts an `Option` of an `Effect` into an `Effect` of an `Option`.
1884 *
1885 * **When to use**
1886 *
1887 * Use when an effect should run only when an optional value is present, while
1888 * preserving absence as a successful `None`.
1889 *
1890 * **Details**
1891 *
1892 * - `None` becomes an effect that succeeds with `None`
1893 * - `Some(effect)` runs the inner effect and wraps its success value in `Some`
1894 * - Inner failures are preserved in the resulting effect
1895 *
1896 * **Example** (Transposing an Option of an Effect)
1897 *
1898 * ```ts import.meta.vitest
1899 * import { Effect, Option } from "effect"
1900 *
1901 * const some = Option.some(Effect.succeed(42))
1902 *
1903 * // ┌─── Effect<Option<number>, never, never>
1904 * // ▼
1905 * const program = Effect.transposeOption(some)
1906 *
1907 * Effect.runSync(program) // => Option.some(42)
1908 * ```
1909 *
1910 * @category converting
1911 * @since 3.13.0
1912 */
1913export const transposeOption: <A = never, E = never, R = never>(
1914 self: Option<Effect<A, E, R>>
1915) => Effect<Option<A>, E, R> = internal.transposeOption
1916
1917/**
1918 * Converts a nullable value to an `Effect`, failing with a `NoSuchElementError`
1919 * when the value is `null` or `undefined`.
1920 *
1921 * **Example** (Failing on nullish values)
1922 *
1923 * ```ts import.meta.vitest
1924 * import { Effect } from "effect"
1925 * const output: Array<unknown> = []
1926 *
1927 * const program = Effect.fn(function*(input: string | null) {
1928 * const value = yield* Effect.fromNullishOr(input)
1929 * yield* Effect.sync(() => { output.push(value) })
1930 * },
1931 * Effect.catch(() => Effect.sync(() => { output.push("missing") }))
1932 * )
1933 *
1934 * await Effect.runPromise(program(null))
1935 * await Effect.runPromise(program("hello"))
1936 * output // => ["missing", "hello"]
1937 * ```
1938 *
1939 * @category converting
1940 * @since 4.0.0
1941 */
1942export const fromNullishOr: <A>(value: A) => Effect<NonNullable<A>, Cause.NoSuchElementError> = internal.fromNullishOr
1943
1944// -----------------------------------------------------------------------------
1945// Mapping
1946// -----------------------------------------------------------------------------
1947
1948/**
1949 * Chains effects to produce new `Effect` instances, useful for combining
1950 * operations that depend on previous results.
1951 *
1952 * **When to use**
1953 *
1954 * Use when you need to chain multiple effects, ensuring that each
1955 * step produces a new `Effect` while flattening any nested effects that may
1956 * occur.
1957 *
1958 * **Details**
1959 *
1960 * `flatMap` lets you sequence effects so that the result of one effect can be
1961 * used in the next step. It is similar to `flatMap` used with arrays but works
1962 * specifically with `Effect` instances, allowing you to avoid deeply nested
1963 * effect structures.
1964 *
1965 * Since effects are immutable, `flatMap` always returns a new effect instead of
1966 * changing the original one.
1967 *
1968 * **Example** (Choosing flatMap syntax variants)
1969 *
1970 * ```ts import.meta.vitest
1971 * import { Effect, pipe } from "effect"
1972 * const output: Array<unknown> = []
1973 *
1974 * const myEffect = Effect.succeed(1)
1975 * const transformation = (n: number) => Effect.succeed(n + 1)
1976 *
1977 * const flatMappedWithPipe = pipe(myEffect, Effect.flatMap(transformation))
1978 * const flatMappedWithDataFirst = Effect.flatMap(myEffect, transformation)
1979 * const flatMappedWithMethod = myEffect.pipe(Effect.flatMap(transformation))
1980 *
1981 * void output.push(Effect.runSync(Effect.all([
1982 * flatMappedWithPipe,
1983 * flatMappedWithDataFirst,
1984 * flatMappedWithMethod
1985 * ])))
1986 * output // => [[2, 2, 2]]
1987 * ```
1988 *
1989 * **Example** (Sequencing dependent effects)
1990 *
1991 * ```ts import.meta.vitest
1992 * import { Data, Effect, pipe } from "effect"
1993 *
1994 * class DiscountRateError extends Data.TaggedError("DiscountRateError")<{}> {}
1995 *
1996 * // Function to apply a discount safely to a transaction amount
1997 * const applyDiscount = (
1998 * total: number,
1999 * discountRate: number
2000 * ): Effect.Effect<number, DiscountRateError> =>
2001 * discountRate === 0
2002 * ? Effect.fail(new DiscountRateError())
2003 * : Effect.succeed(total - (total * discountRate) / 100)
2004 *
2005 * // Simulated asynchronous task to fetch a transaction amount from database
2006 * const fetchTransactionAmount = Effect.promise(() => Promise.resolve(100))
2007 *
2008 * // Chaining the fetch and discount application using `flatMap`
2009 * const finalAmount = pipe(
2010 * fetchTransactionAmount,
2011 * Effect.flatMap((amount) => applyDiscount(amount, 5))
2012 * )
2013 *
2014 * await Effect.runPromise(finalAmount) // => 95
2015 * ```
2016 *
2017 * @see {@link tap} for a version that ignores the result of the effect.
2018 * @category sequencing
2019 * @since 2.0.0
2020 */
2021export const flatMap: {
2022 <A, B, E1, R1>(
2023 f: (a: A) => Effect<B, E1, R1>
2024 ): <E, R>(self: Effect<A, E, R>) => Effect<B, E1 | E, R1 | R>
2025 <A, E, R, B, E1, R1>(
2026 self: Effect<A, E, R>,
2027 f: (a: A) => Effect<B, E1, R1>
2028 ): Effect<B, E | E1, R | R1>
2029} = internal.flatMap
2030
2031/**
2032 * Flattens an `Effect` that produces another `Effect` into a single effect.
2033 *
2034 * **Example** (Flattening nested effects)
2035 *
2036 * ```ts import.meta.vitest
2037 * import { Effect } from "effect"
2038 * const output: Array<unknown> = []
2039 *
2040 * const nested = Effect.succeed(Effect.succeed("hello"))
2041 *
2042 * const program = Effect.gen(function*() {
2043 * const value = yield* Effect.flatten(nested)
2044 * yield* Effect.sync(() => { output.push(value) })
2045 * })
2046 *
2047 * Effect.runSync(program)
2048 * output // => ["hello"]
2049 * ```
2050 *
2051 * @category sequencing
2052 * @since 2.0.0
2053 */
2054export const flatten: <A, E, R, E2, R2>(self: Effect<Effect<A, E, R>, E2, R2>) => Effect<A, E | E2, R | R2> =
2055 internal.flatten
2056
2057/**
2058 * Runs this effect and then runs another effect, optionally using the first
2059 * effect's success value to choose the next effect.
2060 *
2061 * **When to use**
2062 *
2063 * Use when you need one effect to run after another and the second effect may
2064 * depend on the first effect's success value.
2065 *
2066 * **Details**
2067 *
2068 * When the second argument is an `Effect`, the first success value is discarded
2069 * and the returned effect produces the second effect's value. When the second
2070 * argument is a function, it receives the first success value and must return
2071 * the next `Effect`.
2072 *
2073 * Failures or requirements from either effect are preserved in the returned
2074 * effect.
2075 *
2076 * **Example** (Choosing andThen syntax variants)
2077 *
2078 * ```ts import.meta.vitest
2079 * import { Effect, pipe } from "effect"
2080 * const output: Array<unknown> = []
2081 *
2082 * const myEffect = Effect.succeed(1)
2083 * const anotherEffect = Effect.succeed("done")
2084 *
2085 * const transformedWithPipe = pipe(myEffect, Effect.andThen(anotherEffect))
2086 * const transformedWithDataFirst = Effect.andThen(myEffect, anotherEffect)
2087 * const transformedWithMethod = myEffect.pipe(Effect.andThen(anotherEffect))
2088 *
2089 * void output.push(Effect.runSync(Effect.all([
2090 * transformedWithPipe,
2091 * transformedWithDataFirst,
2092 * transformedWithMethod
2093 * ])))
2094 * output // => [['done', 'done', 'done']]
2095 * ```
2096 *
2097 * **Example** (Sequencing a discount calculation after fetching a total)
2098 *
2099 * ```ts import.meta.vitest
2100 * import { Data, Effect, pipe } from "effect"
2101 *
2102 * class DiscountRateError extends Data.TaggedError("DiscountRateError")<{}> {}
2103 *
2104 * // Function to apply a discount safely to a transaction amount
2105 * const applyDiscount = (
2106 * total: number,
2107 * discountRate: number
2108 * ): Effect.Effect<number, DiscountRateError> =>
2109 * discountRate === 0
2110 * ? Effect.fail(new DiscountRateError())
2111 * : Effect.succeed(total - (total * discountRate) / 100)
2112 *
2113 * // Simulated asynchronous task to fetch a transaction amount from database
2114 * const fetchTransactionAmount = Effect.promise(() => Promise.resolve(100))
2115 *
2116 * // Using Effect.map and Effect.flatMap
2117 * const result1 = pipe(
2118 * fetchTransactionAmount,
2119 * Effect.map((amount) => amount * 2),
2120 * Effect.flatMap((amount) => applyDiscount(amount, 5))
2121 * )
2122 *
2123 * await Effect.runPromise(result1) // => 190
2124 *
2125 * // Using Effect.andThen
2126 * const result2 = pipe(
2127 * fetchTransactionAmount,
2128 * Effect.andThen((amount) => Effect.succeed(amount * 2)),
2129 * Effect.andThen((amount) => applyDiscount(amount, 5))
2130 * )
2131 *
2132 * await Effect.runPromise(result2) // => 190
2133 * ```
2134 *
2135 * @category sequencing
2136 * @since 2.0.0
2137 */
2138export const andThen: {
2139 <A, B, E2, R2>(
2140 f: (a: A) => Effect<B, E2, R2>
2141 ): <E, R>(self: Effect<A, E, R>) => Effect<B, E | E2, R | R2>
2142 <B, E2, R2>(
2143 f: Effect<B, E2, R2>
2144 ): <A, E, R>(self: Effect<A, E, R>) => Effect<B, E | E2, R | R2>
2145 <A, E, R, B, E2, R2>(
2146 self: Effect<A, E, R>,
2147 f: (a: A) => Effect<B, E2, R2>
2148 ): Effect<B, E | E2, R | R2>
2149 <A, E, R, B, E2, R2>(
2150 self: Effect<A, E, R>,
2151 f: Effect<B, E2, R2>
2152 ): Effect<B, E | E2, R | R2>
2153} = internal.andThen
2154
2155/**
2156 * Runs a side effect with the result of an effect without changing the original
2157 * value.
2158 *
2159 * **When to use**
2160 *
2161 * Use when you need to run an effectful observation, such as logging or
2162 * tracking, while passing the original success value to the next step.
2163 *
2164 * **Details**
2165 *
2166 * `tap` works similarly to `flatMap`, but it ignores the result of the function
2167 * passed to it. The value from the previous effect remains available for the
2168 * next part of the chain. Note that if the side effect fails, the entire chain
2169 * will fail too.
2170 *
2171 * **Example** (Logging a step in a pipeline)
2172 *
2173 * ```ts import.meta.vitest
2174 * import { Data, Effect, pipe } from "effect"
2175 * const output: Array<unknown> = []
2176 *
2177 * class DiscountRateError extends Data.TaggedError("DiscountRateError")<{}> {}
2178 *
2179 * // Function to apply a discount safely to a transaction amount
2180 * const applyDiscount = (
2181 * total: number,
2182 * discountRate: number
2183 * ): Effect.Effect<number, DiscountRateError> =>
2184 * discountRate === 0
2185 * ? Effect.fail(new DiscountRateError())
2186 * : Effect.succeed(total - (total * discountRate) / 100)
2187 *
2188 * // Simulated asynchronous task to fetch a transaction amount from database
2189 * const fetchTransactionAmount = Effect.promise(() => Promise.resolve(100))
2190 *
2191 * const finalAmount = pipe(
2192 * fetchTransactionAmount,
2193 * // Log the fetched transaction amount
2194 * Effect.tap((amount) => Effect.sync(() => { output.push(`Apply a discount to: ${amount}`) })),
2195 * // `amount` is still available!
2196 * Effect.flatMap((amount) => applyDiscount(amount, 5))
2197 * )
2198 *
2199 * void output.push(await Effect.runPromise(finalAmount))
2200 * output // => ["Apply a discount to: 100", 95]
2201 * ```
2202 *
2203 * @category sequencing
2204 * @since 2.0.0
2205 */
2206export const tap: {
2207 <A, B, E2, R2>(
2208 f: (a: NoInfer<A>) => Effect<B, E2, R2>
2209 ): <E, R>(self: Effect<A, E, R>) => Effect<A, E | E2, R | R2>
2210 <B, E2, R2>(
2211 f: Effect<B, E2, R2>
2212 ): <A, E, R>(self: Effect<A, E, R>) => Effect<A, E | E2, R | R2>
2213 <A, E, R, B, E2, R2>(
2214 self: Effect<A, E, R>,
2215 f: (a: NoInfer<A>) => Effect<B, E2, R2>
2216 ): Effect<A, E | E2, R | R2>
2217 <A, E, R, B, E2, R2>(
2218 self: Effect<A, E, R>,
2219 f: Effect<B, E2, R2>
2220 ): Effect<A, E | E2, R | R2>
2221} = internal.tap
2222
2223/**
2224 * Converts both success and failure of an `Effect` into a `Result` type.
2225 *
2226 * **When to use**
2227 *
2228 * Use when you want an `Effect`'s typed failures to be handled as `Result`
2229 * data while preserving the original error value.
2230 *
2231 * **Details**
2232 *
2233 * This function converts an effect that may fail into an effect that always
2234 * succeeds, wrapping the outcome in a `Result` type. The result will be
2235 * `Result.Failure` if the effect fails, containing the recoverable error, or
2236 * `Result.Success` if it succeeds, containing the result.
2237 *
2238 * Using this function, you can handle recoverable errors explicitly without
2239 * causing the effect to fail. This is particularly useful in scenarios where
2240 * you want to chain effects and manage both success and failure in the same
2241 * logical flow.
2242 *
2243 * The resulting effect cannot fail directly because all recoverable failures
2244 * are represented inside the `Result` type.
2245 *
2246 * **Gotchas**
2247 *
2248 * `result` only captures typed, recoverable failures. Defects and
2249 * interruptions are not captured inside the `Result` and still fail the
2250 * effect.
2251 *
2252 * **Example** (Capturing success or failure as Result)
2253 *
2254 * ```ts import.meta.vitest
2255 * import { Effect, Result } from "effect"
2256 *
2257 * const success = Effect.succeed(42)
2258 * const failure = Effect.fail("Something went wrong")
2259 *
2260 * const program1 = Effect.result(success)
2261 * const program2 = Effect.result(failure)
2262 *
2263 * Effect.runSync(program1) // => Result.succeed(42)
2264 *
2265 * Effect.runSync(program2) // => Result.fail("Something went wrong")
2266 * ```
2267 *
2268 * @see {@link option} for a version that uses `Option` instead.
2269 * @see {@link exit} for a version that encapsulates both recoverable errors and defects in an `Exit`.
2270 *
2271 * @category error handling
2272 * @since 4.0.0
2273 */
2274export const result: <A, E, R>(self: Effect<A, E, R>) => Effect<Result.Result<A, E>, never, R> = internal.result
2275
2276/**
2277 * Converts success to `Option.some` and failure to `Option.none`.
2278 *
2279 * **When to use**
2280 *
2281 * Use when you only care whether an effect succeeds and want recoverable
2282 * failures represented as `Option.none`.
2283 *
2284 * **Details**
2285 *
2286 * Success values become `Option.some`, recoverable failures become
2287 * `Option.none`, and defects still fail the effect.
2288 *
2289 * **Gotchas**
2290 *
2291 * `option` only captures typed, recoverable failures as `Option.none`.
2292 * Defects and interruptions are not captured inside the `Option` and still
2293 * fail the effect.
2294 *
2295 * `option` also discards typed failure values. Use `result` if the failure
2296 * value matters.
2297 *
2298 * **Example** (Capturing success or failure as Option)
2299 *
2300 * ```ts import.meta.vitest
2301 * import { Effect, Option } from "effect"
2302 *
2303 * const program = Effect.all([
2304 * Effect.option(Effect.succeed(1)),
2305 * Effect.option(Effect.fail("missing"))
2306 * ])
2307 *
2308 * Effect.runSync(program) // => [Option.some(1), Option.none()]
2309 * ```
2310 *
2311 * @see {@link result} for a version that uses `Result` instead.
2312 * @see {@link exit} for a version that encapsulates both recoverable errors and defects in an `Exit`.
2313 *
2314 * @category error handling
2315 * @since 2.0.0
2316 */
2317export const option: <A, E, R>(self: Effect<A, E, R>) => Effect<Option<A>, never, R> = internal.option
2318
2319/**
2320 * Transforms an effect to encapsulate both failure and success using the `Exit`
2321 * data type.
2322 *
2323 * **When to use**
2324 *
2325 * Use when you need to inspect the full outcome, including typed failures, defects,
2326 * and interruptions.
2327 *
2328 * **Details**
2329 *
2330 * `exit` wraps an effect's success or failure inside an `Exit` type, allowing
2331 * you to handle both cases explicitly.
2332 *
2333 * The resulting effect cannot fail because the failure is encapsulated within
2334 * the `Exit.Failure` type. The error type is set to `never`, indicating that
2335 * the effect is structured to never fail directly.
2336 *
2337 * **Example** (Capturing completion as Exit)
2338 *
2339 * ```ts import.meta.vitest
2340 * import { Effect, Exit } from "effect"
2341 *
2342 * const success = Effect.succeed(42)
2343 * const failure = Effect.fail("Something went wrong")
2344 *
2345 * const program1 = Effect.exit(success)
2346 * const program2 = Effect.exit(failure)
2347 *
2348 * Effect.runSync(program1) // => Exit.succeed(42)
2349 *
2350 * Effect.runSync(program2) // => Exit.fail("Something went wrong")
2351 * ```
2352 *
2353 * @see {@link option} for a version that uses `Option` instead.
2354 * @see {@link result} for a version that uses `Result` instead.
2355 *
2356 * @category error handling
2357 * @since 2.0.0
2358 */
2359export const exit: <A, E, R>(
2360 self: Effect<A, E, R>
2361) => Effect<Exit.Exit<A, E>, never, R> = internal.exit
2362
2363/**
2364 * Transforms the value inside an effect by applying a function to it.
2365 *
2366 * **When to use**
2367 *
2368 * Use to transform an effect's success value with a function that returns a
2369 * plain value, producing a new effect without changing the original effect's
2370 * typed error or context requirements.
2371 *
2372 * **Details**
2373 *
2374 * `map` takes a function and applies it to the value contained within an
2375 * effect, creating a new effect with the transformed value.
2376 *
2377 * It's important to note that effects are immutable, meaning that the original
2378 * effect is not modified. Instead, a new effect is returned with the updated
2379 * value.
2380 *
2381 * **Example** (Choosing map syntax variants)
2382 *
2383 * ```ts import.meta.vitest
2384 * import { Effect, pipe } from "effect"
2385 * const output: Array<unknown> = []
2386 *
2387 * const myEffect = Effect.succeed(1)
2388 * const transformation = (n: number) => n + 1
2389 *
2390 * const mappedWithPipe = pipe(myEffect, Effect.map(transformation))
2391 * const mappedWithDataFirst = Effect.map(myEffect, transformation)
2392 * const mappedWithMethod = myEffect.pipe(Effect.map(transformation))
2393 *
2394 * void output.push(Effect.runSync(Effect.all([
2395 * mappedWithPipe,
2396 * mappedWithDataFirst,
2397 * mappedWithMethod
2398 * ])))
2399 * output // => [[2, 2, 2]]
2400 * ```
2401 *
2402 * **Example** (Adding a service charge)
2403 *
2404 * ```ts import.meta.vitest
2405 * import { Effect, pipe } from "effect"
2406 *
2407 * const addServiceCharge = (amount: number) => amount + 1
2408 *
2409 * const fetchTransactionAmount = Effect.promise(() => Promise.resolve(100))
2410 *
2411 * const finalAmount = pipe(
2412 * fetchTransactionAmount,
2413 * Effect.map(addServiceCharge)
2414 * )
2415 *
2416 * await Effect.runPromise(finalAmount) // => 101
2417 * ```
2418 *
2419 * @see {@link mapError} for a version that operates on the error channel.
2420 * @see {@link mapBoth} for a version that operates on both channels.
2421 * @see {@link flatMap} or {@link andThen} for a version that can return a new effect.
2422 * @category mapping
2423 * @since 2.0.0
2424 */
2425export const map: {
2426 <A, B>(f: (a: A) => B): <E, R>(self: Effect<A, E, R>) => Effect<B, E, R>
2427 <A, E, R, B>(self: Effect<A, E, R>, f: (a: A) => B): Effect<B, E, R>
2428} = internal.map
2429
2430/**
2431 * Replaces the value inside an effect with a constant value.
2432 *
2433 * **When to use**
2434 *
2435 * Use to replace a successful value with a constant while preserving failures
2436 * and requirements.
2437 *
2438 * **Details**
2439 *
2440 * `as` allows you to ignore the original value inside an effect and
2441 * replace it with a new constant value.
2442 *
2443 * **Example** (Replacing a success value)
2444 *
2445 * ```ts import.meta.vitest
2446 * import { Effect, pipe } from "effect"
2447 *
2448 * // Replaces the value 5 with the constant "new value"
2449 * const program = pipe(Effect.succeed(5), Effect.as("new value"))
2450 *
2451 * Effect.runSync(program) // => "new value"
2452 * ```
2453 *
2454 * @see {@link map} for deriving the replacement value from the success value
2455 * @see {@link asVoid} for replacing the success value with `void`
2456 *
2457 * @category mapping
2458 * @since 2.0.0
2459 */
2460export const as: {
2461 <B>(value: B): <A, E, R>(self: Effect<A, E, R>) => Effect<B, E, R>
2462 <A, E, R, B>(self: Effect<A, E, R>, value: B): Effect<B, E, R>
2463} = internal.as
2464
2465/**
2466 * Maps the success value of an `Effect` to `Some`, preserving failures.
2467 *
2468 * **Example** (Wrapping success in Option.some)
2469 *
2470 * ```ts import.meta.vitest
2471 * import { Effect, Option } from "effect"
2472 *
2473 * const program = Effect.asSome(Effect.succeed(42))
2474 *
2475 * Effect.runSync(program) // => Option.some(42)
2476 * ```
2477 *
2478 * @category mapping
2479 * @since 2.0.0
2480 */
2481export const asSome: <A, E, R>(self: Effect<A, E, R>) => Effect<Option<A>, E, R> = internal.asSome
2482
2483/**
2484 * Maps the success value of an `Effect` to `void`, preserving failures.
2485 *
2486 * **Example** (Discarding success values)
2487 *
2488 * ```ts import.meta.vitest
2489 * import { Effect } from "effect"
2490 *
2491 * const program = Effect.asVoid(Effect.succeed(42))
2492 *
2493 * Effect.runSync(program) // => undefined
2494 * ```
2495 *
2496 * @category mapping
2497 * @since 2.0.0
2498 */
2499export const asVoid: <A, E, R>(self: Effect<A, E, R>) => Effect<void, E, R> = internal.asVoid
2500
2501/**
2502 * Swaps an effect's success and failure channels.
2503 *
2504 * **When to use**
2505 *
2506 * Use to swap an `Effect`'s success and failure channels.
2507 *
2508 * **Details**
2509 *
2510 * For an `Effect<A, E, R>`, the returned effect has type `Effect<E, A, R>`.
2511 *
2512 * **Example** (Swapping success and failure channels)
2513 *
2514 * ```ts import.meta.vitest
2515 * import { Effect } from "effect"
2516 *
2517 * // ┌─── Effect<number, string, never>
2518 * // ▼
2519 * const program = Effect.fail("Oh uh!").pipe(Effect.as(2))
2520 *
2521 * // ┌─── Effect<string, number, never>
2522 * // ▼
2523 * const flipped = Effect.flip(program)
2524 * Effect.runSync(flipped) // => "Oh uh!"
2525 * ```
2526 *
2527 * @category mapping
2528 * @since 2.0.0
2529 */
2530export const flip: <A, E, R>(self: Effect<A, E, R>) => Effect<E, A, R> = internal.flip
2531
2532// -----------------------------------------------------------------------------
2533// Zipping
2534// -----------------------------------------------------------------------------
2535
2536/**
2537 * Combines two effects into a single effect, producing a tuple with the results of both effects.
2538 *
2539 * **When to use**
2540 *
2541 * Use to combine exactly two effects into a tuple.
2542 *
2543 * **Details**
2544 *
2545 * The `zip` function executes the first effect (left) and then the second effect (right).
2546 * Once both effects succeed, their results are combined into a tuple.
2547 *
2548 * Concurrency:
2549 *
2550 * By default, `zip` processes the effects sequentially. To execute the effects concurrently,
2551 * use the `{ concurrent: true }` option.
2552 *
2553 * **Example** (Combining two effects sequentially)
2554 *
2555 * ```ts import.meta.vitest
2556 * import { Effect } from "effect"
2557 *
2558 * const task1 = Effect.succeed(1)
2559 * const task2 = Effect.succeed("hello")
2560 *
2561 * // Combine the two effects together
2562 * //
2563 * // ┌─── Effect<[number, string], never, never>
2564 * // ▼
2565 * const program = Effect.zip(task1, task2)
2566 *
2567 * Effect.runSync(program) // => [1, 'hello']
2568 * ```
2569 *
2570 * **Example** (Combining two effects concurrently)
2571 *
2572 * ```ts import.meta.vitest
2573 * import { Effect } from "effect"
2574 *
2575 * const task1 = Effect.succeed(1)
2576 * const task2 = Effect.succeed("hello")
2577 *
2578 * // Run both effects concurrently using the concurrent option
2579 * const program = Effect.zip(task1, task2, { concurrent: true })
2580 *
2581 * await Effect.runPromise(program) // => [1, 'hello']
2582 * ```
2583 *
2584 * @see {@link zipWith} for a version that combines the results with a custom function.
2585 * @see {@link all} for collecting a larger structure of effects.
2586 *
2587 * @category zipping
2588 * @since 2.0.0
2589 */
2590export const zip: {
2591 <A2, E2, R2>(
2592 that: Effect<A2, E2, R2>,
2593 options?: { readonly concurrent?: boolean | undefined } | undefined
2594 ): <A, E, R>(self: Effect<A, E, R>) => Effect<[A, A2], E2 | E, R2 | R>
2595 <A, E, R, A2, E2, R2>(
2596 self: Effect<A, E, R>,
2597 that: Effect<A2, E2, R2>,
2598 options?: { readonly concurrent?: boolean | undefined }
2599 ): Effect<[A, A2], E | E2, R | R2>
2600} = internal.zip
2601
2602/**
2603 * Combines two effects sequentially and applies a function to their results to
2604 * produce a single value.
2605 *
2606 * **When to use**
2607 *
2608 * Use when you need to run two effects sequentially and combine their results
2609 * with a function instead of keeping the results as a tuple.
2610 *
2611 * **Details**
2612 *
2613 * Concurrency:
2614 *
2615 * By default, the effects are run sequentially. To execute them concurrently,
2616 * use the `{ concurrent: true }` option.
2617 *
2618 * **Example** (Combining two success values with a function)
2619 *
2620 * ```ts import.meta.vitest
2621 * import { Effect } from "effect"
2622 *
2623 * const task1 = Effect.succeed(1)
2624 * const task2 = Effect.succeed("hello")
2625 *
2626 * const task3 = Effect.zipWith(
2627 * task1,
2628 * task2,
2629 * // Combines results into a single value
2630 * (number, string) => number + string.length
2631 * )
2632 *
2633 * Effect.runSync(task3) // => 6
2634 * ```
2635 *
2636 * @category zipping
2637 * @since 2.0.0
2638 */
2639export const zipWith: {
2640 <A2, E2, R2, A, B>(
2641 that: Effect<A2, E2, R2>,
2642 f: (a: A, b: A2) => B,
2643 options?: { readonly concurrent?: boolean | undefined }
2644 ): <E, R>(self: Effect<A, E, R>) => Effect<B, E2 | E, R2 | R>
2645 <A, E, R, A2, E2, R2, B>(
2646 self: Effect<A, E, R>,
2647 that: Effect<A2, E2, R2>,
2648 f: (a: A, b: A2) => B,
2649 options?: { readonly concurrent?: boolean | undefined }
2650 ): Effect<B, E2 | E, R2 | R>
2651} = internal.zipWith
2652
2653// -----------------------------------------------------------------------------
2654// Error handling
2655// -----------------------------------------------------------------------------
2656
2657const catch_: {
2658 <E, A2, E2, R2>(
2659 f: (e: E) => Effect<A2, E2, R2>
2660 ): <A, R>(self: Effect<A, E, R>) => Effect<A2 | A, E2, R2 | R>
2661 <A, E, R, A2, E2, R2>(
2662 self: Effect<A, E, R>,
2663 f: (e: E) => Effect<A2, E2, R2>
2664 ): Effect<A2 | A, E2, R2 | R>
2665} = internal.catch_
2666
2667export {
2668 /**
2669 * Handles all errors in an effect by providing a fallback effect.
2670 *
2671 * **When to use**
2672 *
2673 * Use when every recoverable error from an effect should be handled by the same
2674 * fallback function while unrecoverable defects remain defects.
2675 *
2676 * **Details**
2677 *
2678 * The `catch` function catches any errors that may occur during the
2679 * execution of an effect and allows you to handle them by specifying a fallback
2680 * effect. This ensures that the program continues without failing by recovering
2681 * from errors using the provided fallback logic.
2682 *
2683 * **Gotchas**
2684 *
2685 * `catch` only handles recoverable errors. It will not recover from
2686 * unrecoverable defects.
2687 *
2688 * @see {@link catchCause} for a version that can recover from both recoverable and unrecoverable errors.
2689 *
2690 * @category error handling
2691 * @since 4.0.0
2692 */
2693 catch_ as catch
2694}
2695
2696/**
2697 * Catches and handles specific errors by their `_tag` field, which is used as a
2698 * discriminator.
2699 *
2700 * **When to use**
2701 *
2702 * Use when you need to recover from one specific tagged error in an effect
2703 * error channel.
2704 *
2705 * **Details**
2706 *
2707 * The error type must have a readonly `_tag` field. `catchTag` matches that
2708 * field and only handles errors with the requested tag.
2709 *
2710 * **Example** (Handling a tagged error)
2711 *
2712 * ```ts import.meta.vitest
2713 * import { Effect } from "effect"
2714 *
2715 * class NetworkError {
2716 * readonly _tag = "NetworkError"
2717 * constructor(readonly message: string) {}
2718 * }
2719 *
2720 * class ValidationError {
2721 * readonly _tag = "ValidationError"
2722 * constructor(readonly message: string) {}
2723 * }
2724 *
2725 * const task: Effect.Effect<string, NetworkError | ValidationError> =
2726 * Effect.fail(new NetworkError("offline"))
2727 *
2728 * const program = Effect.catchTag(
2729 * task,
2730 * "NetworkError",
2731 * (error) => Effect.succeed(`Recovered from network error: ${error.message}`)
2732 * )
2733 *
2734 * Effect.runSync(program) // => "Recovered from network error: offline"
2735 * ```
2736 *
2737 * @see {@link catchTags} for handling multiple tagged errors in one call
2738 * @see {@link catchIf} for recovering from errors that match a predicate
2739 *
2740 * @category error handling
2741 * @since 2.0.0
2742 */
2743export const catchTag: {
2744 <
2745 const K extends Tags<E> | Arr.NonEmptyReadonlyArray<Tags<E>>,
2746 E,
2747 A1,
2748 E1,
2749 R1,
2750 A2 = unassigned,
2751 E2 = never,
2752 R2 = never
2753 >(
2754 k: K,
2755 f: (e: ExtractTag<NoInfer<E>, K extends Arr.NonEmptyReadonlyArray<string> ? K[number] : K>) => Effect<A1, E1, R1>,
2756 orElse?:
2757 | ((e: ExcludeTag<E, K extends Arr.NonEmptyReadonlyArray<string> ? K[number] : K>) => Effect<A2, E2, R2>)
2758 | undefined
2759 ): <A, R>(
2760 self: Effect<A, E, R>
2761 ) => Effect<
2762 A | A1 | Exclude<A2, unassigned>,
2763 | E1
2764 | E2
2765 | (A2 extends unassigned ? ExcludeTag<E, K extends Arr.NonEmptyReadonlyArray<string> ? K[number] : K> : never),
2766 R | R1 | R2
2767 >
2768 <
2769 A,
2770 E,
2771 R,
2772 const K extends Tags<E> | Arr.NonEmptyReadonlyArray<Tags<E>>,
2773 R1,
2774 E1,
2775 A1,
2776 A2 = unassigned,
2777 E2 = never,
2778 R2 = never
2779 >(
2780 self: Effect<A, E, R>,
2781 k: K,
2782 f: (e: ExtractTag<E, K extends Arr.NonEmptyReadonlyArray<string> ? K[number] : K>) => Effect<A1, E1, R1>,
2783 orElse?:
2784 | ((e: ExcludeTag<E, K extends Arr.NonEmptyReadonlyArray<string> ? K[number] : K>) => Effect<A2, E2, R2>)
2785 | undefined
2786 ): Effect<
2787 A | A1 | Exclude<A2, unassigned>,
2788 | E1
2789 | E2
2790 | (A2 extends unassigned ? ExcludeTag<E, K extends Arr.NonEmptyReadonlyArray<string> ? K[number] : K> : never),
2791 R | R1 | R2
2792 >
2793} = internal.catchTag
2794
2795/**
2796 * Handles multiple errors in a single block of code using their `_tag` field.
2797 *
2798 * **When to use**
2799 *
2800 * Use when one recovery step should handle several tagged error types by
2801 * matching their readonly `_tag` fields.
2802 *
2803 * **Details**
2804 *
2805 * Pass a handler table whose keys are tags, plus an optional fallback for
2806 * unmatched errors.
2807 *
2808 * The error type must have a readonly `_tag` field to use `catchTags`. This
2809 * field is used to identify and match errors.
2810 *
2811 * **Example** (Handling multiple tagged errors)
2812 *
2813 * ```ts import.meta.vitest
2814 * import { Data, Effect } from "effect"
2815 *
2816 * // Define tagged error types
2817 * class ValidationError extends Data.TaggedError("ValidationError")<{
2818 * message: string
2819 * }> {}
2820 *
2821 * class NetworkError extends Data.TaggedError("NetworkError")<{
2822 * statusCode: number
2823 * }> {}
2824 *
2825 * // An effect that might fail with multiple error types
2826 * const program: Effect.Effect<string, ValidationError | NetworkError> =
2827 * Effect.fail(new NetworkError({ statusCode: 503 }))
2828 *
2829 * // Handle multiple error types at once
2830 * const handled = Effect.catchTags(program, {
2831 * ValidationError: (error) =>
2832 * Effect.succeed(`Validation failed: ${error.message}`),
2833 * NetworkError: (error) => Effect.succeed(`Network error: ${error.statusCode}`)
2834 * })
2835 *
2836 * Effect.runSync(handled) // => "Network error: 503"
2837 * ```
2838 *
2839 * @category error handling
2840 * @since 2.0.0
2841 */
2842export const catchTags: {
2843 <
2844 E,
2845 Cases extends
2846 & { [K in Extract<E, { _tag: string }>["_tag"]]+?: ((error: Extract<E, { _tag: K }>) => Effect<any, any, any>) }
2847 & (unknown extends E ? {} : { [K in Exclude<keyof Cases, Extract<E, { _tag: string }>["_tag"]>]: never }),
2848 A2 = unassigned,
2849 E2 = never,
2850 R2 = never
2851 >(
2852 cases: Cases,
2853 orElse?: ((e: Exclude<E, { _tag: keyof Cases }>) => Effect<A2, E2, R2>) | undefined
2854 ): <A, R>(
2855 self: Effect<A, E, R>
2856 ) => Effect<
2857 | A
2858 | Exclude<A2, unassigned>
2859 | {
2860 [K in keyof Cases]: Cases[K] extends (...args: Array<any>) => Effect<infer A, any, any> ? A : never
2861 }[keyof Cases],
2862 | E2
2863 | (A2 extends unassigned ? Exclude<E, { _tag: keyof Cases }> : never)
2864 | {
2865 [K in keyof Cases]: Cases[K] extends (...args: Array<any>) => Effect<any, infer E, any> ? E : never
2866 }[keyof Cases],
2867 | R
2868 | R2
2869 | {
2870 [K in keyof Cases]: Cases[K] extends (...args: Array<any>) => Effect<any, any, infer R> ? R : never
2871 }[keyof Cases]
2872 >
2873 <
2874 R,
2875 E,
2876 A,
2877 Cases extends
2878 & { [K in Extract<E, { _tag: string }>["_tag"]]+?: ((error: Extract<E, { _tag: K }>) => Effect<any, any, any>) }
2879 & (unknown extends E ? {} : { [K in Exclude<keyof Cases, Extract<E, { _tag: string }>["_tag"]>]: never }),
2880 A2 = unassigned,
2881 E2 = never,
2882 R2 = never
2883 >(
2884 self: Effect<A, E, R>,
2885 cases: Cases,
2886 orElse?: ((e: Exclude<E, { _tag: keyof Cases }>) => Effect<A2, E2, R2>) | undefined
2887 ): Effect<
2888 | A
2889 | Exclude<A2, unassigned>
2890 | {
2891 [K in keyof Cases]: Cases[K] extends (...args: Array<any>) => Effect<infer A, any, any> ? A : never
2892 }[keyof Cases],
2893 | E2
2894 | (A2 extends unassigned ? Exclude<E, { _tag: keyof Cases }> : never)
2895 | {
2896 [K in keyof Cases]: Cases[K] extends (...args: Array<any>) => Effect<any, infer E, any> ? E : never
2897 }[keyof Cases],
2898 | R
2899 | R2
2900 | {
2901 [K in keyof Cases]: Cases[K] extends (...args: Array<any>) => Effect<any, any, infer R> ? R : never
2902 }[keyof Cases]
2903 >
2904} = internal.catchTags
2905
2906/**
2907 * Catches a specific reason within a tagged error.
2908 *
2909 * **When to use**
2910 *
2911 * Use to handle one nested reason inside an `Effect`'s tagged error while
2912 * preserving the parent error shape for unmatched reasons.
2913 *
2914 * **Details**
2915 *
2916 * Use this to handle nested error causes without removing the parent error
2917 * from the error channel. The handler receives the unwrapped reason.
2918 *
2919 * **Example** (Handling an error reason)
2920 *
2921 * ```ts import.meta.vitest
2922 * import { Data, Effect } from "effect"
2923 *
2924 * class RateLimitError extends Data.TaggedError("RateLimitError")<{
2925 * retryAfter: number
2926 * }> {}
2927 *
2928 * class QuotaExceededError extends Data.TaggedError("QuotaExceededError")<{
2929 * limit: number
2930 * }> {}
2931 *
2932 * class AiError extends Data.TaggedError("AiError")<{
2933 * reason: RateLimitError | QuotaExceededError
2934 * }> {}
2935 *
2936 * const program: Effect.Effect<string, AiError> = Effect.fail(
2937 * new AiError({ reason: new RateLimitError({ retryAfter: 30 }) })
2938 * )
2939 *
2940 * // Handle rate limits specifically
2941 * const handled = program.pipe(
2942 * Effect.catchReason("AiError", "RateLimitError", (reason) =>
2943 * Effect.succeed(`Retry after ${reason.retryAfter}s`)
2944 * )
2945 * )
2946 *
2947 * Effect.runSync(handled) // => "Retry after 30s"
2948 * ```
2949 *
2950 * @see {@link catchReasons} for handling several nested reason tags
2951 *
2952 * @category error handling
2953 * @since 4.0.0
2954 */
2955export const catchReason: {
2956 <
2957 K extends Tags<E>,
2958 E,
2959 RK extends ReasonTags<ExtractTag<NoInfer<E>, K>>,
2960 A2,
2961 E2,
2962 R2,
2963 A3 = unassigned,
2964 E3 = never,
2965 R3 = never
2966 >(
2967 errorTag: K,
2968 reasonTag: RK,
2969 f: (
2970 reason: ExtractReason<ExtractTag<NoInfer<E>, K>, RK>,
2971 error: NarrowReason<ExtractTag<NoInfer<E>, K>, RK>
2972 ) => Effect<A2, E2, R2>,
2973 orElse?:
2974 | ((
2975 reasons: ExcludeReason<ExtractTag<NoInfer<E>, K>, RK>,
2976 error: OmitReason<ExtractTag<NoInfer<E>, K>, RK>
2977 ) => Effect<A3, E3, R3>)
2978 | undefined
2979 ): <A, R>(
2980 self: Effect<A, E, R>
2981 ) => Effect<
2982 A | A2 | Exclude<A3, unassigned>,
2983 ExcludeTag<E, K> | E2 | E3 | (A3 extends unassigned ? ExtractTag<E, K> : never),
2984 R | R2 | R3
2985 >
2986 <
2987 A,
2988 E,
2989 R,
2990 K extends Tags<E>,
2991 RK extends ReasonTags<ExtractTag<E, K>>,
2992 A2,
2993 E2,
2994 R2,
2995 A3 = unassigned,
2996 E3 = never,
2997 R3 = never
2998 >(
2999 self: Effect<A, E, R>,
3000 errorTag: K,
3001 reasonTag: RK,
3002 f: (reason: ExtractReason<ExtractTag<E, K>, RK>, error: NarrowReason<ExtractTag<E, K>, RK>) => Effect<A2, E2, R2>,
3003 orElse?:
3004 | ((reasons: ExcludeReason<ExtractTag<E, K>, RK>, error: OmitReason<ExtractTag<E, K>, RK>) => Effect<A3, E3, R3>)
3005 | undefined
3006 ): Effect<
3007 A | A2 | Exclude<A3, unassigned>,
3008 ExcludeTag<E, K> | E2 | E3 | (A3 extends unassigned ? ExtractTag<E, K> : never),
3009 R | R2 | R3
3010 >
3011} = internal.catchReason
3012
3013/**
3014 * Catches multiple reasons within a tagged error using an object of handlers.
3015 *
3016 * **Example** (Handling multiple error reasons)
3017 *
3018 * ```ts import.meta.vitest
3019 * import { Data, Effect } from "effect"
3020 *
3021 * class RateLimitError extends Data.TaggedError("RateLimitError")<{
3022 * retryAfter: number
3023 * }> {}
3024 *
3025 * class QuotaExceededError extends Data.TaggedError("QuotaExceededError")<{
3026 * limit: number
3027 * }> {}
3028 *
3029 * class AiError extends Data.TaggedError("AiError")<{
3030 * reason: RateLimitError | QuotaExceededError
3031 * }> {}
3032 *
3033 * const program: Effect.Effect<string, AiError> = Effect.fail(
3034 * new AiError({ reason: new QuotaExceededError({ limit: 100 }) })
3035 * )
3036 *
3037 * const handled = program.pipe(
3038 * Effect.catchReasons("AiError", {
3039 * RateLimitError: (reason) =>
3040 * Effect.succeed(`Retry after ${reason.retryAfter}s`),
3041 * QuotaExceededError: (reason) =>
3042 * Effect.succeed(`Quota exceeded: ${reason.limit}`)
3043 * })
3044 * )
3045 *
3046 * Effect.runSync(handled) // => "Quota exceeded: 100"
3047 * ```
3048 *
3049 * @category error handling
3050 * @since 4.0.0
3051 */
3052export const catchReasons: {
3053 <
3054 K extends Tags<E>,
3055 E,
3056 Cases extends {
3057 [RK in ReasonTags<ExtractTag<NoInfer<E>, K>>]+?: (
3058 reason: ExtractReason<ExtractTag<NoInfer<E>, K>, RK>,
3059 error: NarrowReason<ExtractTag<NoInfer<E>, K>, RK>
3060 ) => Effect<any, any, any>
3061 },
3062 A2 = unassigned,
3063 E2 = never,
3064 R2 = never
3065 >(
3066 errorTag: K,
3067 cases: Cases,
3068 orElse?:
3069 | ((
3070 reason: ExcludeReason<ExtractTag<NoInfer<E>, K>, Extract<keyof Cases, string>>,
3071 error: OmitReason<ExtractTag<NoInfer<E>, K>, Extract<keyof Cases, string>>
3072 ) => Effect<A2, E2, R2>)
3073 | undefined
3074 ): <A, R>(
3075 self: Effect<A, E, R>
3076 ) => Effect<
3077 | A
3078 | Exclude<A2, unassigned>
3079 | {
3080 [RK in keyof Cases]: Cases[RK] extends (...args: Array<any>) => Effect<infer A, any, any> ? A : never
3081 }[keyof Cases],
3082 | ExcludeTag<E, K>
3083 | E2
3084 | (A2 extends unassigned ? ExtractTag<E, K> : never)
3085 | {
3086 [RK in keyof Cases]: Cases[RK] extends (...args: Array<any>) => Effect<any, infer E, any> ? E : never
3087 }[keyof Cases],
3088 | R
3089 | R2
3090 | {
3091 [RK in keyof Cases]: Cases[RK] extends (...args: Array<any>) => Effect<any, any, infer R> ? R : never
3092 }[keyof Cases]
3093 >
3094 <
3095 A,
3096 E,
3097 R,
3098 K extends Tags<E>,
3099 Cases extends {
3100 [RK in ReasonTags<ExtractTag<E, K>>]+?: (
3101 reason: ExtractReason<ExtractTag<E, K>, RK>,
3102 error: NarrowReason<ExtractTag<E, K>, RK>
3103 ) => Effect<any, any, any>
3104 },
3105 A2 = unassigned,
3106 E2 = never,
3107 R2 = never
3108 >(
3109 self: Effect<A, E, R>,
3110 errorTag: K,
3111 cases: Cases,
3112 orElse?:
3113 | ((
3114 reason: ExcludeReason<ExtractTag<NoInfer<E>, K>, Extract<keyof Cases, string>>,
3115 error: OmitReason<ExtractTag<NoInfer<E>, K>, Extract<keyof Cases, string>>
3116 ) => Effect<A2, E2, R2>)
3117 | undefined
3118 ): Effect<
3119 | A
3120 | Exclude<A2, unassigned>
3121 | {
3122 [RK in keyof Cases]: Cases[RK] extends (...args: Array<any>) => Effect<infer A, any, any> ? A : never
3123 }[keyof Cases],
3124 | ExcludeTag<E, K>
3125 | E2
3126 | (A2 extends unassigned ? ExtractTag<E, K> : never)
3127 | {
3128 [RK in keyof Cases]: Cases[RK] extends (...args: Array<any>) => Effect<any, infer E, any> ? E : never
3129 }[keyof Cases],
3130 | R
3131 | R2
3132 | {
3133 [RK in keyof Cases]: Cases[RK] extends (...args: Array<any>) => Effect<any, any, infer R> ? R : never
3134 }[keyof Cases]
3135 >
3136} = internal.catchReasons
3137
3138/**
3139 * Type helper that keeps only error tags whose tagged error contains a tagged `reason` field.
3140 *
3141 * **When to use**
3142 *
3143 * Use to constrain custom helpers or overloads to parent error tags whose error
3144 * contains a tagged reason.
3145 *
3146 * **Details**
3147 *
3148 * The mapped type keeps each parent error tag whose extracted tagged error has
3149 * at least one reason tag, and removes tags that do not carry tagged reasons.
3150 *
3151 * @see {@link unwrapReason} for promoting nested reason errors into the error channel
3152 * @see {@link catchReason} for handling one nested reason tag
3153 * @see {@link catchReasons} for handling several nested reason tags
3154 *
3155 * @category error handling
3156 * @since 4.0.0
3157 */
3158export type TagsWithReason<E> = {
3159 [T in Tags<E>]: ReasonTags<ExtractTag<E, T>> extends never ? never : T
3160}[Tags<E>]
3161
3162/**
3163 * Promotes nested reason errors into the Effect error channel, replacing
3164 * the parent error.
3165 *
3166 * **Example** (Extracting the reason from a tagged error)
3167 *
3168 * ```ts import.meta.vitest
3169 * import { Data, Effect } from "effect"
3170 *
3171 * class RateLimitError extends Data.TaggedError("RateLimitError")<{
3172 * retryAfter: number
3173 * }> {}
3174 *
3175 * class QuotaExceededError extends Data.TaggedError("QuotaExceededError")<{
3176 * limit: number
3177 * }> {}
3178 *
3179 * class AiError extends Data.TaggedError("AiError")<{
3180 * reason: RateLimitError | QuotaExceededError
3181 * }> {}
3182 *
3183 * const program: Effect.Effect<string, AiError> = Effect.fail(
3184 * new AiError({ reason: new RateLimitError({ retryAfter: 30 }) })
3185 * )
3186 *
3187 * // Before: Effect<string, AiError>
3188 * // After: Effect<string, RateLimitError | QuotaExceededError>
3189 * const unwrapped = program.pipe(Effect.unwrapReason("AiError"))
3190 * Effect.runSync(Effect.flip(unwrapped))._tag // => "RateLimitError"
3191 * ```
3192 *
3193 * @category error handling
3194 * @since 4.0.0
3195 */
3196export const unwrapReason: {
3197 <
3198 K extends TagsWithReason<E>,
3199 E
3200 >(
3201 errorTag: K
3202 ): <A, R>(self: Effect<A, E, R>) => Effect<A, ExcludeTag<E, K> | ReasonOf<ExtractTag<E, K>>, R>
3203 <
3204 A,
3205 E,
3206 R,
3207 K extends TagsWithReason<E>
3208 >(
3209 self: Effect<A, E, R>,
3210 errorTag: K
3211 ): Effect<A, ExcludeTag<E, K> | ReasonOf<ExtractTag<E, K>>, R>
3212} = internal.unwrapReason
3213
3214/**
3215 * Handles both recoverable and unrecoverable errors by providing a recovery
3216 * effect.
3217 *
3218 * **When to use**
3219 *
3220 * Use when you need to recover from an `Effect` by inspecting the full `Cause`,
3221 * including recoverable failures, defects, and interruptions, instead of only
3222 * the typed error value.
3223 *
3224 * **Details**
3225 *
3226 * When to Recover from Defects:
3227 *
3228 * Defects are unexpected errors that typically shouldn't be recovered from, as
3229 * they often indicate serious issues. However, in some cases, such as
3230 * dynamically loaded plugins, controlled recovery might be needed.
3231 *
3232 * **Example** (Recovering from full failure causes)
3233 *
3234 * ```ts import.meta.vitest
3235 * import { Cause, Effect } from "effect"
3236 * const output: Array<unknown> = []
3237 *
3238 * // An effect that might fail in different ways
3239 * const program = Effect.die("Something went wrong")
3240 *
3241 * // Recover from any cause (including defects)
3242 * const recovered = Effect.catchCause(program, (cause) => {
3243 * if (Cause.hasDies(cause)) {
3244 * return Effect.sync(() => { output.push("Caught defect") }).pipe(
3245 * Effect.as("Recovered from defect")
3246 * )
3247 * }
3248 * return Effect.succeed("Unknown error")
3249 * })
3250 *
3251 * void output.push(Effect.runSync(recovered))
3252 * output // => ["Caught defect", "Recovered from defect"]
3253 * ```
3254 *
3255 * @category error handling
3256 * @since 4.0.0
3257 */
3258export const catchCause: {
3259 <E, A2, E2, R2>(
3260 f: (cause: Cause.Cause<E>) => Effect<A2, E2, R2>
3261 ): <A, R>(self: Effect<A, E, R>) => Effect<A2 | A, E2, R2 | R>
3262 <A, E, R, A2, E2, R2>(
3263 self: Effect<A, E, R>,
3264 f: (cause: Cause.Cause<E>) => Effect<A2, E2, R2>
3265 ): Effect<A | A2, E2, R | R2>
3266} = internal.catchCause
3267
3268/**
3269 * Recovers from defects using a provided recovery function.
3270 *
3271 * **When to use**
3272 *
3273 * Use when you need to report or translate defects at integration boundaries.
3274 *
3275 * **Details**
3276 *
3277 * `catchDefect` handles unexpected defects, such as thrown exceptions or
3278 * values passed to `die`, without catching typed failures or interruptions.
3279 *
3280 * When to Recover from Defects:
3281 *
3282 * Defects are unexpected errors that typically should not be recovered from, as
3283 * they often indicate serious issues. In some cases, such as dynamically loaded
3284 * plugins, controlled recovery may be needed.
3285 *
3286 * **Example** (Recovering from defects)
3287 *
3288 * ```ts import.meta.vitest
3289 * import { Effect } from "effect"
3290 * const output: Array<unknown> = []
3291 *
3292 * // An effect that might throw an unexpected error (defect)
3293 * const program = Effect.sync(() => {
3294 * throw new Error("Unexpected error")
3295 * })
3296 *
3297 * // Recover from defects only
3298 * const recovered = Effect.catchDefect(program, (defect) => {
3299 * return Effect.sync(() => { output.push(`Caught defect: ${(defect as Error).message}`) }).pipe(
3300 * Effect.as("Recovered from defect")
3301 * )
3302 * })
3303 *
3304 * void output.push(Effect.runSync(recovered))
3305 * output // => ["Caught defect: Unexpected error", "Recovered from defect"]
3306 * ```
3307 *
3308 * @category error handling
3309 * @since 4.0.0
3310 */
3311export const catchDefect: {
3312 <A2, E2, R2>(
3313 f: (defect: unknown) => Effect<A2, E2, R2>
3314 ): <A, E, R>(self: Effect<A, E, R>) => Effect<A2 | A, E2 | E, R2 | R>
3315 <A, E, R, A2, E2, R2>(
3316 self: Effect<A, E, R>,
3317 f: (defect: unknown) => Effect<A2, E2, R2>
3318 ): Effect<A | A2, E | E2, R | R2>
3319} = internal.catchDefect
3320
3321/**
3322 * Recovers from specific errors using a `Predicate` or `Refinement`.
3323 *
3324 * **When to use**
3325 *
3326 * Use when you need to recover from errors that match a condition.
3327 *
3328 * **Details**
3329 *
3330 * Use a `Refinement` for type narrowing or a `Predicate` for simple boolean
3331 * matching. Non-matching errors re-fail with the original cause. Defects and
3332 * interrupts are not caught.
3333 *
3334 * **Example** (Recovering when a predicate matches)
3335 *
3336 * ```ts import.meta.vitest
3337 * import { Data, Effect, Filter } from "effect"
3338 *
3339 * class NotFound extends Data.TaggedError("NotFound")<{ id: string }> {}
3340 *
3341 * const program = Effect.fail(new NotFound({ id: "user-1" }))
3342 *
3343 * // With a refinement
3344 * const recovered = program.pipe(
3345 * Effect.catchIf(
3346 * (error): error is NotFound => error._tag === "NotFound",
3347 * (error) => Effect.succeed(`missing:${error.id}`)
3348 * )
3349 * )
3350 *
3351 * // With a Filter
3352 * const recovered2 = program.pipe(
3353 * Effect.catchFilter(
3354 * Filter.tagged("NotFound"),
3355 * (error) => Effect.succeed(`missing:${error.id}`)
3356 * )
3357 * )
3358 *
3359 * Effect.runSync(Effect.all([recovered, recovered2])) // => ['missing:user-1', 'missing:user-1']
3360 * ```
3361 *
3362 * @category error handling
3363 * @since 2.0.0
3364 */
3365export const catchIf: {
3366 <E, EB extends E, A2, E2, R2, A3 = unassigned, E3 = never, R3 = never>(
3367 refinement: Predicate.Refinement<NoInfer<E>, EB>,
3368 f: (e: EB) => Effect<A2, E2, R2>,
3369 orElse?: ((e: Exclude<E, EB>) => Effect<A3, E3, R3>) | undefined
3370 ): <A, R>(
3371 self: Effect<A, E, R>
3372 ) => Effect<A | A2 | Exclude<A3, unassigned>, E2 | E3 | (A3 extends unassigned ? Exclude<E, EB> : never), R | R2 | R3>
3373 <E, A2, E2, R2, A3 = unassigned, E3 = never, R3 = never>(
3374 predicate: Predicate.Predicate<NoInfer<E>>,
3375 f: (e: NoInfer<E>) => Effect<A2, E2, R2>,
3376 orElse?: ((e: NoInfer<E>) => Effect<A3, E3, R3>) | undefined
3377 ): <A, R>(
3378 self: Effect<A, E, R>
3379 ) => Effect<A | A2 | Exclude<A3, unassigned>, E2 | E3 | (A3 extends unassigned ? E : never), R | R2 | R3>
3380 <A, E, R, EB extends E, A2, E2, R2, A3 = unassigned, E3 = never, R3 = never>(
3381 self: Effect<A, E, R>,
3382 refinement: Predicate.Refinement<E, EB>,
3383 f: (e: EB) => Effect<A2, E2, R2>,
3384 orElse?: ((e: Exclude<E, EB>) => Effect<A3, E3, R3>) | undefined
3385 ): Effect<A | A2 | Exclude<A3, unassigned>, E2 | E3 | (A3 extends unassigned ? Exclude<E, EB> : never), R | R2 | R3>
3386 <A, E, R, A2, E2, R2, A3 = unassigned, E3 = never, R3 = never>(
3387 self: Effect<A, E, R>,
3388 predicate: Predicate.Predicate<E>,
3389 f: (e: E) => Effect<A2, E2, R2>,
3390 orElse?: ((e: E) => Effect<A3, E3, R3>) | undefined
3391 ): Effect<A | A2 | Exclude<A3, unassigned>, E2 | E3 | (A3 extends unassigned ? E : never), R | R2 | R3>
3392} = internal.catchIf
3393
3394/**
3395 * Recovers from specific errors using a `Filter`.
3396 *
3397 * **When to use**
3398 *
3399 * Use to recover from typed `Effect` errors with a reusable `Filter` when
3400 * matching can also narrow or transform the error before choosing the recovery
3401 * effect.
3402 *
3403 * **Details**
3404 *
3405 * The filter runs on typed failures extracted from the `Cause`. Successful
3406 * filter results are passed to `f`; failed filter results are passed to
3407 * `orElse` when provided. Without `orElse`, the original failure cause is
3408 * preserved.
3409 *
3410 * @see {@link catchIf} for predicate-based recovery from typed errors
3411 * @see {@link catchTag} for recovering from a single tagged error
3412 * @see {@link catchTags} for recovering from several tagged errors
3413 * @see {@link catchCauseFilter} for filtering full causes instead of typed errors
3414 *
3415 * @category error handling
3416 * @since 4.0.0
3417 */
3418export const catchFilter: {
3419 <E, EB, A2, E2, R2, X, A3 = unassigned, E3 = never, R3 = never>(
3420 filter: Filter.Filter<NoInfer<E>, EB, X>,
3421 f: (e: EB) => Effect<A2, E2, R2>,
3422 orElse?: ((e: X) => Effect<A3, E3, R3>) | undefined
3423 ): <A, R>(
3424 self: Effect<A, E, R>
3425 ) => Effect<A | A2 | Exclude<A3, unassigned>, E2 | E3 | (A3 extends unassigned ? X : never), R | R2 | R3>
3426 <A, E, R, EB, A2, E2, R2, X, A3 = unassigned, E3 = never, R3 = never>(
3427 self: Effect<A, E, R>,
3428 filter: Filter.Filter<NoInfer<E>, EB, X>,
3429 f: (e: EB) => Effect<A2, E2, R2>,
3430 orElse?: ((e: X) => Effect<A3, E3, R3>) | undefined
3431 ): Effect<A | A2 | Exclude<A3, unassigned>, E2 | E3 | (A3 extends unassigned ? X : never), R | R2 | R3>
3432} = internal.catchFilter
3433
3434/**
3435 * Catches `NoSuchElementError` failures and converts them to `Option.none`.
3436 *
3437 * **When to use**
3438 *
3439 * Use when you expect missing-value failures and want them to become an
3440 * optional success while all other failures keep failing.
3441 *
3442 * **Details**
3443 *
3444 * Success values become `Option.some`, `NoSuchElementError` becomes
3445 * `Option.none`, and all other errors are preserved.
3446 *
3447 * **Example** (Recovering from missing Option values)
3448 *
3449 * ```ts import.meta.vitest
3450 * import { Effect, Option } from "effect"
3451 * const output: Array<unknown> = []
3452 *
3453 * const some = Effect.fromNullishOr(1).pipe(Effect.catchNoSuchElement)
3454 * const none = Effect.fromNullishOr(null).pipe(Effect.catchNoSuchElement)
3455 *
3456 * void output.push(Effect.runSync(some))
3457 * void output.push(Effect.runSync(none))
3458 * output // => [Option.some(1), Option.none()]
3459 * ```
3460 *
3461 * @see {@link fromOption} for converting `Option.none` into `NoSuchElementError`
3462 * @see {@link fromNullishOr} for converting nullish values into `NoSuchElementError`
3463 * @see {@link option} for converting any failure into `Option.none`
3464 *
3465 * @category error handling
3466 * @since 4.0.0
3467 */
3468export const catchNoSuchElement: <A, E, R>(
3469 self: Effect<A, E, R>
3470) => Effect<Option<A>, Exclude<E, Cause.NoSuchElementError>, R> = internal.catchNoSuchElement
3471
3472/**
3473 * Recovers from specific failures based on a predicate.
3474 *
3475 * **When to use**
3476 *
3477 * Use to recover an `Effect` from full causes selected by a predicate.
3478 *
3479 * **Details**
3480 *
3481 * This function allows you to conditionally catch and recover from failures
3482 * that match a specific predicate. This is useful when you want to handle
3483 * only certain types of errors while letting others propagate.
3484 *
3485 * **Example** (Recovering from selected causes)
3486 *
3487 * ```ts import.meta.vitest
3488 * import { Cause, Effect } from "effect"
3489 * const output: Array<unknown> = []
3490 *
3491 * const httpRequest = Effect.fail("Network Error")
3492 *
3493 * // Only catch network-related failures
3494 * const program = Effect.catchCauseIf(
3495 * httpRequest,
3496 * Cause.hasFails,
3497 * (cause) =>
3498 * Effect.gen(function*() {
3499 * yield* Effect.sync(() => { output.push(`Caught network error: ${Cause.squash(cause)}`) })
3500 * return "Fallback response"
3501 * })
3502 * )
3503 *
3504 * void output.push(Effect.runSync(program))
3505 * output // => ["Caught network error: Network Error", "Fallback response"]
3506 * ```
3507 *
3508 * @see {@link catchCause} for recovering from every cause
3509 * @see {@link catchCauseFilter} for selecting full causes with a `Filter`
3510 * @see {@link catchIf} for predicate-based recovery from typed errors
3511 *
3512 * @category error handling
3513 * @since 4.0.0
3514 */
3515export const catchCauseIf: {
3516 <E, B, E2, R2>(
3517 predicate: Predicate.Predicate<Cause.Cause<E>>,
3518 f: (cause: Cause.Cause<E>) => Effect<B, E2, R2>
3519 ): <A, R>(self: Effect<A, E, R>) => Effect<A | B, E | E2, R | R2>
3520 <A, E, R, B, E2, R2>(
3521 self: Effect<A, E, R>,
3522 predicate: Predicate.Predicate<Cause.Cause<E>>,
3523 f: (cause: Cause.Cause<E>) => Effect<B, E2, R2>
3524 ): Effect<A | B, E | E2, R | R2>
3525} = internal.catchCauseIf
3526
3527/**
3528 * Recovers from specific failures based on a `Filter`.
3529 *
3530 * **When to use**
3531 *
3532 * Use when you need to recover an `Effect` only from causes selected by a
3533 * `Filter`, while giving the recovery both the selected value and the original
3534 * `Cause`.
3535 *
3536 * **Details**
3537 *
3538 * The filter is applied to the full `Cause`. When it succeeds, the handler
3539 * receives the selected value and the original cause. When it fails, the effect
3540 * re-fails with the residual cause returned by the filter.
3541 *
3542 * @see {@link catchCauseIf} for predicate-based cause selection
3543 * @see {@link catchFilter} for filtering typed error values instead of full causes
3544 * @see {@link catchCause} for recovering from every cause without filtering
3545 *
3546 * @category error handling
3547 * @since 4.0.0
3548 */
3549export const catchCauseFilter: {
3550 <E, B, E2, R2, EB, X extends Cause.Cause<any>>(
3551 filter: Filter.Filter<Cause.Cause<E>, EB, X>,
3552 f: (failure: EB, cause: Cause.Cause<E>) => Effect<B, E2, R2>
3553 ): <A, R>(self: Effect<A, E, R>) => Effect<A | B, Cause.Cause.Error<X> | E2, R | R2>
3554 <A, E, R, B, E2, R2, EB, X extends Cause.Cause<any>>(
3555 self: Effect<A, E, R>,
3556 filter: Filter.Filter<Cause.Cause<E>, EB, X>,
3557 f: (failure: EB, cause: Cause.Cause<E>) => Effect<B, E2, R2>
3558 ): Effect<A | B, Cause.Cause.Error<X> | E2, R | R2>
3559} = internal.catchCauseFilter
3560
3561/**
3562 * Transforms the failure value of an effect without changing its success value.
3563 *
3564 * **When to use**
3565 *
3566 * Use to translate an `Effect`'s typed failures while leaving successful values
3567 * unchanged.
3568 *
3569 * **Details**
3570 *
3571 * Only the failure channel is transformed. The success channel and requirements
3572 * are preserved.
3573 *
3574 * **Example** (Transforming the error channel)
3575 *
3576 * ```ts import.meta.vitest
3577 * import { Data, Effect } from "effect"
3578 *
3579 * class TaskError extends Data.TaggedError("TaskError")<{ readonly message: string }> {}
3580 *
3581 * // ┌─── Effect<number, string, never>
3582 * // ▼
3583 * const simulatedTask = Effect.fail("Oh no!").pipe(Effect.as(1))
3584 *
3585 * // ┌─── Effect<number, TaskError, never>
3586 * // ▼
3587 * const mapped = Effect.mapError(
3588 * simulatedTask,
3589 * (message) => new TaskError({ message })
3590 * )
3591 * Effect.runSync(Effect.flip(mapped)).message // => "Oh no!"
3592 * ```
3593 *
3594 * @see {@link map} for a version that operates on the success channel.
3595 * @see {@link mapBoth} for a version that operates on both channels.
3596 *
3597 * @category error handling
3598 * @since 2.0.0
3599 */
3600export const mapError: {
3601 <E, E2>(f: (e: E) => E2): <A, R>(self: Effect<A, E, R>) => Effect<A, E2, R>
3602 <A, E, R, E2>(self: Effect<A, E, R>, f: (e: E) => E2): Effect<A, E2, R>
3603} = internal.mapError
3604
3605/**
3606 * Applies transformations to both the success and error channels of an effect.
3607 *
3608 * **When to use**
3609 *
3610 * Use to transform both success and failure channels of an `Effect` without
3611 * changing whether it succeeds or fails.
3612 *
3613 * **Details**
3614 *
3615 * This function takes two map functions as arguments: one for the error channel
3616 * and one for the success channel. You can use it when you want to modify both
3617 * the error and the success values without altering the overall success or
3618 * failure status of the effect.
3619 *
3620 * **Example** (Transforming success and failure channels)
3621 *
3622 * ```ts import.meta.vitest
3623 * import { Data, Effect } from "effect"
3624 *
3625 * class TaskError extends Data.TaggedError("TaskError")<{ readonly message: string }> {}
3626 *
3627 * // ┌─── Effect<number, string, never>
3628 * // ▼
3629 * const simulatedTask = Effect.fail("Oh no!").pipe(Effect.as(1))
3630 *
3631 * // ┌─── Effect<boolean, TaskError, never>
3632 * // ▼
3633 * const modified = Effect.mapBoth(simulatedTask, {
3634 * onFailure: (message) => new TaskError({ message }),
3635 * onSuccess: (n) => n > 0
3636 * })
3637 * Effect.runSync(Effect.flip(modified)).message // => "Oh no!"
3638 * ```
3639 *
3640 * @see {@link map} for a version that operates on the success channel.
3641 * @see {@link mapError} for a version that operates on the error channel.
3642 *
3643 * @category mapping
3644 * @since 2.0.0
3645 */
3646export const mapBoth: {
3647 <E, E2, A, A2>(
3648 options: { readonly onFailure: (e: E) => E2; readonly onSuccess: (a: A) => A2 }
3649 ): <R>(self: Effect<A, E, R>) => Effect<A2, E2, R>
3650 <A, E, R, E2, A2>(
3651 self: Effect<A, E, R>,
3652 options: { readonly onFailure: (e: E) => E2; readonly onSuccess: (a: A) => A2 }
3653 ): Effect<A2, E2, R>
3654} = internal.mapBoth
3655
3656/**
3657 * Converts typed failures from the error channel into defects, removing the
3658 * error type from the returned effect.
3659 *
3660 * **When to use**
3661 *
3662 * Use when you need to turn an `Effect` typed failure that represents an
3663 * unrecoverable bug or invalid state into a defect.
3664 *
3665 * **Example** (Converting typed failures into defects)
3666 *
3667 * ```ts import.meta.vitest
3668 * import { Data, Effect, Exit } from "effect"
3669 *
3670 * class DivideByZeroError extends Data.TaggedError("DivideByZeroError")<{}> {}
3671 *
3672 * const divide = (a: number, b: number) =>
3673 * b === 0
3674 * ? Effect.fail(new DivideByZeroError())
3675 * : Effect.succeed(a / b)
3676 *
3677 * // ┌─── Effect<number, never, never>
3678 * // ▼
3679 * const program = Effect.orDie(divide(1, 0))
3680 *
3681 * Effect.runSyncExit(program) // => Exit.die(new DivideByZeroError())
3682 * ```
3683 *
3684 * @category error handling
3685 * @since 2.0.0
3686 */
3687export const orDie: <A, E, R>(self: Effect<A, E, R>) => Effect<A, never, R> = internal.orDie
3688
3689/**
3690 * Runs an effectful operation when the source effect fails, while preserving
3691 * the original failure when the operation succeeds.
3692 *
3693 * **Details**
3694 *
3695 * Use this for logging, metrics, or other failure-side observations. If the
3696 * operation passed to `tapError` fails, that error is also represented in the
3697 * returned effect's error channel.
3698 *
3699 * **Example** (Running effects on failure)
3700 *
3701 * ```ts import.meta.vitest
3702 * import { Effect, Exit } from "effect"
3703 * const output: Array<unknown> = []
3704 *
3705 * // Simulate a task that fails with an error
3706 * const task: Effect.Effect<number, string> = Effect.fail("NetworkError")
3707 *
3708 * // Use tapError to log the error message when the task fails
3709 * const tapping = Effect.tapError(
3710 * task,
3711 * (error) => Effect.sync(() => { output.push(`expected error: ${error}`) })
3712 * )
3713 *
3714 * void output.push(Effect.runSyncExit(tapping))
3715 * output // => ["expected error: NetworkError", Exit.fail("NetworkError")]
3716 * ```
3717 *
3718 * @category error handling
3719 * @since 2.0.0
3720 */
3721export const tapError: {
3722 <E, X, E2, R2>(
3723 f: (e: NoInfer<E>) => Effect<X, E2, R2>
3724 ): <A, R>(self: Effect<A, E, R>) => Effect<A, E | E2, R2 | R>
3725 <A, E, R, X, E2, R2>(
3726 self: Effect<A, E, R>,
3727 f: (e: E) => Effect<X, E2, R2>
3728 ): Effect<A, E | E2, R | R2>
3729} = internal.tapError
3730
3731/**
3732 * Runs an effectful handler when a failure's `_tag` matches.
3733 *
3734 * **Details**
3735 *
3736 * Use this with tagged-union errors to perform side effects for one tag or a
3737 * list of tags. When the handler succeeds, the original failure is preserved;
3738 * if the handler fails, its error is also included in the returned effect.
3739 *
3740 * **Example** (Running effects for tagged failures)
3741 *
3742 * ```ts import.meta.vitest
3743 * import { Data, Effect, Exit } from "effect"
3744 * const output: Array<unknown> = []
3745 *
3746 * class NetworkError extends Data.TaggedError("NetworkError")<{
3747 * statusCode: number
3748 * }> {}
3749 *
3750 * class ValidationError extends Data.TaggedError("ValidationError")<{
3751 * field: string
3752 * }> {}
3753 *
3754 * const task: Effect.Effect<number, NetworkError | ValidationError> =
3755 * Effect.fail(new NetworkError({ statusCode: 504 }))
3756 *
3757 * const program = Effect.tapErrorTag(task, "NetworkError", (error) =>
3758 * Effect.sync(() => { output.push(`expected error: ${error.statusCode}`) })
3759 * )
3760 *
3761 * void output.push(Effect.runSyncExit(program))
3762 * output // => ["expected error: 504", Exit.fail(new NetworkError({ statusCode: 504 }))]
3763 * ```
3764 *
3765 * @category error handling
3766 * @since 2.0.0
3767 */
3768export const tapErrorTag: {
3769 <const K extends Tags<E> | Arr.NonEmptyReadonlyArray<Tags<E>>, E, A1, E1, R1>(
3770 k: K,
3771 f: (e: ExtractTag<NoInfer<E>, K extends Arr.NonEmptyReadonlyArray<string> ? K[number] : K>) => Effect<A1, E1, R1>
3772 ): <A, R>(self: Effect<A, E, R>) => Effect<A, E | E1, R1 | R>
3773 <
3774 A,
3775 E,
3776 R,
3777 const K extends Tags<E> | Arr.NonEmptyReadonlyArray<Tags<E>>,
3778 R1,
3779 E1,
3780 A1
3781 >(
3782 self: Effect<A, E, R>,
3783 k: K,
3784 f: (e: ExtractTag<E, K extends Arr.NonEmptyReadonlyArray<string> ? K[number] : K>) => Effect<A1, E1, R1>
3785 ): Effect<A, E | E1, R | R1>
3786} = internal.tapErrorTag
3787
3788/**
3789 * Runs an effectful operation with the full `Cause` when the source effect
3790 * fails.
3791 *
3792 * **When to use**
3793 *
3794 * Use when failure observation needs typed failures, defects, and interruptions
3795 * rather than only the typed error value.
3796 *
3797 * **Details**
3798 *
3799 * Use this to log or inspect typed failures, defects, and interruptions. When
3800 * the operation succeeds, the original cause is preserved. If the operation
3801 * fails, its error is also represented in the returned effect.
3802 *
3803 * **Example** (Observing full failure causes)
3804 *
3805 * ```ts import.meta.vitest
3806 * import { Cause, Effect, Exit } from "effect"
3807 * const output: Array<unknown> = []
3808 *
3809 * const task = Effect.fail("Something went wrong")
3810 *
3811 * const program = Effect.tapCause(
3812 * task,
3813 * (cause) => Effect.sync(() => { output.push(`Logging cause: ${Cause.squash(cause)}`) })
3814 * )
3815 *
3816 * void output.push(Effect.runSyncExit(program))
3817 * output // => ["Logging cause: Something went wrong", Exit.fail("Something went wrong")]
3818 * ```
3819 *
3820 * @category error handling
3821 * @since 4.0.0
3822 */
3823export const tapCause: {
3824 <E, X, E2, R2>(
3825 f: (cause: Cause.Cause<NoInfer<E>>) => Effect<X, E2, R2>
3826 ): <A, R>(self: Effect<A, E, R>) => Effect<A, E | E2, R2 | R>
3827 <A, E, R, X, E2, R2>(
3828 self: Effect<A, E, R>,
3829 f: (cause: Cause.Cause<E>) => Effect<X, E2, R2>
3830 ): Effect<A, E | E2, R | R2>
3831} = internal.tapCause
3832
3833/**
3834 * Executes a side effect conditionally when a failed effect's cause matches a predicate.
3835 *
3836 * **Details**
3837 *
3838 * This function allows you to tap into the cause of an effect's failure only when
3839 * the cause matches a specific predicate. This is useful for conditional logging,
3840 * monitoring, or other side effects based on the type of failure.
3841 *
3842 * **Example** (Observing selected failure causes)
3843 *
3844 * ```ts import.meta.vitest
3845 * import { Cause, Effect, Exit } from "effect"
3846 * const output: Array<unknown> = []
3847 *
3848 * const task = Effect.fail("Network timeout")
3849 *
3850 * // Only log causes that contain failures (not interrupts or defects)
3851 * const program = Effect.tapCauseIf(
3852 * task,
3853 * Cause.hasFails,
3854 * (cause) => Effect.sync(() => { output.push(`Logging failure cause: ${Cause.squash(cause)}`) })
3855 * )
3856 *
3857 * void output.push(Effect.runSyncExit(program))
3858 * output // => ["Logging failure cause: Network timeout", Exit.fail("Network timeout")]
3859 * ```
3860 *
3861 * @category error handling
3862 * @since 4.0.0
3863 */
3864export const tapCauseIf: {
3865 <E, B, E2, R2>(
3866 predicate: Predicate.Predicate<Cause.Cause<E>>,
3867 f: (cause: Cause.Cause<E>) => Effect<B, E2, R2>
3868 ): <A, R>(self: Effect<A, E, R>) => Effect<A, E | E2, R | R2>
3869 <A, E, R, B, E2, R2>(
3870 self: Effect<A, E, R>,
3871 predicate: Predicate.Predicate<Cause.Cause<E>>,
3872 f: (cause: Cause.Cause<E>) => Effect<B, E2, R2>
3873 ): Effect<A, E | E2, R | R2>
3874} = internal.tapCauseIf
3875
3876/**
3877 * Executes a side effect conditionally when a failed effect's cause passes a filter.
3878 *
3879 * **When to use**
3880 *
3881 * Use when you need to observe only failure causes selected by a `Filter`,
3882 * while giving the side effect both the selected value and the original
3883 * `Cause`.
3884 *
3885 * **Details**
3886 *
3887 * A successful filter result runs the side effect with the selected value and
3888 * original cause. A failed filter result skips the side effect and preserves the
3889 * original cause.
3890 *
3891 * @see {@link tapCauseIf} for selecting causes with a boolean predicate
3892 * @see {@link tapCause} for observing every failure cause
3893 * @see {@link catchCauseFilter} for recovering from selected causes instead of only observing them
3894 *
3895 * @category error handling
3896 * @since 4.0.0
3897 */
3898export const tapCauseFilter: {
3899 <E, B, E2, R2, EB, X extends Cause.Cause<any>>(
3900 filter: Filter.Filter<Cause.Cause<E>, EB, X>,
3901 f: (a: EB, cause: Cause.Cause<E>) => Effect<B, E2, R2>
3902 ): <A, R>(self: Effect<A, E, R>) => Effect<A, E | E2, R | R2>
3903 <A, E, R, B, E2, R2, EB, X extends Cause.Cause<any>>(
3904 self: Effect<A, E, R>,
3905 filter: Filter.Filter<Cause.Cause<E>, EB, X>,
3906 f: (a: EB, cause: Cause.Cause<E>) => Effect<B, E2, R2>
3907 ): Effect<A, E | E2, R | R2>
3908} = internal.tapCauseFilter
3909
3910/**
3911 * Runs an effectful operation when the source effect dies with a defect.
3912 *
3913 * **Details**
3914 *
3915 * Use this for diagnostics such as logging unexpected thrown exceptions or
3916 * values passed to `die`. Recoverable failures are not handled. When the
3917 * operation succeeds, the original defect is preserved; if the operation fails,
3918 * its error is also represented in the returned effect.
3919 *
3920 * **Example** (Observing defects)
3921 *
3922 * ```ts import.meta.vitest
3923 * import { Effect, Exit } from "effect"
3924 * const output: Array<unknown> = []
3925 *
3926 * // Simulate a severe failure in the system
3927 * const task2: Effect.Effect<number> = Effect.die(
3928 * "Something went wrong"
3929 * )
3930 *
3931 * // Log the defect using tapDefect
3932 * const tapping2 = Effect.tapDefect(
3933 * task2,
3934 * (defect) => Effect.sync(() => { output.push(`defect: ${defect}`) })
3935 * )
3936 *
3937 * void output.push(Effect.runSyncExit(tapping2))
3938 * output // => ["defect: Something went wrong", Exit.die("Something went wrong")]
3939 * ```
3940 *
3941 * @category error handling
3942 * @since 2.0.0
3943 */
3944export const tapDefect: {
3945 <B, E2, R2>(f: (defect: unknown) => Effect<B, E2, R2>): <A, E, R>(self: Effect<A, E, R>) => Effect<A, E | E2, R | R2>
3946 <A, E, R, B, E2, R2>(self: Effect<A, E, R>, f: (defect: unknown) => Effect<B, E2, R2>): Effect<A, E | E2, R | R2>
3947} = internal.tapDefect
3948
3949/**
3950 * Retries an effect until it succeeds, discarding failures.
3951 *
3952 * **Details**
3953 *
3954 * Yields between attempts so other fibers can run.
3955 *
3956 * **Example** (Retrying until success)
3957 *
3958 * ```ts import.meta.vitest
3959 * import { Effect } from "effect"
3960 * const output: Array<unknown> = []
3961 *
3962 * let attempts = 0
3963 *
3964 * const flaky = Effect.gen(function*() {
3965 * attempts++
3966 * yield* Effect.sync(() => { output.push(`Attempt ${attempts}`) })
3967 * if (attempts < 3) {
3968 * return yield* Effect.fail("Not ready")
3969 * }
3970 * return "Ready"
3971 * })
3972 *
3973 * const program = Effect.eventually(flaky)
3974 *
3975 * void output.push(await Effect.runPromise(program))
3976 * output // => ["Attempt 1", "Attempt 2", "Attempt 3", "Ready"]
3977 * ```
3978 *
3979 * @category repetition
3980 * @since 2.0.0
3981 */
3982export const eventually: <A, E, R>(self: Effect<A, E, R>) => Effect<A, never, R> = internal.eventually
3983
3984// -----------------------------------------------------------------------------
3985// Error Handling
3986// -----------------------------------------------------------------------------
3987
3988/**
3989 * Type helpers for retrying effects.
3990 *
3991 * @category error handling
3992 * @since 2.0.0
3993 */
3994export declare namespace Retry {
3995 /**
3996 * Computes the result type of `Effect.retry` from the original effect and retry options.
3997 *
3998 * @category error handling
3999 * @since 2.0.0
4000 */
4001 export type Return<R, E, A, O extends Options<E>> = Effect<
4002 A,
4003 | (O extends { schedule: Schedule<infer _O, infer _I, infer _E1, infer _R> } ? E
4004 : O extends { times: number } ? E
4005 : O extends { until: Predicate.Refinement<E, infer E2> } ? E2
4006 : O extends { while: Predicate.Refinement<E, infer E2> } ? Exclude<E, E2>
4007 : E)
4008 | (O extends { schedule: Schedule<infer _O, infer _I, infer E, infer _R> } ? E
4009 : never)
4010 | (O extends { while: (...args: Array<any>) => Effect<infer _A, infer E, infer _R> } ? E
4011 : never)
4012 | (O extends { until: (...args: Array<any>) => Effect<infer _A, infer E, infer _R> } ? E
4013 : never),
4014 | R
4015 | (O extends { schedule: Schedule<infer _O, infer _I, infer _E1, infer R> } ? R
4016 : never)
4017 | (O extends { while: (...args: Array<any>) => Effect<infer _A, infer _E, infer R> } ? R
4018 : never)
4019 | (O extends { until: (...args: Array<any>) => Effect<infer _A, infer _E, infer R> } ? R
4020 : never)
4021 > extends infer Z ? Z
4022 : never
4023
4024 /**
4025 * Options that control whether and how a failing effect is retried.
4026 *
4027 * @category error handling
4028 * @since 2.0.0
4029 */
4030 export interface Options<E> {
4031 while?: ((error: E) => boolean | Effect<boolean, any, any>) | undefined
4032 until?: ((error: E) => boolean | Effect<boolean, any, any>) | undefined
4033 times?: number | undefined
4034 schedule?: Schedule<any, E, any, any> | undefined
4035 }
4036}
4037
4038/**
4039 * Retries typed failures from an effect according to a retry policy.
4040 *
4041 * **When to use**
4042 *
4043 * Use when you need to rerun an effect after transient typed failures, such as
4044 * network issues or temporary resource unavailability.
4045 *
4046 * **Details**
4047 *
4048 * The policy can be a `Schedule`, a schedule builder, or a `Retry.Options`
4049 * object using `schedule`, `times`, `while`, or `until`. If a retry eventually
4050 * succeeds, the returned effect succeeds with that value. If the policy stops
4051 * while the effect is still failing, the last failure is propagated.
4052 *
4053 * **Gotchas**
4054 *
4055 * The source effect is always evaluated once before any retry policy is
4056 * applied. For example, `Schedule.recurs(3)` allows up to three retries after
4057 * the initial attempt.
4058 *
4059 * Defects and interruptions are not retried.
4060 *
4061 * **Example** (Retrying with a schedule)
4062 *
4063 * ```ts import.meta.vitest
4064 * import { Data, Effect, Schedule } from "effect"
4065 *
4066 * class AttemptError extends Data.TaggedError("AttemptError")<{ readonly attempt: number }> {}
4067 *
4068 * let attempt = 0
4069 * const task = Effect.callback<string, AttemptError>((resume) => {
4070 * attempt++
4071 * if (attempt <= 2) {
4072 * resume(Effect.fail(new AttemptError({ attempt })))
4073 * } else {
4074 * resume(Effect.succeed("Success!"))
4075 * }
4076 * })
4077 *
4078 * const policy = Schedule.recurs(5)
4079 * const program = Effect.retry(task, policy)
4080 *
4081 * await Effect.runPromise(program) // => "Success!"
4082 * ```
4083 *
4084 * @see {@link retryOrElse} for a version that allows you to run a fallback.
4085 * @see {@link repeat} if your retry condition is based on successful outcomes rather than errors.
4086 * @category error handling
4087 * @since 2.0.0
4088 */
4089export const retry: {
4090 <E, O extends Retry.Options<E>>(options: O): <A, R>(self: Effect<A, E, R>) => Retry.Return<R, E, A, O>
4091 <B, E, Error, Env>(
4092 policy: Schedule<B, NoInfer<E>, Error, Env>
4093 ): <A, R>(self: Effect<A, E, R>) => Effect<A, E | Error, R | Env>
4094 <B, E, Error, Env>(
4095 builder: (
4096 $: <O, SE, R>(_: Schedule<O, NoInfer<E>, SE, R>) => Schedule<O, E, SE, R>
4097 ) => Schedule<B, NoInfer<E>, Error, Env>
4098 ): <A, R>(self: Effect<A, E, R>) => Effect<A, E | Error, R | Env>
4099 <A, E, R, O extends Retry.Options<E>>(self: Effect<A, E, R>, options: O): Retry.Return<R, E, A, O>
4100 <A, E, R, B, Error, Env>(
4101 self: Effect<A, E, R>,
4102 policy: Schedule<B, NoInfer<E>, Error, Env>
4103 ): Effect<A, E | Error, R | Env>
4104 <A, E, R, B, Error, Env>(
4105 self: Effect<A, E, R>,
4106 builder: (
4107 $: <O, SE, R>(_: Schedule<O, NoInfer<E>, SE, R>) => Schedule<O, E, SE, R>
4108 ) => Schedule<B, NoInfer<E>, Error, Env>
4109 ): Effect<A, E | Error, R | Env>
4110} = internalSchedule.retry
4111
4112/**
4113 * Retries a failing effect and runs a fallback effect if retries are exhausted.
4114 *
4115 * **When to use**
4116 *
4117 * Use when you want to handle failures gracefully by specifying an alternative
4118 * action after repeated failures.
4119 *
4120 * **Details**
4121 *
4122 * The `Effect.retryOrElse` function attempts to retry a failing effect multiple
4123 * times according to a defined {@link Schedule} policy.
4124 *
4125 * If the retries are exhausted and the effect still fails, it runs a fallback
4126 * effect instead.
4127 *
4128 * **Example** (Falling back after retries are exhausted)
4129 *
4130 * ```ts import.meta.vitest
4131 * import { Data, Effect, Schedule } from "effect"
4132 * const output: Array<unknown> = []
4133 *
4134 * class NetworkTimeoutError extends Data.TaggedError("NetworkTimeoutError")<{}> {}
4135 *
4136 * let attempt = 0
4137 * const networkRequest = Effect.gen(function*() {
4138 * attempt++
4139 * yield* Effect.sync(() => { output.push(`Network attempt ${attempt}`) })
4140 * if (attempt < 3) {
4141 * return yield* Effect.fail(new NetworkTimeoutError())
4142 * }
4143 * return "Network data"
4144 * })
4145 *
4146 * // Retry up to 2 times, then fall back to cached data
4147 * const program = Effect.retryOrElse(
4148 * networkRequest,
4149 * Schedule.recurs(2),
4150 * (error, retryCount) =>
4151 * Effect.gen(function*() {
4152 * yield* Effect.sync(() => { output.push(`All ${retryCount} retries failed, using cache`) })
4153 * return "Cached data"
4154 * })
4155 * )
4156 *
4157 * void output.push(await Effect.runPromise(program))
4158 * output // => ["Network attempt 1", "Network attempt 2", "Network attempt 3", "Network data"]
4159 * ```
4160 *
4161 * @see {@link retry} for a version that does not run a fallback effect.
4162 * @category error handling
4163 * @since 2.0.0
4164 */
4165export const retryOrElse: {
4166 <A1, E, E1, R1, A2, E2, R2>(
4167 policy: Schedule<A1, NoInfer<E>, E1, R1>,
4168 orElse: (e: NoInfer<E>, out: A1) => Effect<A2, E2, R2>
4169 ): <A, R>(self: Effect<A, E, R>) => Effect<A | A2, E1 | E2, R | R1 | R2>
4170 <A, E, R, A1, E1, R1, A2, E2, R2>(
4171 self: Effect<A, E, R>,
4172 policy: Schedule<A1, NoInfer<E>, E1, R1>,
4173 orElse: (e: NoInfer<E>, out: A1) => Effect<A2, E2, R2>
4174 ): Effect<A | A2, E1 | E2, R | R1 | R2>
4175} = internalSchedule.retryOrElse
4176
4177/**
4178 * Exposes an effect's full failure cause in the error channel as `Cause<E>`.
4179 *
4180 * **Details**
4181 *
4182 * Use `sandbox` when downstream error handling needs to distinguish typed
4183 * failures, defects, and interruptions. Use `unsandbox` to restore the original
4184 * typed error channel after cause-level handling.
4185 *
4186 * **Example** (Exposing failures as causes)
4187 *
4188 * ```ts import.meta.vitest
4189 * import { Cause, Effect } from "effect"
4190 *
4191 * const task = Effect.fail("Something went wrong")
4192 *
4193 * // Sandbox exposes the full cause as the error type
4194 * const program = Effect.gen(function*() {
4195 * const result = yield* Effect.flip(Effect.sandbox(task))
4196 * return `Caught cause: ${Cause.squash(result)}`
4197 * })
4198 *
4199 * Effect.runSync(program) // => "Caught cause: Something went wrong"
4200 * ```
4201 *
4202 * @category error handling
4203 * @since 2.0.0
4204 */
4205export const sandbox: <A, E, R>(
4206 self: Effect<A, E, R>
4207) => Effect<A, Cause.Cause<E>, R> = internal.sandbox
4208
4209/**
4210 * Discards both the success and failure values of an effect.
4211 *
4212 * **When to use**
4213 *
4214 * Use when an effect should run for its side effects while both success and
4215 * failure values are discarded.
4216 *
4217 * **Details**
4218 *
4219 * Use the `log` option to emit the full {@link Cause} when the effect fails,
4220 * and `message` to prepend a custom log message.
4221 *
4222 * **Example** (Discarding success and failure values)
4223 *
4224 * ```ts import.meta.vitest
4225 * import { Effect } from "effect"
4226 *
4227 * // ┌─── Effect<number, string, never>
4228 * // ▼
4229 * const task = Effect.fail("Uh oh!").pipe(Effect.as(5))
4230 *
4231 * // ┌─── Effect<void, never, never>
4232 * // ▼
4233 * const program = task.pipe(Effect.ignore)
4234 * Effect.runSync(program) // => undefined
4235 * ```
4236 *
4237 * **Example** (Logging failures while ignoring results)
4238 *
4239 * ```ts import.meta.vitest
4240 * import { Effect } from "effect"
4241 *
4242 * const task = Effect.fail("Uh oh!")
4243 *
4244 * const program = task.pipe(Effect.ignore)
4245 * Effect.runSync(program) // => undefined
4246 * ```
4247 *
4248 * @category error handling
4249 * @since 2.0.0
4250 */
4251export const ignore: <
4252 Arg extends Effect<any, any, any> | {
4253 readonly log?: boolean | Severity | undefined
4254 readonly message?: string | undefined
4255 } | undefined = {
4256 readonly log?: boolean | Severity | undefined
4257 readonly message?: string | undefined
4258 }
4259>(
4260 effectOrOptions?: Arg,
4261 options?: {
4262 readonly log?: boolean | Severity | undefined
4263 readonly message?: string | undefined
4264 } | undefined
4265) => [Arg] extends [Effect<infer _A, infer _E, infer _R>] ? Effect<void, never, _R>
4266 : <A, E, R>(self: Effect<A, E, R>) => Effect<void, never, R> = internal.ignore
4267
4268/**
4269 * Ignores the effect's failure cause, including defects and interruptions.
4270 *
4271 * **When to use**
4272 *
4273 * Use when a best-effort effect should never fail, even from defects or
4274 * interruption, and optional cause logging is enough.
4275 *
4276 * **Details**
4277 *
4278 * Use the `log` option to emit the full {@link Cause} when the effect fails,
4279 * and `message` to prepend a custom log message.
4280 *
4281 * **Example** (Ignoring failures and logging causes)
4282 *
4283 * ```ts import.meta.vitest
4284 * import { Effect } from "effect"
4285 *
4286 * const task = Effect.fail("boom")
4287 *
4288 * const program = task.pipe(Effect.ignoreCause)
4289 * Effect.runSync(program) // => undefined
4290 * ```
4291 *
4292 * @category error handling
4293 * @since 4.0.0
4294 */
4295export const ignoreCause: <
4296 Arg extends Effect<any, any, any> | {
4297 readonly log?: boolean | Severity | undefined
4298 readonly message?: string | undefined
4299 } | undefined = {
4300 readonly log?: boolean | Severity | undefined
4301 readonly message?: string | undefined
4302 }
4303>(
4304 effectOrOptions?: Arg,
4305 options?: {
4306 readonly log?: boolean | Severity | undefined
4307 readonly message?: string | undefined
4308 } | undefined
4309) => [Arg] extends [Effect<infer _A, infer _E, infer _R>] ? Effect<void, never, _R>
4310 : <A, E, R>(self: Effect<A, E, R>) => Effect<void, never, R> = internal.ignoreCause
4311
4312/**
4313 * Applies an `ExecutionPlan` to an effect, retrying with step-provided resources
4314 * until it succeeds or the plan is exhausted.
4315 *
4316 * **Details**
4317 *
4318 * Each attempt updates `ExecutionPlan.CurrentMetadata` (attempt and step index),
4319 * and retry timing is derived per step (the first attempt uses the remaining
4320 * attempts schedule; later retries apply the step schedule at least once).
4321 *
4322 * Attempts can be observed from outside the effect by passing
4323 * `options.onEvent`, which receives an `ExecutionPlan.Event` before each
4324 * attempt and after it settles. The handler is awaited inline before and after
4325 * every attempt, so events are strictly ordered; keep it cheap. It cannot
4326 * fail, which keeps observation from changing the plan's outcome, and its
4327 * requirements are added to the resulting effect. Terminal events run like
4328 * finalizers, so they are emitted even when the attempt is interrupted.
4329 *
4330 * **Example** (Retrying with an execution plan)
4331 *
4332 * ```ts import.meta.vitest
4333 * import { Context, Effect, ExecutionPlan, Layer } from "effect"
4334 *
4335 * const Endpoint = Context.Service<{ url: string }>("Endpoint")
4336 *
4337 * const fetchUrl = Effect.gen(function*() {
4338 * const endpoint = yield* Effect.service(Endpoint)
4339 * if (endpoint.url === "bad") {
4340 * return yield* Effect.fail("Unavailable")
4341 * }
4342 * return endpoint.url
4343 * })
4344 *
4345 * const plan = ExecutionPlan.make(
4346 * { provide: Layer.succeed(Endpoint, { url: "bad" }), attempts: 2 },
4347 * { provide: Layer.succeed(Endpoint, { url: "good" }) }
4348 * )
4349 *
4350 * const program = Effect.withExecutionPlan(fetchUrl, plan)
4351 * Effect.runSync(program) // => "good"
4352 * ```
4353 *
4354 * **Example** (Observing execution-plan attempts)
4355 *
4356 * ```ts import.meta.vitest
4357 * import { Context, Effect, ExecutionPlan, Layer } from "effect"
4358 *
4359 * const Endpoint = Context.Service<{ url: string }>("Endpoint")
4360 *
4361 * const fetchUrl = Effect.gen(function*() {
4362 * const endpoint = yield* Effect.service(Endpoint)
4363 * if (endpoint.url === "bad") {
4364 * return yield* Effect.fail("Unavailable")
4365 * }
4366 * return endpoint.url
4367 * })
4368 *
4369 * const plan = ExecutionPlan.make(
4370 * { provide: Layer.succeed(Endpoint, { url: "bad" }) },
4371 * { provide: Layer.succeed(Endpoint, { url: "good" }) }
4372 * )
4373 *
4374 * const events: Array<string> = []
4375 * const program = Effect.withExecutionPlan(fetchUrl, plan, {
4376 * onEvent: (event) => Effect.sync(() => events.push(`${event._tag}:${event.stepIndex}`))
4377 * })
4378 *
4379 * await Effect.runPromise(program) // => "good"
4380 *
4381 * events // => ["AttemptStart:0", "AttemptFailure:0", "AttemptStart:1", "AttemptSuccess:1"]
4382 * ```
4383 *
4384 * @category error handling
4385 * @since 3.16.0
4386 */
4387export const withExecutionPlan: {
4388 <Input, Provides, PlanE, PlanR, RX = never>(
4389 plan: ExecutionPlan.ExecutionPlan<{ provides: Provides; input: Input; error: PlanE; requirements: PlanR }>,
4390 options?: {
4391 readonly onEvent?: ((event: ExecutionPlan.Event<Input | PlanE>) => Effect<void, never, RX>) | undefined
4392 }
4393 ): <A, E extends Input, R>(
4394 effect: Effect<A, E, R>
4395 ) => Effect<A, E | PlanE, Exclude<R, Provides> | PlanR | RX>
4396 <A, E extends Input, R, Provides, Input, PlanE, PlanR, RX = never>(
4397 effect: Effect<A, E, R>,
4398 plan: ExecutionPlan.ExecutionPlan<{ provides: Provides; input: Input; error: PlanE; requirements: PlanR }>,
4399 options?: {
4400 readonly onEvent?: ((event: ExecutionPlan.Event<E | PlanE>) => Effect<void, never, RX>) | undefined
4401 }
4402 ): Effect<A, E | PlanE, Exclude<R, Provides> | PlanR | RX>
4403} = internalExecutionPlan.withExecutionPlan
4404
4405/**
4406 * Runs an effect and reports any errors to the configured `ErrorReporter`s.
4407 *
4408 * **Details**
4409 *
4410 * If the `defectsOnly` option is set to `true`, only defects (unrecoverable
4411 * errors) will be reported, while regular failures will be ignored.
4412 *
4413 * @category error handling
4414 * @since 4.0.0
4415 */
4416export const withErrorReporting: <
4417 Arg extends Effect<any, any, any> | { readonly defectsOnly?: boolean | undefined } | undefined = {
4418 readonly defectsOnly?: boolean | undefined
4419 }
4420>(
4421 effectOrOptions: Arg,
4422 options?: { readonly defectsOnly?: boolean | undefined } | undefined
4423) => [Arg] extends [Effect<infer A, infer E, infer R>] ? Effect<A, E, R>
4424 : <A, E, R>(self: Effect<A, E, R>) => Effect<A, E, R> = internal.withErrorReporting
4425
4426// -----------------------------------------------------------------------------
4427// Fallback
4428// -----------------------------------------------------------------------------
4429
4430/**
4431 * Recovers from a typed failure by producing a fallback success value.
4432 *
4433 * **Details**
4434 *
4435 * If the source effect succeeds, its value is preserved. If it fails in the
4436 * error channel, `orElseSucceed` evaluates the fallback with that error and
4437 * succeeds with the returned value, removing the typed error from the returned
4438 * effect.
4439 *
4440 * Defects and interruptions are not recovered by this operator.
4441 *
4442 * **Example** (Replacing failures with a value)
4443 *
4444 * ```ts import.meta.vitest
4445 * import { Effect, Exit } from "effect"
4446 *
4447 * const validate = (age: number): Effect.Effect<number, string> => {
4448 * if (age < 0) {
4449 * return Effect.fail("NegativeAgeError")
4450 * } else if (age < 18) {
4451 * return Effect.fail("IllegalAgeError")
4452 * } else {
4453 * return Effect.succeed(age)
4454 * }
4455 * }
4456 *
4457 * const program = Effect.orElseSucceed(validate(-1), (error) => error === "IllegalAgeError" ? 18 : 0)
4458 *
4459 * Effect.runSyncExit(program) // => Exit.succeed(0)
4460 * ```
4461 *
4462 * @category error handling
4463 * @since 2.0.0
4464 */
4465export const orElseSucceed: {
4466 <E, A2>(
4467 f: (error: NoInfer<E>) => A2
4468 ): <A, R>(self: Effect<A, E, R>) => Effect<A2 | A, never, R>
4469 <A, E, R, A2>(
4470 self: Effect<A, E, R>,
4471 f: (error: E) => A2
4472 ): Effect<A | A2, never, R>
4473} = internal.orElseSucceed
4474
4475/**
4476 * Runs a sequence of effects and returns the result of the first successful
4477 * one.
4478 *
4479 * **When to use**
4480 *
4481 * Use when you have prioritized fallback `Effect`s, such as attempting
4482 * multiple APIs, reading configuration from several sources, or trying
4483 * alternative resource locations in order.
4484 *
4485 * **Details**
4486 *
4487 * This function executes the provided effects in sequence, stopping at the
4488 * first success. If an effect succeeds, its result is returned immediately and
4489 * no further effects in the sequence are executed.
4490 *
4491 * If all effects fail, the returned effect fails with the error from the last
4492 * effect. If the collection is empty, the returned effect defects with an
4493 * `Error` whose message is `"Received an empty collection of effects"`.
4494 *
4495 * **Example** (Trying alternatives until one succeeds)
4496 *
4497 * ```ts import.meta.vitest
4498 * import { Effect } from "effect"
4499 *
4500 * const primary = Effect.fail("primary unavailable")
4501 * const secondary = Effect.succeed("secondary result")
4502 * const tertiary = Effect.sync(() => {
4503 * throw new Error("not evaluated")
4504 * })
4505 *
4506 * const program = Effect.firstSuccessOf([
4507 * primary,
4508 * secondary,
4509 * tertiary
4510 * ])
4511 *
4512 * Effect.runSync(program) // => "secondary result"
4513 * ```
4514 *
4515 * @category error handling
4516 * @since 2.0.0
4517 */
4518export const firstSuccessOf: <Eff extends Effect<any, any, any>>(
4519 effects: Iterable<Eff>
4520) => Effect<Success<Eff>, Error<Eff>, Services<Eff>> = internal.firstSuccessOf
4521
4522// -----------------------------------------------------------------------------
4523// Delays & timeouts
4524// -----------------------------------------------------------------------------
4525
4526/**
4527 * Adds a time limit to an effect, triggering a timeout if the effect exceeds
4528 * the duration.
4529 *
4530 * **When to use**
4531 *
4532 * Use when you need a timeout of an `Effect` to be represented as a typed
4533 * failure.
4534 *
4535 * **Details**
4536 *
4537 * The `timeout` function allows you to specify a time limit for an
4538 * effect's execution. If the effect does not complete within the given time, a
4539 * `TimeoutError` is raised. This can be useful for controlling how long your
4540 * program waits for a task to finish, ensuring that it doesn't hang
4541 * indefinitely if the task takes too long.
4542 *
4543 * **Gotchas**
4544 *
4545 * If the timeout wins, the source effect is interrupted.
4546 *
4547 * **Example** (Failing when work takes too long)
4548 *
4549 * ```ts import.meta.vitest
4550 * import { Effect } from "effect"
4551 *
4552 * const timedEffect = Effect.never.pipe(Effect.timeout(0))
4553 * const error = await Effect.runPromise(Effect.flip(timedEffect))
4554 * error._tag // => "TimeoutError"
4555 * ```
4556 *
4557 * @see {@link timeoutOption} for returning `Option.none` on timeout.
4558 * @see {@link timeoutOrElse} for a version that allows specifying both success and timeout handlers.
4559 *
4560 * @category delays & timeouts
4561 * @since 2.0.0
4562 */
4563export const timeout: {
4564 (
4565 duration: Duration.Input
4566 ): <A, E, R>(self: Effect<A, E, R>) => Effect<A, E | Cause.TimeoutError, R>
4567 <A, E, R>(
4568 self: Effect<A, E, R>,
4569 duration: Duration.Input
4570 ): Effect<A, E | Cause.TimeoutError, R>
4571} = internal.timeout
4572
4573/**
4574 * Runs an effect with a time limit and represents only the timeout case as
4575 * `Option.none`.
4576 *
4577 * **When to use**
4578 *
4579 * Use when a timeout of an `Effect` should be handled as `Option.none`.
4580 *
4581 * **Details**
4582 *
4583 * If the source effect succeeds before the timeout, the returned effect
4584 * succeeds with `Option.some(value)`. If the timeout wins, the source effect is
4585 * interrupted and the returned effect succeeds with `Option.none`. If the
4586 * source effect fails before the timeout, that failure is preserved.
4587 *
4588 * **Example** (Returning None on timeout)
4589 *
4590 * ```ts import.meta.vitest
4591 * import { Effect, Option } from "effect"
4592 *
4593 * const timedOutEffect = Effect.never.pipe(Effect.timeoutOption(0))
4594 * await Effect.runPromise(timedOutEffect) // => Option.none()
4595 * ```
4596 *
4597 * @see {@link timeout} for a version that raises a `TimeoutError`.
4598 * @see {@link timeoutOrElse} for a version that allows specifying both success and timeout handlers.
4599 *
4600 * @category delays & timeouts
4601 * @since 3.1.0
4602 */
4603export const timeoutOption: {
4604 (
4605 duration: Duration.Input
4606 ): <A, E, R>(self: Effect<A, E, R>) => Effect<Option<A>, E, R>
4607 <A, E, R>(
4608 self: Effect<A, E, R>,
4609 duration: Duration.Input
4610 ): Effect<Option<A>, E, R>
4611} = internal.timeoutOption
4612
4613/**
4614 * Applies a timeout to an effect, lazily evaluating `orElse` after interrupting
4615 * the source if the timeout is reached.
4616 *
4617 * **Example** (Falling back on timeout)
4618 *
4619 * ```ts import.meta.vitest
4620 * import { Effect } from "effect"
4621 * const output: Array<unknown> = []
4622 *
4623 * const program = Effect.timeoutOrElse(Effect.never, {
4624 * duration: 0,
4625 * orElse: () => Effect.sync(() => { output.push("Query timed out, using cached data") }).pipe(
4626 * Effect.as("Cached result")
4627 * )
4628 * })
4629 *
4630 * void output.push(await Effect.runPromise(program))
4631 * output // => ["Query timed out, using cached data", "Cached result"]
4632 * ```
4633 *
4634 * @see {@link timeout} for failing with a `TimeoutError`.
4635 * @see {@link timeoutOption} for returning `Option.none` on timeout.
4636 *
4637 * @category delays & timeouts
4638 * @since 4.0.0
4639 */
4640export const timeoutOrElse: {
4641 <A2, E2, R2>(options: {
4642 readonly duration: Duration.Input
4643 readonly orElse: LazyArg<Effect<A2, E2, R2>>
4644 }): <A, E, R>(self: Effect<A, E, R>) => Effect<A | A2, E | E2, R | R2>
4645 <A, E, R, A2, E2, R2>(
4646 self: Effect<A, E, R>,
4647 options: {
4648 readonly duration: Duration.Input
4649 readonly orElse: LazyArg<Effect<A2, E2, R2>>
4650 }
4651 ): Effect<A | A2, E | E2, R | R2>
4652} = internal.timeoutOrElse
4653
4654/**
4655 * Returns an effect that is delayed from this effect by the specified
4656 * `Duration`.
4657 *
4658 * **Example** (Delaying an effect)
4659 *
4660 * ```ts import.meta.vitest
4661 * import { Effect } from "effect"
4662 * const output: Array<unknown> = []
4663 *
4664 * const program = Effect.delay(Effect.sync(() => { output.push("Delayed message") }), 0)
4665 *
4666 * await Effect.runPromise(program)
4667 * output // => ["Delayed message"]
4668 * ```
4669 *
4670 * @category delays & timeouts
4671 * @since 2.0.0
4672 */
4673export const delay: {
4674 (
4675 duration: Duration.Input
4676 ): <A, E, R>(self: Effect<A, E, R>) => Effect<A, E, R>
4677 <A, E, R>(
4678 self: Effect<A, E, R>,
4679 duration: Duration.Input
4680 ): Effect<A, E, R>
4681} = internal.delay
4682
4683/**
4684 * Returns an effect that suspends the current fiber for the specified duration
4685 * without blocking a JavaScript thread.
4686 *
4687 * **Example** (Pausing without blocking)
4688 *
4689 * ```ts import.meta.vitest
4690 * import { Effect } from "effect"
4691 * const output: Array<unknown> = []
4692 *
4693 * const program = Effect.gen(function*() {
4694 * yield* Effect.sync(() => { output.push("Start") })
4695 * yield* Effect.sleep(0)
4696 * yield* Effect.sync(() => { output.push("End") })
4697 * })
4698 *
4699 * await Effect.runPromise(program)
4700 * output // => ["Start", "End"]
4701 * ```
4702 *
4703 * @category delays & timeouts
4704 * @since 2.0.0
4705 */
4706export const sleep: (duration: Duration.Input) => Effect<void> = internal.sleep
4707
4708/**
4709 * Returns the runtime duration of an effect together with its result.
4710 *
4711 * **Details**
4712 *
4713 * The original success, failure, or interruption is preserved; only the success
4714 * value is paired with the duration.
4715 *
4716 * **Example** (Measuring execution time)
4717 *
4718 * ```ts import.meta.vitest
4719 * import { Effect } from "effect"
4720 *
4721 * const program = Effect.gen(function*() {
4722 * const [, value] = yield* Effect.timed(Effect.succeed("ok"))
4723 * return value
4724 * })
4725 *
4726 * Effect.runSync(program) // => "ok"
4727 * ```
4728 *
4729 * @category delays & timeouts
4730 * @since 2.0.0
4731 */
4732export const timed: <A, E, R>(self: Effect<A, E, R>) => Effect<[duration: Duration.Duration, result: A], E, R> =
4733 internal.timed
4734
4735// -----------------------------------------------------------------------------
4736// Racing
4737// -----------------------------------------------------------------------------
4738
4739/**
4740 * Runs multiple effects concurrently and returns the first successful result.
4741 *
4742 * **When to use**
4743 *
4744 * Use when early failures should be ignored until a success occurs
4745 * or all effects fail.
4746 *
4747 * **Details**
4748 *
4749 * Early failures do not finish the race; `raceAll` keeps waiting until one
4750 * effect succeeds or every effect has failed. When one effect succeeds, the
4751 * remaining effects are interrupted. If every effect fails, the returned effect
4752 * fails with a cause containing the collected failure reasons.
4753 *
4754 * **Example** (Racing many effects)
4755 *
4756 * ```ts import.meta.vitest
4757 * import { Effect } from "effect"
4758 *
4759 * const raced = Effect.raceAll([
4760 * Effect.succeed("Fast"),
4761 * Effect.never
4762 * ])
4763 * await Effect.runPromise(raced) // => "Fast"
4764 * ```
4765 *
4766 * @see {@link race} for a version that handles only two effects.
4767 * @category racing
4768 * @since 2.0.0
4769 */
4770export const raceAll: <Eff extends Effect<any, any, any>>(
4771 all: Iterable<Eff>,
4772 options?: {
4773 readonly onWinner?: (options: {
4774 readonly fiber: Fiber<any, any>
4775 readonly index: number
4776 readonly parentFiber: Fiber<any, any>
4777 }) => void
4778 }
4779) => Effect<Success<Eff>, Error<Eff>, Services<Eff>> = internal.raceAll
4780
4781/**
4782 * Runs multiple effects concurrently and completes with the first effect to
4783 * finish, whether it succeeds or fails.
4784 *
4785 * **Details**
4786 *
4787 * After the first effect completes, all remaining effects are interrupted. Use
4788 * `raceAll` when early failures should be ignored until a success occurs or
4789 * all effects fail.
4790 *
4791 * **Example** (Taking the first settled result)
4792 *
4793 * ```ts import.meta.vitest
4794 * import { Effect } from "effect"
4795 *
4796 * const raced = Effect.raceAllFirst([
4797 * Effect.fail("First failed"),
4798 * Effect.never
4799 * ])
4800 * await Effect.runPromise(Effect.flip(raced)) // => "First failed"
4801 * ```
4802 *
4803 * @category racing
4804 * @since 4.0.0
4805 */
4806export const raceAllFirst: <Eff extends Effect<any, any, any>>(
4807 all: Iterable<Eff>,
4808 options?: {
4809 readonly onWinner?: (options: {
4810 readonly fiber: Fiber<any, any>
4811 readonly index: number
4812 readonly parentFiber: Fiber<any, any>
4813 }) => void
4814 }
4815) => Effect<Success<Eff>, Error<Eff>, Services<Eff>> = internal.raceAllFirst
4816
4817/**
4818 * Races two effects and returns the first successful result.
4819 *
4820 * **Details**
4821 *
4822 * If one effect succeeds, the other is interrupted and `onWinner` can observe the
4823 * winning fiber. If both fail, the race fails.
4824 *
4825 * **Example** (Racing two effects)
4826 *
4827 * ```ts import.meta.vitest
4828 * import { Effect } from "effect"
4829 * const output: Array<unknown> = []
4830 *
4831 * const fastFail = Effect.fail("fast-fail")
4832 * const slowSuccess = Effect.succeed("slow-success")
4833 *
4834 * const program = Effect.gen(function*() {
4835 * const result = yield* Effect.race(fastFail, slowSuccess)
4836 * yield* Effect.sync(() => { output.push(`winner: ${result}`) })
4837 * })
4838 *
4839 * await Effect.runPromise(program)
4840 * output // => ["winner: slow-success"]
4841 * ```
4842 *
4843 * @category racing
4844 * @since 2.0.0
4845 */
4846export const race: {
4847 <A2, E2, R2>(
4848 that: Effect<A2, E2, R2>,
4849 options?: {
4850 readonly onWinner?: (
4851 options: { readonly fiber: Fiber<any, any>; readonly index: number; readonly parentFiber: Fiber<any, any> }
4852 ) => void
4853 }
4854 ): <A, E, R>(self: Effect<A, E, R>) => Effect<A | A2, E | E2, R | R2>
4855 <A, E, R, A2, E2, R2>(
4856 self: Effect<A, E, R>,
4857 that: Effect<A2, E2, R2>,
4858 options?: {
4859 readonly onWinner?: (
4860 options: { readonly fiber: Fiber<any, any>; readonly index: number; readonly parentFiber: Fiber<any, any> }
4861 ) => void
4862 }
4863 ): Effect<A | A2, E | E2, R | R2>
4864} = internal.race
4865
4866/**
4867 * Races two effects and returns the result of the first one to complete, whether
4868 * it succeeds or fails.
4869 *
4870 * **When to use**
4871 *
4872 * Use when any completion, including failure, should decide the race and
4873 * interrupt the losing effect.
4874 *
4875 * **Details**
4876 *
4877 * The losing effect is interrupted, and `onWinner` can observe the winning fiber.
4878 *
4879 * **Example** (Observing the winning fiber)
4880 *
4881 * ```ts import.meta.vitest
4882 * import { Effect } from "effect"
4883 * const output: Array<unknown> = []
4884 *
4885 * const fastFail = Effect.fail("fast-fail")
4886 * const slowSuccess = Effect.never
4887 *
4888 * const program = Effect.gen(function*() {
4889 * const message = yield* Effect.match(Effect.raceFirst(fastFail, slowSuccess), {
4890 * onFailure: (error) => `failed: ${error}`,
4891 * onSuccess: (value) => `succeeded: ${value}`
4892 * })
4893 * yield* Effect.sync(() => { output.push(message) })
4894 * })
4895 *
4896 * await Effect.runPromise(program)
4897 * output // => ["failed: fast-fail"]
4898 * ```
4899 *
4900 * @category racing
4901 * @since 2.0.0
4902 */
4903export const raceFirst: {
4904 <A2, E2, R2>(
4905 that: Effect<A2, E2, R2>,
4906 options?: {
4907 readonly onWinner?: (
4908 options: { readonly fiber: Fiber<any, any>; readonly index: number; readonly parentFiber: Fiber<any, any> }
4909 ) => void
4910 }
4911 ): <A, E, R>(self: Effect<A, E, R>) => Effect<A | A2, E | E2, R | R2>
4912 <A, E, R, A2, E2, R2>(
4913 self: Effect<A, E, R>,
4914 that: Effect<A2, E2, R2>,
4915 options?: {
4916 readonly onWinner?: (
4917 options: { readonly fiber: Fiber<any, any>; readonly index: number; readonly parentFiber: Fiber<any, any> }
4918 ) => void
4919 }
4920 ): Effect<A | A2, E | E2, R | R2>
4921} = internal.raceFirst
4922
4923// -----------------------------------------------------------------------------
4924// Filtering
4925// -----------------------------------------------------------------------------
4926
4927/**
4928 * Filters elements of an iterable using a predicate, refinement, or effectful
4929 * predicate.
4930 *
4931 * **Example** (Filtering success values)
4932 *
4933 * ```ts import.meta.vitest
4934 * import { Effect } from "effect"
4935 * const output: Array<unknown> = []
4936 *
4937 * // Sync predicate
4938 * const evens = Effect.filter([1, 2, 3, 4], (n) => n % 2 === 0)
4939 *
4940 * // Effectful predicate
4941 * const checked = Effect.filter([1, 2, 3], (n) => Effect.succeed(n > 1))
4942 *
4943 * void output.push(Effect.runSync(evens))
4944 * void output.push(Effect.runSync(checked))
4945 * output // => [[2, 4], [2, 3]]
4946 * ```
4947 *
4948 * @category collecting
4949 * @since 2.0.0
4950 */
4951export const filter: {
4952 <A, B extends A>(
4953 refinement: Predicate.Refinement<NoInfer<A>, B>
4954 ): (elements: Iterable<A>) => Effect<Array<B>>
4955 <A>(
4956 predicate: Predicate.Predicate<NoInfer<A>>
4957 ): (elements: Iterable<A>) => Effect<Array<A>>
4958 <A, E, R>(
4959 predicate: (a: NoInfer<A>, i: number) => Effect<boolean, E, R>,
4960 options?: { readonly concurrency?: Concurrency | undefined }
4961 ): (iterable: Iterable<A>) => Effect<Array<A>, E, R>
4962 <A, B extends A>(
4963 elements: Iterable<A>,
4964 refinement: Predicate.Refinement<A, B>
4965 ): Effect<Array<B>>
4966 <A>(
4967 elements: Iterable<A>,
4968 predicate: Predicate.Predicate<A>
4969 ): Effect<Array<A>>
4970 <A, E, R>(
4971 iterable: Iterable<A>,
4972 predicate: (a: NoInfer<A>, i: number) => Effect<boolean, E, R>,
4973 options?: { readonly concurrency?: Concurrency | undefined }
4974 ): Effect<Array<A>, E, R>
4975} = internal.filter
4976
4977/**
4978 * Filters and maps elements of an iterable with a `Filter`.
4979 *
4980 * **When to use**
4981 *
4982 * Use when you need to filter an iterable with a `Filter` inside an `Effect`,
4983 * collecting each filter success value.
4984 *
4985 * **Details**
4986 *
4987 * `Result.succeed` values are collected in the returned array, and
4988 * `Result.fail` values are skipped.
4989 *
4990 * @see {@link filter} for keeping original elements with a boolean predicate, refinement, or effectful predicate
4991 * @see {@link filterMapEffect} for using an effectful `Filter`
4992 *
4993 * @category collecting
4994 * @since 2.0.0
4995 */
4996export const filterMap: {
4997 <A, B, X>(
4998 filter: Filter.Filter<NoInfer<A>, B, X>
4999 ): (elements: Iterable<A>) => Effect<Array<B>>
5000 <A, B, X>(
5001 elements: Iterable<A>,
5002 filter: Filter.Filter<NoInfer<A>, B, X>
5003 ): Effect<Array<B>>
5004} = internal.filterMap
5005
5006/**
5007 * Filters and maps elements of an iterable effectfully with a `FilterEffect`.
5008 *
5009 * **When to use**
5010 *
5011 * Use when you need to filter each iterable element effectfully and transform
5012 * accepted elements into successful output values.
5013 *
5014 * **Details**
5015 *
5016 * `Result.succeed` values are collected in the returned array, and
5017 * `Result.fail` values are skipped.
5018 *
5019 * **Gotchas**
5020 *
5021 * With concurrent execution, successful values are collected in completion
5022 * order, not input order.
5023 *
5024 * @see {@link filterMap} for using a synchronous `Filter`
5025 * @see {@link filter} for keeping original elements with a predicate
5026 *
5027 * @category collecting
5028 * @since 4.0.0
5029 */
5030export const filterMapEffect: {
5031 <A, B, X, E, R>(
5032 filter: Filter.FilterEffect<NoInfer<A>, B, X, E, R>,
5033 options?: { readonly concurrency?: Concurrency | undefined }
5034 ): (elements: Iterable<A>) => Effect<Array<B>, E, R>
5035 <A, B, X, E, R>(
5036 elements: Iterable<A>,
5037 filter: Filter.FilterEffect<NoInfer<A>, B, X, E, R>,
5038 options?: { readonly concurrency?: Concurrency | undefined }
5039 ): Effect<Array<B>, E, R>
5040} = internal.filterMapEffect
5041
5042/**
5043 * Filters an effect, providing an alternative effect if the predicate fails.
5044 *
5045 * **When to use**
5046 *
5047 * Use when a successful value that fails a predicate should continue with an
5048 * effectful fallback instead of failing the effect.
5049 *
5050 * **Details**
5051 *
5052 * This function applies a predicate to the result of an effect. If the
5053 * predicate evaluates to `false`, it executes the `orElse` effect instead. The
5054 * `orElse` effect can produce an alternative value or perform additional
5055 * computations.
5056 *
5057 * **Example** (Filtering with a fallback effect)
5058 *
5059 * ```ts import.meta.vitest
5060 * import { Effect } from "effect"
5061 *
5062 * // An effect that produces a number
5063 * const program = Effect.succeed(5)
5064 *
5065 * // Filter for even numbers, provide alternative for odd numbers
5066 * const filtered = Effect.filterOrElse(
5067 * program,
5068 * (n) => n % 2 === 0,
5069 * (n) => Effect.succeed(`Number ${n} is odd`)
5070 * )
5071 *
5072 * Effect.runSync(filtered) // => "Number 5 is odd"
5073 * ```
5074 *
5075 * @category filtering
5076 * @since 2.0.0
5077 */
5078export const filterOrElse: {
5079 <A, C, E2, R2, B extends A>(
5080 refinement: Predicate.Refinement<NoInfer<A>, B>,
5081 orElse: (a: EqualsWith<A, B, NoInfer<A>, Exclude<NoInfer<A>, B>>) => Effect<C, E2, R2>
5082 ): <E, R>(self: Effect<A, E, R>) => Effect<B | C, E2 | E, R2 | R>
5083 <A, C, E2, R2>(
5084 predicate: Predicate.Predicate<NoInfer<A>>,
5085 orElse: (a: NoInfer<A>) => Effect<C, E2, R2>
5086 ): <E, R>(self: Effect<A, E, R>) => Effect<A | C, E2 | E, R2 | R>
5087 <A, E, R, C, E2, R2, B extends A>(
5088 self: Effect<A, E, R>,
5089 refinement: Predicate.Refinement<A, B>,
5090 orElse: (a: EqualsWith<A, B, A, Exclude<A, B>>) => Effect<C, E2, R2>
5091 ): Effect<B | C, E | E2, R | R2>
5092 <A, E, R, C, E2, R2>(
5093 self: Effect<A, E, R>,
5094 predicate: Predicate.Predicate<NoInfer<A>>,
5095 orElse: (a: NoInfer<A>) => Effect<C, E2, R2>
5096 ): Effect<A | C, E | E2, R | R2>
5097} = internal.filterOrElse
5098
5099/**
5100 * Filters an effect with a `Filter`, providing an alternative effect on failure.
5101 *
5102 * **When to use**
5103 *
5104 * Use when a successful effect value should be accepted and transformed by a
5105 * `Filter`, while rejected values should continue with an alternative effect
5106 * built from the filter failure.
5107 *
5108 * **Details**
5109 *
5110 * `Result.succeed` becomes the returned success value, and `Result.fail` is
5111 * passed to `orElse`.
5112 *
5113 * @see {@link filterOrElse} for using a predicate and fallback effect
5114 * @see {@link filterMapOrFail} for failing the effect when the filter fails
5115 *
5116 * @category filtering
5117 * @since 4.0.0
5118 */
5119export const filterMapOrElse: {
5120 <A, B, X, C, E2, R2>(
5121 filter: Filter.Filter<NoInfer<A>, B, X>,
5122 orElse: (x: X) => Effect<C, E2, R2>
5123 ): <E, R>(self: Effect<A, E, R>) => Effect<B | C, E2 | E, R2 | R>
5124 <A, E, R, B, X, C, E2, R2>(
5125 self: Effect<A, E, R>,
5126 filter: Filter.Filter<NoInfer<A>, B, X>,
5127 orElse: (x: X) => Effect<C, E2, R2>
5128 ): Effect<B | C, E | E2, R | R2>
5129} = internal.filterMapOrElse
5130
5131/**
5132 * Filters an effect, failing with a custom error if the predicate fails.
5133 *
5134 * **Details**
5135 *
5136 * This function applies a predicate to the result of an effect. If the
5137 * predicate evaluates to `false`, the effect fails with either a custom
5138 * error (if `orFailWith` is provided) or a `NoSuchElementError`.
5139 *
5140 * **Example** (Filtering with a custom failure)
5141 *
5142 * ```ts import.meta.vitest
5143 * import { Effect } from "effect"
5144 *
5145 * // An effect that produces a number
5146 * const program = Effect.succeed(5)
5147 *
5148 * // Filter for even numbers, fail for odd numbers
5149 * const filtered = Effect.filterOrFail(
5150 * program,
5151 * (n) => n % 2 === 0,
5152 * (n) => `Expected even number, got ${n}`
5153 * )
5154 *
5155 * Effect.runSync(Effect.flip(filtered)) // => "Expected even number, got 5"
5156 * ```
5157 *
5158 * @category filtering
5159 * @since 2.0.0
5160 */
5161export const filterOrFail: {
5162 <A, E2, B extends A>(
5163 refinement: Predicate.Refinement<NoInfer<A>, B>,
5164 orFailWith: (a: NoInfer<A>) => E2
5165 ): <E, R>(self: Effect<A, E, R>) => Effect<B, E2 | E, R>
5166 <A, E2>(
5167 predicate: Predicate.Predicate<NoInfer<A>>,
5168 orFailWith: (a: NoInfer<A>) => E2
5169 ): <E, R>(self: Effect<A, E, R>) => Effect<A, E2 | E, R>
5170 <A, B extends A>(
5171 refinement: Predicate.Refinement<NoInfer<A>, B>
5172 ): <E, R>(self: Effect<A, E, R>) => Effect<B, Cause.NoSuchElementError | E, R>
5173 <A>(
5174 predicate: Predicate.Predicate<NoInfer<A>>
5175 ): <E, R>(self: Effect<A, E, R>) => Effect<A, Cause.NoSuchElementError | E, R>
5176 <A, E, R, E2, B extends A>(
5177 self: Effect<A, E, R>,
5178 refinement: Predicate.Refinement<NoInfer<A>, B>,
5179 orFailWith: (a: NoInfer<A>) => E2
5180 ): Effect<B, E2 | E, R>
5181 <A, E, R, E2>(
5182 self: Effect<A, E, R>,
5183 predicate: Predicate.Predicate<NoInfer<A>>,
5184 orFailWith: (a: NoInfer<A>) => E2
5185 ): Effect<A, E2 | E, R>
5186 <A, E, R, B extends A>(
5187 self: Effect<A, E, R>,
5188 refinement: Predicate.Refinement<NoInfer<A>, B>
5189 ): Effect<B, E | Cause.NoSuchElementError, R>
5190 <A, E, R>(
5191 self: Effect<A, E, R>,
5192 predicate: Predicate.Predicate<NoInfer<A>>
5193 ): Effect<A, E | Cause.NoSuchElementError, R>
5194} = internal.filterOrFail
5195
5196/**
5197 * Filters and maps an effect with a `Filter`, failing when the filter fails.
5198 *
5199 * **When to use**
5200 *
5201 * Use when validating and transforming one effect success with a synchronous
5202 * `Filter`, while rejected values should fail the effect.
5203 *
5204 * **Details**
5205 *
5206 * `Result.succeed` becomes the returned success value. `Result.fail` is mapped
5207 * with `orFailWith` when provided, or fails with `NoSuchElementError`.
5208 *
5209 * @see {@link filterMapOrElse} for continuing with a fallback effect when the filter fails
5210 * @see {@link filterOrFail} for validating with a predicate instead of a `Filter`
5211 * @see {@link filterMap} for filtering and mapping iterable elements
5212 *
5213 * @category filtering
5214 * @since 4.0.0
5215 */
5216export const filterMapOrFail: {
5217 <A, B, X, E2>(
5218 filter: Filter.Filter<NoInfer<A>, B, X>,
5219 orFailWith: (x: X) => E2
5220 ): <E, R>(self: Effect<A, E, R>) => Effect<B, E2 | E, R>
5221 <A, B, X>(
5222 filter: Filter.Filter<NoInfer<A>, B, X>
5223 ): <E, R>(self: Effect<A, E, R>) => Effect<B, Cause.NoSuchElementError | E, R>
5224 <A, E, R, B, X, E2>(
5225 self: Effect<A, E, R>,
5226 filter: Filter.Filter<A, B, X>,
5227 orFailWith: (x: X) => E2
5228 ): Effect<B, E2 | E, R>
5229 <A, E, R, B, X>(
5230 self: Effect<A, E, R>,
5231 filter: Filter.Filter<A, B, X>
5232 ): Effect<B, Cause.NoSuchElementError | E, R>
5233} = internal.filterMapOrFail
5234
5235// -----------------------------------------------------------------------------
5236// Conditional Operators
5237// -----------------------------------------------------------------------------
5238
5239/**
5240 * Runs an effect conditionally based on the result of an effectful boolean
5241 * condition.
5242 *
5243 * **When to use**
5244 *
5245 * Use when you need an effectful check to decide whether another effect should
5246 * run while representing the skipped case explicitly.
5247 *
5248 * **Details**
5249 *
5250 * The condition effect is evaluated first. If it succeeds with `true`, the
5251 * source effect is run and its success value is wrapped in `Option.some`. If it
5252 * succeeds with `false`, the source effect is skipped and the result is
5253 * `Option.none`. If the condition effect fails, that failure is preserved.
5254 *
5255 * **Example** (Conditionally running an effect)
5256 *
5257 * ```ts import.meta.vitest
5258 * import { Effect, Option } from "effect"
5259 * const output: Array<unknown> = []
5260 *
5261 * const shouldLog = true
5262 *
5263 * const program = Effect.when(
5264 * Effect.sync(() => { output.push("Condition is true!") }),
5265 * Effect.succeed(shouldLog)
5266 * )
5267 *
5268 * void output.push(Effect.runSync(program))
5269 * output // => ["Condition is true!", Option.some(undefined)]
5270 * ```
5271 *
5272 * @category filtering
5273 * @since 2.0.0
5274 */
5275export const when: {
5276 <E2 = never, R2 = never>(
5277 condition: Effect<boolean, E2, R2>
5278 ): <A, E, R>(self: Effect<A, E, R>) => Effect<Option<A>, E | E2, R | R2>
5279 <A, E, R, E2 = never, R2 = never>(
5280 self: Effect<A, E, R>,
5281 condition: Effect<boolean, E2, R2>
5282 ): Effect<Option<A>, E | E2, R | R2>
5283} = internal.when
5284
5285// -----------------------------------------------------------------------------
5286// Pattern matching
5287// -----------------------------------------------------------------------------
5288
5289/**
5290 * Handles both success and failure cases of an effect without performing side
5291 * effects.
5292 *
5293 * **When to use**
5294 *
5295 * Use when you need to fold an `Effect` into a value by handling success and
5296 * failure differently without triggering side effects.
5297 *
5298 * **Details**
5299 *
5300 * `match` lets you define custom handlers for both success and failure
5301 * scenarios. You provide separate functions to handle each case, allowing you
5302 * to process the result if the effect succeeds, or handle the error if the
5303 * effect fails.
5304 *
5305 * **Example** (Matching success and failure values)
5306 *
5307 * ```ts import.meta.vitest
5308 * import { Data, Effect } from "effect"
5309 *
5310 * class ExampleError extends Data.TaggedError("ExampleError")<{ readonly message: string }> {}
5311 *
5312 * const success: Effect.Effect<number, ExampleError> = Effect.succeed(42)
5313 *
5314 * const program1 = Effect.match(success, {
5315 * onFailure: (error) => `failure: ${error.message}`,
5316 * onSuccess: (value) => `success: ${value}`
5317 * })
5318 *
5319 * // Run and log the result of the successful effect
5320 * Effect.runSync(program1) // => "success: 42"
5321 *
5322 * const failure: Effect.Effect<number, ExampleError> = Effect.fail(
5323 * new ExampleError({ message: "Uh oh!" })
5324 * )
5325 *
5326 * const program2 = Effect.match(failure, {
5327 * onFailure: (error) => `failure: ${error.message}`,
5328 * onSuccess: (value) => `success: ${value}`
5329 * })
5330 *
5331 * // Run and log the result of the failed effect
5332 * Effect.runSync(program2) // => "failure: Uh oh!"
5333 * ```
5334 *
5335 * @see {@link matchEffect} if you need to perform side effects in the handlers.
5336 * @category pattern matching
5337 * @since 2.0.0
5338 */
5339export const match: {
5340 <E, A2, A, A3>(options: {
5341 readonly onFailure: (error: E) => A2
5342 readonly onSuccess: (value: A) => A3
5343 }): <R>(self: Effect<A, E, R>) => Effect<A2 | A3, never, R>
5344 <A, E, R, A2, A3>(
5345 self: Effect<A, E, R>,
5346 options: {
5347 readonly onFailure: (error: E) => A2
5348 readonly onSuccess: (value: A) => A3
5349 }
5350 ): Effect<A2 | A3, never, R>
5351} = internal.match
5352
5353/**
5354 * Handles both success and failure cases of an effect without performing side
5355 * effects, with eager evaluation for resolved effects.
5356 *
5357 * **When to use**
5358 *
5359 * Use when you need to handle both success and failure cases of an
5360 * already-resolved `Effect` with optimized handling.
5361 *
5362 * **Details**
5363 *
5364 * `matchEager` works like `match` but provides better performance for resolved
5365 * effects (Success or Failure). When the effect is already resolved, it applies
5366 * the handlers immediately without fiber scheduling. For unresolved effects,
5367 * it falls back to the regular `match` behavior.
5368 *
5369 * **Example** (Pattern matching eagerly when possible)
5370 *
5371 * ```ts import.meta.vitest
5372 * import { Effect } from "effect"
5373 * const output: Array<unknown> = []
5374 *
5375 * const program = Effect.gen(function*() {
5376 * const result = yield* Effect.matchEager(Effect.succeed(42), {
5377 * onFailure: (error) => `Failed: ${error}`,
5378 * onSuccess: (value) => `Success: ${value}`
5379 * })
5380 * void output.push(result)
5381 * })
5382 *
5383 * Effect.runSync(program)
5384 * output // => ["Success: 42"]
5385 * ```
5386 *
5387 * @see {@link match} for the non-eager version.
5388 * @see {@link matchEffect} if you need to perform side effects in the handlers.
5389 * @category pattern matching
5390 * @since 4.0.0
5391 */
5392export const matchEager: {
5393 <E, A2, A, A3>(options: {
5394 readonly onFailure: (error: E) => A2
5395 readonly onSuccess: (value: A) => A3
5396 }): <R>(self: Effect<A, E, R>) => Effect<A2 | A3, never, R>
5397 <A, E, R, A2, A3>(
5398 self: Effect<A, E, R>,
5399 options: {
5400 readonly onFailure: (error: E) => A2
5401 readonly onSuccess: (value: A) => A3
5402 }
5403 ): Effect<A2 | A3, never, R>
5404} = internal.matchEager
5405
5406/**
5407 * Handles failures by matching the cause of failure.
5408 *
5409 * **When to use**
5410 *
5411 * Use when you need to fold an `Effect` while the failure handler inspects the
5412 * full `Cause`.
5413 *
5414 * **Details**
5415 *
5416 * The `matchCause` function allows you to handle failures with access to the
5417 * full cause of the failure within a fiber.
5418 *
5419 * **Example** (Matching on success or failure causes)
5420 *
5421 * ```ts import.meta.vitest
5422 * import { Cause, Effect } from "effect"
5423 *
5424 * const task = Effect.fail("Something went wrong")
5425 *
5426 * const program = Effect.matchCause(task, {
5427 * onFailure: (cause) => `Failed: ${Cause.squash(cause)}`,
5428 * onSuccess: (value) => `Success: ${value}`
5429 * })
5430 *
5431 * Effect.runSync(program) // => "Failed: Something went wrong"
5432 * ```
5433 *
5434 * @see {@link matchCauseEffect} if you need to perform side effects in the
5435 * handlers.
5436 * @see {@link match} if you don't need to handle the cause of the failure.
5437 * @category pattern matching
5438 * @since 2.0.0
5439 */
5440export const matchCause: {
5441 <E, A2, A, A3>(options: {
5442 readonly onFailure: (cause: Cause.Cause<E>) => A2
5443 readonly onSuccess: (a: A) => A3
5444 }): <R>(self: Effect<A, E, R>) => Effect<A2 | A3, never, R>
5445 <A, E, R, A2, A3>(
5446 self: Effect<A, E, R>,
5447 options: {
5448 readonly onFailure: (cause: Cause.Cause<E>) => A2
5449 readonly onSuccess: (a: A) => A3
5450 }
5451 ): Effect<A2 | A3, never, R>
5452} = internal.matchCause
5453
5454/**
5455 * Handles failures by matching the cause of failure with eager evaluation.
5456 *
5457 * **When to use**
5458 *
5459 * Use when you expect an `Effect` to already be resolved and want to match the
5460 * `Cause` without regular effect pipeline overhead.
5461 *
5462 * **Details**
5463 *
5464 * `matchCauseEager` works like `matchCause` but provides better performance for resolved
5465 * effects by immediately applying the matching function instead of deferring it
5466 * through the effect pipeline.
5467 *
5468 * **Example** (Eagerly matching already completed effects)
5469 *
5470 * ```ts import.meta.vitest
5471 * import { Effect } from "effect"
5472 *
5473 * const handleResult = Effect.matchCauseEager(Effect.succeed(42), {
5474 * onSuccess: (value) => `Success: ${value}`,
5475 * onFailure: (cause) => `Failed: ${cause}`
5476 * })
5477 * Effect.runSync(handleResult) // => "Success: 42"
5478 * ```
5479 *
5480 * @category pattern matching
5481 * @since 4.0.0
5482 */
5483export const matchCauseEager: {
5484 <E, A2, A, A3>(options: {
5485 readonly onFailure: (cause: Cause.Cause<E>) => A2
5486 readonly onSuccess: (value: A) => A3
5487 }): <R>(self: Effect<A, E, R>) => Effect<A2 | A3, never, R>
5488 <A, E, R, A2, A3>(
5489 self: Effect<A, E, R>,
5490 options: {
5491 readonly onFailure: (cause: Cause.Cause<E>) => A2
5492 readonly onSuccess: (value: A) => A3
5493 }
5494 ): Effect<A2 | A3, never, R>
5495} = internal.matchCauseEager
5496
5497/**
5498 * Handles success or failure eagerly with effectful handlers when the effect is already resolved.
5499 *
5500 * **When to use**
5501 *
5502 * Use when you need effectful success and cause-aware failure handlers for
5503 * `Effect` inputs that may already be resolved.
5504 *
5505 * **Details**
5506 *
5507 * If the effect is an `Exit`, the matching handler runs immediately; otherwise it behaves like
5508 * {@link matchCauseEffect}.
5509 *
5510 * @see {@link matchCauseEffect} for the non-eager effectful variant
5511 * @see {@link matchCauseEager} for eager cause matching with pure handlers
5512 * @see {@link matchEffect} for effectful matching on typed failures instead of full causes
5513 *
5514 * @category pattern matching
5515 * @since 4.0.0
5516 */
5517export const matchCauseEffectEager: {
5518 <E, A2, E2, R2, A, A3, E3, R3>(
5519 options: {
5520 readonly onFailure: (cause: Cause.Cause<E>) => Effect<A2, E2, R2>
5521 readonly onSuccess: (a: A) => Effect<A3, E3, R3>
5522 }
5523 ): <R>(self: Effect<A, E, R>) => Effect<A2 | A3, E2 | E3, R2 | R3 | R>
5524 <A, E, R, A2, E2, R2, A3, E3, R3>(
5525 self: Effect<A, E, R>,
5526 options: {
5527 readonly onFailure: (cause: Cause.Cause<E>) => Effect<A2, E2, R2>
5528 readonly onSuccess: (a: A) => Effect<A3, E3, R3>
5529 }
5530 ): Effect<A2 | A3, E2 | E3, R2 | R3 | R>
5531} = internal.matchCauseEffectEager
5532
5533/**
5534 * Handles failures with access to the cause and allows performing side effects.
5535 *
5536 * **When to use**
5537 *
5538 * Use when you need to fold an `Effect` with effectful success handlers and
5539 * `Cause`-aware failure handlers.
5540 *
5541 * **Details**
5542 *
5543 * The `matchCauseEffect` function works similarly to {@link matchCause}, but it
5544 * also allows you to perform additional side effects based on the failure
5545 * cause. This function provides access to the complete cause of the failure,
5546 * making it possible to differentiate between various failure types, and allows
5547 * you to respond accordingly while performing side effects (like logging or
5548 * other operations).
5549 *
5550 * **Example** (Effectfully matching on causes)
5551 *
5552 * ```ts import.meta.vitest
5553 * import { Cause, Data, Effect, Result } from "effect"
5554 * const output: Array<unknown> = []
5555 *
5556 * class TaskError extends Data.TaggedError("TaskError")<{ readonly message: string }> {}
5557 *
5558 * const task = Effect.fail(new TaskError({ message: "Task failed" }))
5559 *
5560 * const program = Effect.matchCauseEffect(task, {
5561 * onFailure: (cause) =>
5562 * Effect.gen(function*() {
5563 * if (Cause.hasFails(cause)) {
5564 * const error = Cause.findError(cause)
5565 * if (Result.isSuccess(error)) {
5566 * yield* Effect.sync(() => { output.push(`Handling error: ${error.success.message}`) })
5567 * }
5568 * return "recovered from error"
5569 * } else {
5570 * yield* Effect.sync(() => { output.push("Handling interruption or defect") })
5571 * return "recovered from interruption/defect"
5572 * }
5573 * }),
5574 * onSuccess: (value) =>
5575 * Effect.gen(function*() {
5576 * yield* Effect.sync(() => { output.push(`Success: ${value}`) })
5577 * return `processed ${value}`
5578 * })
5579 * })
5580 *
5581 * void output.push(Effect.runSync(program))
5582 * output // => ["Handling error: Task failed", "recovered from error"]
5583 * ```
5584 *
5585 * @see {@link matchCause} if you don't need side effects and only want to handle the result or failure.
5586 * @see {@link matchEffect} if you don't need to handle the cause of the failure.
5587 *
5588 * @category pattern matching
5589 * @since 2.0.0
5590 */
5591export const matchCauseEffect: {
5592 <E, A2, E2, R2, A, A3, E3, R3>(options: {
5593 readonly onFailure: (cause: Cause.Cause<E>) => Effect<A2, E2, R2>
5594 readonly onSuccess: (a: A) => Effect<A3, E3, R3>
5595 }): <R>(self: Effect<A, E, R>) => Effect<A2 | A3, E2 | E3, R2 | R3 | R>
5596 <A, E, R, A2, E2, R2, A3, E3, R3>(
5597 self: Effect<A, E, R>,
5598 options: {
5599 readonly onFailure: (cause: Cause.Cause<E>) => Effect<A2, E2, R2>
5600 readonly onSuccess: (a: A) => Effect<A3, E3, R3>
5601 }
5602 ): Effect<A2 | A3, E2 | E3, R2 | R3 | R>
5603} = internal.matchCauseEffect
5604
5605/**
5606 * Handles both success and failure by running effectful handlers.
5607 *
5608 * **When to use**
5609 *
5610 * Use when you need to handle an `Effect`'s failure or success with handlers
5611 * that return effects.
5612 *
5613 * **Details**
5614 *
5615 * Use `matchEffect` when either branch needs to return an `Effect`, such as
5616 * performing logging, recovery, notification, or other effectful work. The
5617 * returned effect succeeds or fails according to the handler that is run.
5618 *
5619 * **Example** (Matching success and failure with effectful handlers)
5620 *
5621 * ```ts import.meta.vitest
5622 * import { Data, Effect } from "effect"
5623 *
5624 * class ExampleError extends Data.TaggedError("ExampleError")<{ readonly message: string }> {}
5625 *
5626 * const success: Effect.Effect<number, ExampleError> = Effect.succeed(42)
5627 * const failure: Effect.Effect<number, ExampleError> = Effect.fail(
5628 * new ExampleError({ message: "Uh oh!" })
5629 * )
5630 *
5631 * const program1 = Effect.matchEffect(success, {
5632 * onFailure: (error) =>
5633 * Effect.succeed(`failure: ${error.message}`),
5634 * onSuccess: (value) =>
5635 * Effect.succeed(`success: ${value}`)
5636 * })
5637 *
5638 * Effect.runSync(program1) // => "success: 42"
5639 *
5640 * const program2 = Effect.matchEffect(failure, {
5641 * onFailure: (error) =>
5642 * Effect.succeed(`failure: ${error.message}`),
5643 * onSuccess: (value) =>
5644 * Effect.succeed(`success: ${value}`)
5645 * })
5646 *
5647 * Effect.runSync(program2) // => "failure: Uh oh!"
5648 * ```
5649 *
5650 * @see {@link match} if you don't need side effects and only want to handle the
5651 * result or failure.
5652 * @category pattern matching
5653 * @since 2.0.0
5654 */
5655export const matchEffect: {
5656 <E, A2, E2, R2, A, A3, E3, R3>(options: {
5657 readonly onFailure: (e: E) => Effect<A2, E2, R2>
5658 readonly onSuccess: (a: A) => Effect<A3, E3, R3>
5659 }): <R>(self: Effect<A, E, R>) => Effect<A2 | A3, E2 | E3, R2 | R3 | R>
5660 <A, E, R, A2, E2, R2, A3, E3, R3>(
5661 self: Effect<A, E, R>,
5662 options: {
5663 readonly onFailure: (e: E) => Effect<A2, E2, R2>
5664 readonly onSuccess: (a: A) => Effect<A3, E3, R3>
5665 }
5666 ): Effect<A2 | A3, E2 | E3, R2 | R3 | R>
5667} = internal.matchEffect
5668
5669// -----------------------------------------------------------------------------
5670// Condition checking
5671// -----------------------------------------------------------------------------
5672
5673/**
5674 * Determines whether an effect fails.
5675 *
5676 * **Details**
5677 *
5678 * Defects are not converted; if the effect dies, the resulting effect dies too.
5679 *
5680 * **Example** (Checking whether an effect fails)
5681 *
5682 * ```ts import.meta.vitest
5683 * import { Effect } from "effect"
5684 * const output: Array<unknown> = []
5685 *
5686 * const program = Effect.gen(function*() {
5687 * const failed = yield* Effect.isFailure(Effect.fail("Uh oh!"))
5688 * yield* Effect.sync(() => { output.push(failed) })
5689 * })
5690 *
5691 * Effect.runSync(program)
5692 * output // => [true]
5693 * ```
5694 *
5695 * @category predicates
5696 * @since 2.0.0
5697 */
5698export const isFailure: <A, E, R>(self: Effect<A, E, R>) => Effect<boolean, never, R> = internal.isFailure
5699
5700/**
5701 * Returns whether an effect completes successfully.
5702 *
5703 * **Details**
5704 *
5705 * Returns `false` for failures in the error channel, but defects still fail the
5706 * effect.
5707 *
5708 * **Example** (Checking whether an effect succeeds)
5709 *
5710 * ```ts import.meta.vitest
5711 * import { Effect } from "effect"
5712 * const output: Array<unknown> = []
5713 *
5714 * const program = Effect.gen(function*() {
5715 * const ok = yield* Effect.isSuccess(Effect.succeed("done"))
5716 * const failed = yield* Effect.isSuccess(Effect.fail("Uh oh"))
5717 * yield* Effect.sync(() => { output.push(`ok: ${ok}`) })
5718 * yield* Effect.sync(() => { output.push(`failed: ${failed}`) })
5719 * })
5720 *
5721 * Effect.runSync(program)
5722 * output // => ["ok: true", "failed: false"]
5723 * ```
5724 *
5725 * @category predicates
5726 * @since 2.0.0
5727 */
5728export const isSuccess: <A, E, R>(self: Effect<A, E, R>) => Effect<boolean, never, R> = internal.isSuccess
5729
5730// -----------------------------------------------------------------------------
5731// Environment
5732// -----------------------------------------------------------------------------
5733
5734/**
5735 * Returns the complete context.
5736 *
5737 * **When to use**
5738 *
5739 * Use to read the complete `Context` available to the current effect.
5740 *
5741 * **Details**
5742 *
5743 * This function allows you to access all services that are currently available
5744 * in the effect's environment. This can be useful for debugging, introspection,
5745 * or when you need to pass the entire context to another function.
5746 *
5747 * **Example** (Reading the full context)
5748 *
5749 * ```ts import.meta.vitest
5750 * import { Context, Effect, Option } from "effect"
5751 * const output: Array<unknown> = []
5752 *
5753 * const Logger = Context.Service<{
5754 * log: (msg: string) => void
5755 * }>("Logger")
5756 * const Database = Context.Service<{
5757 * query: (sql: string) => string
5758 * }>("Database")
5759 *
5760 * const program = Effect.gen(function*() {
5761 * const allServices = yield* Effect.context()
5762 *
5763 * // Check if specific services are available
5764 * const loggerOption = Context.getOption(allServices, Logger)
5765 * const databaseOption = Context.getOption(allServices, Database)
5766 *
5767 * yield* Effect.sync(() => { output.push(`Logger available: ${Option.isSome(loggerOption)}`) })
5768 * yield* Effect.sync(() => { output.push(`Database available: ${Option.isSome(databaseOption)}`) })
5769 * })
5770 *
5771 * const context = Context.make(Logger, { log: () => {} })
5772 * .pipe(Context.add(Database, { query: () => "result" }))
5773 *
5774 * const provided = Effect.provideContext(program, context)
5775 * Effect.runSync(provided)
5776 * output // => ["Logger available: true", "Database available: true"]
5777 * ```
5778 *
5779 * @see {@link contextWith} for deriving an effect from the complete context
5780 * @see {@link service} for reading one service from the context
5781 *
5782 * @category accessors
5783 * @since 2.0.0
5784 */
5785export const context: <R = never>() => Effect<Context.Context<R>, never, R> = internal.context
5786
5787/**
5788 * Transforms the current context using the provided function.
5789 *
5790 * **When to use**
5791 *
5792 * Use to derive an effect from the complete `Context`.
5793 *
5794 * **Details**
5795 *
5796 * This function allows you to access the complete context and perform
5797 * computations based on all available services. This is useful when you need
5798 * to conditionally execute logic based on what services are available.
5799 *
5800 * **Example** (Deriving values from the context)
5801 *
5802 * ```ts import.meta.vitest
5803 * import { Context, Effect, Option } from "effect"
5804 * const output: Array<unknown> = []
5805 *
5806 * const Logger = Context.Service<{
5807 * log: (msg: string) => void
5808 * }>("Logger")
5809 * const Cache = Context.Service<{
5810 * get: (key: string) => string | null
5811 * }>("Cache")
5812 *
5813 * const program = Effect.contextWith((services: Context.Context<Context.Service.Identifier<typeof Cache>>) => {
5814 * const cacheOption = Context.getOption(services, Cache)
5815 * const hasCache = Option.isSome(cacheOption)
5816 *
5817 * if (hasCache) {
5818 * return Effect.gen(function*() {
5819 * const cache = yield* Effect.service(Cache)
5820 * yield* Effect.sync(() => { output.push("Using cached data") })
5821 * return cache.get("user:123") || "default"
5822 * })
5823 * } else {
5824 * return Effect.gen(function*() {
5825 * yield* Effect.sync(() => { output.push("No cache available, using fallback") })
5826 * return "fallback data"
5827 * })
5828 * }
5829 * })
5830 *
5831 * const withCache = Effect.provideService(program, Cache, {
5832 * get: () => "cached_value"
5833 * })
5834 * void output.push(Effect.runSync(withCache))
5835 * output // => ["Using cached data", "cached_value"]
5836 * ```
5837 *
5838 * @see {@link context} for reading the complete context as a value
5839 * @see {@link service} for reading one service from the context
5840 *
5841 * @category accessors
5842 * @since 2.0.0
5843 */
5844export const contextWith: <R, A, E, R2>(
5845 f: (context: Context.Context<R>) => Effect<A, E, R2>
5846) => Effect<A, E, R | R2> = internal.contextWith
5847
5848/**
5849 * Provides dependencies to an effect using layers or a context. Use `options.local`
5850 * to build the layer every time; by default, layers are shared between provide
5851 * calls.
5852 *
5853 * **Example** (Providing dependencies with a layer)
5854 *
5855 * ```ts import.meta.vitest
5856 * import { Context, Effect, Layer } from "effect"
5857 *
5858 * interface Database {
5859 * readonly query: (sql: string) => Effect.Effect<string>
5860 * }
5861 *
5862 * const Database = Context.Service<Database>("Database")
5863 *
5864 * const DatabaseLayer = Layer.succeed(Database)({
5865 * query: Effect.fn("Database.query")((sql: string) => Effect.succeed(`Result for: ${sql}`))
5866 * })
5867 *
5868 * const program = Effect.gen(function*() {
5869 * const db = yield* Database
5870 * return yield* db.query("SELECT * FROM users")
5871 * })
5872 *
5873 * const provided = Effect.provide(program, DatabaseLayer)
5874 *
5875 * await Effect.runPromise(provided) // => "Result for: SELECT * FROM users"
5876 * ```
5877 *
5878 * @category providing services
5879 * @since 2.0.0
5880 */
5881export const provide: {
5882 <const Layers extends [Layer.Any, ...Array<Layer.Any>]>(
5883 layers: Layers,
5884 options?: {
5885 readonly local?: boolean | undefined
5886 } | undefined
5887 ): <A, E, R>(
5888 self: Effect<A, E, R>
5889 ) => Effect<
5890 A,
5891 E | Layer.Error<Layers[number]>,
5892 Layer.Services<Layers[number]> | Exclude<R, Layer.Success<Layers[number]>>
5893 >
5894 <ROut, E2, RIn>(
5895 layer: Layer.Layer<ROut, E2, RIn>,
5896 options?: {
5897 readonly local?: boolean | undefined
5898 } | undefined
5899 ): <A, E, R>(
5900 self: Effect<A, E, R>
5901 ) => Effect<A, E | E2, RIn | Exclude<R, ROut>>
5902 <R2>(
5903 context: Context.Context<R2>
5904 ): <A, E, R>(self: Effect<A, E, R>) => Effect<A, E, Exclude<R, R2>>
5905 <A, E, R, const Layers extends [Layer.Any, ...Array<Layer.Any>]>(
5906 self: Effect<A, E, R>,
5907 layers: Layers,
5908 options?: {
5909 readonly local?: boolean | undefined
5910 } | undefined
5911 ): Effect<
5912 A,
5913 E | Layer.Error<Layers[number]>,
5914 Layer.Services<Layers[number]> | Exclude<R, Layer.Success<Layers[number]>>
5915 >
5916 <A, E, R, ROut, E2, RIn>(
5917 self: Effect<A, E, R>,
5918 layer: Layer.Layer<ROut, E2, RIn>,
5919 options?: {
5920 readonly local?: boolean | undefined
5921 } | undefined
5922 ): Effect<A, E | E2, RIn | Exclude<R, ROut>>
5923 <A, E, R, R2>(
5924 self: Effect<A, E, R>,
5925 context: Context.Context<R2>
5926 ): Effect<A, E, Exclude<R, R2>>
5927} = internalLayer.provide
5928
5929/**
5930 * Provides a context to an effect, fulfilling its service requirements.
5931 *
5932 * **Details**
5933 *
5934 * This function provides multiple services at once by supplying a context
5935 * that contains all the required services. It removes the provided services
5936 * from the effect's requirements, making them available to the effect.
5937 *
5938 * **Example** (Providing a complete context)
5939 *
5940 * ```ts import.meta.vitest
5941 * import { Context, Effect } from "effect"
5942 * const output: Array<unknown> = []
5943 *
5944 * // Define service keys
5945 * const Logger = Context.Service<{
5946 * log: (msg: string) => void
5947 * }>("Logger")
5948 * const Database = Context.Service<{
5949 * query: (sql: string) => string
5950 * }>("Database")
5951 *
5952 * // Create a context with multiple services
5953 * const context = Context.make(Logger, { log: (message) => { output.push(message) } })
5954 * .pipe(Context.add(Database, { query: () => "result" }))
5955 *
5956 * // An effect that requires both services
5957 * const program = Effect.gen(function*() {
5958 * const logger = yield* Effect.service(Logger)
5959 * const db = yield* Effect.service(Database)
5960 * logger.log("Querying database")
5961 * return db.query("SELECT * FROM users")
5962 * })
5963 *
5964 * const provided = Effect.provideContext(program, context)
5965 * void output.push(Effect.runSync(provided))
5966 * output // => ["Querying database", "result"]
5967 * ```
5968 *
5969 * @category providing services
5970 * @since 4.0.0
5971 */
5972export const provideContext: {
5973 <XR>(
5974 context: Context.Context<XR>
5975 ): <A, E, R>(self: Effect<A, E, R>) => Effect<A, E, Exclude<R, XR>>
5976 <A, E, R, XR>(
5977 self: Effect<A, E, R>,
5978 context: Context.Context<XR>
5979 ): Effect<A, E, Exclude<R, XR>>
5980} = internal.provideContext
5981
5982/**
5983 * Runs an effect with the provided context as its complete environment.
5984 *
5985 * **When to use**
5986 *
5987 * Use when you already have a `Context` containing every service required by
5988 * the effect and want the wrapped effect to run with exactly that context.
5989 *
5990 * **Gotchas**
5991 *
5992 * `setContext` replaces the current context for the wrapped effect. Services
5993 * from an outer context are not inherited unless they are also present in the
5994 * context passed to `setContext`.
5995 *
5996 * **Example** (Running with a complete context)
5997 *
5998 * ```ts import.meta.vitest
5999 * import { Context, Effect } from "effect"
6000 *
6001 * class Config extends Context.Service<Config, {
6002 * readonly greeting: string
6003 * }>()("Config") {}
6004 *
6005 * const program = Effect.gen(function*() {
6006 * const config = yield* Effect.service(Config)
6007 * return `${config.greeting}, World!`
6008 * })
6009 *
6010 * const context = Context.make(Config, { greeting: "Hello" })
6011 *
6012 * const runnable = Effect.setContext(program, context)
6013 *
6014 * Effect.runSync(runnable) // => "Hello, World!"
6015 * ```
6016 *
6017 * @see {@link provideContext} for partially satisfying an effect's context requirements.
6018 * @see {@link updateContext} for deriving the required context from the current one.
6019 *
6020 * @category providing services
6021 * @since 4.0.0
6022 */
6023export const setContext: {
6024 <R>(context: Context.Context<R>): <A, E>(self: Effect<A, E, R>) => Effect<A, E>
6025 <A, E, R>(self: Effect<A, E, R>, context: Context.Context<R>): Effect<A, E>
6026} = internal.setContext
6027
6028/**
6029 * Accesses a service from the context.
6030 *
6031 * **Example** (Accessing a required service)
6032 *
6033 * ```ts import.meta.vitest
6034 * import { Context, Effect } from "effect"
6035 *
6036 * interface Database {
6037 * readonly query: (sql: string) => Effect.Effect<string>
6038 * }
6039 *
6040 * const Database = Context.Service<Database>("Database")
6041 *
6042 * const program = Effect.gen(function*() {
6043 * const db = yield* Effect.service(Database)
6044 * return yield* db.query("SELECT * FROM users")
6045 * })
6046 *
6047 * const runnable = Effect.provideService(program, Database, {
6048 * query: (sql) => Effect.succeed(`Result for: ${sql}`)
6049 * })
6050 * Effect.runSync(runnable) // => "Result for: SELECT * FROM users"
6051 * ```
6052 *
6053 * @category accessors
6054 * @since 4.0.0
6055 */
6056export const service: <I, S>(service: Context.Key<I, S>) => Effect<S, never, I> = internal.service
6057
6058/**
6059 * Optionally accesses a service from the environment.
6060 *
6061 * **When to use**
6062 *
6063 * Use to read an optional dependency from the current context without making
6064 * that dependency part of the effect's required environment.
6065 *
6066 * **Details**
6067 *
6068 * This function attempts to access a service from the environment. If the
6069 * service is available, it returns `Some(service)`. If the service is not
6070 * available, it returns `None`. Unlike `service`, this function does not
6071 * require the service to be present in the environment.
6072 *
6073 * **Example** (Accessing an optional service)
6074 *
6075 * ```ts import.meta.vitest
6076 * import { Context, Effect, Option } from "effect"
6077 * const output: Array<unknown> = []
6078 *
6079 * // Define a service key
6080 * const Logger = Context.Service<{
6081 * log: (msg: string) => void
6082 * }>("Logger")
6083 *
6084 * // Use serviceOption to optionally access the logger
6085 * const program = Effect.gen(function*() {
6086 * const maybeLogger = yield* Effect.serviceOption(Logger)
6087 *
6088 * if (Option.isSome(maybeLogger)) {
6089 * maybeLogger.value.log("Service is available")
6090 * } else {
6091 * void output.push("Service not available")
6092 * }
6093 * })
6094 *
6095 * Effect.runSync(program)
6096 * output // => ["Service not available"]
6097 * ```
6098 *
6099 * @category accessors
6100 * @since 2.0.0
6101 */
6102export const serviceOption: <I, S>(key: Context.Key<I, S>) => Effect<Option<S>> = internal.serviceOption
6103
6104/**
6105 * Provides part of the required context while leaving the rest unchanged.
6106 *
6107 * **Details**
6108 *
6109 * This function allows you to transform the context required by an effect,
6110 * providing part of the context and leaving the rest to be fulfilled later.
6111 *
6112 * **Example** (Updating the context before running)
6113 *
6114 * ```ts import.meta.vitest
6115 * import { Context, Effect } from "effect"
6116 *
6117 * // Define services
6118 * const Logger = Context.Service<{
6119 * log: (msg: string) => void
6120 * }>("Logger")
6121 * const Config = Context.Service<{
6122 * name: string
6123 * }>("Config")
6124 *
6125 * const program = Effect.service(Config).pipe(
6126 * Effect.map((config) => `Hello ${config.name}!`)
6127 * )
6128 *
6129 * // Transform services by providing Config while keeping Logger requirement
6130 * const configured = program.pipe(
6131 * Effect.updateContext((context: Context.Context<Context.Service.Identifier<typeof Logger>>) =>
6132 * Context.add(context, Config, { name: "World" })
6133 * )
6134 * )
6135 *
6136 * // The effect now requires only Logger service
6137 * const result = Effect.provideService(configured, Logger, {
6138 * log: () => {}
6139 * })
6140 * Effect.runSync(result) // => "Hello World!"
6141 * ```
6142 *
6143 * @category providing services
6144 * @since 4.0.0
6145 */
6146export const updateContext: {
6147 <R2, R>(
6148 f: (context: Context.Context<R2>) => Context.Context<NoInfer<R>>
6149 ): <A, E>(self: Effect<A, E, R>) => Effect<A, E, R2>
6150 <A, E, R, R2>(
6151 self: Effect<A, E, R>,
6152 f: (context: Context.Context<R2>) => Context.Context<NoInfer<R>>
6153 ): Effect<A, E, R2>
6154} = internal.updateContext
6155
6156/**
6157 * Runs an effect with a service implementation transformed by the provided
6158 * function.
6159 *
6160 * **Details**
6161 *
6162 * The service must be available in the effect's context; `updateService`
6163 * replaces it for the wrapped effect with the value returned by the updater.
6164 *
6165 * **Example** (Replacing a service for one effect)
6166 *
6167 * ```ts import.meta.vitest
6168 * import { Context, Effect } from "effect"
6169 * const output: Array<unknown> = []
6170 *
6171 * // Define a counter service
6172 * const Counter = Context.Service<{ count: number }>("Counter")
6173 *
6174 * const program = Effect.gen(function*() {
6175 * const updatedCounter = yield* Effect.service(Counter)
6176 * yield* Effect.sync(() => { output.push(`Updated count: ${updatedCounter.count}`) })
6177 * return updatedCounter.count
6178 * }).pipe(
6179 * Effect.updateService(Counter, (counter) => ({ count: counter.count + 1 }))
6180 * )
6181 *
6182 * // Provide initial service and run
6183 * const result = Effect.provideService(program, Counter, { count: 0 })
6184 * void output.push(Effect.runSync(result))
6185 * output // => ["Updated count: 1", 1]
6186 * ```
6187 *
6188 * @category providing services
6189 * @since 2.0.0
6190 */
6191export const updateService: {
6192 <I, A>(
6193 service: Context.Key<I, A>,
6194 f: (value: A) => NoInfer<A>
6195 ): <XA, E, R>(self: Effect<XA, E, R>) => Effect<XA, E, R | I>
6196 <XA, E, R, I, A>(
6197 self: Effect<XA, E, R>,
6198 service: Context.Key<I, A>,
6199 f: (value: A) => NoInfer<A>
6200 ): Effect<XA, E, R | I>
6201} = internal.updateService
6202
6203/**
6204 * Updates a service for the lifetime of the current scope and restores its
6205 * previous value when the scope closes.
6206 *
6207 * **When to use**
6208 *
6209 * Use when you need a setup effect to change a service for subsequent effects
6210 * in the same scope.
6211 *
6212 * **Details**
6213 *
6214 * The updater receives the currently visible service value. A
6215 * `Context.Service` remains in the requirements, while a `Context.Reference`
6216 * uses its default when no override is present and adds no service requirement.
6217 * The returned effect always requires `Scope`. The optional `reset` function
6218 * receives the original, updated, and current values when the scope closes,
6219 * allowing changes to be merged during restoration. It defaults to returning
6220 * the original value.
6221 *
6222 * **Example** (Updating a reference within a scope)
6223 *
6224 * ```ts import.meta.vitest
6225 * import { Context, Effect } from "effect"
6226 * const output: Array<unknown> = []
6227 *
6228 * const CurrentNumber = Context.Reference<number>("CurrentNumber", {
6229 * defaultValue: () => 1
6230 * })
6231 *
6232 * const program = Effect.gen(function*() {
6233 * const before = yield* CurrentNumber
6234 * const during = yield* Effect.scoped(
6235 * Effect.gen(function*() {
6236 * yield* Effect.updateServiceScoped(
6237 * CurrentNumber,
6238 * (value) => value + 1,
6239 * {
6240 * // Optional: when omitted, the original value is restored
6241 * reset: (original, updated, current) =>
6242 * Math.max(original, updated, current) + 1
6243 * }
6244 * )
6245 * return yield* CurrentNumber
6246 * })
6247 * )
6248 * const after = yield* CurrentNumber
6249 *
6250 * void output.push([before, during, after])
6251 * })
6252 *
6253 * await Effect.runPromise(program)
6254 * output // => [[1, 2, 3]]
6255 * ```
6256 *
6257 * @see {@link updateService} for updating a service only within a wrapped effect
6258 *
6259 * @category providing services
6260 * @since 4.0.0
6261 */
6262export const updateServiceScoped: <I, A>(
6263 service: Context.Key<I, A>,
6264 f: (value: A) => NoInfer<A>,
6265 options?: {
6266 readonly reset?: ((original: A, updated: A, current: A) => A) | undefined
6267 } | undefined
6268) => Effect<void, never, I | Scope> = internal.updateServiceScoped
6269
6270/**
6271 * Provides one concrete service implementation to an effect.
6272 *
6273 * **When to use**
6274 *
6275 * Use to satisfy one service requirement with an already-built implementation.
6276 *
6277 * **Details**
6278 *
6279 * The service requirement identified by the `Context.Key` is removed from the
6280 * effect requirements after the implementation is provided.
6281 *
6282 * **Example** (Providing a service value)
6283 *
6284 * ```ts import.meta.vitest
6285 * import { Context, Effect } from "effect"
6286 * const output: Array<unknown> = []
6287 *
6288 * // Define a service for configuration
6289 * const Config = Context.Service<{
6290 * apiUrl: string
6291 * timeout: number
6292 * }>("Config")
6293 *
6294 * const fetchData = Effect.gen(function*() {
6295 * const config = yield* Effect.service(Config)
6296 * yield* Effect.sync(() => { output.push(`Fetching from: ${config.apiUrl}`) })
6297 * yield* Effect.sync(() => { output.push(`Timeout: ${config.timeout}ms`) })
6298 * return "data"
6299 * })
6300 *
6301 * // Provide the service implementation
6302 * const program = Effect.provideService(fetchData, Config, {
6303 * apiUrl: "https://api.example.com",
6304 * timeout: 5000
6305 * })
6306 *
6307 * void output.push(Effect.runSync(program))
6308 * output // => ["Fetching from: https://api.example.com", "Timeout: 5000ms", "data"]
6309 * ```
6310 *
6311 * @see {@link provide} for providing multiple layers to an effect.
6312 * @see {@link provideServiceEffect} for acquiring the service implementation effectfully.
6313 * @see {@link provideContext} for providing a complete context.
6314 * @category providing services
6315 * @since 2.0.0
6316 */
6317export const provideService: {
6318 <I, S>(
6319 service: Context.Key<I, S>
6320 ): {
6321 (implementation: S): <A, E, R>(self: Effect<A, E, R>) => Effect<A, E, Exclude<R, I>>
6322 <A, E, R>(self: Effect<A, E, R>, implementation: S): Effect<A, E, Exclude<R, I>>
6323 }
6324 <I, S>(
6325 service: Context.Key<I, S>,
6326 implementation: S
6327 ): <A, E, R>(self: Effect<A, E, R>) => Effect<A, E, Exclude<R, I>>
6328 <A, E, R, I, S>(
6329 self: Effect<A, E, R>,
6330 service: Context.Key<I, S>,
6331 implementation: S
6332 ): Effect<A, E, Exclude<R, I>>
6333} = internal.provideService
6334
6335/**
6336 * Provides one service to an effect using an effectful acquisition.
6337 *
6338 * **When to use**
6339 *
6340 * Use when the service implementation must be created by an effect and its
6341 * acquisition failure should remain in the returned effect.
6342 *
6343 * **Details**
6344 *
6345 * `provideServiceEffect` runs the acquisition effect to produce the service
6346 * implementation, removes that service from the wrapped effect's requirements,
6347 * and leaves any other requirements to be provided later. Acquisition failures
6348 * are included in the returned effect's error channel.
6349 *
6350 * **Example** (Providing a service with an effect)
6351 *
6352 * ```ts import.meta.vitest
6353 * import { Context, Effect } from "effect"
6354 * const output: Array<unknown> = []
6355 *
6356 * // Define a database connection service
6357 * interface DatabaseConnection {
6358 * readonly query: (sql: string) => Effect.Effect<string>
6359 * }
6360 * const Database = Context.Service<DatabaseConnection>("Database")
6361 *
6362 * // Effect that creates a database connection
6363 * const createConnection = Effect.gen(function*() {
6364 * yield* Effect.sync(() => { output.push("Establishing database connection...") })
6365 * yield* Effect.sync(() => { output.push("Database connected!") })
6366 * return {
6367 * query: (sql: string) => Effect.succeed(`Result for: ${sql}`)
6368 * }
6369 * })
6370 *
6371 * const program = Effect.gen(function*() {
6372 * const db = yield* Effect.service(Database)
6373 * return yield* db.query("SELECT * FROM users")
6374 * })
6375 *
6376 * // Provide the service through an effect
6377 * const withDatabase = Effect.provideServiceEffect(
6378 * program,
6379 * Database,
6380 * createConnection
6381 * )
6382 *
6383 * void output.push(await Effect.runPromise(withDatabase))
6384 * output // => ["Establishing database connection...", "Database connected!", "Result for: SELECT * FROM users"]
6385 * ```
6386 *
6387 * @category providing services
6388 * @since 2.0.0
6389 */
6390export const provideServiceEffect: {
6391 <I, S, E2, R2>(
6392 service: Context.Key<I, S>,
6393 acquire: Effect<NoInfer<S>, E2, R2>
6394 ): <A, E, R>(self: Effect<A, E, R>) => Effect<A, E | E2, Exclude<R, I> | R2>
6395 <A, E, R, I, S, E2, R2>(
6396 self: Effect<A, E, R>,
6397 service: Context.Key<I, S>,
6398 acquire: Effect<NoInfer<S>, E2, R2>
6399 ): Effect<A, E | E2, Exclude<R, I> | R2>
6400} = internal.provideServiceEffect
6401
6402// -----------------------------------------------------------------------------
6403// Resource management & finalization
6404// -----------------------------------------------------------------------------
6405
6406/**
6407 * Returns the current scope for resource management.
6408 *
6409 * **Example** (Accessing the current scope)
6410 *
6411 * ```ts import.meta.vitest
6412 * import { Effect } from "effect"
6413 * const output: Array<unknown> = []
6414 *
6415 * const program = Effect.gen(function*() {
6416 * const currentScope = yield* Effect.scope
6417 * yield* Effect.sync(() => { output.push("Got scope for resource management") })
6418 *
6419 * // Use the scope to manually manage resources if needed
6420 * const resource = yield* Effect.acquireRelease(
6421 * Effect.sync(() => { output.push("Acquiring resource") }).pipe(Effect.as("resource")),
6422 * () => Effect.sync(() => { output.push("Releasing resource") })
6423 * )
6424 *
6425 * return resource
6426 * })
6427 *
6428 * void output.push(Effect.runSync(Effect.scoped(program)))
6429 * output // => ["Got scope for resource management", "Acquiring resource", "Releasing resource", "resource"]
6430 * ```
6431 *
6432 * @category resource management
6433 * @since 2.0.0
6434 */
6435export const scope: Effect<Scope, never, Scope> = internal.scope
6436
6437/**
6438 * Runs an effect with a scope that closes when the effect completes.
6439 *
6440 * **When to use**
6441 *
6442 * Use to acquire scoped resources for the duration of a single workflow.
6443 *
6444 * **Details**
6445 *
6446 * Finalizers for resources acquired inside the workflow run as soon as the
6447 * workflow completes, whether by success, failure, or interruption.
6448 *
6449 * **Example** (Running a scoped acquisition)
6450 *
6451 * ```ts import.meta.vitest
6452 * import { Effect } from "effect"
6453 * const output: Array<unknown> = []
6454 *
6455 * const resource = Effect.acquireRelease(
6456 * Effect.sync(() => { output.push("Acquiring resource") }).pipe(Effect.as("resource")),
6457 * () => Effect.sync(() => { output.push("Releasing resource") })
6458 * )
6459 *
6460 * const program = Effect.scoped(
6461 * Effect.gen(function*() {
6462 * const res = yield* resource
6463 * yield* Effect.sync(() => { output.push(`Using ${res}`) })
6464 * return res
6465 * })
6466 * )
6467 *
6468 * Effect.runSync(program)
6469 * output // => ["Acquiring resource", "Using resource", "Releasing resource"]
6470 * ```
6471 *
6472 * @category resource management
6473 * @since 2.0.0
6474 */
6475export const scoped: <A, E, R>(
6476 self: Effect<A, E, R>
6477) => Effect<A, E, Exclude<R, Scope>> = internal.scoped
6478
6479/**
6480 * Creates a scoped effect by providing access to the scope.
6481 *
6482 * **When to use**
6483 *
6484 * Use when resource acquisition needs direct access to the scope being created,
6485 * for example to register finalizers manually.
6486 *
6487 * **Example** (Working with an explicit scope)
6488 *
6489 * ```ts import.meta.vitest
6490 * import { Effect, Scope } from "effect"
6491 * const output: Array<unknown> = []
6492 *
6493 * const program = Effect.scopedWith((scope) =>
6494 * Effect.gen(function*() {
6495 * yield* Effect.sync(() => { output.push("Inside scoped context") })
6496 *
6497 * // Manually add a finalizer to the scope
6498 * yield* Scope.addFinalizer(scope, Effect.sync(() => { output.push("Manual finalizer") }))
6499 *
6500 * // Create a scoped resource
6501 * const resource = yield* Effect.scoped(
6502 * Effect.acquireRelease(
6503 * Effect.sync(() => { output.push("Acquiring resource") }).pipe(Effect.as("resource")),
6504 * () => Effect.sync(() => { output.push("Releasing resource") })
6505 * )
6506 * )
6507 *
6508 * return resource
6509 * })
6510 * )
6511 *
6512 * void output.push(Effect.runSync(program))
6513 * output // => ["Inside scoped context", "Acquiring resource", "Releasing resource", "Manual finalizer", "resource"]
6514 * ```
6515 *
6516 * @category resource management
6517 * @since 3.11.0
6518 */
6519export const scopedWith: <A, E, R>(
6520 f: (scope: Scope) => Effect<A, E, R>
6521) => Effect<A, E, R> = internal.scopedWith
6522
6523/**
6524 * Constructs a scoped resource from an acquisition effect and a release
6525 * finalizer.
6526 *
6527 * **When to use**
6528 *
6529 * Use to acquire a scoped resource with an explicit release finalizer.
6530 *
6531 * **Details**
6532 *
6533 * If acquisition succeeds, the release finalizer is added to the current scope
6534 * and is guaranteed to run when that scope closes. The finalizer receives the
6535 * `Exit` value used to close the scope.
6536 *
6537 * By default, acquisition is protected by an uninterruptible region. Pass
6538 * `{ interruptible: true }` to allow the acquisition effect to be interrupted.
6539 *
6540 * **Example** (Acquiring and releasing a resource)
6541 *
6542 * ```ts import.meta.vitest
6543 * import { Effect, Exit } from "effect"
6544 * const output: Array<unknown> = []
6545 *
6546 * // Simulate a resource that needs cleanup
6547 * interface FileHandle {
6548 * readonly path: string
6549 * readonly content: string
6550 * }
6551 *
6552 * // Acquire a file handle
6553 * const acquire = Effect.gen(function*() {
6554 * yield* Effect.sync(() => { output.push("Opening file") })
6555 * return { path: "/tmp/file.txt", content: "file content" }
6556 * })
6557 *
6558 * // Release the file handle
6559 * const release = (handle: FileHandle, exit: Exit.Exit<unknown, unknown>) =>
6560 * Effect.sync(() => { output.push(
6561 * `Closing file ${handle.path} with exit: ${
6562 * Exit.isSuccess(exit) ? "success" : "failure"
6563 * }`
6564 * ) })
6565 *
6566 * // Create a scoped resource
6567 * const resource = Effect.acquireRelease(acquire, release)
6568 *
6569 * // Use the resource within a scope
6570 * const program = Effect.scoped(
6571 * Effect.gen(function*() {
6572 * const handle = yield* resource
6573 * yield* Effect.sync(() => { output.push(`Using file: ${handle.path}`) })
6574 * return handle.content
6575 * })
6576 * )
6577 *
6578 * void output.push(Effect.runSync(program))
6579 * output // => ["Opening file", "Using file: /tmp/file.txt", "Closing file /tmp/file.txt with exit: success", "file content"]
6580 * ```
6581 *
6582 * @see {@link acquireDisposable} for resources that implement JavaScript disposal protocols
6583 * @see {@link acquireUseRelease} for bracketing acquire, use, and release in one effect
6584 *
6585 * @category resource management
6586 * @since 2.0.0
6587 */
6588export const acquireRelease: <A, E, R, R2>(
6589 acquire: Effect<A, E, R>,
6590 release: (a: A, exit: Exit.Exit<unknown, unknown>) => Effect<unknown, never, R2>,
6591 options?: { readonly interruptible?: boolean }
6592) => Effect<A, E, R | R2 | Scope> = internal.acquireRelease
6593
6594/**
6595 * Acquires a scoped resource that implements JavaScript disposal protocols.
6596 *
6597 * **When to use**
6598 *
6599 * Use when you work with JavaScript `Disposable` or `AsyncDisposable` resources
6600 * that should be closed with the surrounding scope.
6601 *
6602 * **Details**
6603 *
6604 * The resource is automatically disposed when the surrounding
6605 * {@link Scope} is closed, using {@link Symbol.dispose} for
6606 * synchronous disposables or {@link Symbol.asyncDispose} for asynchronous
6607 * disposables.
6608 *
6609 * This is similar to {@link acquireRelease}, but uses the standard
6610 * JavaScript disposal protocol instead of requiring an explicit release
6611 * function. It works with JavaScript `Disposable` and `AsyncDisposable`
6612 * resources.
6613 *
6614 * **Example** (Acquiring a disposable resource)
6615 *
6616 * ```ts import.meta.vitest
6617 * import { Effect } from "effect"
6618 * const output: Array<unknown> = []
6619 *
6620 * class Resource implements Disposable {
6621 * [Symbol.dispose]() {
6622 * void output.push("disposed")
6623 * }
6624 * }
6625 *
6626 * const program = Effect.scoped(
6627 * Effect.gen(function*() {
6628 * yield* Effect.acquireDisposable(Effect.succeed(new Resource()))
6629 * void output.push("acquired")
6630 * })
6631 * )
6632 *
6633 * Effect.runSync(program)
6634 * output // => ["acquired", "disposed"]
6635 * ```
6636 *
6637 * @see {@link acquireRelease} for resources that need an explicit finalizer
6638 *
6639 * @category resource management
6640 * @since 4.0.0
6641 */
6642export const acquireDisposable: <A extends AsyncDisposable | Disposable, E, R>(
6643 acquire: Effect<A, E, R>
6644) => Effect<A, E, R | Scope> = internal.acquireDisposable
6645
6646/**
6647 * Runs resource acquisition, usage, and release as one bracketed effect.
6648 *
6649 * **When to use**
6650 *
6651 * Use to bracket acquire, use, and release logic in one effect.
6652 *
6653 * **Details**
6654 *
6655 * `acquireUseRelease` does the following:
6656 *
6657 * 1. Ensures that the `Effect` value that acquires the resource will not be
6658 * interrupted. Note that acquisition may still fail due to internal
6659 * reasons (such as an uncaught exception).
6660 * 2. Ensures that the `release` `Effect` value will not be interrupted,
6661 * and will be executed as long as the acquisition `Effect` value
6662 * successfully acquires the resource.
6663 *
6664 * During the time period between the acquisition and release of the resource,
6665 * the `use` `Effect` value will be executed.
6666 *
6667 * If the `release` `Effect` value fails, then the entire `Effect` value will
6668 * fail, even if the `use` `Effect` value succeeds. If this fail-fast behavior
6669 * is not desired, errors produced by the `release` `Effect` value can be caught
6670 * and ignored.
6671 *
6672 * **Example** (Acquiring resources with cleanup)
6673 *
6674 * ```ts import.meta.vitest
6675 * import { Effect, Exit } from "effect"
6676 * const output: Array<unknown> = []
6677 *
6678 * interface Database {
6679 * readonly connection: string
6680 * readonly query: (sql: string) => Effect.Effect<string>
6681 * }
6682 *
6683 * const program = Effect.acquireUseRelease(
6684 * // Acquire - connect to database
6685 * Effect.gen(function*() {
6686 * yield* Effect.sync(() => { output.push("Connecting to database...") })
6687 * return {
6688 * connection: "db://localhost:5432",
6689 * query: (sql: string) => Effect.succeed(`Result for: ${sql}`)
6690 * }
6691 * }),
6692 * // Use - perform database operations
6693 * (db) =>
6694 * Effect.gen(function*() {
6695 * yield* Effect.sync(() => { output.push(`Connected to ${db.connection}`) })
6696 * const result = yield* db.query("SELECT * FROM users")
6697 * yield* Effect.sync(() => { output.push(`Query result: ${result}`) })
6698 * return result
6699 * }),
6700 * // Release - close database connection
6701 * (db, exit) =>
6702 * Effect.gen(function*() {
6703 * if (Exit.isSuccess(exit)) {
6704 * yield* Effect.sync(() => { output.push(`Closing connection to ${db.connection} (success)`) })
6705 * } else {
6706 * yield* Effect.sync(() => { output.push(`Closing connection to ${db.connection} (failure)`) })
6707 * }
6708 * })
6709 * )
6710 *
6711 * await Effect.runPromise(program)
6712 * output // => ["Connecting to database...", "Connected to db://localhost:5432", "Query result: Result for: SELECT * FROM users", "Closing connection to db://localhost:5432 (success)"]
6713 * ```
6714 *
6715 * @see {@link acquireRelease} for scoped resources whose use happens later
6716 *
6717 * @category resource management
6718 * @since 2.0.0
6719 */
6720export const acquireUseRelease: <Resource, E, R, A, E2, R2, E3, R3>(
6721 acquire: Effect<Resource, E, R>,
6722 use: (a: Resource) => Effect<A, E2, R2>,
6723 release: (a: Resource, exit: Exit.Exit<A, E2>) => Effect<void, E3, R3>
6724) => Effect<A, E | E2 | E3, R | R2 | R3> = internal.acquireUseRelease
6725
6726/**
6727 * Adds a finalizer to the current scope.
6728 *
6729 * **When to use**
6730 *
6731 * Use to register low-level cleanup in the current scope.
6732 *
6733 * **Details**
6734 *
6735 * The finalizer runs when the surrounding scope is closed and receives the
6736 * `Exit` value used to close the scope.
6737 *
6738 * **Example** (Registering scope finalizers)
6739 *
6740 * ```ts import.meta.vitest
6741 * import { Effect, Exit } from "effect"
6742 * const output: Array<unknown> = []
6743 *
6744 * const program = Effect.scoped(
6745 * Effect.gen(function*() {
6746 * // Add a finalizer that runs when the scope closes
6747 * yield* Effect.addFinalizer((exit) =>
6748 * Effect.sync(() => { output.push(
6749 * Exit.isSuccess(exit)
6750 * ? "Cleanup: Operation completed successfully"
6751 * : "Cleanup: Operation failed, cleaning up resources"
6752 * ) })
6753 * )
6754 *
6755 * yield* Effect.sync(() => { output.push("Performing main operation...") })
6756 *
6757 * // This could succeed or fail
6758 * return "operation result"
6759 * })
6760 * )
6761 *
6762 * void output.push(Effect.runSync(program))
6763 * output // => ["Performing main operation...", "Cleanup: Operation completed successfully", "operation result"]
6764 * ```
6765 *
6766 * @see {@link acquireRelease} for resource acquisition with a release finalizer
6767 * @see {@link ensuring} for attaching a finalizer to one effect
6768 *
6769 * @category resource management
6770 * @since 2.0.0
6771 */
6772export const addFinalizer: <R>(
6773 finalizer: (exit: Exit.Exit<unknown, unknown>) => Effect<void, never, R>
6774) => Effect<void, never, R | Scope> = internal.addFinalizer
6775
6776/**
6777 * Returns an effect that, if this effect _starts_ execution, then the
6778 * specified `finalizer` is guaranteed to be executed, whether this effect
6779 * succeeds, fails, or is interrupted.
6780 *
6781 * **Details**
6782 *
6783 * For use cases that need access to the effect's result, see `onExit`.
6784 *
6785 * Finalizers offer very powerful guarantees, but they are low-level, and
6786 * should generally not be used for releasing resources. For higher-level
6787 * logic built on `ensuring`, see the `acquireRelease` family of methods.
6788 *
6789 * **Example** (Always running cleanup)
6790 *
6791 * ```ts import.meta.vitest
6792 * import { Effect } from "effect"
6793 * const output: Array<unknown> = []
6794 *
6795 * const task = Effect.gen(function*() {
6796 * yield* Effect.sync(() => { output.push("Task started") })
6797 * yield* Effect.sync(() => { output.push("Task completed") })
6798 * return 42
6799 * })
6800 *
6801 * // Ensure cleanup always runs, regardless of success or failure
6802 * const program = Effect.ensuring(
6803 * task,
6804 * Effect.sync(() => { output.push("Cleanup: This always runs!") })
6805 * )
6806 *
6807 * void output.push(Effect.runSync(program))
6808 * output // => ["Task started", "Task completed", "Cleanup: This always runs!", 42]
6809 * ```
6810 *
6811 * @category resource management
6812 * @since 2.0.0
6813 */
6814export const ensuring: {
6815 <X, R1>(
6816 finalizer: Effect<X, never, R1>
6817 ): <A, E, R>(self: Effect<A, E, R>) => Effect<A, E, R1 | R>
6818 <A, E, R, X, R1>(
6819 self: Effect<A, E, R>,
6820 finalizer: Effect<X, never, R1>
6821 ): Effect<A, E, R1 | R>
6822} = internal.ensuring
6823
6824/**
6825 * Runs the specified effect if this effect fails, providing the error to the
6826 * effect if it exists. The provided effect will not be interrupted.
6827 *
6828 * **Example** (Running cleanup on failure)
6829 *
6830 * ```ts import.meta.vitest
6831 * import { Cause, Data, Effect, Exit } from "effect"
6832 * const output: Array<unknown> = []
6833 *
6834 * class TaskError extends Data.TaggedError("TaskError")<{ readonly message: string }> {}
6835 *
6836 * const error = new TaskError({ message: "Something went wrong" })
6837 * const task = Effect.fail(error)
6838 *
6839 * const program = Effect.onError(
6840 * task,
6841 * (cause) => Effect.sync(() => { output.push(`Cleanup on error: ${Cause.squash(cause)}`) })
6842 * )
6843 *
6844 * void output.push(Effect.runSyncExit(program))
6845 * output // => ["Cleanup on error: TaskError: Something went wrong", Exit.fail(error)]
6846 * ```
6847 *
6848 * @category resource management
6849 * @since 2.0.0
6850 */
6851export const onError: {
6852 <E, X, R2>(
6853 cleanup: (cause: Cause.Cause<E>) => Effect<X, never, R2>
6854 ): <A, R>(self: Effect<A, E, R>) => Effect<A, E, R2 | R>
6855 <A, E, R, X, R2>(
6856 self: Effect<A, E, R>,
6857 cleanup: (cause: Cause.Cause<E>) => Effect<X, never, R2>
6858 ): Effect<A, E, R2 | R>
6859} = internal.onError
6860
6861/**
6862 * Runs the finalizer only when this effect fails and the `Cause` matches the
6863 * provided predicate.
6864 *
6865 * **Example** (Running cleanup for selected failures)
6866 *
6867 * ```ts import.meta.vitest
6868 * import { Cause, Effect, Exit } from "effect"
6869 * const output: Array<unknown> = []
6870 *
6871 * const task = Effect.fail("boom")
6872 *
6873 * const program = Effect.onErrorIf(
6874 * task,
6875 * Cause.hasFails,
6876 * (cause) =>
6877 * Effect.gen(function*() {
6878 * yield* Effect.sync(() => { output.push(`Cause: ${Cause.squash(cause)}`) })
6879 * })
6880 * )
6881 *
6882 * void output.push(Effect.runSyncExit(program))
6883 * output // => ["Cause: boom", Exit.fail("boom")]
6884 * ```
6885 *
6886 * @category resource management
6887 * @since 4.0.0
6888 */
6889export const onErrorIf: {
6890 <E, XE, XR>(
6891 predicate: Predicate.Predicate<Cause.Cause<E>>,
6892 f: (cause: Cause.Cause<E>) => Effect<void, XE, XR>
6893 ): <A, R>(self: Effect<A, E, R>) => Effect<A, E | XE, R | XR>
6894 <A, E, R, XE, XR>(
6895 self: Effect<A, E, R>,
6896 predicate: Predicate.Predicate<Cause.Cause<E>>,
6897 f: (cause: Cause.Cause<E>) => Effect<void, XE, XR>
6898 ): Effect<A, E | XE, R | XR>
6899} = internal.onErrorIf
6900
6901/**
6902 * Runs the finalizer only when this effect fails and the cause matches the provided `Filter`.
6903 *
6904 * **When to use**
6905 *
6906 * Use when cleanup or diagnostics should run only for failures whose full
6907 * `Cause` is accepted or transformed by a `Filter`, and the finalizer needs the
6908 * filter's pass value plus the original cause.
6909 *
6910 * @see {@link onError} for cleanup on every failure
6911 * @see {@link onErrorIf} for selecting failures with a boolean predicate
6912 * @see {@link onExitFilter} for selecting from every exit instead of only failures
6913 *
6914 * @category resource management
6915 * @since 4.0.0
6916 */
6917export const onErrorFilter: {
6918 <A, E, EB, X, XE, XR>(
6919 filter: Filter.Filter<Cause.Cause<E>, EB, X>,
6920 f: (failure: EB, cause: Cause.Cause<E>) => Effect<void, XE, XR>
6921 ): <R>(self: Effect<A, E, R>) => Effect<A, E | XE, R | XR>
6922 <A, E, R, EB, X, XE, XR>(
6923 self: Effect<A, E, R>,
6924 filter: Filter.Filter<Cause.Cause<E>, EB, X>,
6925 f: (failure: EB, cause: Cause.Cause<E>) => Effect<void, XE, XR>
6926 ): Effect<A, E | XE, R | XR>
6927} = internal.onErrorFilter
6928
6929/**
6930 * Runs an optional finalizer with the effect's `Exit` value when the effect
6931 * completes.
6932 *
6933 * **When to use**
6934 *
6935 * Use when you are building a low-level `Effect` operator that must inspect the
6936 * source effect's `Exit`, may skip finalization by returning `undefined`, or
6937 * must choose whether finalization is forced into an uninterruptible region.
6938 *
6939 * **Details**
6940 *
6941 * This low-level operator preserves the source effect's result unless the
6942 * finalizer fails. If both the source effect and the finalizer fail, the two
6943 * causes are merged. Prefer `onExit` for normal cleanup logic.
6944 *
6945 * @see {@link onExit} for ordinary exit-aware cleanup whose finalizer always returns an effect
6946 *
6947 * @category resource management
6948 * @since 4.0.0
6949 */
6950export const onExitPrimitive: <A, E, R, XE = never, XR = never>(
6951 self: Effect<A, E, R>,
6952 f: (exit: Exit.Exit<A, E>) => Effect<void, XE, XR> | undefined,
6953 interruptible?: boolean
6954) => Effect<A, E | XE, R | XR> = internal.onExitPrimitive
6955
6956/**
6957 * Ensures that a cleanup function runs whether this effect succeeds, fails, or
6958 * is interrupted.
6959 *
6960 * **Details**
6961 *
6962 * If both the effect and the cleanup function fail, the two causes are merged.
6963 *
6964 * **Example** (Observing every exit)
6965 *
6966 * ```ts import.meta.vitest
6967 * import { Effect, Exit } from "effect"
6968 * const output: Array<unknown> = []
6969 *
6970 * const task = Effect.succeed(42)
6971 *
6972 * const program = Effect.onExit(task, (exit) =>
6973 * Effect.sync(() => { output.push(
6974 * Exit.isSuccess(exit)
6975 * ? `Task succeeded with: ${exit.value}`
6976 * : `Task failed: ${Exit.isFailure(exit) ? exit.cause : "interrupted"}`
6977 * ) }))
6978 *
6979 * void output.push(Effect.runSync(program))
6980 * output // => ["Task succeeded with: 42", 42]
6981 * ```
6982 *
6983 * @category resource management
6984 * @since 2.0.0
6985 */
6986export const onExit: {
6987 <A, E, XE = never, XR = never>(
6988 f: (exit: Exit.Exit<A, E>) => Effect<void, XE, XR>
6989 ): <R>(self: Effect<A, E, R>) => Effect<A, E | XE, R | XR>
6990 <A, E, R, XE = never, XR = never>(
6991 self: Effect<A, E, R>,
6992 f: (exit: Exit.Exit<A, E>) => Effect<void, XE, XR>
6993 ): Effect<A, E | XE, R | XR>
6994} = internal.onExit
6995
6996/**
6997 * Runs the cleanup effect only when the `Exit` satisfies the provided
6998 * predicate.
6999 *
7000 * **Example** (Observing selected exits)
7001 *
7002 * ```ts import.meta.vitest
7003 * import { Effect, Exit } from "effect"
7004 * const output: Array<unknown> = []
7005 *
7006 * const program = Effect.onExitIf(
7007 * Effect.succeed(42),
7008 * Exit.isSuccess,
7009 * (exit) =>
7010 * Exit.isSuccess(exit)
7011 * ? Effect.sync(() => { output.push(`Succeeded with: ${exit.value}`) })
7012 * : Effect.void
7013 * )
7014 *
7015 * void output.push(Effect.runSync(program))
7016 * output // => ["Succeeded with: 42", 42]
7017 * ```
7018 *
7019 * @category resource management
7020 * @since 4.0.0
7021 */
7022export const onExitIf: {
7023 <A, E, XE, XR>(
7024 predicate: Predicate.Predicate<Exit.Exit<NoInfer<A>, NoInfer<E>>>,
7025 f: (exit: Exit.Exit<NoInfer<A>, NoInfer<E>>) => Effect<void, XE, XR>
7026 ): <R>(self: Effect<A, E, R>) => Effect<A, E | XE, R | XR>
7027 <A, E, R, XE, XR>(
7028 self: Effect<A, E, R>,
7029 predicate: Predicate.Predicate<Exit.Exit<NoInfer<A>, NoInfer<E>>>,
7030 f: (exit: Exit.Exit<NoInfer<A>, NoInfer<E>>) => Effect<void, XE, XR>
7031 ): Effect<A, E | XE, R | XR>
7032} = internal.onExitIf
7033
7034/**
7035 * Runs the cleanup effect only when the `Exit` matches the provided `Filter`.
7036 *
7037 * **When to use**
7038 *
7039 * Use when cleanup should run only for `Exit` values selected by a `Filter`,
7040 * and the cleanup needs the extracted pass value together with the original
7041 * `Exit`.
7042 *
7043 * **Details**
7044 *
7045 * `Result.fail` skips cleanup, and `Result.succeed` runs cleanup with the
7046 * selected value and the original `Exit`.
7047 *
7048 * @see {@link onExit} for cleanup on every exit
7049 * @see {@link onExitIf} for selecting exits with a boolean predicate
7050 * @see {@link onErrorFilter} for selecting only failure causes
7051 *
7052 * @category resource management
7053 * @since 4.0.0
7054 */
7055export const onExitFilter: {
7056 <A, E, XE, XR, B, X>(
7057 filter: Filter.Filter<Exit.Exit<NoInfer<A>, NoInfer<E>>, B, X>,
7058 f: (b: B, exit: Exit.Exit<NoInfer<A>, NoInfer<E>>) => Effect<void, XE, XR>
7059 ): <R>(self: Effect<A, E, R>) => Effect<A, E | XE, R | XR>
7060 <A, E, R, XE, XR, B, X>(
7061 self: Effect<A, E, R>,
7062 filter: Filter.Filter<Exit.Exit<NoInfer<A>, NoInfer<E>>, B, X>,
7063 f: (b: B, exit: Exit.Exit<NoInfer<A>, NoInfer<E>>) => Effect<void, XE, XR>
7064 ): Effect<A, E | XE, R | XR>
7065} = internal.onExitFilter
7066
7067// -----------------------------------------------------------------------------
7068// Caching
7069// -----------------------------------------------------------------------------
7070
7071/**
7072 * Returns an effect that lazily computes a result and caches it for subsequent
7073 * evaluations.
7074 *
7075 * **When to use**
7076 *
7077 * Use when you need an expensive or time-consuming operation to be evaluated
7078 * once and reused by later callers.
7079 *
7080 * **Details**
7081 *
7082 * This function wraps an effect and ensures that its result is computed only
7083 * once. Once the result is computed, it is cached, meaning that subsequent
7084 * evaluations of the same effect will return the cached result without
7085 * re-executing the logic.
7086 *
7087 * Concurrent callers share the pending computation, which is interrupted only
7088 * once every caller waiting on it has been interrupted. Interrupted
7089 * computations are never cached, so the next evaluation starts a fresh
7090 * computation.
7091 *
7092 * **Example** (Memoizing an effect until invalidated)
7093 *
7094 * ```ts import.meta.vitest
7095 * import { Effect } from "effect"
7096 * const output: Array<unknown> = []
7097 * const record = (value: unknown) => Effect.sync(() => { output.push(value) })
7098 *
7099 * let i = 1
7100 * const expensiveTask = Effect.sync(() => {
7101 * void output.push("expensive task...")
7102 * return `result ${i++}`
7103 * })
7104 *
7105 * const program = Effect.gen(function*() {
7106 * void output.push("non-cached version:")
7107 * yield* expensiveTask.pipe(Effect.andThen(record))
7108 * yield* expensiveTask.pipe(Effect.andThen(record))
7109 * void output.push("cached version:")
7110 * const cached = yield* Effect.cached(expensiveTask)
7111 * yield* cached.pipe(Effect.andThen(record))
7112 * yield* cached.pipe(Effect.andThen(record))
7113 * })
7114 *
7115 * await Effect.runPromise(program)
7116 * output // => ["non-cached version:", "expensive task...", "result 1", "expensive task...", "result 2", "cached version:", "expensive task...", "result 3", "result 3"]
7117 * ```
7118 *
7119 * @see {@link cachedWithTTL} for a similar function that includes a
7120 * time-to-live duration for the cached value.
7121 * @see {@link cachedInvalidateWithTTL} for a similar function that includes an
7122 * additional effect for manually invalidating the cached value.
7123 * @category caching
7124 * @since 2.0.0
7125 */
7126export const cached: <A, E, R>(self: Effect<A, E, R>) => Effect<Effect<A, E, R>> = internal.cached
7127
7128/**
7129 * Returns an effect that caches its result for a fixed duration or a duration
7130 * computed from its `Exit`, known as "timeToLive" (TTL).
7131 *
7132 * **When to use**
7133 *
7134 * Use when you need a costly effect result to be reused for a bounded duration
7135 * before being recomputed.
7136 *
7137 * **Details**
7138 *
7139 * This function is used to cache the result of an effect for a specified amount
7140 * of time. This means that the first time the effect is evaluated, its result
7141 * is computed and stored.
7142 *
7143 * If the effect is evaluated again within the specified `timeToLive`, the
7144 * cached result will be used, avoiding recomputation.
7145 *
7146 * After the specified duration has passed, the cache expires, and the effect
7147 * will be recomputed upon the next evaluation.
7148 *
7149 * `timeToLive` accepts a `Duration.Input` or a function from `Exit<A, E>` to
7150 * `Duration.Input`. The function runs once after each fresh computation,
7151 * including failures, so successes and failures can have different TTLs. It
7152 * does not run when the cache is created or when a cached result is reused.
7153 * Interrupted computations are never cached and do not call the function.
7154 *
7155 * The TTL starts when the computation completes. Concurrent callers share the
7156 * pending computation, which is interrupted only once every caller waiting on
7157 * it has been interrupted. The next evaluation then starts a fresh
7158 * computation. A zero TTL expires immediately, and an infinite TTL
7159 * keeps the result indefinitely.
7160 *
7161 * **Example** (Memoizing an effect with TTL)
7162 *
7163 * ```ts import.meta.vitest
7164 * import { Effect } from "effect"
7165 * const output: Array<unknown> = []
7166 * const record = (value: unknown) => Effect.sync(() => { output.push(value) })
7167 *
7168 * let i = 1
7169 * const expensiveTask = Effect.sync(() => {
7170 * void output.push("expensive task...")
7171 * return `result ${i++}`
7172 * })
7173 *
7174 * const program = Effect.gen(function*() {
7175 * const cached = yield* Effect.cachedWithTTL(expensiveTask, "1 hour")
7176 * yield* cached.pipe(Effect.andThen(record))
7177 * yield* cached.pipe(Effect.andThen(record))
7178 * yield* cached.pipe(Effect.andThen(record))
7179 * })
7180 *
7181 * Effect.runSync(program)
7182 * output // => ["expensive task...", "result 1", "result 1", "result 1"]
7183 * ```
7184 *
7185 * **Example** (Caching successes while retrying failures)
7186 *
7187 * ```ts import.meta.vitest
7188 * import { Effect, Exit } from "effect"
7189 *
7190 * let attempts = 0
7191 * const task = Effect.suspend(() =>
7192 * ++attempts === 1 ? Effect.fail("temporary failure") : Effect.succeed(42)
7193 * )
7194 * const program = Effect.gen(function*() {
7195 * const cached = yield* task.pipe(
7196 * Effect.cachedWithTTL((exit) => Exit.isSuccess(exit) ? "1 hour" : 0)
7197 * )
7198 * yield* Effect.exit(cached)
7199 * return yield* cached
7200 * })
7201 *
7202 * Effect.runSync(program) // => 42
7203 * ```
7204 *
7205 * @see {@link cached} for a similar function that caches the result
7206 * indefinitely.
7207 * @see {@link cachedInvalidateWithTTL} for a similar function that includes an
7208 * additional effect for manually invalidating the cached value.
7209 * @category caching
7210 * @since 2.0.0
7211 */
7212export const cachedWithTTL: {
7213 <A, E>(
7214 timeToLive: (exit: Exit.Exit<A, E>) => Duration.Input
7215 ): <R>(self: Effect<A, E, R>) => Effect<Effect<A, E, R>>
7216 (timeToLive: Duration.Input): <A, E, R>(self: Effect<A, E, R>) => Effect<Effect<A, E, R>>
7217 <A, E>(
7218 timeToLive: Duration.Input | ((exit: Exit.Exit<A, E>) => Duration.Input)
7219 ): <R>(self: Effect<A, E, R>) => Effect<Effect<A, E, R>>
7220 <A, E, R>(
7221 self: Effect<A, E, R>,
7222 timeToLive: Duration.Input | ((exit: Exit.Exit<A, E>) => Duration.Input)
7223 ): Effect<Effect<A, E, R>>
7224} = internal.cachedWithTTL
7225
7226/**
7227 * Creates a cached effect result for a fixed duration or a duration computed
7228 * from its `Exit` and allows manual invalidation before expiration.
7229 *
7230 * **When to use**
7231 *
7232 * Use when an effect result should be cached for a bounded time and callers
7233 * also need a manual invalidation effect to force recomputation before
7234 * expiration.
7235 *
7236 * **Details**
7237 *
7238 * This function behaves similarly to {@link cachedWithTTL} by caching the
7239 * result of an effect for a specified period of time. However, it introduces an
7240 * additional feature: it provides an effect that allows you to manually
7241 * invalidate the cached result before it naturally expires.
7242 *
7243 * This gives you more control over the cache, allowing you to refresh the
7244 * result when needed, even if the original cache has not yet expired.
7245 *
7246 * Once the cache is invalidated, the next time the effect is evaluated, the
7247 * result will be recomputed, and the cache will be refreshed.
7248 *
7249 * **Example** (Memoizing with TTL and invalidation)
7250 *
7251 * ```ts import.meta.vitest
7252 * import { Effect } from "effect"
7253 * const output: Array<unknown> = []
7254 * const record = (value: unknown) => Effect.sync(() => { output.push(value) })
7255 *
7256 * let i = 1
7257 * const expensiveTask = Effect.sync(() => {
7258 * void output.push("expensive task...")
7259 * return `result ${i++}`
7260 * })
7261 *
7262 * const program = Effect.gen(function*() {
7263 * const [cached, invalidate] = yield* Effect.cachedInvalidateWithTTL(
7264 * expensiveTask,
7265 * "1 hour"
7266 * )
7267 * yield* cached.pipe(Effect.andThen(record))
7268 * yield* cached.pipe(Effect.andThen(record))
7269 * yield* invalidate
7270 * yield* cached.pipe(Effect.andThen(record))
7271 * })
7272 *
7273 * Effect.runSync(program)
7274 * output // => ["expensive task...", "result 1", "result 1", "expensive task...", "result 2"]
7275 * ```
7276 *
7277 * @see {@link cached} for a similar function that caches the result
7278 * indefinitely.
7279 * @see {@link cachedWithTTL} for a similar function that caches the result for
7280 * a specified duration but does not include an effect for manual invalidation.
7281 * @category caching
7282 * @since 2.0.0
7283 */
7284export const cachedInvalidateWithTTL: {
7285 <A, E>(
7286 timeToLive: (exit: Exit.Exit<A, E>) => Duration.Input
7287 ): <R>(self: Effect<A, E, R>) => Effect<[Effect<A, E, R>, Effect<void>]>
7288 (timeToLive: Duration.Input): <A, E, R>(self: Effect<A, E, R>) => Effect<[Effect<A, E, R>, Effect<void>]>
7289 <A, E>(
7290 timeToLive: Duration.Input | ((exit: Exit.Exit<A, E>) => Duration.Input)
7291 ): <R>(self: Effect<A, E, R>) => Effect<[Effect<A, E, R>, Effect<void>]>
7292 <A, E, R>(
7293 self: Effect<A, E, R>,
7294 timeToLive: Duration.Input | ((exit: Exit.Exit<A, E>) => Duration.Input)
7295 ): Effect<[Effect<A, E, R>, Effect<void>]>
7296} = internal.cachedInvalidateWithTTL
7297
7298// -----------------------------------------------------------------------------
7299// Interruption
7300// -----------------------------------------------------------------------------
7301
7302/**
7303 * Returns an effect that is immediately interrupted.
7304 *
7305 * **Example** (Creating an interrupted effect)
7306 *
7307 * ```ts import.meta.vitest
7308 * import { Effect } from "effect"
7309 *
7310 * const program = Effect.gen(function*() {
7311 * return yield* Effect.interrupt
7312 * yield* Effect.succeed("This won't execute and is unreachable")
7313 * })
7314 *
7315 * Effect.runSyncExit(program)._tag // => "Failure"
7316 * ```
7317 *
7318 * @category interruption
7319 * @since 2.0.0
7320 */
7321export const interrupt: Effect<never> = internal.interrupt
7322
7323/**
7324 * Returns a new effect that allows the effect to be interruptible.
7325 *
7326 * **Example** (Allowing interruption)
7327 *
7328 * ```ts import.meta.vitest
7329 * import { Effect, Option } from "effect"
7330 *
7331 * const program = Effect.interruptible(Effect.never).pipe(
7332 * Effect.timeoutOption(0)
7333 * )
7334 * await Effect.runPromise(program) // => Option.none()
7335 * ```
7336 *
7337 * @category interruption
7338 * @since 2.0.0
7339 */
7340export const interruptible: <A, E, R>(
7341 self: Effect<A, E, R>
7342) => Effect<A, E, R> = internal.interruptible
7343
7344/**
7345 * Runs the specified finalizer effect if this effect is interrupted.
7346 *
7347 * **Example** (Running cleanup on interruption)
7348 *
7349 * ```ts import.meta.vitest
7350 * import { Effect, Fiber } from "effect"
7351 * const output: Array<unknown> = []
7352 *
7353 * const task = Effect.forever(Effect.succeed("working..."))
7354 *
7355 * const program = Effect.onInterrupt(
7356 * task,
7357 * () => Effect.sync(() => { output.push("Task was interrupted, cleaning up...") })
7358 * )
7359 *
7360 * const fiber = Effect.runFork(program)
7361 * await Effect.runPromise(Fiber.interrupt(fiber))
7362 * output // => ["Task was interrupted, cleaning up..."]
7363 * ```
7364 *
7365 * @category interruption
7366 * @since 2.0.0
7367 */
7368export const onInterrupt: {
7369 <XE, XR>(
7370 finalizer: (interruptors: ReadonlySet<number>) => Effect<void, XE, XR>
7371 ): <A, E, R>(self: Effect<A, E, R>) => Effect<A, E | XE, R | XR>
7372 <A, E, R, XE, XR>(
7373 self: Effect<A, E, R>,
7374 finalizer: (interruptors: ReadonlySet<number>) => Effect<void, XE, XR>
7375 ): Effect<A, E | XE, R | XR>
7376} = internal.onInterrupt
7377
7378/**
7379 * Returns a new effect that disables interruption for the given effect.
7380 *
7381 * **Example** (Preventing interruption)
7382 *
7383 * ```ts import.meta.vitest
7384 * import { Effect } from "effect"
7385 * const output: Array<unknown> = []
7386 *
7387 * const criticalTask = Effect.gen(function*() {
7388 * yield* Effect.sync(() => { output.push("Starting critical section...") })
7389 * yield* Effect.sync(() => { output.push("Critical section completed") })
7390 * })
7391 *
7392 * const program = Effect.uninterruptible(criticalTask)
7393 *
7394 * Effect.runSync(program)
7395 * output // => ["Starting critical section...", "Critical section completed"]
7396 * ```
7397 *
7398 * @category interruption
7399 * @since 2.0.0
7400 */
7401export const uninterruptible: <A, E, R>(
7402 self: Effect<A, E, R>
7403) => Effect<A, E, R> = internal.uninterruptible
7404
7405/**
7406 * Disables interruption and provides a restore function to restore the
7407 * interruptible state within the effect.
7408 *
7409 * **Example** (Restoring interruption in protected regions)
7410 *
7411 * ```ts import.meta.vitest
7412 * import { Effect } from "effect"
7413 * const output: Array<unknown> = []
7414 *
7415 * const program = Effect.uninterruptibleMask((restore) =>
7416 * Effect.gen(function*() {
7417 * yield* Effect.sync(() => { output.push("Uninterruptible phase...") })
7418 * // Restore interruptibility for this part
7419 * yield* restore(
7420 * Effect.gen(function*() {
7421 * yield* Effect.sync(() => { output.push("Interruptible phase...") })
7422 * })
7423 * )
7424 *
7425 * yield* Effect.sync(() => { output.push("Back to uninterruptible") })
7426 * })
7427 * )
7428 *
7429 * Effect.runSync(program)
7430 * output // => ["Uninterruptible phase...", "Interruptible phase...", "Back to uninterruptible"]
7431 * ```
7432 *
7433 * @category interruption
7434 * @since 2.0.0
7435 */
7436export const uninterruptibleMask: <A, E, R>(
7437 f: (
7438 restore: <AX, EX, RX>(effect: Effect<AX, EX, RX>) => Effect<AX, EX, RX>
7439 ) => Effect<A, E, R>
7440) => Effect<A, E, R> = internal.uninterruptibleMask
7441
7442/**
7443 * Runs an effect in an interruptible region while providing `restore` for
7444 * locally restoring the previous interruptibility.
7445 *
7446 * **Example** (Controlling interruptibility locally)
7447 *
7448 * ```ts import.meta.vitest
7449 * import { Effect } from "effect"
7450 * const output: Array<unknown> = []
7451 *
7452 * const program = Effect.interruptibleMask((restore) =>
7453 * Effect.gen(function*() {
7454 * yield* Effect.sync(() => { output.push("Interruptible phase...") })
7455 * // Make this part uninterruptible
7456 * yield* restore(
7457 * Effect.gen(function*() {
7458 * yield* Effect.sync(() => { output.push("Uninterruptible phase...") })
7459 * })
7460 * )
7461 *
7462 * yield* Effect.sync(() => { output.push("Back to interruptible") })
7463 * })
7464 * )
7465 *
7466 * Effect.runSync(program)
7467 * output // => ["Interruptible phase...", "Uninterruptible phase...", "Back to interruptible"]
7468 * ```
7469 *
7470 * @category interruption
7471 * @since 2.0.0
7472 */
7473export const interruptibleMask: <A, E, R>(
7474 f: (
7475 restore: <AX, EX, RX>(effect: Effect<AX, EX, RX>) => Effect<AX, EX, RX>
7476 ) => Effect<A, E, R>
7477) => Effect<A, E, R> = internal.interruptibleMask
7478
7479/**
7480 * Creates an AbortSignal that is managed by the provided scope.
7481 *
7482 * **When to use**
7483 *
7484 * Use to obtain a scope-managed `AbortSignal` for APIs that accept cancellation
7485 * through a signal.
7486 *
7487 * **Details**
7488 *
7489 * Each acquisition creates a fresh `AbortController`. Closing the owning scope
7490 * runs a finalizer that aborts the controller and the effect succeeds with the
7491 * controller's signal.
7492 *
7493 * **Gotchas**
7494 *
7495 * The signal is aborted when its owning scope closes, so avoid keeping it for
7496 * work that outlives that scope.
7497 *
7498 * @see {@link scoped} for binding resource lifetime to a scope
7499 *
7500 * @category interruption
7501 * @since 4.0.0
7502 */
7503export const abortSignal: Effect<AbortSignal, never, Scope> = internal.abortSignal
7504
7505// -----------------------------------------------------------------------------
7506// Repetition & Recursion
7507// -----------------------------------------------------------------------------
7508
7509/**
7510 * Type helpers for repeating effects.
7511 *
7512 * @category repetition
7513 * @since 2.0.0
7514 */
7515export declare namespace Repeat {
7516 /**
7517 * Computes the result type of `Effect.repeat` from the original effect and repeat options.
7518 *
7519 * @category repetition
7520 * @since 2.0.0
7521 */
7522 export type Return<R, E, A, O extends Options<A>> = Effect<
7523 O extends unknown ? "schedule" extends keyof O ? A
7524 : "times" extends keyof O ? A
7525 : O extends { until: Predicate.Refinement<A, infer B> } ? B
7526 : O extends { while: Predicate.Refinement<A, infer B> } ? Exclude<A, B>
7527 : A
7528 : never,
7529 | E
7530 | (O extends { schedule: Schedule<infer _Out, infer _I, infer E, infer _R> } ? E
7531 : never)
7532 | (O extends { while: (...args: Array<any>) => Effect<infer _A, infer E, infer _R> } ? E
7533 : never)
7534 | (O extends { until: (...args: Array<any>) => Effect<infer _A, infer E, infer _R> } ? E
7535 : never),
7536 | R
7537 | (O extends { schedule: Schedule<infer _O, infer _I, infer _E, infer R> } ? R
7538 : never)
7539 | (O extends {
7540 while: (...args: Array<any>) => Effect<infer _A, infer _E, infer R>
7541 } ? R
7542 : never)
7543 | (O extends {
7544 until: (...args: Array<any>) => Effect<infer _A, infer _E, infer R>
7545 } ? R
7546 : never)
7547 > extends infer Z ? Z
7548 : never
7549
7550 /**
7551 * Options that control whether and how an effect is repeated.
7552 *
7553 * @category repetition
7554 * @since 2.0.0
7555 */
7556 export interface Options<A> {
7557 while?: ((_: A) => boolean | Effect<boolean, any, any>) | undefined
7558 until?: ((_: A) => boolean | Effect<boolean, any, any>) | undefined
7559 times?: number | undefined
7560 schedule?: Schedule<any, A, any, any> | undefined
7561 }
7562}
7563
7564/**
7565 * Repeats this effect forever (until the first error).
7566 *
7567 * **Example** (Repeating forever)
7568 *
7569 * ```ts import.meta.vitest
7570 * import { Effect, Option } from "effect"
7571 *
7572 * const program = Effect.forever(Effect.never).pipe(Effect.timeoutOption(0))
7573 * await Effect.runPromise(program) // => Option.none()
7574 * ```
7575 *
7576 * @category repetition
7577 * @since 2.0.0
7578 */
7579export const forever: <
7580 Arg extends Effect<any, any, any> | {
7581 readonly disableYield?: boolean | undefined
7582 } | undefined = {
7583 readonly disableYield?: boolean | undefined
7584 }
7585>(
7586 effectOrOptions?: Arg,
7587 options?: {
7588 readonly disableYield?: boolean | undefined
7589 } | undefined
7590) => [Arg] extends [Effect<infer _A, infer _E, infer _R>] ? Effect<never, _E, _R>
7591 : <A, E, R>(self: Effect<A, E, R>) => Effect<never, E, R> = internal.forever
7592
7593/**
7594 * Repeats an effect based on a specified schedule or until the first failure.
7595 *
7596 * **When to use**
7597 *
7598 * Use to rerun an effect after successful executions.
7599 *
7600 * **Details**
7601 *
7602 * This function executes an effect repeatedly according to the given schedule.
7603 * Each repetition occurs after the initial execution of the effect, meaning
7604 * that the schedule determines the number of additional repetitions. For
7605 * example, using `Schedule.once` will result in the effect being executed twice
7606 * (once initially and once as part of the repetition).
7607 *
7608 * If the effect succeeds, it is repeated according to the schedule. If it
7609 * fails, the repetition stops immediately, and the failure is returned.
7610 *
7611 * The schedule can also specify delays between repetitions, making it useful
7612 * for tasks like retrying operations with backoff, periodic execution, or
7613 * performing a series of dependent actions.
7614 *
7615 * You can combine schedules for more advanced repetition logic, such as adding
7616 * delays, limiting recursions, or dynamically adjusting based on the outcome of
7617 * each execution.
7618 *
7619 * **Gotchas**
7620 *
7621 * The source effect is always evaluated once before the schedule is stepped.
7622 * The schedule controls additional repetitions, not the initial execution.
7623 *
7624 * **Example** (Repeating successful effects with a schedule)
7625 *
7626 * ```ts import.meta.vitest
7627 * // Success Example
7628 * import { Effect, Schedule } from "effect"
7629 * const output: Array<unknown> = []
7630 *
7631 * const action = Effect.sync(() => { output.push("success") })
7632 * const policy = Schedule.recurs(2)
7633 * const program = Effect.repeat(action, policy)
7634 *
7635 * void output.push(Effect.runSync(program))
7636 * output // => ["success", "success", "success", 2]
7637 * ```
7638 *
7639 * **Example** (Stopping repetition on failure)
7640 *
7641 * ```ts import.meta.vitest
7642 * // Failure Example
7643 * import { Effect, Schedule } from "effect"
7644 * const output: Array<unknown> = []
7645 *
7646 * let count = 0
7647 *
7648 * // Define a callback effect that simulates an action with possible failures
7649 * const action = Effect.callback<string, string>((resume) => {
7650 * if (count > 1) {
7651 * void output.push("failure")
7652 * resume(Effect.fail("Uh oh!"))
7653 * } else {
7654 * count++
7655 * void output.push("success")
7656 * resume(Effect.succeed("yay!"))
7657 * }
7658 * })
7659 *
7660 * const policy = Schedule.recurs(2)
7661 * const program = Effect.repeat(action, policy)
7662 *
7663 * void output.push((await Effect.runPromiseExit(program))._tag)
7664 * output // => ["success", "success", "failure", "Failure"]
7665 * ```
7666 *
7667 * @see {@link retry} for failure-based repetition
7668 * @see {@link repeatOrElse} for fallback handling when repetition fails
7669 *
7670 * @category repetition
7671 * @since 2.0.0
7672 */
7673export const repeat: {
7674 <O extends Repeat.Options<A>, A>(options: O): <E, R>(self: Effect<A, E, R>) => Repeat.Return<R, E, A, O>
7675 <Output, Input, Error, Env>(
7676 schedule: Schedule<Output, NoInfer<Input>, Error, Env>
7677 ): <E, R>(self: Effect<Input, E, R>) => Effect<Output, E | Error, R | Env>
7678 <Output, Input, Error, Env>(
7679 builder: (
7680 $: <O, E, R>(_: Schedule<O, NoInfer<Input>, E, R>) => Schedule<O, Input, E, R>
7681 ) => Schedule<Output, NoInfer<Input>, Error, Env>
7682 ): <E, R>(self: Effect<Input, E, R>) => Effect<Output, E | Error, R | Env>
7683 <A, E, R, O extends Repeat.Options<A>>(self: Effect<A, E, R>, options: O): Repeat.Return<R, E, A, O>
7684 <Input, E, R, Output, Error, Env>(
7685 self: Effect<Input, E, R>,
7686 schedule: Schedule<Output, NoInfer<Input>, Error, Env>
7687 ): Effect<Output, E | Error, R | Env>
7688 <Input, E, R, Output, Error, Env>(
7689 self: Effect<Input, E, R>,
7690 builder: (
7691 $: <O, E, R>(_: Schedule<O, NoInfer<Input>, E, R>) => Schedule<O, Input, E, R>
7692 ) => Schedule<Output, NoInfer<Input>, Error, Env>
7693 ): Effect<Output, E | Error, R | Env>
7694} = internalSchedule.repeat
7695
7696/**
7697 * Repeats an effect according to a schedule and runs a fallback effect if
7698 * repetition fails before the schedule completes.
7699 *
7700 * **When to use**
7701 *
7702 * Use when successful repetitions should follow a schedule, but failures from
7703 * the repeated effect or schedule need an effectful fallback.
7704 *
7705 * **Details**
7706 *
7707 * If the repeated effect or schedule step fails, `orElse` receives the failure
7708 * and the latest schedule metadata when at least one schedule step has run;
7709 * otherwise it receives `None`. If the schedule completes normally, the
7710 * returned effect succeeds with the schedule's output.
7711 *
7712 * **Example** (Recovering after repetition stops)
7713 *
7714 * ```ts import.meta.vitest
7715 * import { Effect, Option, Schedule } from "effect"
7716 * const output: Array<unknown> = []
7717 *
7718 * let attempt = 0
7719 * const task = Effect.gen(function*() {
7720 * attempt++
7721 * if (attempt <= 2) {
7722 * yield* Effect.sync(() => { output.push(`Attempt ${attempt} failed`) })
7723 * return yield* Effect.fail(`Error ${attempt}`)
7724 * }
7725 * yield* Effect.sync(() => { output.push(`Attempt ${attempt} succeeded`) })
7726 * return "success"
7727 * })
7728 *
7729 * const program = Effect.repeatOrElse(
7730 * task,
7731 * Schedule.recurs(3),
7732 * (error, previous) =>
7733 * Effect.sync(() => { output.push(
7734 * `Final failure: ${error}, after ${
7735 * Option.isSome(previous) ? previous.value.attempt : 0
7736 * } attempts`
7737 * ) }).pipe(Effect.map(() => 0))
7738 * )
7739 *
7740 * void output.push(Effect.runSync(program))
7741 * output // => ["Attempt 1 failed", "Final failure: Error 1, after 0 attempts", 0]
7742 * ```
7743 *
7744 * @category repetition
7745 * @since 2.0.0
7746 */
7747export const repeatOrElse: {
7748 <R2, A, B, E, E2, E3, R3>(
7749 schedule: Schedule<B, A, E2, R2>,
7750 orElse: (error: E | E2, option: Option<ScheduleMetadata<B, A>>) => Effect<B, E3, R3>
7751 ): <R>(self: Effect<A, E, R>) => Effect<B, E3, R | R2 | R3>
7752 <A, E, R, R2, B, E2, E3, R3>(
7753 self: Effect<A, E, R>,
7754 schedule: Schedule<B, A, E2, R2>,
7755 orElse: (error: E | E2, option: Option<ScheduleMetadata<B, A>>) => Effect<B, E3, R3>
7756 ): Effect<B, E3, R | R2 | R3>
7757} = internalSchedule.repeatOrElse
7758
7759/**
7760 * Returns an array of `n` identical effects.
7761 *
7762 * **When to use**
7763 *
7764 * Use when you need an array of identical effect values without running them
7765 * yet.
7766 *
7767 * **Details**
7768 *
7769 * This only creates the array of effects. It does not run or collect them.
7770 *
7771 * @see {@link all} for running the returned effects and collecting results
7772 * @see {@link replicateEffect} for repeating an effect and collecting results in one step with concurrency and discard options
7773 *
7774 * @category repetition
7775 * @since 2.0.0
7776 */
7777export const replicate: {
7778 (n: number): <A, E, R>(self: Effect<A, E, R>) => Array<Effect<A, E, R>>
7779 <A, E, R>(self: Effect<A, E, R>, n: number): Array<Effect<A, E, R>>
7780} = internal.replicate
7781
7782/**
7783 * Performs this effect `n` times and collects results with `Effect.all` semantics.
7784 *
7785 * **When to use**
7786 *
7787 * Use when you want to run the repeated effects immediately, with optional
7788 * concurrency control or result discarding.
7789 *
7790 * **Details**
7791 *
7792 * Use `concurrency` to control parallelism and `discard: true` to ignore results.
7793 *
7794 * **Example** (Replicating an effect)
7795 *
7796 * ```ts import.meta.vitest
7797 * import { Effect } from "effect"
7798 * const output: Array<unknown> = []
7799 *
7800 * const program = Effect.gen(function*() {
7801 * const results = yield* Effect.replicateEffect(3)(Effect.succeed(1))
7802 * yield* Effect.sync(() => { output.push(results) })
7803 * })
7804 *
7805 * Effect.runSync(program)
7806 * output // => [[1, 1, 1]]
7807 * ```
7808 *
7809 * @category repetition
7810 * @since 2.0.0
7811 */
7812export const replicateEffect: {
7813 (
7814 n: number,
7815 options?: { readonly concurrency?: Concurrency | undefined; readonly discard?: false | undefined }
7816 ): <A, E, R>(self: Effect<A, E, R>) => Effect<Array<A>, E, R>
7817 (
7818 n: number,
7819 options: { readonly concurrency?: Concurrency | undefined; readonly discard: true }
7820 ): <A, E, R>(self: Effect<A, E, R>) => Effect<void, E, R>
7821 <A, E, R>(
7822 self: Effect<A, E, R>,
7823 n: number,
7824 options?: { readonly concurrency?: Concurrency | undefined; readonly discard?: false | undefined }
7825 ): Effect<Array<A>, E, R>
7826 <A, E, R>(
7827 self: Effect<A, E, R>,
7828 n: number,
7829 options: { readonly concurrency?: Concurrency | undefined; readonly discard: true }
7830 ): Effect<void, E, R>
7831} = internal.replicateEffect
7832
7833/**
7834 * Runs an effect repeatedly according to a schedule and returns the schedule's
7835 * final output.
7836 *
7837 * **When to use**
7838 *
7839 * Use to rerun a successful effect according to a `Schedule` when the schedule
7840 * does not need a custom initial input.
7841 *
7842 * **Details**
7843 *
7844 * The schedule is first stepped with `undefined`. After each successful
7845 * execution, the effect's success value is fed to the schedule to decide
7846 * whether to run again. The returned effect fails if the effect or schedule
7847 * fails, and otherwise succeeds with the schedule output when the schedule
7848 * completes.
7849 *
7850 * **Example** (Scheduling repeated execution)
7851 *
7852 * ```ts import.meta.vitest
7853 * import { Effect, Schedule } from "effect"
7854 * const output: Array<unknown> = []
7855 *
7856 * const task = Effect.gen(function*() {
7857 * yield* Effect.sync(() => { output.push("Task executing...") })
7858 * return 1
7859 * })
7860 *
7861 * const program = Effect.schedule(task, Schedule.recurs(2))
7862 *
7863 * void output.push(Effect.runSync(program))
7864 * output // => ["Task executing...", "Task executing...", 2]
7865 * ```
7866 *
7867 * @see {@link scheduleFrom} for a variant that allows the schedule's decision
7868 * to depend on the result of this effect.
7869 *
7870 * @category repetition
7871 * @since 2.0.0
7872 */
7873export const schedule: {
7874 <Output, Error, Env>(
7875 schedule: Schedule<Output, unknown, Error, Env>
7876 ): <A, E, R>(self: Effect<A, E, R>) => Effect<Output, E | Error, R | Env>
7877 <A, E, R, Output, Error, Env>(
7878 self: Effect<A, E, R>,
7879 schedule: Schedule<Output, unknown, Error, Env>
7880 ): Effect<Output, E | Error, R | Env>
7881} = dual(2, <A, E, R, Output, Error, Env>(
7882 self: Effect<A, E, R>,
7883 schedule: Schedule<Output, unknown, Error, Env>
7884): Effect<Output, E | Error, R | Env> => scheduleFrom(self, undefined, schedule))
7885
7886/**
7887 * Runs an effect repeatedly according to a schedule that is initialized with a
7888 * specific schedule input.
7889 *
7890 * **Details**
7891 *
7892 * `initial` is passed to the schedule before the first execution, not to the
7893 * effect itself. After each successful execution, the effect's success value is
7894 * fed back into the schedule to decide whether to continue. The returned effect
7895 * succeeds with the schedule output when the schedule completes and fails if
7896 * the effect or schedule fails.
7897 *
7898 * **Example** (Scheduling from an initial value)
7899 *
7900 * ```ts import.meta.vitest
7901 * import { Effect, Schedule } from "effect"
7902 * const output: Array<unknown> = []
7903 *
7904 * const task = (input: number) =>
7905 * Effect.gen(function*() {
7906 * yield* Effect.sync(() => { output.push(`Processing: ${input}`) })
7907 * return input + 1
7908 * })
7909 *
7910 * // Start with 0, repeat 3 times
7911 * const program = Effect.scheduleFrom(
7912 * task(0),
7913 * 0,
7914 * Schedule.recurs(2)
7915 * )
7916 *
7917 * void output.push(Effect.runSync(program))
7918 * output // => ["Processing: 0", "Processing: 0", 2]
7919 * ```
7920 *
7921 * @category repetition
7922 * @since 2.0.0
7923 */
7924export const scheduleFrom: {
7925 <Input, Output, Error, Env>(
7926 initial: Input,
7927 schedule: Schedule<Output, Input, Error, Env>
7928 ): <E, R>(self: Effect<Input, E, R>) => Effect<Output, E | Error, R | Env>
7929 <Input, E, R, Output, Error, Env>(
7930 self: Effect<Input, E, R>,
7931 initial: Input,
7932 schedule: Schedule<Output, Input, Error, Env>
7933 ): Effect<Output, E | Error, R | Env>
7934} = internalSchedule.scheduleFrom
7935
7936// -----------------------------------------------------------------------------
7937// Tracing
7938// -----------------------------------------------------------------------------
7939
7940/**
7941 * Returns the current tracer from the context.
7942 *
7943 * **Example** (Accessing the current tracer)
7944 *
7945 * ```ts import.meta.vitest
7946 * import { Effect } from "effect"
7947 *
7948 * const program = Effect.gen(function*() {
7949 * const currentTracer = yield* Effect.tracer
7950 * return typeof currentTracer.span
7951 * })
7952 *
7953 * Effect.runSync(program) // => "function"
7954 * ```
7955 *
7956 * @category tracing
7957 * @since 2.0.0
7958 */
7959export const tracer: Effect<Tracer> = internal.tracer
7960
7961/**
7962 * Provides a tracer to an effect.
7963 *
7964 * **Example** (Providing a tracer)
7965 *
7966 * ```ts import.meta.vitest
7967 * import { Effect } from "effect"
7968 *
7969 * const program = Effect.gen(function*() {
7970 * const tracer = yield* Effect.tracer
7971 * return yield* Effect.withTracer(Effect.succeed("completed"), tracer)
7972 * })
7973 *
7974 * Effect.runSync(program) // => "completed"
7975 * ```
7976 *
7977 * @category tracing
7978 * @since 2.0.0
7979 */
7980export const withTracer: {
7981 (value: Tracer): <A, E, R>(effect: Effect<A, E, R>) => Effect<A, E, R>
7982 <A, E, R>(effect: Effect<A, E, R>, value: Tracer): Effect<A, E, R>
7983} = internal.withTracer
7984
7985/**
7986 * Enables or disables tracing for spans created by the given effect.
7987 *
7988 * **Details**
7989 *
7990 * When `enabled` is `false`, spans created inside the effect are not registered
7991 * with the current tracer and do not propagate as normal trace parents.
7992 *
7993 * **Example** (Enabling or disabling tracing)
7994 *
7995 * ```ts import.meta.vitest
7996 * import { Effect } from "effect"
7997 *
7998 * const program = Effect.succeed(42).pipe(
7999 * Effect.withSpan("my-span"),
8000 * // the span will not be registered with the tracer
8001 * Effect.withTracerEnabled(false)
8002 * )
8003 * Effect.runSync(program) // => 42
8004 * ```
8005 *
8006 * @category tracing
8007 * @since 2.0.0
8008 */
8009export const withTracerEnabled: {
8010 (enabled: boolean): <A, E, R>(effect: Effect<A, E, R>) => Effect<A, E, R>
8011 <A, E, R>(effect: Effect<A, E, R>, enabled: boolean): Effect<A, E, R>
8012} = internal.withTracerEnabled
8013
8014/**
8015 * Enables or disables tracer timing for the given Effect.
8016 *
8017 * **Example** (Enabling or disabling tracing timing)
8018 *
8019 * ```ts import.meta.vitest
8020 * import { Effect } from "effect"
8021 *
8022 * const program = Effect.succeed(42).pipe(
8023 * Effect.withSpan("my-span"),
8024 * // the span will not have timing information
8025 * Effect.withTracerTiming(false)
8026 * )
8027 * Effect.runSync(program) // => 42
8028 * ```
8029 *
8030 * @category tracing
8031 * @since 2.0.0
8032 */
8033export const withTracerTiming: {
8034 (enabled: boolean): <A, E, R>(effect: Effect<A, E, R>) => Effect<A, E, R>
8035 <A, E, R>(effect: Effect<A, E, R>, enabled: boolean): Effect<A, E, R>
8036} = internal.withTracerTiming
8037
8038/**
8039 * Adds an annotation to each span in this effect.
8040 *
8041 * **Example** (Annotating all spans)
8042 *
8043 * ```ts import.meta.vitest
8044 * import { Effect } from "effect"
8045 *
8046 * const program = Effect.succeed("result")
8047 *
8048 * // Add single annotation
8049 * const annotated1 = Effect.annotateSpans(program, "user", "john")
8050 *
8051 * // Add multiple annotations
8052 * const annotated2 = Effect.annotateSpans(program, {
8053 * operation: "data-processing",
8054 * version: "1.0.0",
8055 * environment: "production"
8056 * })
8057 *
8058 * Effect.runSync(Effect.all([annotated1, annotated2])) // => ['result', 'result']
8059 * ```
8060 *
8061 * @category tracing
8062 * @since 2.0.0
8063 */
8064export const annotateSpans: {
8065 (
8066 key: string,
8067 value: unknown
8068 ): <A, E, R>(effect: Effect<A, E, R>) => Effect<A, E, R>
8069 (
8070 values: Record<string, unknown>
8071 ): <A, E, R>(effect: Effect<A, E, R>) => Effect<A, E, R>
8072 <A, E, R>(
8073 effect: Effect<A, E, R>,
8074 key: string,
8075 value: unknown
8076 ): Effect<A, E, R>
8077 <A, E, R>(
8078 effect: Effect<A, E, R>,
8079 values: Record<string, unknown>
8080 ): Effect<A, E, R>
8081} = internal.annotateSpans
8082
8083/**
8084 * Adds an annotation to the current span if available.
8085 *
8086 * **Example** (Annotating the current span)
8087 *
8088 * ```ts import.meta.vitest
8089 * import { Effect } from "effect"
8090 *
8091 * const program = Effect.gen(function*() {
8092 * yield* Effect.annotateCurrentSpan("userId", "123")
8093 * yield* Effect.annotateCurrentSpan({
8094 * operation: "user-lookup"
8095 * })
8096 * return "success"
8097 * })
8098 *
8099 * const traced = Effect.withSpan(program, "user-operation")
8100 * Effect.runSync(traced) // => "success"
8101 * ```
8102 *
8103 * @category tracing
8104 * @since 2.0.0
8105 */
8106export const annotateCurrentSpan: {
8107 (key: string, value: unknown): Effect<void>
8108 (values: Record<string, unknown>): Effect<void>
8109} = internal.annotateCurrentSpan
8110
8111/**
8112 * Returns the currently active local tracing span.
8113 *
8114 * **Details**
8115 *
8116 * The effect fails with `NoSuchElementError` when there is no active local
8117 * `Span`.
8118 *
8119 * **Example** (Reading the current span)
8120 *
8121 * ```ts import.meta.vitest
8122 * import { Effect } from "effect"
8123 *
8124 * const program = Effect.gen(function*() {
8125 * const span = yield* Effect.currentSpan
8126 * return span.name
8127 * })
8128 *
8129 * const traced = Effect.withSpan(program, "my-span")
8130 * Effect.runSync(traced) // => "my-span"
8131 * ```
8132 *
8133 * @category tracing
8134 * @since 2.0.0
8135 */
8136export const currentSpan: Effect<Span, Cause.NoSuchElementError> = internal.currentSpan
8137
8138/**
8139 * Returns the current parent span from the effect context.
8140 *
8141 * **Details**
8142 *
8143 * The effect succeeds with either a local span or external span when one is
8144 * present, and fails with `NoSuchElementError` when no parent span is
8145 * available.
8146 *
8147 * **Example** (Reading the parent span)
8148 *
8149 * ```ts import.meta.vitest
8150 * import { Effect } from "effect"
8151 *
8152 * const childOperation = Effect.gen(function*() {
8153 * const parentSpan = yield* Effect.currentParentSpan
8154 * return parentSpan._tag
8155 * })
8156 *
8157 * const program = Effect.withSpan(childOperation, "child-span")
8158 *
8159 * const traced = Effect.withSpan(program, "parent-span")
8160 * Effect.runSync(traced) // => "Span"
8161 * ```
8162 *
8163 * @category tracing
8164 * @since 2.0.0
8165 */
8166export const currentParentSpan: Effect<AnySpan, Cause.NoSuchElementError> = internal.currentParentSpan
8167
8168/**
8169 * Returns the tracing span annotations currently carried in the effect context.
8170 *
8171 * **Details**
8172 *
8173 * These annotations are applied to spans created inside the context, such as
8174 * spans created by `withSpan`, `useSpan`, or `makeSpan`.
8175 *
8176 * **Example** (Providing span annotations)
8177 *
8178 * ```ts import.meta.vitest
8179 * import { Effect } from "effect"
8180 *
8181 * const program = Effect.gen(function*() {
8182 * const annotations = yield* Effect.spanAnnotations
8183 * return annotations
8184 * }).pipe(Effect.annotateSpans({ userId: "123", operation: "data-processing" }))
8185 *
8186 * Effect.runSync(program) // => { userId: '123', operation: 'data-processing' }
8187 * ```
8188 *
8189 * @category tracing
8190 * @since 2.0.0
8191 */
8192export const spanAnnotations: Effect<Readonly<Record<string, unknown>>> = internal.spanAnnotations
8193
8194/**
8195 * Returns the tracing span links currently carried in the effect context.
8196 *
8197 * **Details**
8198 *
8199 * These links are attached to spans created inside the context. Span links
8200 * connect related spans without making one span the parent of another.
8201 *
8202 * **Example** (Providing span links)
8203 *
8204 * ```ts import.meta.vitest
8205 * import { Effect } from "effect"
8206 *
8207 * const program = Effect.gen(function*() {
8208 * // Get the current span links
8209 * const links = yield* Effect.spanLinks
8210 * return links
8211 * })
8212 *
8213 * Effect.runSync(program).length // => 0
8214 * ```
8215 *
8216 * @category tracing
8217 * @since 2.0.0
8218 */
8219export const spanLinks: Effect<ReadonlyArray<SpanLink>> = internal.spanLinks
8220
8221/**
8222 * Adds a link with the provided span to all spans in this effect.
8223 *
8224 * **Details**
8225 *
8226 * This is useful for connecting spans that are related but not in a direct
8227 * parent-child relationship. For example, you might want to link spans from
8228 * parallel operations or connect spans across different traces.
8229 *
8230 * **Example** (Linking one span to another span)
8231 *
8232 * ```ts import.meta.vitest
8233 * import { Effect } from "effect"
8234 *
8235 * const program = Effect.withSpan(Effect.gen(function*() {
8236 * const parentSpan = yield* Effect.currentSpan
8237 * return yield* Effect.spanLinks.pipe(
8238 * Effect.linkSpans(parentSpan, { relationship: "follows" })
8239 * )
8240 * }), "parent-operation")
8241 *
8242 * Effect.runSync(program).length // => 1
8243 * ```
8244 *
8245 * **Example** (Linking multiple spans at once)
8246 *
8247 * ```ts import.meta.vitest
8248 * import { Effect } from "effect"
8249 *
8250 * const program = Effect.gen(function*() {
8251 * const span1 = yield* Effect.makeSpan("span-1")
8252 * const span2 = yield* Effect.makeSpan("span-2")
8253 *
8254 * return yield* Effect.spanLinks.pipe(
8255 * Effect.linkSpans([span1, span2], {
8256 * type: "dependency",
8257 * source: "multiple-operations"
8258 * })
8259 * )
8260 * })
8261 *
8262 * Effect.runSync(program).length // => 2
8263 * ```
8264 *
8265 * @category tracing
8266 * @since 2.0.0
8267 */
8268export const linkSpans: {
8269 (
8270 span: AnySpan | ReadonlyArray<AnySpan>,
8271 attributes?: Record<string, unknown>
8272 ): <A, E, R>(self: Effect<A, E, R>) => Effect<A, E, R>
8273 <A, E, R>(
8274 self: Effect<A, E, R>,
8275 span: AnySpan | ReadonlyArray<AnySpan>,
8276 attributes?: Record<string, unknown>
8277 ): Effect<A, E, R>
8278} = internal.linkSpans
8279
8280/**
8281 * Creates a new tracing span and returns it without managing its lifetime.
8282 *
8283 * **Details**
8284 *
8285 * The span is not added to the current span stack and is not ended
8286 * automatically. Use `withSpan`, `useSpan`, or `makeSpanScoped` when the span
8287 * should be installed as context or closed automatically.
8288 *
8289 * **Example** (Creating a span manually)
8290 *
8291 * ```ts import.meta.vitest
8292 * import { Effect } from "effect"
8293 *
8294 * const program = Effect.gen(function*() {
8295 * const span = yield* Effect.makeSpan("my-operation")
8296 * return span.name
8297 * })
8298 *
8299 * Effect.runSync(program) // => "my-operation"
8300 * ```
8301 *
8302 * @category tracing
8303 * @since 2.0.0
8304 */
8305export const makeSpan: (name: string, options?: SpanOptionsNoTrace) => Effect<Span> = internal.makeSpan
8306
8307/**
8308 * Create a new span for tracing, and automatically close it when the Scope
8309 * finalizes.
8310 *
8311 * **Details**
8312 *
8313 * The span is not added to the current span stack, so no child spans will be
8314 * created for it.
8315 *
8316 * **Example** (Creating a scoped standalone span)
8317 *
8318 * ```ts import.meta.vitest
8319 * import { Effect } from "effect"
8320 *
8321 * const program = Effect.scoped(
8322 * Effect.gen(function*() {
8323 * const span = yield* Effect.makeSpanScoped("scoped-operation")
8324 * return span.name
8325 * // Span automatically closes when scope ends
8326 * })
8327 * )
8328 *
8329 * Effect.runSync(program) // => "scoped-operation"
8330 * ```
8331 *
8332 * @category tracing
8333 * @since 2.0.0
8334 */
8335export const makeSpanScoped: (
8336 name: string,
8337 options?: SpanOptionsNoTrace | undefined
8338) => Effect<Span, never, Scope> = internal.makeSpanScoped
8339
8340/**
8341 * Create a new span for tracing, and automatically close it when the effect
8342 * completes.
8343 *
8344 * **Details**
8345 *
8346 * The span is not added to the current span stack, so no child spans will be
8347 * created for it.
8348 *
8349 * **Example** (Running an effect with a standalone span)
8350 *
8351 * ```ts import.meta.vitest
8352 * import { Effect } from "effect"
8353 *
8354 * const program = Effect.useSpan(
8355 * "user-operation",
8356 * (span) => Effect.succeed(`${span.name}: success`)
8357 * )
8358 * Effect.runSync(program) // => "user-operation: success"
8359 * ```
8360 *
8361 * @category tracing
8362 * @since 2.0.0
8363 */
8364export const useSpan: {
8365 <A, E, R>(name: string, evaluate: (span: Span) => Effect<A, E, R>): Effect<A, E, R>
8366 <A, E, R>(name: string, options: SpanOptionsNoTrace, evaluate: (span: Span) => Effect<A, E, R>): Effect<A, E, R>
8367} = internal.useSpan
8368
8369/**
8370 * Wraps the effect with a child span for tracing.
8371 *
8372 * **Example** (Wrapping an effect in a child span)
8373 *
8374 * ```ts import.meta.vitest
8375 * import { Effect } from "effect"
8376 *
8377 * const task = Effect.succeed("result")
8378 *
8379 * const traced = Effect.withSpan(task, "my-task", {
8380 * attributes: { version: "1.0" }
8381 * })
8382 * Effect.runSync(traced) // => "result"
8383 * ```
8384 *
8385 * @category tracing
8386 * @since 2.0.0
8387 */
8388export const withSpan: {
8389 <Args extends ReadonlyArray<any>>(
8390 name: string,
8391 options?:
8392 | SpanOptionsNoTrace
8393 | ((...args: NoInfer<Args>) => SpanOptionsNoTrace)
8394 | undefined,
8395 traceOptions?: TraceOptions | undefined
8396 ): <A, E, R>(self: Effect<A, E, R>, ...args: Args) => Effect<A, E, Exclude<R, ParentSpan>>
8397 <A, E, R>(
8398 self: Effect<A, E, R>,
8399 name: string,
8400 options?: SpanOptions | undefined
8401 ): Effect<A, E, Exclude<R, ParentSpan>>
8402} = internal.withSpan
8403
8404/**
8405 * Wraps the effect with a scoped child span for tracing.
8406 *
8407 * **Details**
8408 *
8409 * The span is ended when the Scope is finalized.
8410 *
8411 * **Example** (Creating a scoped child span)
8412 *
8413 * ```ts import.meta.vitest
8414 * import { Effect } from "effect"
8415 *
8416 * const program = Effect.scoped(
8417 * Effect.gen(function*() {
8418 * const task = Effect.succeed("working")
8419 * yield* Effect.withSpanScoped(task, "scoped-task")
8420 * return "completed"
8421 * })
8422 * )
8423 * Effect.runSync(program) // => "completed"
8424 * ```
8425 *
8426 * @category tracing
8427 * @since 2.0.0
8428 */
8429export const withSpanScoped: {
8430 (
8431 name: string,
8432 options?: SpanOptions
8433 ): <A, E, R>(
8434 self: Effect<A, E, R>
8435 ) => Effect<A, E, Exclude<R, ParentSpan> | Scope>
8436 <A, E, R>(
8437 self: Effect<A, E, R>,
8438 name: string,
8439 options?: SpanOptions
8440 ): Effect<A, E, Exclude<R, ParentSpan> | Scope>
8441} = internal.withSpanScoped
8442
8443/**
8444 * Adds the provided span to the current span stack.
8445 *
8446 * **Example** (Setting a parent span)
8447 *
8448 * ```ts import.meta.vitest
8449 * import { Effect } from "effect"
8450 *
8451 * const program = Effect.gen(function*() {
8452 * const span = yield* Effect.makeSpan("parent-span")
8453 * const childTask = Effect.succeed("child operation")
8454 * yield* Effect.withParentSpan(childTask, span)
8455 * return "completed"
8456 * })
8457 * Effect.runSync(program) // => "completed"
8458 * ```
8459 *
8460 * @category tracing
8461 * @since 2.0.0
8462 */
8463export const withParentSpan: {
8464 (value: AnySpan, options?: TraceOptions): <A, E, R>(self: Effect<A, E, R>) => Effect<A, E, Exclude<R, ParentSpan>>
8465 <A, E, R>(self: Effect<A, E, R>, value: AnySpan, options?: TraceOptions): Effect<A, E, Exclude<R, ParentSpan>>
8466} = internal.withParentSpan
8467
8468// -----------------------------------------------------------------------------
8469// Batching
8470// -----------------------------------------------------------------------------
8471
8472/**
8473 * Executes a request using the provided resolver.
8474 *
8475 * **When to use**
8476 *
8477 * Use when you need resolver-driven batching for a typed `Request`.
8478 *
8479 * **Example** (Executing a request through a resolver)
8480 *
8481 * ```ts import.meta.vitest
8482 * import { Effect, Exit, Request, RequestResolver } from "effect"
8483 * const output: Array<unknown> = []
8484 *
8485 * interface GetUser extends Request.Request<string> {
8486 * readonly _tag: "GetUser"
8487 * readonly id: number
8488 * }
8489 * const GetUser = Request.tagged<GetUser>("GetUser")
8490 *
8491 * const resolver = RequestResolver.make<GetUser>(
8492 * Effect.fnUntraced(function*(entries) {
8493 * for (const entry of entries) {
8494 * yield* Request.complete(entry, Exit.succeed(`user-${entry.request.id}`))
8495 * }
8496 * })
8497 * )
8498 *
8499 * const program = Effect.gen(function*() {
8500 * const name = yield* Effect.request(GetUser({ id: 1 }), resolver)
8501 * yield* Effect.sync(() => { output.push(name) })
8502 * })
8503 *
8504 * await Effect.runPromise(program)
8505 * output // => ["user-1"]
8506 * ```
8507 *
8508 * @see {@link requestUnsafe} for the low-level entry point when you already have a `Context` and need to enqueue outside an `Effect`
8509 *
8510 * @category running
8511 * @since 2.0.0
8512 */
8513export const request: {
8514 <A extends Request.Any, EX = never, RX = never>(
8515 resolver: RequestResolver<A> | Effect<RequestResolver<A>, EX, RX>
8516 ): (self: A) => Effect<Request.Success<A>, Request.Error<A> | EX, Request.Services<A> | RX>
8517 <A extends Request.Any, EX = never, RX = never>(
8518 self: A,
8519 resolver: RequestResolver<A> | Effect<RequestResolver<A>, EX, RX>
8520 ): Effect<Request.Success<A>, Request.Error<A> | EX, Request.Services<A> | RX>
8521} = internalRequest.request
8522
8523/**
8524 * Registers a request with a resolver and delivers the exit value via `onExit`.
8525 *
8526 * **When to use**
8527 *
8528 * Use when you already have a `Context` and need to enqueue a request outside
8529 * an `Effect` while receiving completion through `onExit`.
8530 *
8531 * **Details**
8532 *
8533 * It returns a canceler that removes the pending request entry.
8534 *
8535 * @see {@link request} for the `Effect`-returning API used for normal request execution
8536 *
8537 * @category unsafe
8538 * @since 4.0.0
8539 */
8540export const requestUnsafe: <A extends Request.Any>(
8541 self: A,
8542 options: {
8543 readonly resolver: RequestResolver<A>
8544 readonly onExit: (exit: Exit.Exit<Request.Success<A>, Request.Error<A>>) => void
8545 readonly context: Context.Context<never>
8546 }
8547) => () => void = internalRequest.requestUnsafe
8548
8549// -----------------------------------------------------------------------------
8550// Supervision & Fiber's
8551// -----------------------------------------------------------------------------
8552
8553/**
8554 * Returns an effect that forks this effect into its own separate fiber,
8555 * returning the fiber immediately, without waiting for it to begin executing
8556 * the effect.
8557 *
8558 * **Details**
8559 *
8560 * You can use the `forkChild` method whenever you want to execute an effect in a
8561 * new fiber, concurrently and without "blocking" the fiber executing other
8562 * effects. Using fibers can be tricky, so instead of using this method
8563 * directly, consider other higher-level methods, such as `raceWith`,
8564 * `zipPar`, and so forth.
8565 *
8566 * The fiber returned by this method has methods to interrupt the fiber and to
8567 * wait for it to finish executing the effect. See `Fiber` for more
8568 * information.
8569 *
8570 * Whenever you use this method to launch a new fiber, the new fiber is
8571 * attached to the parent fiber's scope. This means when the parent fiber
8572 * terminates, the child fiber will be terminated as well, ensuring that no
8573 * fibers leak. This behavior is called "auto supervision", and if this
8574 * behavior is not desired, you may use the `forkDetach` or `forkIn` methods.
8575 *
8576 * **Example** (Forking a child fiber)
8577 *
8578 * ```ts import.meta.vitest
8579 * import { Effect, Fiber } from "effect"
8580 *
8581 * const task = Effect.succeed("result")
8582 *
8583 * const program = Effect.gen(function*() {
8584 * const fiber = yield* task.pipe(Effect.forkChild)
8585 * const result = yield* Fiber.join(fiber)
8586 * return result
8587 * })
8588 *
8589 * await Effect.runPromise(program) // => "result"
8590 * ```
8591 *
8592 * @category forking
8593 * @since 4.0.0
8594 */
8595export const forkChild: <
8596 Arg extends Effect<any, any, any> | {
8597 readonly startImmediately?: boolean | undefined
8598 readonly uninterruptible?: boolean | "inherit" | undefined
8599 } | undefined = {
8600 readonly startImmediately?: boolean | undefined
8601 readonly uninterruptible?: boolean | "inherit" | undefined
8602 }
8603>(
8604 effectOrOptions?: Arg,
8605 options?: {
8606 readonly startImmediately?: boolean | undefined
8607 readonly uninterruptible?: boolean | "inherit" | undefined
8608 } | undefined
8609) => [Arg] extends [Effect<infer _A, infer _E, infer _R>] ? Effect<Fiber<_A, _E>, never, _R>
8610 : <A, E, R>(self: Effect<A, E, R>) => Effect<Fiber<A, E>, never, R> = internal.forkChild
8611
8612/**
8613 * Forks the effect in the specified scope. The fiber will be interrupted
8614 * when the scope is closed.
8615 *
8616 * **Example** (Forking into a supplied scope)
8617 *
8618 * ```ts import.meta.vitest
8619 * import { Effect } from "effect"
8620 *
8621 * const task = Effect.never
8622 *
8623 * const program = Effect.scoped(
8624 * Effect.gen(function*() {
8625 * const scope = yield* Effect.scope
8626 * const fiber = yield* Effect.forkIn(task, scope)
8627 * // Fiber will be interrupted when scope closes
8628 * return "done"
8629 * })
8630 * )
8631 *
8632 * await Effect.runPromise(program) // => "done"
8633 * ```
8634 *
8635 * @category forking
8636 * @since 2.0.0
8637 */
8638export const forkIn: {
8639 (
8640 scope: Scope,
8641 options?: {
8642 readonly startImmediately?: boolean | undefined
8643 readonly uninterruptible?: boolean | "inherit" | undefined
8644 }
8645 ): <A, E, R>(self: Effect<A, E, R>) => Effect<Fiber<A, E>, never, R>
8646 <A, E, R>(
8647 self: Effect<A, E, R>,
8648 scope: Scope,
8649 options?: {
8650 readonly startImmediately?: boolean | undefined
8651 readonly uninterruptible?: boolean | "inherit" | undefined
8652 }
8653 ): Effect<Fiber<A, E>, never, R>
8654} = internal.forkIn
8655
8656/**
8657 * Forks the fiber in a `Scope`, interrupting it when the scope is closed.
8658 *
8659 * **Example** (Forking into the current scope)
8660 *
8661 * ```ts import.meta.vitest
8662 * import { Effect } from "effect"
8663 *
8664 * const backgroundTask = Effect.never
8665 *
8666 * const program = Effect.scoped(
8667 * Effect.gen(function*() {
8668 * yield* backgroundTask.pipe(Effect.forkScoped)
8669 *
8670 * // Fiber will be interrupted when scope closes
8671 * return "scope completed"
8672 * })
8673 * )
8674 *
8675 * await Effect.runPromise(program) // => "scope completed"
8676 * ```
8677 *
8678 * @category forking
8679 * @since 2.0.0
8680 */
8681export const forkScoped: <
8682 Arg extends Effect<any, any, any> | {
8683 readonly startImmediately?: boolean | undefined
8684 readonly uninterruptible?: boolean | "inherit" | undefined
8685 } | undefined = {
8686 readonly startImmediately?: boolean | undefined
8687 readonly uninterruptible?: boolean | "inherit" | undefined
8688 }
8689>(
8690 effectOrOptions?: Arg,
8691 options?: {
8692 readonly startImmediately?: boolean | undefined
8693 readonly uninterruptible?: boolean | "inherit" | undefined
8694 } | undefined
8695) => [Arg] extends [Effect<infer _A, infer _E, infer _R>] ? Effect<Fiber<_A, _E>, never, _R | Scope>
8696 : <A, E, R>(self: Effect<A, E, R>) => Effect<Fiber<A, E>, never, R | Scope> = internal.forkScoped
8697
8698/**
8699 * Forks the effect into a new fiber attached to the global scope. Because the
8700 * new fiber is attached to the global scope, when the fiber executing the
8701 * returned effect terminates, the forked fiber will continue running.
8702 *
8703 * **Example** (Forking a detached fiber)
8704 *
8705 * ```ts import.meta.vitest
8706 * import { Effect, Fiber } from "effect"
8707 *
8708 * const daemonTask = Effect.succeed("daemon result")
8709 *
8710 * const program = Effect.gen(function*() {
8711 * const fiber = yield* daemonTask.pipe(Effect.forkDetach)
8712 * return yield* Fiber.join(fiber)
8713 * })
8714 *
8715 * await Effect.runPromise(program) // => "daemon result"
8716 * ```
8717 *
8718 * @category forking
8719 * @since 4.0.0
8720 */
8721export const forkDetach: <
8722 Arg extends Effect<any, any, any> | {
8723 readonly startImmediately?: boolean | undefined
8724 readonly uninterruptible?: boolean | "inherit" | undefined
8725 } | undefined = {
8726 readonly startImmediately?: boolean | undefined
8727 readonly uninterruptible?: boolean | "inherit" | undefined
8728 }
8729>(
8730 effectOrOptions?: Arg,
8731 options?: {
8732 readonly startImmediately?: boolean | undefined
8733 readonly uninterruptible?: boolean | "inherit" | undefined
8734 } | undefined
8735) => [Arg] extends [Effect<infer _A, infer _E, infer _R>] ? Effect<Fiber<_A, _E>, never, _R>
8736 : <A, E, R>(self: Effect<A, E, R>) => Effect<Fiber<A, E>, never, R> = internal.forkDetach
8737
8738/**
8739 * Waits for all child fibers forked by this effect to complete before this
8740 * effect completes.
8741 *
8742 * **When to use**
8743 *
8744 * Use to let an effect start child work concurrently while still delaying its
8745 * own completion until that child work is done.
8746 *
8747 * **Gotchas**
8748 *
8749 * Child fibers that already exist before the wrapped effect starts are not
8750 * awaited.
8751 *
8752 * If interrupted while awaiting child fibers after the wrapped effect fails,
8753 * both the original failure and the interruption are retained in the cause.
8754 * An enclosing uninterruptible region keeps the child wait uninterruptible.
8755 *
8756 * @see {@link forkChild} for forking child fibers that are awaited by this operator
8757 * @see {@link forkDetach} for forking fibers outside the child scope
8758 * @see {@link forkIn} for forking into an explicit scope
8759 * @see {@link forkScoped} for forking fibers tied to the current scope
8760 *
8761 * @category forking
8762 * @since 2.0.0
8763 */
8764export const awaitAllChildren: <A, E, R>(self: Effect<A, E, R>) => Effect<A, E, R> = internal.awaitAllChildren
8765
8766/**
8767 * Accesses the fiber currently executing the effect.
8768 *
8769 * **Example** (Accessing the current fiber)
8770 *
8771 * ```ts import.meta.vitest
8772 * import { Effect } from "effect"
8773 * const output: Array<unknown> = []
8774 *
8775 * const program = Effect.gen(function*() {
8776 * const fiber = yield* Effect.fiber
8777 * yield* Effect.sync(() => { output.push(typeof fiber.id) })
8778 * })
8779 *
8780 * Effect.runSync(program)
8781 * output // => ["number"]
8782 * ```
8783 *
8784 * @category accessors
8785 * @since 4.0.0
8786 */
8787export const fiber: Effect<Fiber<unknown, unknown>> = internal.fiber
8788
8789/**
8790 * Accesses the current fiber id executing the effect.
8791 *
8792 * **Example** (Accessing the current fiber id)
8793 *
8794 * ```ts import.meta.vitest
8795 * import { Effect } from "effect"
8796 *
8797 * const program = Effect.fiberId.pipe(Effect.map((id) => typeof id))
8798 * Effect.runSync(program) // => "number"
8799 * ```
8800 *
8801 * @category accessors
8802 * @since 2.0.0
8803 */
8804export const fiberId: Effect<number> = internal.fiberId
8805
8806// -----------------------------------------------------------------------------
8807// Running Effects
8808// -----------------------------------------------------------------------------
8809
8810/**
8811 * Configuration options for running Effect programs, providing control over
8812 * interruption and scheduling behavior.
8813 *
8814 * **When to use**
8815 *
8816 * Use to pass cancellation, scheduler, interruptibility, and fiber-start hooks
8817 * when running an `Effect` at a program boundary.
8818 *
8819 * **Details**
8820 *
8821 * `signal` interrupts the fiber, `scheduler` provides the scheduler service,
8822 * `uninterruptible` starts the fiber uninterruptibly, and `onFiberStart`
8823 * receives the created fiber.
8824 *
8825 * @see {@link runFork} for starting a fiber with these options
8826 * @see {@link runCallback} for callback-based running with these options
8827 * @see {@link runPromise} for promise-based running with these options
8828 * @see {@link runPromiseExit} for promise-based running that returns an `Exit`
8829 *
8830 * @category running
8831 * @since 4.0.0
8832 */
8833export interface RunOptions {
8834 readonly signal?: AbortSignal | undefined
8835 readonly scheduler?: Scheduler | undefined
8836 readonly uninterruptible?: boolean | undefined
8837 readonly onFiberStart?: ((fiber: Fiber<unknown, unknown>) => void) | undefined
8838}
8839
8840/**
8841 * Runs an effect in the background, returning a fiber that can
8842 * be observed or interrupted.
8843 *
8844 * **When to use**
8845 *
8846 * Use when you need to start an effect in the background and receive a fiber.
8847 *
8848 * **Example** (Running an effect in the background)
8849 *
8850 * ```ts import.meta.vitest
8851 * import { Effect, Fiber } from "effect"
8852 * const output: Array<unknown> = []
8853 *
8854 * // ┌─── Effect<number, never, never>
8855 * // ▼
8856 * const program = Effect.sync(() => { output.push("running...") }).pipe(Effect.as("done"))
8857 *
8858 * // ┌─── RuntimeFiber<number, never>
8859 * // ▼
8860 * const fiber = Effect.runFork(program)
8861 *
8862 * void output.push(await Effect.runPromise(Fiber.join(fiber)))
8863 * output // => ["running...", "done"]
8864 * ```
8865 *
8866 * @category running
8867 * @since 2.0.0
8868 */
8869export const runFork: <A, E>(effect: Effect<A, E, never>, options?: RunOptions | undefined) => Fiber<A, E> =
8870 internal.runFork
8871
8872/**
8873 * Runs an effect in the background with the provided services.
8874 *
8875 * **When to use**
8876 *
8877 * Use when an effect still requires services, you already have a `Context`, and
8878 * you want a background fiber.
8879 *
8880 * **Example** (Running with services in the background)
8881 *
8882 * ```ts import.meta.vitest
8883 * import { Context, Effect, Fiber } from "effect"
8884 * const output: Array<unknown> = []
8885 *
8886 * interface Logger {
8887 * log: (message: string) => void
8888 * }
8889 *
8890 * const Logger = Context.Service<Logger>("Logger")
8891 *
8892 * const services = Context.make(Logger, {
8893 * log: (message) => void output.push(message)
8894 * })
8895 *
8896 * const program = Effect.gen(function*() {
8897 * const logger = yield* Logger
8898 * logger.log("Hello from service!")
8899 * return "done"
8900 * })
8901 *
8902 * const fiber = Effect.runForkWith(services)(program)
8903 * void output.push(await Effect.runPromise(Fiber.join(fiber)))
8904 * output // => ["Hello from service!", "done"]
8905 * ```
8906 *
8907 * @category running
8908 * @since 4.0.0
8909 */
8910export const runForkWith: <R>(
8911 context: Context.Context<R>
8912) => <A, E>(effect: Effect<A, E, R>, options?: RunOptions | undefined) => Fiber<A, E> = internal.runForkWith
8913
8914/**
8915 * Forks an effect with the provided services, registers `onExit` as a fiber observer, and returns an interruptor.
8916 *
8917 * **When to use**
8918 *
8919 * Use when embedding an effect into callback-style code with explicit services
8920 * and a synchronous interruptor.
8921 *
8922 * **Details**
8923 *
8924 * The returned interruptor calls `fiber.interruptUnsafe`, optionally with an interruptor id.
8925 *
8926 * **Example** (Running with services and a callback)
8927 *
8928 * ```ts import.meta.vitest
8929 * import { Context, Effect } from "effect"
8930 * const output: Array<unknown> = []
8931 *
8932 * interface Logger {
8933 * log: (message: string) => Effect.Effect<void>
8934 * }
8935 *
8936 * const Logger = Context.Service<Logger>("Logger")
8937 *
8938 * const services = Context.make(Logger, {
8939 * log: (message) => Effect.sync(() => { output.push(message) })
8940 * })
8941 *
8942 * const program = Effect.gen(function*() {
8943 * const logger = yield* Logger
8944 * yield* logger.log("Started")
8945 * return "done"
8946 * })
8947 *
8948 * await new Promise<void>((resolve) => {
8949 * Effect.runCallbackWith(services)(program, {
8950 * onExit: (exit) => {
8951 * void output.push(exit._tag)
8952 * resolve()
8953 * }
8954 * })
8955 * })
8956 * output // => ["Started", "Success"]
8957 * ```
8958 *
8959 * @category running
8960 * @since 4.0.0
8961 */
8962export const runCallbackWith: <R>(
8963 context: Context.Context<R>
8964) => <A, E>(
8965 effect: Effect<A, E, R>,
8966 options?: (RunOptions & { readonly onExit: (exit: Exit.Exit<A, E>) => void }) | undefined
8967) => (interruptor?: number | undefined) => void = internal.runCallbackWith
8968
8969/**
8970 * Runs an effect asynchronously, registering `onExit` as a fiber observer and
8971 * returning an interruptor.
8972 *
8973 * **Details**
8974 *
8975 * The interruptor calls `fiber.interruptUnsafe` with the optional interruptor
8976 * id.
8977 *
8978 * **Example** (Running with a callback)
8979 *
8980 * ```ts import.meta.vitest
8981 * import { Effect, Exit } from "effect"
8982 * const output: Array<unknown> = []
8983 *
8984 * const program = Effect.gen(function*() {
8985 * yield* Effect.sync(() => { output.push("working") })
8986 * return "done"
8987 * })
8988 *
8989 * await new Promise<void>((resolve) => {
8990 * Effect.runCallback(program, {
8991 * onExit: (exit) => {
8992 * Effect.runSync(
8993 * Exit.match(exit, {
8994 * onFailure: () => Effect.sync(() => { output.push("failed") }),
8995 * onSuccess: (value) => Effect.sync(() => { output.push(`success: ${value}`) })
8996 * })
8997 * )
8998 * resolve()
8999 * }
9000 * })
9001 * })
9002 *
9003 * output // => ["working", "success: done"]
9004 * ```
9005 *
9006 * @category running
9007 * @since 2.0.0
9008 */
9009export const runCallback: <A, E>(
9010 effect: Effect<A, E, never>,
9011 options?: (RunOptions & { readonly onExit: (exit: Exit.Exit<A, E>) => void }) | undefined
9012) => (interruptor?: number | undefined) => void = internal.runCallback
9013
9014/**
9015 * Executes an effect and returns the result as a `Promise`.
9016 *
9017 * **When to use**
9018 *
9019 * Use when you need to execute an effect and work with the
9020 * result using `Promise` syntax, typically for compatibility with other
9021 * promise-based code.
9022 *
9023 * If the effect succeeds, the promise will resolve with the result. If the
9024 * effect fails, the promise will reject with an error.
9025 *
9026 * **Example** (Running a successful effect as a Promise)
9027 *
9028 * ```ts import.meta.vitest
9029 * import { Effect } from "effect"
9030 *
9031 * await Effect.runPromise(Effect.succeed(1)) // => 1
9032 * ```
9033 *
9034 * **Example** (Running effects as promises)
9035 *
9036 * ```ts import.meta.vitest
9037 * //Example: Handling a Failing Effect as a Rejected Promise
9038 * import { Effect } from "effect"
9039 * const output: Array<unknown> = []
9040 *
9041 * await Effect.runPromise(Effect.fail("my error")).catch(() => {
9042 * void output.push("rejected")
9043 * })
9044 * output // => ["rejected"]
9045 * ```
9046 *
9047 * @see {@link runPromiseExit} for a version that returns an `Exit` type instead of rejecting.
9048 * @category running
9049 * @since 2.0.0
9050 */
9051export const runPromise: <A, E>(
9052 effect: Effect<A, E>,
9053 options?: RunOptions | undefined
9054) => Promise<A> = internal.runPromise
9055
9056/**
9057 * Executes an effect as a Promise with the provided services.
9058 *
9059 * **When to use**
9060 *
9061 * Use when you already have a `Context` and need Promise interop that rejects on
9062 * effect failure.
9063 *
9064 * **Example** (Running with services as a promise)
9065 *
9066 * ```ts import.meta.vitest
9067 * import { Context, Effect } from "effect"
9068 *
9069 * interface Config {
9070 * apiUrl: string
9071 * }
9072 *
9073 * const Config = Context.Service<Config>("Config")
9074 *
9075 * const context = Context.make(Config, {
9076 * apiUrl: "https://api.example.com"
9077 * })
9078 *
9079 * const program = Effect.gen(function*() {
9080 * const config = yield* Config
9081 * return `Connecting to ${config.apiUrl}`
9082 * })
9083 *
9084 * await Effect.runPromiseWith(context)(program) // => "Connecting to https://api.example.com"
9085 * ```
9086 *
9087 * @category running
9088 * @since 4.0.0
9089 */
9090export const runPromiseWith: <R>(
9091 context: Context.Context<R>
9092) => <A, E>(effect: Effect<A, E, R>, options?: RunOptions | undefined) => Promise<A> = internal.runPromiseWith
9093
9094/**
9095 * Runs an effect and returns a `Promise` that resolves to an `Exit`, which
9096 * represents the outcome (success or failure) of the effect.
9097 *
9098 * **When to use**
9099 *
9100 * Use when you need to determine if an effect succeeded
9101 * or failed, including any defects, and you want to work with a `Promise`.
9102 *
9103 * **Details**
9104 *
9105 * The `Exit` type represents the result of the effect. Successful effects are
9106 * wrapped in `Success`, and failed effects are wrapped in `Failure` with a
9107 * `Cause`.
9108 *
9109 * **Example** (Observing promise results as Exit)
9110 *
9111 * ```ts import.meta.vitest
9112 * import { Effect, Exit } from "effect"
9113 *
9114 * // Execute a successful effect and get the Exit result as a Promise
9115 * await Effect.runPromiseExit(Effect.succeed(1)) // => Exit.succeed(1)
9116 *
9117 * // Execute a failing effect and get the Exit result as a Promise
9118 * await Effect.runPromiseExit(Effect.fail("my error")) // => Exit.fail("my error")
9119 * ```
9120 *
9121 * @see {@link runPromise} for a version that rejects on failure.
9122 *
9123 * @category running
9124 * @since 2.0.0
9125 */
9126export const runPromiseExit: <A, E>(
9127 effect: Effect<A, E>,
9128 options?: RunOptions | undefined
9129) => Promise<Exit.Exit<A, E>> = internal.runPromiseExit
9130
9131/**
9132 * Runs an effect and returns a Promise of Exit with provided services.
9133 *
9134 * **When to use**
9135 *
9136 * Use when you already have a `Context` and need Promise interop that preserves
9137 * success and failure as an `Exit`.
9138 *
9139 * **Example** (Running with services as an Exit promise)
9140 *
9141 * ```ts import.meta.vitest
9142 * import { Context, Effect, Exit } from "effect"
9143 * const output: Array<unknown> = []
9144 *
9145 * interface Database {
9146 * query: (sql: string) => string
9147 * }
9148 *
9149 * const Database = Context.Service<Database>("Database")
9150 *
9151 * const services = Context.make(Database, {
9152 * query: (sql) => `Result for: ${sql}`
9153 * })
9154 *
9155 * const program = Effect.gen(function*() {
9156 * const db = yield* Database
9157 * return db.query("SELECT * FROM users")
9158 * })
9159 *
9160 * const exit = await Effect.runPromiseExitWith(services)(program)
9161 * if (Exit.isSuccess(exit)) {
9162 * void output.push(`Success: ${exit.value}`)
9163 * }
9164 * output // => ["Success: Result for: SELECT * FROM users"]
9165 * ```
9166 *
9167 * @category running
9168 * @since 4.0.0
9169 */
9170export const runPromiseExitWith: <R>(
9171 context: Context.Context<R>
9172) => <A, E>(effect: Effect<A, E, R>, options?: RunOptions | undefined) => Promise<Exit.Exit<A, E>> =
9173 internal.runPromiseExitWith
9174
9175/**
9176 * Executes an effect synchronously and returns its success value.
9177 *
9178 * **When to use**
9179 *
9180 * Use when you need to execute an effect that is guaranteed to complete
9181 * synchronously.
9182 *
9183 * **Details**
9184 *
9185 * If the effect fails, dies, is interrupted, or performs asynchronous work,
9186 * `runSync` throws a `FiberFailure` instead of returning a value. Use
9187 * `runSyncExit` when you want the failure captured as an `Exit`.
9188 *
9189 * **Example** (Running a synchronous effect)
9190 *
9191 * ```ts import.meta.vitest
9192 * import { Effect } from "effect"
9193 * const output: Array<unknown> = []
9194 *
9195 * const program = Effect.sync(() => {
9196 * void output.push("Hello, World!")
9197 * return 1
9198 * })
9199 *
9200 * const result = Effect.runSync(program)
9201 * void output.push(result)
9202 * output // => ["Hello, World!", 1]
9203 * ```
9204 *
9205 * **Example** (Throwing for failed or async effects)
9206 *
9207 * ```ts import.meta.vitest
9208 * import { Effect } from "effect"
9209 * const output: Array<unknown> = []
9210 *
9211 * try {
9212 * // Attempt to run an effect that fails
9213 * Effect.runSync(Effect.fail("my error"))
9214 * } catch (e) {
9215 * void output.push("failed effect")
9216 * }
9217 * try {
9218 * // Attempt to run an effect that involves async work
9219 * Effect.runSync(Effect.promise(() => Promise.resolve(1)))
9220 * } catch (e) {
9221 * void output.push("async effect")
9222 * }
9223 * output // => ["failed effect", "async effect"]
9224 * ```
9225 *
9226 * @see {@link runSyncExit} for a version that returns an `Exit` type instead of
9227 * throwing an error.
9228 * @category running
9229 * @since 2.0.0
9230 */
9231export const runSync: <A, E>(effect: Effect<A, E>) => A = internal.runSync
9232
9233/**
9234 * Executes an effect synchronously with provided services.
9235 *
9236 * **When to use**
9237 *
9238 * Use when you already have a `Context`, the effect is known to complete
9239 * synchronously, and failures should throw.
9240 *
9241 * **Example** (Running synchronously with services)
9242 *
9243 * ```ts import.meta.vitest
9244 * import { Context, Effect } from "effect"
9245 *
9246 * interface MathService {
9247 * add: (a: number, b: number) => number
9248 * }
9249 *
9250 * const MathService = Context.Service<MathService>("MathService")
9251 *
9252 * const context = Context.make(MathService, {
9253 * add: (a, b) => a + b
9254 * })
9255 *
9256 * const program = Effect.gen(function*() {
9257 * const math = yield* MathService
9258 * return math.add(2, 3)
9259 * })
9260 *
9261 * const result = Effect.runSyncWith(context)(program)
9262 * result // => 5
9263 * ```
9264 *
9265 * @category running
9266 * @since 4.0.0
9267 */
9268export const runSyncWith: <R>(
9269 context: Context.Context<R>
9270) => <A, E>(effect: Effect<A, E, R>) => A = internal.runSyncWith
9271
9272/**
9273 * Runs an effect synchronously and captures the outcome safely as an `Exit` type, which
9274 * represents the outcome (success or failure) of the effect.
9275 *
9276 * **When to use**
9277 *
9278 * Use to find out whether an effect succeeded or failed,
9279 * including any defects, without dealing with asynchronous operations.
9280 *
9281 * **Details**
9282 *
9283 * The `Exit` type represents the result of the effect. Successful effects are
9284 * wrapped in `Success`, and failed effects are wrapped in `Failure` with a
9285 * `Cause`.
9286 *
9287 * If the effect contains asynchronous operations, `runSyncExit` will
9288 * return an `Failure` with a `Die` cause, indicating that the effect cannot be
9289 * resolved synchronously.
9290 *
9291 * **Example** (Observing synchronous results as Exit)
9292 *
9293 * ```ts import.meta.vitest
9294 * import { Effect, Exit } from "effect"
9295 *
9296 * Effect.runSyncExit(Effect.succeed(1)) // => Exit.succeed(1)
9297 *
9298 * Effect.runSyncExit(Effect.fail("my error")) // => Exit.fail("my error")
9299 * ```
9300 *
9301 * **Example** (Capturing async work as a Die cause)
9302 *
9303 * ```ts import.meta.vitest
9304 * import { Cause, Effect, Exit } from "effect"
9305 *
9306 * const exit = Effect.runSyncExit(Effect.promise(() => Promise.resolve(1)))
9307 * const isAsyncDie = Exit.hasDies(exit) && exit.cause.reasons.some(
9308 * (reason) => Cause.isDieReason(reason) && Cause.isAsyncFiberError(reason.defect)
9309 * )
9310 *
9311 * isAsyncDie // => true
9312 * ```
9313 *
9314 * @see {@link runSync} for a version that throws on failure.
9315 *
9316 * @category running
9317 * @since 2.0.0
9318 */
9319export const runSyncExit: <A, E>(effect: Effect<A, E>) => Exit.Exit<A, E> = internal.runSyncExit
9320
9321/**
9322 * Runs an effect synchronously with provided services, returning an Exit result safely.
9323 *
9324 * **When to use**
9325 *
9326 * Use when you already have a `Context` and need a synchronous `Exit` instead of
9327 * throwing on failure.
9328 *
9329 * **Example** (Running synchronously with services as Exit)
9330 *
9331 * ```ts import.meta.vitest
9332 * import { Context, Effect, Exit } from "effect"
9333 * const output: Array<unknown> = []
9334 *
9335 * // Define a logger service
9336 * const Logger = Context.Service<{
9337 * log: (msg: string) => void
9338 * }>("Logger")
9339 *
9340 * const program = Effect.gen(function*() {
9341 * const logger = yield* Effect.service(Logger)
9342 * logger.log("Computing result...")
9343 * return 42
9344 * })
9345 *
9346 * // Prepare context
9347 * const context = Context.make(Logger, {
9348 * log: (msg) => void output.push(`[LOG] ${msg}`)
9349 * })
9350 *
9351 * const exit = Effect.runSyncExitWith(context)(program)
9352 *
9353 * if (Exit.isSuccess(exit)) {
9354 * void output.push(`Success: ${exit.value}`)
9355 * } else {
9356 * void output.push(`Failure: ${exit.cause}`)
9357 * }
9358 * output // => ["[LOG] Computing result...", "Success: 42"]
9359 * ```
9360 *
9361 * @category running
9362 * @since 4.0.0
9363 */
9364export const runSyncExitWith: <R>(
9365 context: Context.Context<R>
9366) => <A, E>(effect: Effect<A, E, R>) => Exit.Exit<A, E> = internal.runSyncExitWith
9367
9368// -----------------------------------------------------------------------------
9369// Function
9370// -----------------------------------------------------------------------------
9371
9372/**
9373 * Type helpers for functions built with `Effect.fn` and `Effect.fnUntraced`.
9374 *
9375 * **Details**
9376 *
9377 * Use these to describe generator-based signatures and traced or untraced variants.
9378 *
9379 * @category constructors
9380 * @since 3.11.0
9381 */
9382export declare namespace fn {
9383 /**
9384 * Generator return type accepted by {@link fn} and {@link fnUntraced}.
9385 *
9386 * **When to use**
9387 *
9388 * Use when you need to annotate the return type of a generator body while
9389 * keeping the produced function's `Effect` return type inferred.
9390 *
9391 * **Example** (Annotating an Effect function)
9392 *
9393 * ```ts import.meta.vitest
9394 * import { Effect } from "effect"
9395 *
9396 * const f = Effect.fnUntraced(function*(
9397 * value: string
9398 * ): Effect.fn.Return<number> {
9399 * return yield* Effect.succeed(value.length)
9400 * })
9401 *
9402 * // ┌─── Effect.Effect<number>
9403 * // ▼
9404 * const program = f("hello")
9405 * Effect.runSync(program) // => 5
9406 * ```
9407 *
9408 * **Example** (Annotating a parametric Effect function)
9409 *
9410 * ```ts import.meta.vitest
9411 * import { Effect } from "effect"
9412 *
9413 * const f = Effect.fnUntraced(function*<A>(
9414 * value: A
9415 * ): Effect.fn.Return<A> {
9416 * return yield* Effect.succeed(value)
9417 * })
9418 *
9419 * // ┌─── Effect.Effect<string>
9420 * // ▼
9421 * const program = f("hello")
9422 * Effect.runSync(program) // => "hello"
9423 * ```
9424 *
9425 * @category utility types
9426 * @since 3.19.0
9427 */
9428 export type Return<A, E = never, R = never> = Generator<Effect<any, E, R>, A, any>
9429
9430 /**
9431 * Type of the untraced function builder used by `Effect.fnUntraced`.
9432 *
9433 * @category utility types
9434 * @since 3.11.0
9435 */
9436 export type Untraced = {
9437 <Eff extends Effect<any, any, any>, AEff, Args extends Array<any>>(
9438 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>
9439 ): (...args: Args) => Effect<
9440 AEff,
9441 [Eff] extends [never] ? never
9442 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9443 : never,
9444 [Eff] extends [never] ? never
9445 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9446 : never
9447 >
9448 <Self, Eff extends Effect<any, any, any>, AEff, Args extends Array<any>>(
9449 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>
9450 ): (this: Self, ...args: Args) => Effect<
9451 AEff,
9452 [Eff] extends [never] ? never
9453 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9454 : never,
9455 [Eff] extends [never] ? never
9456 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9457 : never
9458 >
9459
9460 <Eff extends Effect<any, any, any>, AEff, Args extends Array<any>, A>(
9461 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
9462 a: (
9463 _: Effect<
9464 AEff,
9465 [Eff] extends [never] ? never
9466 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9467 : never,
9468 [Eff] extends [never] ? never
9469 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9470 : never
9471 >,
9472 ...args: Args
9473 ) => A
9474 ): (...args: Args) => A
9475 <Self, Eff extends Effect<any, any, any>, AEff, Args extends Array<any>, A>(
9476 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
9477 a: (
9478 _: Effect<
9479 AEff,
9480 [Eff] extends [never] ? never
9481 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9482 : never,
9483 [Eff] extends [never] ? never
9484 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9485 : never
9486 >,
9487 ...args: Args
9488 ) => A
9489 ): (this: Self, ...args: Args) => A
9490 <Eff extends Effect<any, any, any>, AEff, Args extends Array<any>, A, B>(
9491 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
9492 a: (
9493 _: Effect<
9494 AEff,
9495 [Eff] extends [never] ? never
9496 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9497 : never,
9498 [Eff] extends [never] ? never
9499 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9500 : never
9501 >,
9502 ...args: Args
9503 ) => A,
9504 b: (_: A, ...args: Args) => B
9505 ): (...args: Args) => B
9506 <Self, Eff extends Effect<any, any, any>, AEff, Args extends Array<any>, A, B>(
9507 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
9508 a: (
9509 _: Effect<
9510 AEff,
9511 [Eff] extends [never] ? never
9512 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9513 : never,
9514 [Eff] extends [never] ? never
9515 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9516 : never
9517 >,
9518 ...args: Args
9519 ) => A,
9520 b: (_: A, ...args: Args) => B
9521 ): (this: Self, ...args: Args) => B
9522 <
9523 Eff extends Effect<any, any, any>,
9524 AEff,
9525 Args extends Array<any>,
9526 A,
9527 B,
9528 C
9529 >(
9530 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
9531 a: (
9532 _: Effect<
9533 AEff,
9534 [Eff] extends [never] ? never
9535 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9536 : never,
9537 [Eff] extends [never] ? never
9538 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9539 : never
9540 >,
9541 ...args: Args
9542 ) => A,
9543 b: (_: A, ...args: Args) => B,
9544 c: (_: B, ...args: Args) => C
9545 ): (...args: Args) => C
9546 <
9547 Self,
9548 Eff extends Effect<any, any, any>,
9549 AEff,
9550 Args extends Array<any>,
9551 A,
9552 B,
9553 C
9554 >(
9555 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
9556 a: (
9557 _: Effect<
9558 AEff,
9559 [Eff] extends [never] ? never
9560 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9561 : never,
9562 [Eff] extends [never] ? never
9563 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9564 : never
9565 >,
9566 ...args: Args
9567 ) => A,
9568 b: (_: A, ...args: Args) => B,
9569 c: (_: B, ...args: Args) => C
9570 ): (this: Self, ...args: Args) => C
9571 <
9572 Eff extends Effect<any, any, any>,
9573 AEff,
9574 Args extends Array<any>,
9575 A,
9576 B,
9577 C,
9578 D
9579 >(
9580 body: (...args: Args) => Generator<Eff, AEff, never>,
9581 a: (
9582 _: Effect<
9583 AEff,
9584 [Eff] extends [never] ? never
9585 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9586 : never,
9587 [Eff] extends [never] ? never
9588 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9589 : never
9590 >,
9591 ...args: Args
9592 ) => A,
9593 b: (_: A, ...args: Args) => B,
9594 c: (_: B, ...args: Args) => C,
9595 d: (_: C, ...args: Args) => D
9596 ): (...args: Args) => D
9597 <
9598 Self,
9599 Eff extends Effect<any, any, any>,
9600 AEff,
9601 Args extends Array<any>,
9602 A,
9603 B,
9604 C,
9605 D
9606 >(
9607 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
9608 a: (
9609 _: Effect<
9610 AEff,
9611 [Eff] extends [never] ? never
9612 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9613 : never,
9614 [Eff] extends [never] ? never
9615 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9616 : never
9617 >,
9618 ...args: Args
9619 ) => A,
9620 b: (_: A, ...args: Args) => B,
9621 c: (_: B, ...args: Args) => C,
9622 d: (_: C, ...args: Args) => D
9623 ): (this: Self, ...args: Args) => D
9624 <
9625 Eff extends Effect<any, any, any>,
9626 AEff,
9627 Args extends Array<any>,
9628 A,
9629 B,
9630 C,
9631 D,
9632 E
9633 >(
9634 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
9635 a: (
9636 _: Effect<
9637 AEff,
9638 [Eff] extends [never] ? never
9639 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9640 : never,
9641 [Eff] extends [never] ? never
9642 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9643 : never
9644 >,
9645 ...args: Args
9646 ) => A,
9647 b: (_: A, ...args: Args) => B,
9648 c: (_: B, ...args: Args) => C,
9649 d: (_: C, ...args: Args) => D,
9650 e: (_: D, ...args: Args) => E
9651 ): (...args: Args) => E
9652 <
9653 Self,
9654 Eff extends Effect<any, any, any>,
9655 AEff,
9656 Args extends Array<any>,
9657 A,
9658 B,
9659 C,
9660 D,
9661 E
9662 >(
9663 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
9664 a: (
9665 _: Effect<
9666 AEff,
9667 [Eff] extends [never] ? never
9668 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9669 : never,
9670 [Eff] extends [never] ? never
9671 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9672 : never
9673 >,
9674 ...args: Args
9675 ) => A,
9676 b: (_: A, ...args: Args) => B,
9677 c: (_: B, ...args: Args) => C,
9678 d: (_: C, ...args: Args) => D,
9679 e: (_: D, ...args: Args) => E
9680 ): (this: Self, ...args: Args) => E
9681 <
9682 Eff extends Effect<any, any, any>,
9683 AEff,
9684 Args extends Array<any>,
9685 A,
9686 B,
9687 C,
9688 D,
9689 E,
9690 F
9691 >(
9692 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
9693 a: (
9694 _: Effect<
9695 AEff,
9696 [Eff] extends [never] ? never
9697 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9698 : never,
9699 [Eff] extends [never] ? never
9700 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9701 : never
9702 >,
9703 ...args: Args
9704 ) => A,
9705 b: (_: A, ...args: Args) => B,
9706 c: (_: B, ...args: Args) => C,
9707 d: (_: C, ...args: Args) => D,
9708 e: (_: D, ...args: Args) => E,
9709 f: (_: E, ...args: Args) => F
9710 ): (...args: Args) => F
9711 <
9712 Self,
9713 Eff extends Effect<any, any, any>,
9714 AEff,
9715 Args extends Array<any>,
9716 A,
9717 B,
9718 C,
9719 D,
9720 E,
9721 F
9722 >(
9723 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
9724 a: (
9725 _: Effect<
9726 AEff,
9727 [Eff] extends [never] ? never
9728 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9729 : never,
9730 [Eff] extends [never] ? never
9731 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9732 : never
9733 >,
9734 ...args: Args
9735 ) => A,
9736 b: (_: A, ...args: Args) => B,
9737 c: (_: B, ...args: Args) => C,
9738 d: (_: C, ...args: Args) => D,
9739 e: (_: D, ...args: Args) => E,
9740 f: (_: E, ...args: Args) => F
9741 ): (this: Self, ...args: Args) => F
9742 <
9743 Eff extends Effect<any, any, any>,
9744 AEff,
9745 Args extends Array<any>,
9746 A,
9747 B,
9748 C,
9749 D,
9750 E,
9751 F,
9752 G
9753 >(
9754 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
9755 a: (
9756 _: Effect<
9757 AEff,
9758 [Eff] extends [never] ? never
9759 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9760 : never,
9761 [Eff] extends [never] ? never
9762 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9763 : never
9764 >,
9765 ...args: Args
9766 ) => A,
9767 b: (_: A, ...args: Args) => B,
9768 c: (_: B, ...args: Args) => C,
9769 d: (_: C, ...args: Args) => D,
9770 e: (_: D, ...args: Args) => E,
9771 f: (_: E, ...args: Args) => F,
9772 g: (_: F, ...args: Args) => G
9773 ): (...args: Args) => G
9774 <
9775 Self,
9776 Eff extends Effect<any, any, any>,
9777 AEff,
9778 Args extends Array<any>,
9779 A,
9780 B,
9781 C,
9782 D,
9783 E,
9784 F,
9785 G
9786 >(
9787 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
9788 a: (
9789 _: Effect<
9790 AEff,
9791 [Eff] extends [never] ? never
9792 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9793 : never,
9794 [Eff] extends [never] ? never
9795 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9796 : never
9797 >,
9798 ...args: Args
9799 ) => A,
9800 b: (_: A, ...args: Args) => B,
9801 c: (_: B, ...args: Args) => C,
9802 d: (_: C, ...args: Args) => D,
9803 e: (_: D, ...args: Args) => E,
9804 f: (_: E, ...args: Args) => F,
9805 g: (_: F, ...args: Args) => G
9806 ): (this: Self, ...args: Args) => G
9807 <
9808 Eff extends Effect<any, any, any>,
9809 AEff,
9810 Args extends Array<any>,
9811 A,
9812 B,
9813 C,
9814 D,
9815 E,
9816 F,
9817 G,
9818 H
9819 >(
9820 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
9821 a: (
9822 _: Effect<
9823 AEff,
9824 [Eff] extends [never] ? never
9825 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9826 : never,
9827 [Eff] extends [never] ? never
9828 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9829 : never
9830 >,
9831 ...args: Args
9832 ) => A,
9833 b: (_: A, ...args: Args) => B,
9834 c: (_: B, ...args: Args) => C,
9835 d: (_: C, ...args: Args) => D,
9836 e: (_: D, ...args: Args) => E,
9837 f: (_: E, ...args: Args) => F,
9838 g: (_: F, ...args: Args) => G,
9839 h: (_: G, ...args: Args) => H
9840 ): (...args: Args) => H
9841 <
9842 Self,
9843 Eff extends Effect<any, any, any>,
9844 AEff,
9845 Args extends Array<any>,
9846 A,
9847 B,
9848 C,
9849 D,
9850 E,
9851 F,
9852 G,
9853 H
9854 >(
9855 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
9856 a: (
9857 _: Effect<
9858 AEff,
9859 [Eff] extends [never] ? never
9860 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9861 : never,
9862 [Eff] extends [never] ? never
9863 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9864 : never
9865 >,
9866 ...args: Args
9867 ) => A,
9868 b: (_: A, ...args: Args) => B,
9869 c: (_: B, ...args: Args) => C,
9870 d: (_: C, ...args: Args) => D,
9871 e: (_: D, ...args: Args) => E,
9872 f: (_: E, ...args: Args) => F,
9873 g: (_: F, ...args: Args) => G,
9874 h: (_: G, ...args: Args) => H
9875 ): (this: Self, ...args: Args) => H
9876 <
9877 Eff extends Effect<any, any, any>,
9878 AEff,
9879 Args extends Array<any>,
9880 A,
9881 B,
9882 C,
9883 D,
9884 E,
9885 F,
9886 G,
9887 H,
9888 I
9889 >(
9890 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
9891 a: (
9892 _: Effect<
9893 AEff,
9894 [Eff] extends [never] ? never
9895 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9896 : never,
9897 [Eff] extends [never] ? never
9898 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9899 : never
9900 >,
9901 ...args: Args
9902 ) => A,
9903 b: (_: A, ...args: Args) => B,
9904 c: (_: B, ...args: Args) => C,
9905 d: (_: C, ...args: Args) => D,
9906 e: (_: D, ...args: Args) => E,
9907 f: (_: E, ...args: Args) => F,
9908 g: (_: F, ...args: Args) => G,
9909 h: (_: G, ...args: Args) => H,
9910 i: (_: H, ...args: Args) => I
9911 ): (...args: Args) => I
9912 <
9913 Self,
9914 Eff extends Effect<any, any, any>,
9915 AEff,
9916 Args extends Array<any>,
9917 A,
9918 B,
9919 C,
9920 D,
9921 E,
9922 F,
9923 G,
9924 H,
9925 I
9926 >(
9927 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
9928 a: (
9929 _: Effect<
9930 AEff,
9931 [Eff] extends [never] ? never
9932 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9933 : never,
9934 [Eff] extends [never] ? never
9935 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9936 : never
9937 >,
9938 ...args: Args
9939 ) => A,
9940 b: (_: A, ...args: Args) => B,
9941 c: (_: B, ...args: Args) => C,
9942 d: (_: C, ...args: Args) => D,
9943 e: (_: D, ...args: Args) => E,
9944 f: (_: E, ...args: Args) => F,
9945 g: (_: F, ...args: Args) => G,
9946 h: (_: G, ...args: Args) => H,
9947 i: (_: H, ...args: Args) => I
9948 ): (this: Self, ...args: Args) => I
9949 <
9950 Eff extends Effect<any, any, any>,
9951 AEff,
9952 Args extends Array<any>,
9953 A,
9954 B,
9955 C,
9956 D,
9957 E,
9958 F,
9959 G,
9960 H,
9961 I,
9962 J
9963 >(
9964 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
9965 a: (
9966 _: Effect<
9967 AEff,
9968 [Eff] extends [never] ? never
9969 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
9970 : never,
9971 [Eff] extends [never] ? never
9972 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
9973 : never
9974 >,
9975 ...args: Args
9976 ) => A,
9977 b: (_: A, ...args: Args) => B,
9978 c: (_: B, ...args: Args) => C,
9979 d: (_: C, ...args: Args) => D,
9980 e: (_: D, ...args: Args) => E,
9981 f: (_: E, ...args: Args) => F,
9982 g: (_: F, ...args: Args) => G,
9983 h: (_: G, ...args: Args) => H,
9984 i: (_: H, ...args: Args) => I,
9985 j: (_: I, ...args: Args) => J
9986 ): (...args: Args) => J
9987 <
9988 Self,
9989 Eff extends Effect<any, any, any>,
9990 AEff,
9991 Args extends Array<any>,
9992 A,
9993 B,
9994 C,
9995 D,
9996 E,
9997 F,
9998 G,
9999 H,
10000 I,
10001 J
10002 >(
10003 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
10004 a: (
10005 _: Effect<
10006 AEff,
10007 [Eff] extends [never] ? never
10008 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10009 : never,
10010 [Eff] extends [never] ? never
10011 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10012 : never
10013 >,
10014 ...args: Args
10015 ) => A,
10016 b: (_: A, ...args: Args) => B,
10017 c: (_: B, ...args: Args) => C,
10018 d: (_: C, ...args: Args) => D,
10019 e: (_: D, ...args: Args) => E,
10020 f: (_: E, ...args: Args) => F,
10021 g: (_: F, ...args: Args) => G,
10022 h: (_: G, ...args: Args) => H,
10023 i: (_: H, ...args: Args) => I,
10024 j: (_: I, ...args: Args) => J
10025 ): (this: Self, ...args: Args) => J
10026 <
10027 Eff extends Effect<any, any, any>,
10028 AEff,
10029 Args extends Array<any>,
10030 A,
10031 B,
10032 C,
10033 D,
10034 E,
10035 F,
10036 G,
10037 H,
10038 I,
10039 J,
10040 K
10041 >(
10042 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
10043 a: (
10044 _: Effect<
10045 AEff,
10046 [Eff] extends [never] ? never
10047 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10048 : never,
10049 [Eff] extends [never] ? never
10050 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10051 : never
10052 >,
10053 ...args: Args
10054 ) => A,
10055 b: (_: A, ...args: Args) => B,
10056 c: (_: B, ...args: Args) => C,
10057 d: (_: C, ...args: Args) => D,
10058 e: (_: D, ...args: Args) => E,
10059 f: (_: E, ...args: Args) => F,
10060 g: (_: F, ...args: Args) => G,
10061 h: (_: G, ...args: Args) => H,
10062 i: (_: H, ...args: Args) => I,
10063 j: (_: I, ...args: Args) => J,
10064 k: (_: J, ...args: Args) => K
10065 ): (...args: Args) => K
10066 <
10067 Self,
10068 Eff extends Effect<any, any, any>,
10069 AEff,
10070 Args extends Array<any>,
10071 A,
10072 B,
10073 C,
10074 D,
10075 E,
10076 F,
10077 G,
10078 H,
10079 I,
10080 J,
10081 K
10082 >(
10083 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
10084 a: (
10085 _: Effect<
10086 AEff,
10087 [Eff] extends [never] ? never
10088 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10089 : never,
10090 [Eff] extends [never] ? never
10091 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10092 : never
10093 >,
10094 ...args: Args
10095 ) => A,
10096 b: (_: A, ...args: Args) => B,
10097 c: (_: B, ...args: Args) => C,
10098 d: (_: C, ...args: Args) => D,
10099 e: (_: D, ...args: Args) => E,
10100 f: (_: E, ...args: Args) => F,
10101 g: (_: F, ...args: Args) => G,
10102 h: (_: G, ...args: Args) => H,
10103 i: (_: H, ...args: Args) => I,
10104 j: (_: I, ...args: Args) => J,
10105 k: (_: J, ...args: Args) => K
10106 ): (this: Self, ...args: Args) => K
10107 <
10108 Eff extends Effect<any, any, any>,
10109 AEff,
10110 Args extends Array<any>,
10111 A,
10112 B,
10113 C,
10114 D,
10115 E,
10116 F,
10117 G,
10118 H,
10119 I,
10120 J,
10121 K,
10122 L
10123 >(
10124 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
10125 a: (
10126 _: Effect<
10127 AEff,
10128 [Eff] extends [never] ? never
10129 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10130 : never,
10131 [Eff] extends [never] ? never
10132 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10133 : never
10134 >,
10135 ...args: Args
10136 ) => A,
10137 b: (_: A, ...args: Args) => B,
10138 c: (_: B, ...args: Args) => C,
10139 d: (_: C, ...args: Args) => D,
10140 e: (_: D, ...args: Args) => E,
10141 f: (_: E, ...args: Args) => F,
10142 g: (_: F, ...args: Args) => G,
10143 h: (_: G, ...args: Args) => H,
10144 i: (_: H, ...args: Args) => I,
10145 j: (_: I, ...args: Args) => J,
10146 k: (_: J, ...args: Args) => K,
10147 l: (_: K, ...args: Args) => L
10148 ): (...args: Args) => L
10149 <
10150 Self,
10151 Eff extends Effect<any, any, any>,
10152 AEff,
10153 Args extends Array<any>,
10154 A,
10155 B,
10156 C,
10157 D,
10158 E,
10159 F,
10160 G,
10161 H,
10162 I,
10163 J,
10164 K,
10165 L
10166 >(
10167 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
10168 a: (
10169 _: Effect<
10170 AEff,
10171 [Eff] extends [never] ? never
10172 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10173 : never,
10174 [Eff] extends [never] ? never
10175 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10176 : never
10177 >,
10178 ...args: Args
10179 ) => A,
10180 b: (_: A, ...args: Args) => B,
10181 c: (_: B, ...args: Args) => C,
10182 d: (_: C, ...args: Args) => D,
10183 e: (_: D, ...args: Args) => E,
10184 f: (_: E, ...args: Args) => F,
10185 g: (_: F, ...args: Args) => G,
10186 h: (_: G, ...args: Args) => H,
10187 i: (_: H, ...args: Args) => I,
10188 j: (_: I, ...args: Args) => J,
10189 k: (_: J, ...args: Args) => K,
10190 l: (_: K, ...args: Args) => L
10191 ): (this: Self, ...args: Args) => L
10192 <
10193 Eff extends Effect<any, any, any>,
10194 AEff,
10195 Args extends Array<any>,
10196 A,
10197 B,
10198 C,
10199 D,
10200 E,
10201 F,
10202 G,
10203 H,
10204 I,
10205 J,
10206 K,
10207 L,
10208 M
10209 >(
10210 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
10211 a: (
10212 _: Effect<
10213 AEff,
10214 [Eff] extends [never] ? never
10215 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10216 : never,
10217 [Eff] extends [never] ? never
10218 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10219 : never
10220 >,
10221 ...args: Args
10222 ) => A,
10223 b: (_: A, ...args: Args) => B,
10224 c: (_: B, ...args: Args) => C,
10225 d: (_: C, ...args: Args) => D,
10226 e: (_: D, ...args: Args) => E,
10227 f: (_: E, ...args: Args) => F,
10228 g: (_: F, ...args: Args) => G,
10229 h: (_: G, ...args: Args) => H,
10230 i: (_: H, ...args: Args) => I,
10231 j: (_: I, ...args: Args) => J,
10232 k: (_: J, ...args: Args) => K,
10233 l: (_: K, ...args: Args) => L,
10234 m: (_: L, ...args: Args) => M
10235 ): (...args: Args) => M
10236 <
10237 Self,
10238 Eff extends Effect<any, any, any>,
10239 AEff,
10240 Args extends Array<any>,
10241 A,
10242 B,
10243 C,
10244 D,
10245 E,
10246 F,
10247 G,
10248 H,
10249 I,
10250 J,
10251 K,
10252 L,
10253 M
10254 >(
10255 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
10256 a: (
10257 _: Effect<
10258 AEff,
10259 [Eff] extends [never] ? never
10260 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10261 : never,
10262 [Eff] extends [never] ? never
10263 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10264 : never
10265 >,
10266 ...args: Args
10267 ) => A,
10268 b: (_: A, ...args: Args) => B,
10269 c: (_: B, ...args: Args) => C,
10270 d: (_: C, ...args: Args) => D,
10271 e: (_: D, ...args: Args) => E,
10272 f: (_: E, ...args: Args) => F,
10273 g: (_: F, ...args: Args) => G,
10274 h: (_: G, ...args: Args) => H,
10275 i: (_: H, ...args: Args) => I,
10276 j: (_: I, ...args: Args) => J,
10277 k: (_: J, ...args: Args) => K,
10278 l: (_: K, ...args: Args) => L,
10279 m: (_: L, ...args: Args) => M
10280 ): (this: Self, ...args: Args) => M
10281 <
10282 Eff extends Effect<any, any, any>,
10283 AEff,
10284 Args extends Array<any>,
10285 A,
10286 B,
10287 C,
10288 D,
10289 E,
10290 F,
10291 G,
10292 H,
10293 I,
10294 J,
10295 K,
10296 L,
10297 M,
10298 N
10299 >(
10300 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
10301 a: (
10302 _: Effect<
10303 AEff,
10304 [Eff] extends [never] ? never
10305 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10306 : never,
10307 [Eff] extends [never] ? never
10308 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10309 : never
10310 >,
10311 ...args: Args
10312 ) => A,
10313 b: (_: A, ...args: Args) => B,
10314 c: (_: B, ...args: Args) => C,
10315 d: (_: C, ...args: Args) => D,
10316 e: (_: D, ...args: Args) => E,
10317 f: (_: E, ...args: Args) => F,
10318 g: (_: F, ...args: Args) => G,
10319 h: (_: G, ...args: Args) => H,
10320 i: (_: H, ...args: Args) => I,
10321 j: (_: I, ...args: Args) => J,
10322 k: (_: J, ...args: Args) => K,
10323 l: (_: K, ...args: Args) => L,
10324 m: (_: L, ...args: Args) => M,
10325 n: (_: M, ...args: Args) => N
10326 ): (...args: Args) => N
10327 <
10328 Self,
10329 Eff extends Effect<any, any, any>,
10330 AEff,
10331 Args extends Array<any>,
10332 A,
10333 B,
10334 C,
10335 D,
10336 E,
10337 F,
10338 G,
10339 H,
10340 I,
10341 J,
10342 K,
10343 L,
10344 M,
10345 N
10346 >(
10347 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
10348 a: (
10349 _: Effect<
10350 AEff,
10351 [Eff] extends [never] ? never
10352 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10353 : never,
10354 [Eff] extends [never] ? never
10355 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10356 : never
10357 >,
10358 ...args: Args
10359 ) => A,
10360 b: (_: A, ...args: Args) => B,
10361 c: (_: B, ...args: Args) => C,
10362 d: (_: C, ...args: Args) => D,
10363 e: (_: D, ...args: Args) => E,
10364 f: (_: E, ...args: Args) => F,
10365 g: (_: F, ...args: Args) => G,
10366 h: (_: G, ...args: Args) => H,
10367 i: (_: H, ...args: Args) => I,
10368 j: (_: I, ...args: Args) => J,
10369 k: (_: J, ...args: Args) => K,
10370 l: (_: K, ...args: Args) => L,
10371 m: (_: L, ...args: Args) => M,
10372 n: (_: M, ...args: Args) => N
10373 ): (this: Self, ...args: Args) => N
10374 <
10375 Eff extends Effect<any, any, any>,
10376 AEff,
10377 Args extends Array<any>,
10378 A,
10379 B,
10380 C,
10381 D,
10382 E,
10383 F,
10384 G,
10385 H,
10386 I,
10387 J,
10388 K,
10389 L,
10390 M,
10391 N,
10392 O
10393 >(
10394 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
10395 a: (
10396 _: Effect<
10397 AEff,
10398 [Eff] extends [never] ? never
10399 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10400 : never,
10401 [Eff] extends [never] ? never
10402 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10403 : never
10404 >,
10405 ...args: Args
10406 ) => A,
10407 b: (_: A, ...args: Args) => B,
10408 c: (_: B, ...args: Args) => C,
10409 d: (_: C, ...args: Args) => D,
10410 e: (_: D, ...args: Args) => E,
10411 f: (_: E, ...args: Args) => F,
10412 g: (_: F, ...args: Args) => G,
10413 h: (_: G, ...args: Args) => H,
10414 i: (_: H, ...args: Args) => I,
10415 j: (_: I, ...args: Args) => J,
10416 k: (_: J, ...args: Args) => K,
10417 l: (_: K, ...args: Args) => L,
10418 m: (_: L, ...args: Args) => M,
10419 n: (_: M, ...args: Args) => N,
10420 o: (_: N, ...args: Args) => O
10421 ): (...args: Args) => O
10422 <
10423 Self,
10424 Eff extends Effect<any, any, any>,
10425 AEff,
10426 Args extends Array<any>,
10427 A,
10428 B,
10429 C,
10430 D,
10431 E,
10432 F,
10433 G,
10434 H,
10435 I,
10436 J,
10437 K,
10438 L,
10439 M,
10440 N,
10441 O
10442 >(
10443 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
10444 a: (
10445 _: Effect<
10446 AEff,
10447 [Eff] extends [never] ? never
10448 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10449 : never,
10450 [Eff] extends [never] ? never
10451 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10452 : never
10453 >,
10454 ...args: Args
10455 ) => A,
10456 b: (_: A, ...args: Args) => B,
10457 c: (_: B, ...args: Args) => C,
10458 d: (_: C, ...args: Args) => D,
10459 e: (_: D, ...args: Args) => E,
10460 f: (_: E, ...args: Args) => F,
10461 g: (_: F, ...args: Args) => G,
10462 h: (_: G, ...args: Args) => H,
10463 i: (_: H, ...args: Args) => I,
10464 j: (_: I, ...args: Args) => J,
10465 k: (_: J, ...args: Args) => K,
10466 l: (_: K, ...args: Args) => L,
10467 m: (_: L, ...args: Args) => M,
10468 n: (_: M, ...args: Args) => N,
10469 o: (_: N, ...args: Args) => O
10470 ): (this: Self, ...args: Args) => O
10471 <
10472 Eff extends Effect<any, any, any>,
10473 AEff,
10474 Args extends Array<any>,
10475 A,
10476 B,
10477 C,
10478 D,
10479 E,
10480 F,
10481 G,
10482 H,
10483 I,
10484 J,
10485 K,
10486 L,
10487 M,
10488 N,
10489 O,
10490 P
10491 >(
10492 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
10493 a: (
10494 _: Effect<
10495 AEff,
10496 [Eff] extends [never] ? never
10497 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10498 : never,
10499 [Eff] extends [never] ? never
10500 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10501 : never
10502 >,
10503 ...args: Args
10504 ) => A,
10505 b: (_: A, ...args: Args) => B,
10506 c: (_: B, ...args: Args) => C,
10507 d: (_: C, ...args: Args) => D,
10508 e: (_: D, ...args: Args) => E,
10509 f: (_: E, ...args: Args) => F,
10510 g: (_: F, ...args: Args) => G,
10511 h: (_: G, ...args: Args) => H,
10512 i: (_: H, ...args: Args) => I,
10513 j: (_: I, ...args: Args) => J,
10514 k: (_: J, ...args: Args) => K,
10515 l: (_: K, ...args: Args) => L,
10516 m: (_: L, ...args: Args) => M,
10517 n: (_: M, ...args: Args) => N,
10518 o: (_: N, ...args: Args) => O,
10519 p: (_: O, ...args: Args) => P
10520 ): (...args: Args) => P
10521 <
10522 Self,
10523 Eff extends Effect<any, any, any>,
10524 AEff,
10525 Args extends Array<any>,
10526 A,
10527 B,
10528 C,
10529 D,
10530 E,
10531 F,
10532 G,
10533 H,
10534 I,
10535 J,
10536 K,
10537 L,
10538 M,
10539 N,
10540 O,
10541 P
10542 >(
10543 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
10544 a: (
10545 _: Effect<
10546 AEff,
10547 [Eff] extends [never] ? never
10548 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10549 : never,
10550 [Eff] extends [never] ? never
10551 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10552 : never
10553 >,
10554 ...args: Args
10555 ) => A,
10556 b: (_: A, ...args: Args) => B,
10557 c: (_: B, ...args: Args) => C,
10558 d: (_: C, ...args: Args) => D,
10559 e: (_: D, ...args: Args) => E,
10560 f: (_: E, ...args: Args) => F,
10561 g: (_: F, ...args: Args) => G,
10562 h: (_: G, ...args: Args) => H,
10563 i: (_: H, ...args: Args) => I,
10564 j: (_: I, ...args: Args) => J,
10565 k: (_: J, ...args: Args) => K,
10566 l: (_: K, ...args: Args) => L,
10567 m: (_: L, ...args: Args) => M,
10568 n: (_: M, ...args: Args) => N,
10569 o: (_: N, ...args: Args) => O,
10570 p: (_: O, ...args: Args) => P
10571 ): (this: Self, ...args: Args) => P
10572 <
10573 Eff extends Effect<any, any, any>,
10574 AEff,
10575 Args extends Array<any>,
10576 A,
10577 B,
10578 C,
10579 D,
10580 E,
10581 F,
10582 G,
10583 H,
10584 I,
10585 J,
10586 K,
10587 L,
10588 M,
10589 N,
10590 O,
10591 P,
10592 Q
10593 >(
10594 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
10595 a: (
10596 _: Effect<
10597 AEff,
10598 [Eff] extends [never] ? never
10599 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10600 : never,
10601 [Eff] extends [never] ? never
10602 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10603 : never
10604 >,
10605 ...args: Args
10606 ) => A,
10607 b: (_: A, ...args: Args) => B,
10608 c: (_: B, ...args: Args) => C,
10609 d: (_: C, ...args: Args) => D,
10610 e: (_: D, ...args: Args) => E,
10611 f: (_: E, ...args: Args) => F,
10612 g: (_: F, ...args: Args) => G,
10613 h: (_: G, ...args: Args) => H,
10614 i: (_: H, ...args: Args) => I,
10615 j: (_: I, ...args: Args) => J,
10616 k: (_: J, ...args: Args) => K,
10617 l: (_: K, ...args: Args) => L,
10618 m: (_: L, ...args: Args) => M,
10619 n: (_: M, ...args: Args) => N,
10620 o: (_: N, ...args: Args) => O,
10621 p: (_: O, ...args: Args) => P,
10622 q: (_: P, ...args: Args) => Q
10623 ): (...args: Args) => Q
10624 <
10625 Self,
10626 Eff extends Effect<any, any, any>,
10627 AEff,
10628 Args extends Array<any>,
10629 A,
10630 B,
10631 C,
10632 D,
10633 E,
10634 F,
10635 G,
10636 H,
10637 I,
10638 J,
10639 K,
10640 L,
10641 M,
10642 N,
10643 O,
10644 P,
10645 Q
10646 >(
10647 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
10648 a: (
10649 _: Effect<
10650 AEff,
10651 [Eff] extends [never] ? never
10652 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10653 : never,
10654 [Eff] extends [never] ? never
10655 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10656 : never
10657 >,
10658 ...args: Args
10659 ) => A,
10660 b: (_: A, ...args: Args) => B,
10661 c: (_: B, ...args: Args) => C,
10662 d: (_: C, ...args: Args) => D,
10663 e: (_: D, ...args: Args) => E,
10664 f: (_: E, ...args: Args) => F,
10665 g: (_: F, ...args: Args) => G,
10666 h: (_: G, ...args: Args) => H,
10667 i: (_: H, ...args: Args) => I,
10668 j: (_: I, ...args: Args) => J,
10669 k: (_: J, ...args: Args) => K,
10670 l: (_: K, ...args: Args) => L,
10671 m: (_: L, ...args: Args) => M,
10672 n: (_: M, ...args: Args) => N,
10673 o: (_: N, ...args: Args) => O,
10674 p: (_: O, ...args: Args) => P,
10675 q: (_: P, ...args: Args) => Q
10676 ): (this: Self, ...args: Args) => Q
10677 <
10678 Eff extends Effect<any, any, any>,
10679 AEff,
10680 Args extends Array<any>,
10681 A,
10682 B,
10683 C,
10684 D,
10685 E,
10686 F,
10687 G,
10688 H,
10689 I,
10690 J,
10691 K,
10692 L,
10693 M,
10694 N,
10695 O,
10696 P,
10697 Q,
10698 R
10699 >(
10700 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
10701 a: (
10702 _: Effect<
10703 AEff,
10704 [Eff] extends [never] ? never
10705 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10706 : never,
10707 [Eff] extends [never] ? never
10708 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10709 : never
10710 >,
10711 ...args: Args
10712 ) => A,
10713 b: (_: A, ...args: Args) => B,
10714 c: (_: B, ...args: Args) => C,
10715 d: (_: C, ...args: Args) => D,
10716 e: (_: D, ...args: Args) => E,
10717 f: (_: E, ...args: Args) => F,
10718 g: (_: F, ...args: Args) => G,
10719 h: (_: G, ...args: Args) => H,
10720 i: (_: H, ...args: Args) => I,
10721 j: (_: I, ...args: Args) => J,
10722 k: (_: J, ...args: Args) => K,
10723 l: (_: K, ...args: Args) => L,
10724 m: (_: L, ...args: Args) => M,
10725 n: (_: M, ...args: Args) => N,
10726 o: (_: N, ...args: Args) => O,
10727 p: (_: O, ...args: Args) => P,
10728 q: (_: P, ...args: Args) => Q,
10729 r: (_: Q, ...args: Args) => R
10730 ): (...args: Args) => R
10731 <
10732 Self,
10733 Eff extends Effect<any, any, any>,
10734 AEff,
10735 Args extends Array<any>,
10736 A,
10737 B,
10738 C,
10739 D,
10740 E,
10741 F,
10742 G,
10743 H,
10744 I,
10745 J,
10746 K,
10747 L,
10748 M,
10749 N,
10750 O,
10751 P,
10752 Q,
10753 R
10754 >(
10755 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
10756 a: (
10757 _: Effect<
10758 AEff,
10759 [Eff] extends [never] ? never
10760 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10761 : never,
10762 [Eff] extends [never] ? never
10763 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10764 : never
10765 >,
10766 ...args: Args
10767 ) => A,
10768 b: (_: A, ...args: Args) => B,
10769 c: (_: B, ...args: Args) => C,
10770 d: (_: C, ...args: Args) => D,
10771 e: (_: D, ...args: Args) => E,
10772 f: (_: E, ...args: Args) => F,
10773 g: (_: F, ...args: Args) => G,
10774 h: (_: G, ...args: Args) => H,
10775 i: (_: H, ...args: Args) => I,
10776 j: (_: I, ...args: Args) => J,
10777 k: (_: J, ...args: Args) => K,
10778 l: (_: K, ...args: Args) => L,
10779 m: (_: L, ...args: Args) => M,
10780 n: (_: M, ...args: Args) => N,
10781 o: (_: N, ...args: Args) => O,
10782 p: (_: O, ...args: Args) => P,
10783 q: (_: P, ...args: Args) => Q,
10784 r: (_: Q, ...args: Args) => R
10785 ): (this: Self, ...args: Args) => R
10786 <
10787 Eff extends Effect<any, any, any>,
10788 AEff,
10789 Args extends Array<any>,
10790 A,
10791 B,
10792 C,
10793 D,
10794 E,
10795 F,
10796 G,
10797 H,
10798 I,
10799 J,
10800 K,
10801 L,
10802 M,
10803 N,
10804 O,
10805 P,
10806 Q,
10807 R,
10808 S
10809 >(
10810 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
10811 a: (
10812 _: Effect<
10813 AEff,
10814 [Eff] extends [never] ? never
10815 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10816 : never,
10817 [Eff] extends [never] ? never
10818 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10819 : never
10820 >,
10821 ...args: Args
10822 ) => A,
10823 b: (_: A, ...args: Args) => B,
10824 c: (_: B, ...args: Args) => C,
10825 d: (_: C, ...args: Args) => D,
10826 e: (_: D, ...args: Args) => E,
10827 f: (_: E, ...args: Args) => F,
10828 g: (_: F, ...args: Args) => G,
10829 h: (_: G, ...args: Args) => H,
10830 i: (_: H, ...args: Args) => I,
10831 j: (_: I, ...args: Args) => J,
10832 k: (_: J, ...args: Args) => K,
10833 l: (_: K, ...args: Args) => L,
10834 m: (_: L, ...args: Args) => M,
10835 n: (_: M, ...args: Args) => N,
10836 o: (_: N, ...args: Args) => O,
10837 p: (_: O, ...args: Args) => P,
10838 q: (_: P, ...args: Args) => Q,
10839 r: (_: Q, ...args: Args) => R,
10840 s: (_: R, ...args: Args) => S
10841 ): (...args: Args) => S
10842 <
10843 Self,
10844 Eff extends Effect<any, any, any>,
10845 AEff,
10846 Args extends Array<any>,
10847 A,
10848 B,
10849 C,
10850 D,
10851 E,
10852 F,
10853 G,
10854 H,
10855 I,
10856 J,
10857 K,
10858 L,
10859 M,
10860 N,
10861 O,
10862 P,
10863 Q,
10864 R,
10865 S
10866 >(
10867 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
10868 a: (
10869 _: Effect<
10870 AEff,
10871 [Eff] extends [never] ? never
10872 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10873 : never,
10874 [Eff] extends [never] ? never
10875 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10876 : never
10877 >,
10878 ...args: Args
10879 ) => A,
10880 b: (_: A, ...args: Args) => B,
10881 c: (_: B, ...args: Args) => C,
10882 d: (_: C, ...args: Args) => D,
10883 e: (_: D, ...args: Args) => E,
10884 f: (_: E, ...args: Args) => F,
10885 g: (_: F, ...args: Args) => G,
10886 h: (_: G, ...args: Args) => H,
10887 i: (_: H, ...args: Args) => I,
10888 j: (_: I, ...args: Args) => J,
10889 k: (_: J, ...args: Args) => K,
10890 l: (_: K, ...args: Args) => L,
10891 m: (_: L, ...args: Args) => M,
10892 n: (_: M, ...args: Args) => N,
10893 o: (_: N, ...args: Args) => O,
10894 p: (_: O, ...args: Args) => P,
10895 q: (_: P, ...args: Args) => Q,
10896 r: (_: Q, ...args: Args) => R,
10897 s: (_: R, ...args: Args) => S
10898 ): (this: Self, ...args: Args) => S
10899 <
10900 Eff extends Effect<any, any, any>,
10901 AEff,
10902 Args extends Array<any>,
10903 A,
10904 B,
10905 C,
10906 D,
10907 E,
10908 F,
10909 G,
10910 H,
10911 I,
10912 J,
10913 K,
10914 L,
10915 M,
10916 N,
10917 O,
10918 P,
10919 Q,
10920 R,
10921 S,
10922 T
10923 >(
10924 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never>,
10925 a: (
10926 _: Effect<
10927 AEff,
10928 [Eff] extends [never] ? never
10929 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10930 : never,
10931 [Eff] extends [never] ? never
10932 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10933 : never
10934 >,
10935 ...args: Args
10936 ) => A,
10937 b: (_: A, ...args: Args) => B,
10938 c: (_: B, ...args: Args) => C,
10939 d: (_: C, ...args: Args) => D,
10940 e: (_: D, ...args: Args) => E,
10941 f: (_: E, ...args: Args) => F,
10942 g: (_: F, ...args: Args) => G,
10943 h: (_: G, ...args: Args) => H,
10944 i: (_: H, ...args: Args) => I,
10945 j: (_: I, ...args: Args) => J,
10946 k: (_: J, ...args: Args) => K,
10947 l: (_: K, ...args: Args) => L,
10948 m: (_: L, ...args: Args) => M,
10949 n: (_: M, ...args: Args) => N,
10950 o: (_: N, ...args: Args) => O,
10951 p: (_: O, ...args: Args) => P,
10952 q: (_: P, ...args: Args) => Q,
10953 r: (_: Q, ...args: Args) => R,
10954 s: (_: R, ...args: Args) => S,
10955 t: (_: S, ...args: Args) => T
10956 ): (...args: Args) => T
10957 <
10958 Self,
10959 Eff extends Effect<any, any, any>,
10960 AEff,
10961 Args extends Array<any>,
10962 A,
10963 B,
10964 C,
10965 D,
10966 E,
10967 F,
10968 G,
10969 H,
10970 I,
10971 J,
10972 K,
10973 L,
10974 M,
10975 N,
10976 O,
10977 P,
10978 Q,
10979 R,
10980 S,
10981 T
10982 >(
10983 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never>,
10984 a: (
10985 _: Effect<
10986 AEff,
10987 [Eff] extends [never] ? never
10988 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
10989 : never,
10990 [Eff] extends [never] ? never
10991 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
10992 : never
10993 >,
10994 ...args: Args
10995 ) => A,
10996 b: (_: A, ...args: Args) => B,
10997 c: (_: B, ...args: Args) => C,
10998 d: (_: C, ...args: Args) => D,
10999 e: (_: D, ...args: Args) => E,
11000 f: (_: E, ...args: Args) => F,
11001 g: (_: F, ...args: Args) => G,
11002 h: (_: G, ...args: Args) => H,
11003 i: (_: H, ...args: Args) => I,
11004 j: (_: I, ...args: Args) => J,
11005 k: (_: J, ...args: Args) => K,
11006 l: (_: K, ...args: Args) => L,
11007 m: (_: L, ...args: Args) => M,
11008 n: (_: M, ...args: Args) => N,
11009 o: (_: N, ...args: Args) => O,
11010 p: (_: O, ...args: Args) => P,
11011 q: (_: P, ...args: Args) => Q,
11012 r: (_: Q, ...args: Args) => R,
11013 s: (_: R, ...args: Args) => S,
11014 t: (_: S, ...args: Args) => T
11015 ): (this: Self, ...args: Args) => T
11016 }
11017
11018 /**
11019 * Type of the traced function builder used by `Effect.fn`.
11020 *
11021 * @category utility types
11022 * @since 4.0.0
11023 */
11024 export type Traced = {
11025 <Eff extends Effect<any, any, any>, AEff, Args extends Array<any>>(
11026 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>)
11027 ): (...args: Args) => Effect<
11028 AEff,
11029 [Eff] extends [never] ? never
11030 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11031 : never,
11032 [Eff] extends [never] ? never
11033 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11034 : never
11035 >
11036 <Self, Eff extends Effect<any, any, any>, AEff, Args extends Array<any>>(
11037 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>)
11038 ): (this: Self, ...args: Args) => Effect<
11039 AEff,
11040 [Eff] extends [never] ? never
11041 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11042 : never,
11043 [Eff] extends [never] ? never
11044 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11045 : never
11046 >
11047 <Self, Eff extends Effect<any, any, any>, AEff, Args extends Array<any>>(
11048 options: { readonly self: Self },
11049 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>)
11050 ): (...args: Args) => Effect<
11051 AEff,
11052 [Eff] extends [never] ? never
11053 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11054 : never,
11055 [Eff] extends [never] ? never
11056 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11057 : never
11058 >
11059
11060 <Eff extends Effect<any, any, any>, AEff, Args extends Array<any>, A>(
11061 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11062 a: (
11063 _: Effect<
11064 AEff,
11065 [Eff] extends [never] ? never
11066 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11067 : never,
11068 [Eff] extends [never] ? never
11069 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11070 : never
11071 >,
11072 ...args: Args
11073 ) => A
11074 ): (...args: Args) => A
11075 <Self, Eff extends Effect<any, any, any>, AEff, Args extends Array<any>, A>(
11076 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11077 a: (
11078 _: Effect<
11079 AEff,
11080 [Eff] extends [never] ? never
11081 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11082 : never,
11083 [Eff] extends [never] ? never
11084 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11085 : never
11086 >,
11087 ...args: Args
11088 ) => A
11089 ): (this: Self, ...args: Args) => A
11090 <Self, Eff extends Effect<any, any, any>, AEff, Args extends Array<any>, A>(
11091 options: { readonly self: Self },
11092 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11093 a: (
11094 _: Effect<
11095 AEff,
11096 [Eff] extends [never] ? never
11097 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11098 : never,
11099 [Eff] extends [never] ? never
11100 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11101 : never
11102 >,
11103 ...args: Args
11104 ) => A
11105 ): (...args: Args) => A
11106
11107 <Eff extends Effect<any, any, any>, AEff, Args extends Array<any>, A, B>(
11108 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11109 a: (
11110 _: Effect<
11111 AEff,
11112 [Eff] extends [never] ? never
11113 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11114 : never,
11115 [Eff] extends [never] ? never
11116 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11117 : never
11118 >,
11119 ...args: Args
11120 ) => A,
11121 b: (_: A, ...args: Args) => B
11122 ): (...args: Args) => B
11123 <Self, Eff extends Effect<any, any, any>, AEff, Args extends Array<any>, A, B>(
11124 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11125 a: (
11126 _: Effect<
11127 AEff,
11128 [Eff] extends [never] ? never
11129 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11130 : never,
11131 [Eff] extends [never] ? never
11132 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11133 : never
11134 >,
11135 ...args: Args
11136 ) => A,
11137 b: (_: A, ...args: Args) => B
11138 ): (this: Self, ...args: Args) => B
11139 <Self, Eff extends Effect<any, any, any>, AEff, Args extends Array<any>, A, B>(
11140 options: { readonly self: Self },
11141 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11142 a: (
11143 _: Effect<
11144 AEff,
11145 [Eff] extends [never] ? never
11146 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11147 : never,
11148 [Eff] extends [never] ? never
11149 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11150 : never
11151 >,
11152 ...args: Args
11153 ) => A,
11154 b: (_: A, ...args: Args) => B
11155 ): (...args: Args) => B
11156
11157 <
11158 Eff extends Effect<any, any, any>,
11159 AEff,
11160 Args extends Array<any>,
11161 A,
11162 B,
11163 C
11164 >(
11165 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11166 a: (
11167 _: Effect<
11168 AEff,
11169 [Eff] extends [never] ? never
11170 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11171 : never,
11172 [Eff] extends [never] ? never
11173 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11174 : never
11175 >,
11176 ...args: Args
11177 ) => A,
11178 b: (_: A, ...args: Args) => B,
11179 c: (_: B, ...args: Args) => C
11180 ): (...args: Args) => C
11181 <
11182 Self,
11183 Eff extends Effect<any, any, any>,
11184 AEff,
11185 Args extends Array<any>,
11186 A,
11187 B,
11188 C
11189 >(
11190 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11191 a: (
11192 _: Effect<
11193 AEff,
11194 [Eff] extends [never] ? never
11195 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11196 : never,
11197 [Eff] extends [never] ? never
11198 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11199 : never
11200 >,
11201 ...args: Args
11202 ) => A,
11203 b: (_: A, ...args: Args) => B,
11204 c: (_: B, ...args: Args) => C
11205 ): (this: Self, ...args: Args) => C
11206 <
11207 Self,
11208 Eff extends Effect<any, any, any>,
11209 AEff,
11210 Args extends Array<any>,
11211 A,
11212 B,
11213 C
11214 >(
11215 options: { readonly self: Self },
11216 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11217 a: (
11218 _: Effect<
11219 AEff,
11220 [Eff] extends [never] ? never
11221 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11222 : never,
11223 [Eff] extends [never] ? never
11224 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11225 : never
11226 >,
11227 ...args: Args
11228 ) => A,
11229 b: (_: A, ...args: Args) => B,
11230 c: (_: B, ...args: Args) => C
11231 ): (...args: Args) => C
11232
11233 <
11234 Eff extends Effect<any, any, any>,
11235 AEff,
11236 Args extends Array<any>,
11237 A,
11238 B,
11239 C,
11240 D
11241 >(
11242 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11243 a: (
11244 _: Effect<
11245 AEff,
11246 [Eff] extends [never] ? never
11247 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11248 : never,
11249 [Eff] extends [never] ? never
11250 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11251 : never
11252 >,
11253 ...args: Args
11254 ) => A,
11255 b: (_: A, ...args: Args) => B,
11256 c: (_: B, ...args: Args) => C,
11257 d: (_: C, ...args: Args) => D
11258 ): (...args: Args) => D
11259 <
11260 Self,
11261 Eff extends Effect<any, any, any>,
11262 AEff,
11263 Args extends Array<any>,
11264 A,
11265 B,
11266 C,
11267 D
11268 >(
11269 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11270 a: (
11271 _: Effect<
11272 AEff,
11273 [Eff] extends [never] ? never
11274 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11275 : never,
11276 [Eff] extends [never] ? never
11277 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11278 : never
11279 >,
11280 ...args: Args
11281 ) => A,
11282 b: (_: A, ...args: Args) => B,
11283 c: (_: B, ...args: Args) => C,
11284 d: (_: C, ...args: Args) => D
11285 ): (this: Self, ...args: Args) => D
11286
11287 <
11288 Self,
11289 Eff extends Effect<any, any, any>,
11290 AEff,
11291 Args extends Array<any>,
11292 A,
11293 B,
11294 C,
11295 D
11296 >(
11297 options: { readonly self: Self },
11298 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11299 a: (
11300 _: Effect<
11301 AEff,
11302 [Eff] extends [never] ? never
11303 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11304 : never,
11305 [Eff] extends [never] ? never
11306 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11307 : never
11308 >,
11309 ...args: Args
11310 ) => A,
11311 b: (_: A, ...args: Args) => B,
11312 c: (_: B, ...args: Args) => C,
11313 d: (_: C, ...args: Args) => D
11314 ): (...args: Args) => D
11315
11316 <
11317 Eff extends Effect<any, any, any>,
11318 AEff,
11319 Args extends Array<any>,
11320 A,
11321 B,
11322 C,
11323 D,
11324 E
11325 >(
11326 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11327 a: (
11328 _: Effect<
11329 AEff,
11330 [Eff] extends [never] ? never
11331 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11332 : never,
11333 [Eff] extends [never] ? never
11334 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11335 : never
11336 >,
11337 ...args: Args
11338 ) => A,
11339 b: (_: A, ...args: Args) => B,
11340 c: (_: B, ...args: Args) => C,
11341 d: (_: C, ...args: Args) => D,
11342 e: (_: D, ...args: Args) => E
11343 ): (...args: Args) => E
11344 <
11345 Self,
11346 Eff extends Effect<any, any, any>,
11347 AEff,
11348 Args extends Array<any>,
11349 A,
11350 B,
11351 C,
11352 D,
11353 E
11354 >(
11355 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11356 a: (
11357 _: Effect<
11358 AEff,
11359 [Eff] extends [never] ? never
11360 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11361 : never,
11362 [Eff] extends [never] ? never
11363 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11364 : never
11365 >,
11366 ...args: Args
11367 ) => A,
11368 b: (_: A, ...args: Args) => B,
11369 c: (_: B, ...args: Args) => C,
11370 d: (_: C, ...args: Args) => D,
11371 e: (_: D, ...args: Args) => E
11372 ): (this: Self, ...args: Args) => E
11373
11374 <
11375 Self,
11376 Eff extends Effect<any, any, any>,
11377 AEff,
11378 Args extends Array<any>,
11379 A,
11380 B,
11381 C,
11382 D,
11383 E
11384 >(
11385 options: { readonly self: Self },
11386 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11387 a: (
11388 _: Effect<
11389 AEff,
11390 [Eff] extends [never] ? never
11391 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11392 : never,
11393 [Eff] extends [never] ? never
11394 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11395 : never
11396 >,
11397 ...args: Args
11398 ) => A,
11399 b: (_: A, ...args: Args) => B,
11400 c: (_: B, ...args: Args) => C,
11401 d: (_: C, ...args: Args) => D,
11402 e: (_: D, ...args: Args) => E
11403 ): (...args: Args) => E
11404
11405 <
11406 Eff extends Effect<any, any, any>,
11407 AEff,
11408 Args extends Array<any>,
11409 A,
11410 B,
11411 C,
11412 D,
11413 E,
11414 F
11415 >(
11416 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11417 a: (
11418 _: Effect<
11419 AEff,
11420 [Eff] extends [never] ? never
11421 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11422 : never,
11423 [Eff] extends [never] ? never
11424 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11425 : never
11426 >,
11427 ...args: Args
11428 ) => A,
11429 b: (_: A, ...args: Args) => B,
11430 c: (_: B, ...args: Args) => C,
11431 d: (_: C, ...args: Args) => D,
11432 e: (_: D, ...args: Args) => E,
11433 f: (_: E, ...args: Args) => F
11434 ): (...args: Args) => F
11435 <
11436 Self,
11437 Eff extends Effect<any, any, any>,
11438 AEff,
11439 Args extends Array<any>,
11440 A,
11441 B,
11442 C,
11443 D,
11444 E,
11445 F
11446 >(
11447 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11448 a: (
11449 _: Effect<
11450 AEff,
11451 [Eff] extends [never] ? never
11452 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11453 : never,
11454 [Eff] extends [never] ? never
11455 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11456 : never
11457 >,
11458 ...args: Args
11459 ) => A,
11460 b: (_: A, ...args: Args) => B,
11461 c: (_: B, ...args: Args) => C,
11462 d: (_: C, ...args: Args) => D,
11463 e: (_: D, ...args: Args) => E,
11464 f: (_: E, ...args: Args) => F
11465 ): (this: Self, ...args: Args) => F
11466
11467 <
11468 Self,
11469 Eff extends Effect<any, any, any>,
11470 AEff,
11471 Args extends Array<any>,
11472 A,
11473 B,
11474 C,
11475 D,
11476 E,
11477 F
11478 >(
11479 options: { readonly self: Self },
11480 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11481 a: (
11482 _: Effect<
11483 AEff,
11484 [Eff] extends [never] ? never
11485 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11486 : never,
11487 [Eff] extends [never] ? never
11488 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11489 : never
11490 >,
11491 ...args: Args
11492 ) => A,
11493 b: (_: A, ...args: Args) => B,
11494 c: (_: B, ...args: Args) => C,
11495 d: (_: C, ...args: Args) => D,
11496 e: (_: D, ...args: Args) => E,
11497 f: (_: E, ...args: Args) => F
11498 ): (...args: Args) => F
11499
11500 <
11501 Eff extends Effect<any, any, any>,
11502 AEff,
11503 Args extends Array<any>,
11504 A,
11505 B,
11506 C,
11507 D,
11508 E,
11509 F,
11510 G
11511 >(
11512 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11513 a: (
11514 _: Effect<
11515 AEff,
11516 [Eff] extends [never] ? never
11517 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11518 : never,
11519 [Eff] extends [never] ? never
11520 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11521 : never
11522 >,
11523 ...args: Args
11524 ) => A,
11525 b: (_: A, ...args: Args) => B,
11526 c: (_: B, ...args: Args) => C,
11527 d: (_: C, ...args: Args) => D,
11528 e: (_: D, ...args: Args) => E,
11529 f: (_: E, ...args: Args) => F,
11530 g: (_: F, ...args: Args) => G
11531 ): (...args: Args) => G
11532 <
11533 Self,
11534 Eff extends Effect<any, any, any>,
11535 AEff,
11536 Args extends Array<any>,
11537 A,
11538 B,
11539 C,
11540 D,
11541 E,
11542 F,
11543 G
11544 >(
11545 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11546 a: (
11547 _: Effect<
11548 AEff,
11549 [Eff] extends [never] ? never
11550 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11551 : never,
11552 [Eff] extends [never] ? never
11553 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11554 : never
11555 >,
11556 ...args: Args
11557 ) => A,
11558 b: (_: A, ...args: Args) => B,
11559 c: (_: B, ...args: Args) => C,
11560 d: (_: C, ...args: Args) => D,
11561 e: (_: D, ...args: Args) => E,
11562 f: (_: E, ...args: Args) => F,
11563 g: (_: F, ...args: Args) => G
11564 ): (this: Self, ...args: Args) => G
11565
11566 <
11567 Self,
11568 Eff extends Effect<any, any, any>,
11569 AEff,
11570 Args extends Array<any>,
11571 A,
11572 B,
11573 C,
11574 D,
11575 E,
11576 F,
11577 G
11578 >(
11579 options: { readonly self: Self },
11580 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11581 a: (
11582 _: Effect<
11583 AEff,
11584 [Eff] extends [never] ? never
11585 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11586 : never,
11587 [Eff] extends [never] ? never
11588 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11589 : never
11590 >,
11591 ...args: Args
11592 ) => A,
11593 b: (_: A, ...args: Args) => B,
11594 c: (_: B, ...args: Args) => C,
11595 d: (_: C, ...args: Args) => D,
11596 e: (_: D, ...args: Args) => E,
11597 f: (_: E, ...args: Args) => F,
11598 g: (_: F, ...args: Args) => G
11599 ): (...args: Args) => G
11600
11601 <
11602 Eff extends Effect<any, any, any>,
11603 AEff,
11604 Args extends Array<any>,
11605 A,
11606 B,
11607 C,
11608 D,
11609 E,
11610 F,
11611 G,
11612 H
11613 >(
11614 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11615 a: (
11616 _: Effect<
11617 AEff,
11618 [Eff] extends [never] ? never
11619 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11620 : never,
11621 [Eff] extends [never] ? never
11622 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11623 : never
11624 >,
11625 ...args: Args
11626 ) => A,
11627 b: (_: A, ...args: Args) => B,
11628 c: (_: B, ...args: Args) => C,
11629 d: (_: C, ...args: Args) => D,
11630 e: (_: D, ...args: Args) => E,
11631 f: (_: E, ...args: Args) => F,
11632 g: (_: F, ...args: Args) => G,
11633 h: (_: G, ...args: Args) => H
11634 ): (...args: Args) => H
11635 <
11636 Self,
11637 Eff extends Effect<any, any, any>,
11638 AEff,
11639 Args extends Array<any>,
11640 A,
11641 B,
11642 C,
11643 D,
11644 E,
11645 F,
11646 G,
11647 H
11648 >(
11649 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11650 a: (
11651 _: Effect<
11652 AEff,
11653 [Eff] extends [never] ? never
11654 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11655 : never,
11656 [Eff] extends [never] ? never
11657 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11658 : never
11659 >,
11660 ...args: Args
11661 ) => A,
11662 b: (_: A, ...args: Args) => B,
11663 c: (_: B, ...args: Args) => C,
11664 d: (_: C, ...args: Args) => D,
11665 e: (_: D, ...args: Args) => E,
11666 f: (_: E, ...args: Args) => F,
11667 g: (_: F, ...args: Args) => G,
11668 h: (_: G, ...args: Args) => H
11669 ): (this: Self, ...args: Args) => H
11670
11671 <
11672 Self,
11673 Eff extends Effect<any, any, any>,
11674 AEff,
11675 Args extends Array<any>,
11676 A,
11677 B,
11678 C,
11679 D,
11680 E,
11681 F,
11682 G,
11683 H
11684 >(
11685 options: { readonly self: Self },
11686 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11687 a: (
11688 _: Effect<
11689 AEff,
11690 [Eff] extends [never] ? never
11691 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11692 : never,
11693 [Eff] extends [never] ? never
11694 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11695 : never
11696 >,
11697 ...args: Args
11698 ) => A,
11699 b: (_: A, ...args: Args) => B,
11700 c: (_: B, ...args: Args) => C,
11701 d: (_: C, ...args: Args) => D,
11702 e: (_: D, ...args: Args) => E,
11703 f: (_: E, ...args: Args) => F,
11704 g: (_: F, ...args: Args) => G,
11705 h: (_: G, ...args: Args) => H
11706 ): (...args: Args) => H
11707
11708 <
11709 Eff extends Effect<any, any, any>,
11710 AEff,
11711 Args extends Array<any>,
11712 A,
11713 B,
11714 C,
11715 D,
11716 E,
11717 F,
11718 G,
11719 H,
11720 I
11721 >(
11722 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11723 a: (
11724 _: Effect<
11725 AEff,
11726 [Eff] extends [never] ? never
11727 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11728 : never,
11729 [Eff] extends [never] ? never
11730 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11731 : never
11732 >,
11733 ...args: Args
11734 ) => A,
11735 b: (_: A, ...args: Args) => B,
11736 c: (_: B, ...args: Args) => C,
11737 d: (_: C, ...args: Args) => D,
11738 e: (_: D, ...args: Args) => E,
11739 f: (_: E, ...args: Args) => F,
11740 g: (_: F, ...args: Args) => G,
11741 h: (_: G, ...args: Args) => H,
11742 i: (_: H, ...args: Args) => I
11743 ): (...args: Args) => I
11744 <
11745 Self,
11746 Eff extends Effect<any, any, any>,
11747 AEff,
11748 Args extends Array<any>,
11749 A,
11750 B,
11751 C,
11752 D,
11753 E,
11754 F,
11755 G,
11756 H,
11757 I
11758 >(
11759 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11760 a: (
11761 _: Effect<
11762 AEff,
11763 [Eff] extends [never] ? never
11764 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11765 : never,
11766 [Eff] extends [never] ? never
11767 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11768 : never
11769 >,
11770 ...args: Args
11771 ) => A,
11772 b: (_: A, ...args: Args) => B,
11773 c: (_: B, ...args: Args) => C,
11774 d: (_: C, ...args: Args) => D,
11775 e: (_: D, ...args: Args) => E,
11776 f: (_: E, ...args: Args) => F,
11777 g: (_: F, ...args: Args) => G,
11778 h: (_: G, ...args: Args) => H,
11779 i: (_: H, ...args: Args) => I
11780 ): (this: Self, ...args: Args) => I
11781
11782 <
11783 Self,
11784 Eff extends Effect<any, any, any>,
11785 AEff,
11786 Args extends Array<any>,
11787 A,
11788 B,
11789 C,
11790 D,
11791 E,
11792 F,
11793 G,
11794 H,
11795 I
11796 >(
11797 options: { readonly self: Self },
11798 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11799 a: (
11800 _: Effect<
11801 AEff,
11802 [Eff] extends [never] ? never
11803 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11804 : never,
11805 [Eff] extends [never] ? never
11806 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11807 : never
11808 >,
11809 ...args: Args
11810 ) => A,
11811 b: (_: A, ...args: Args) => B,
11812 c: (_: B, ...args: Args) => C,
11813 d: (_: C, ...args: Args) => D,
11814 e: (_: D, ...args: Args) => E,
11815 f: (_: E, ...args: Args) => F,
11816 g: (_: F, ...args: Args) => G,
11817 h: (_: G, ...args: Args) => H,
11818 i: (_: H, ...args: Args) => I
11819 ): (...args: Args) => I
11820
11821 <
11822 Eff extends Effect<any, any, any>,
11823 AEff,
11824 Args extends Array<any>,
11825 A,
11826 B,
11827 C,
11828 D,
11829 E,
11830 F,
11831 G,
11832 H,
11833 I,
11834 J
11835 >(
11836 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11837 a: (
11838 _: Effect<
11839 AEff,
11840 [Eff] extends [never] ? never
11841 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11842 : never,
11843 [Eff] extends [never] ? never
11844 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11845 : never
11846 >,
11847 ...args: Args
11848 ) => A,
11849 b: (_: A, ...args: Args) => B,
11850 c: (_: B, ...args: Args) => C,
11851 d: (_: C, ...args: Args) => D,
11852 e: (_: D, ...args: Args) => E,
11853 f: (_: E, ...args: Args) => F,
11854 g: (_: F, ...args: Args) => G,
11855 h: (_: G, ...args: Args) => H,
11856 i: (_: H, ...args: Args) => I,
11857 j: (_: I, ...args: Args) => J
11858 ): (...args: Args) => J
11859 <
11860 Self,
11861 Eff extends Effect<any, any, any>,
11862 AEff,
11863 Args extends Array<any>,
11864 A,
11865 B,
11866 C,
11867 D,
11868 E,
11869 F,
11870 G,
11871 H,
11872 I,
11873 J
11874 >(
11875 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11876 a: (
11877 _: Effect<
11878 AEff,
11879 [Eff] extends [never] ? never
11880 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11881 : never,
11882 [Eff] extends [never] ? never
11883 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11884 : never
11885 >,
11886 ...args: Args
11887 ) => A,
11888 b: (_: A, ...args: Args) => B,
11889 c: (_: B, ...args: Args) => C,
11890 d: (_: C, ...args: Args) => D,
11891 e: (_: D, ...args: Args) => E,
11892 f: (_: E, ...args: Args) => F,
11893 g: (_: F, ...args: Args) => G,
11894 h: (_: G, ...args: Args) => H,
11895 i: (_: H, ...args: Args) => I,
11896 j: (_: I, ...args: Args) => J
11897 ): (this: Self, ...args: Args) => J
11898
11899 <
11900 Self,
11901 Eff extends Effect<any, any, any>,
11902 AEff,
11903 Args extends Array<any>,
11904 A,
11905 B,
11906 C,
11907 D,
11908 E,
11909 F,
11910 G,
11911 H,
11912 I,
11913 J
11914 >(
11915 options: { readonly self: Self },
11916 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11917 a: (
11918 _: Effect<
11919 AEff,
11920 [Eff] extends [never] ? never
11921 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11922 : never,
11923 [Eff] extends [never] ? never
11924 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11925 : never
11926 >,
11927 ...args: Args
11928 ) => A,
11929 b: (_: A, ...args: Args) => B,
11930 c: (_: B, ...args: Args) => C,
11931 d: (_: C, ...args: Args) => D,
11932 e: (_: D, ...args: Args) => E,
11933 f: (_: E, ...args: Args) => F,
11934 g: (_: F, ...args: Args) => G,
11935 h: (_: G, ...args: Args) => H,
11936 i: (_: H, ...args: Args) => I,
11937 j: (_: I, ...args: Args) => J
11938 ): (...args: Args) => J
11939
11940 <
11941 Eff extends Effect<any, any, any>,
11942 AEff,
11943 Args extends Array<any>,
11944 A,
11945 B,
11946 C,
11947 D,
11948 E,
11949 F,
11950 G,
11951 H,
11952 I,
11953 J,
11954 K
11955 >(
11956 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11957 a: (
11958 _: Effect<
11959 AEff,
11960 [Eff] extends [never] ? never
11961 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
11962 : never,
11963 [Eff] extends [never] ? never
11964 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
11965 : never
11966 >,
11967 ...args: Args
11968 ) => A,
11969 b: (_: A, ...args: Args) => B,
11970 c: (_: B, ...args: Args) => C,
11971 d: (_: C, ...args: Args) => D,
11972 e: (_: D, ...args: Args) => E,
11973 f: (_: E, ...args: Args) => F,
11974 g: (_: F, ...args: Args) => G,
11975 h: (_: G, ...args: Args) => H,
11976 i: (_: H, ...args: Args) => I,
11977 j: (_: I, ...args: Args) => J,
11978 k: (_: J, ...args: Args) => K
11979 ): (...args: Args) => K
11980 <
11981 Self,
11982 Eff extends Effect<any, any, any>,
11983 AEff,
11984 Args extends Array<any>,
11985 A,
11986 B,
11987 C,
11988 D,
11989 E,
11990 F,
11991 G,
11992 H,
11993 I,
11994 J,
11995 K
11996 >(
11997 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
11998 a: (
11999 _: Effect<
12000 AEff,
12001 [Eff] extends [never] ? never
12002 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12003 : never,
12004 [Eff] extends [never] ? never
12005 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12006 : never
12007 >,
12008 ...args: Args
12009 ) => A,
12010 b: (_: A, ...args: Args) => B,
12011 c: (_: B, ...args: Args) => C,
12012 d: (_: C, ...args: Args) => D,
12013 e: (_: D, ...args: Args) => E,
12014 f: (_: E, ...args: Args) => F,
12015 g: (_: F, ...args: Args) => G,
12016 h: (_: G, ...args: Args) => H,
12017 i: (_: H, ...args: Args) => I,
12018 j: (_: I, ...args: Args) => J,
12019 k: (_: J, ...args: Args) => K
12020 ): (this: Self, ...args: Args) => K
12021
12022 <
12023 Self,
12024 Eff extends Effect<any, any, any>,
12025 AEff,
12026 Args extends Array<any>,
12027 A,
12028 B,
12029 C,
12030 D,
12031 E,
12032 F,
12033 G,
12034 H,
12035 I,
12036 J,
12037 K
12038 >(
12039 options: { readonly self: Self },
12040 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12041 a: (
12042 _: Effect<
12043 AEff,
12044 [Eff] extends [never] ? never
12045 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12046 : never,
12047 [Eff] extends [never] ? never
12048 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12049 : never
12050 >,
12051 ...args: Args
12052 ) => A,
12053 b: (_: A, ...args: Args) => B,
12054 c: (_: B, ...args: Args) => C,
12055 d: (_: C, ...args: Args) => D,
12056 e: (_: D, ...args: Args) => E,
12057 f: (_: E, ...args: Args) => F,
12058 g: (_: F, ...args: Args) => G,
12059 h: (_: G, ...args: Args) => H,
12060 i: (_: H, ...args: Args) => I,
12061 j: (_: I, ...args: Args) => J,
12062 k: (_: J, ...args: Args) => K
12063 ): (...args: Args) => K
12064
12065 <
12066 Eff extends Effect<any, any, any>,
12067 AEff,
12068 Args extends Array<any>,
12069 A,
12070 B,
12071 C,
12072 D,
12073 E,
12074 F,
12075 G,
12076 H,
12077 I,
12078 J,
12079 K,
12080 L
12081 >(
12082 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12083 a: (
12084 _: Effect<
12085 AEff,
12086 [Eff] extends [never] ? never
12087 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12088 : never,
12089 [Eff] extends [never] ? never
12090 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12091 : never
12092 >,
12093 ...args: Args
12094 ) => A,
12095 b: (_: A, ...args: Args) => B,
12096 c: (_: B, ...args: Args) => C,
12097 d: (_: C, ...args: Args) => D,
12098 e: (_: D, ...args: Args) => E,
12099 f: (_: E, ...args: Args) => F,
12100 g: (_: F, ...args: Args) => G,
12101 h: (_: G, ...args: Args) => H,
12102 i: (_: H, ...args: Args) => I,
12103 j: (_: I, ...args: Args) => J,
12104 k: (_: J, ...args: Args) => K,
12105 l: (_: K, ...args: Args) => L
12106 ): (...args: Args) => L
12107 <
12108 Self,
12109 Eff extends Effect<any, any, any>,
12110 AEff,
12111 Args extends Array<any>,
12112 A,
12113 B,
12114 C,
12115 D,
12116 E,
12117 F,
12118 G,
12119 H,
12120 I,
12121 J,
12122 K,
12123 L
12124 >(
12125 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12126 a: (
12127 _: Effect<
12128 AEff,
12129 [Eff] extends [never] ? never
12130 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12131 : never,
12132 [Eff] extends [never] ? never
12133 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12134 : never
12135 >,
12136 ...args: Args
12137 ) => A,
12138 b: (_: A, ...args: Args) => B,
12139 c: (_: B, ...args: Args) => C,
12140 d: (_: C, ...args: Args) => D,
12141 e: (_: D, ...args: Args) => E,
12142 f: (_: E, ...args: Args) => F,
12143 g: (_: F, ...args: Args) => G,
12144 h: (_: G, ...args: Args) => H,
12145 i: (_: H, ...args: Args) => I,
12146 j: (_: I, ...args: Args) => J,
12147 k: (_: J, ...args: Args) => K,
12148 l: (_: K, ...args: Args) => L
12149 ): (this: Self, ...args: Args) => L
12150
12151 <
12152 Self,
12153 Eff extends Effect<any, any, any>,
12154 AEff,
12155 Args extends Array<any>,
12156 A,
12157 B,
12158 C,
12159 D,
12160 E,
12161 F,
12162 G,
12163 H,
12164 I,
12165 J,
12166 K,
12167 L
12168 >(
12169 options: { readonly self: Self },
12170 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12171 a: (
12172 _: Effect<
12173 AEff,
12174 [Eff] extends [never] ? never
12175 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12176 : never,
12177 [Eff] extends [never] ? never
12178 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12179 : never
12180 >,
12181 ...args: Args
12182 ) => A,
12183 b: (_: A, ...args: Args) => B,
12184 c: (_: B, ...args: Args) => C,
12185 d: (_: C, ...args: Args) => D,
12186 e: (_: D, ...args: Args) => E,
12187 f: (_: E, ...args: Args) => F,
12188 g: (_: F, ...args: Args) => G,
12189 h: (_: G, ...args: Args) => H,
12190 i: (_: H, ...args: Args) => I,
12191 j: (_: I, ...args: Args) => J,
12192 k: (_: J, ...args: Args) => K,
12193 l: (_: K, ...args: Args) => L
12194 ): (...args: Args) => L
12195
12196 <
12197 Eff extends Effect<any, any, any>,
12198 AEff,
12199 Args extends Array<any>,
12200 A,
12201 B,
12202 C,
12203 D,
12204 E,
12205 F,
12206 G,
12207 H,
12208 I,
12209 J,
12210 K,
12211 L,
12212 M
12213 >(
12214 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12215 a: (
12216 _: Effect<
12217 AEff,
12218 [Eff] extends [never] ? never
12219 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12220 : never,
12221 [Eff] extends [never] ? never
12222 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12223 : never
12224 >,
12225 ...args: Args
12226 ) => A,
12227 b: (_: A, ...args: Args) => B,
12228 c: (_: B, ...args: Args) => C,
12229 d: (_: C, ...args: Args) => D,
12230 e: (_: D, ...args: Args) => E,
12231 f: (_: E, ...args: Args) => F,
12232 g: (_: F, ...args: Args) => G,
12233 h: (_: G, ...args: Args) => H,
12234 i: (_: H, ...args: Args) => I,
12235 j: (_: I, ...args: Args) => J,
12236 k: (_: J, ...args: Args) => K,
12237 l: (_: K, ...args: Args) => L,
12238 m: (_: L, ...args: Args) => M
12239 ): (...args: Args) => M
12240 <
12241 Self,
12242 Eff extends Effect<any, any, any>,
12243 AEff,
12244 Args extends Array<any>,
12245 A,
12246 B,
12247 C,
12248 D,
12249 E,
12250 F,
12251 G,
12252 H,
12253 I,
12254 J,
12255 K,
12256 L,
12257 M
12258 >(
12259 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12260 a: (
12261 _: Effect<
12262 AEff,
12263 [Eff] extends [never] ? never
12264 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12265 : never,
12266 [Eff] extends [never] ? never
12267 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12268 : never
12269 >,
12270 ...args: Args
12271 ) => A,
12272 b: (_: A, ...args: Args) => B,
12273 c: (_: B, ...args: Args) => C,
12274 d: (_: C, ...args: Args) => D,
12275 e: (_: D, ...args: Args) => E,
12276 f: (_: E, ...args: Args) => F,
12277 g: (_: F, ...args: Args) => G,
12278 h: (_: G, ...args: Args) => H,
12279 i: (_: H, ...args: Args) => I,
12280 j: (_: I, ...args: Args) => J,
12281 k: (_: J, ...args: Args) => K,
12282 l: (_: K, ...args: Args) => L,
12283 m: (_: L, ...args: Args) => M
12284 ): (this: Self, ...args: Args) => M
12285
12286 <
12287 Self,
12288 Eff extends Effect<any, any, any>,
12289 AEff,
12290 Args extends Array<any>,
12291 A,
12292 B,
12293 C,
12294 D,
12295 E,
12296 F,
12297 G,
12298 H,
12299 I,
12300 J,
12301 K,
12302 L,
12303 M
12304 >(
12305 options: { readonly self: Self },
12306 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12307 a: (
12308 _: Effect<
12309 AEff,
12310 [Eff] extends [never] ? never
12311 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12312 : never,
12313 [Eff] extends [never] ? never
12314 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12315 : never
12316 >,
12317 ...args: Args
12318 ) => A,
12319 b: (_: A, ...args: Args) => B,
12320 c: (_: B, ...args: Args) => C,
12321 d: (_: C, ...args: Args) => D,
12322 e: (_: D, ...args: Args) => E,
12323 f: (_: E, ...args: Args) => F,
12324 g: (_: F, ...args: Args) => G,
12325 h: (_: G, ...args: Args) => H,
12326 i: (_: H, ...args: Args) => I,
12327 j: (_: I, ...args: Args) => J,
12328 k: (_: J, ...args: Args) => K,
12329 l: (_: K, ...args: Args) => L,
12330 m: (_: L, ...args: Args) => M
12331 ): (...args: Args) => M
12332
12333 <
12334 Eff extends Effect<any, any, any>,
12335 AEff,
12336 Args extends Array<any>,
12337 A,
12338 B,
12339 C,
12340 D,
12341 E,
12342 F,
12343 G,
12344 H,
12345 I,
12346 J,
12347 K,
12348 L,
12349 M,
12350 N
12351 >(
12352 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12353 a: (
12354 _: Effect<
12355 AEff,
12356 [Eff] extends [never] ? never
12357 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12358 : never,
12359 [Eff] extends [never] ? never
12360 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12361 : never
12362 >,
12363 ...args: Args
12364 ) => A,
12365 b: (_: A, ...args: Args) => B,
12366 c: (_: B, ...args: Args) => C,
12367 d: (_: C, ...args: Args) => D,
12368 e: (_: D, ...args: Args) => E,
12369 f: (_: E, ...args: Args) => F,
12370 g: (_: F, ...args: Args) => G,
12371 h: (_: G, ...args: Args) => H,
12372 i: (_: H, ...args: Args) => I,
12373 j: (_: I, ...args: Args) => J,
12374 k: (_: J, ...args: Args) => K,
12375 l: (_: K, ...args: Args) => L,
12376 m: (_: L, ...args: Args) => M,
12377 n: (_: M, ...args: Args) => N
12378 ): (...args: Args) => N
12379 <
12380 Self,
12381 Eff extends Effect<any, any, any>,
12382 AEff,
12383 Args extends Array<any>,
12384 A,
12385 B,
12386 C,
12387 D,
12388 E,
12389 F,
12390 G,
12391 H,
12392 I,
12393 J,
12394 K,
12395 L,
12396 M,
12397 N
12398 >(
12399 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12400 a: (
12401 _: Effect<
12402 AEff,
12403 [Eff] extends [never] ? never
12404 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12405 : never,
12406 [Eff] extends [never] ? never
12407 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12408 : never
12409 >,
12410 ...args: Args
12411 ) => A,
12412 b: (_: A, ...args: Args) => B,
12413 c: (_: B, ...args: Args) => C,
12414 d: (_: C, ...args: Args) => D,
12415 e: (_: D, ...args: Args) => E,
12416 f: (_: E, ...args: Args) => F,
12417 g: (_: F, ...args: Args) => G,
12418 h: (_: G, ...args: Args) => H,
12419 i: (_: H, ...args: Args) => I,
12420 j: (_: I, ...args: Args) => J,
12421 k: (_: J, ...args: Args) => K,
12422 l: (_: K, ...args: Args) => L,
12423 m: (_: L, ...args: Args) => M,
12424 n: (_: M, ...args: Args) => N
12425 ): (this: Self, ...args: Args) => N
12426
12427 <
12428 Self,
12429 Eff extends Effect<any, any, any>,
12430 AEff,
12431 Args extends Array<any>,
12432 A,
12433 B,
12434 C,
12435 D,
12436 E,
12437 F,
12438 G,
12439 H,
12440 I,
12441 J,
12442 K,
12443 L,
12444 M,
12445 N
12446 >(
12447 options: { readonly self: Self },
12448 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12449 a: (
12450 _: Effect<
12451 AEff,
12452 [Eff] extends [never] ? never
12453 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12454 : never,
12455 [Eff] extends [never] ? never
12456 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12457 : never
12458 >,
12459 ...args: Args
12460 ) => A,
12461 b: (_: A, ...args: Args) => B,
12462 c: (_: B, ...args: Args) => C,
12463 d: (_: C, ...args: Args) => D,
12464 e: (_: D, ...args: Args) => E,
12465 f: (_: E, ...args: Args) => F,
12466 g: (_: F, ...args: Args) => G,
12467 h: (_: G, ...args: Args) => H,
12468 i: (_: H, ...args: Args) => I,
12469 j: (_: I, ...args: Args) => J,
12470 k: (_: J, ...args: Args) => K,
12471 l: (_: K, ...args: Args) => L,
12472 m: (_: L, ...args: Args) => M,
12473 n: (_: M, ...args: Args) => N
12474 ): (...args: Args) => N
12475
12476 <
12477 Eff extends Effect<any, any, any>,
12478 AEff,
12479 Args extends Array<any>,
12480 A,
12481 B,
12482 C,
12483 D,
12484 E,
12485 F,
12486 G,
12487 H,
12488 I,
12489 J,
12490 K,
12491 L,
12492 M,
12493 N,
12494 O
12495 >(
12496 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12497 a: (
12498 _: Effect<
12499 AEff,
12500 [Eff] extends [never] ? never
12501 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12502 : never,
12503 [Eff] extends [never] ? never
12504 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12505 : never
12506 >,
12507 ...args: Args
12508 ) => A,
12509 b: (_: A, ...args: Args) => B,
12510 c: (_: B, ...args: Args) => C,
12511 d: (_: C, ...args: Args) => D,
12512 e: (_: D, ...args: Args) => E,
12513 f: (_: E, ...args: Args) => F,
12514 g: (_: F, ...args: Args) => G,
12515 h: (_: G, ...args: Args) => H,
12516 i: (_: H, ...args: Args) => I,
12517 j: (_: I, ...args: Args) => J,
12518 k: (_: J, ...args: Args) => K,
12519 l: (_: K, ...args: Args) => L,
12520 m: (_: L, ...args: Args) => M,
12521 n: (_: M, ...args: Args) => N,
12522 o: (_: N, ...args: Args) => O
12523 ): (...args: Args) => O
12524 <
12525 Self,
12526 Eff extends Effect<any, any, any>,
12527 AEff,
12528 Args extends Array<any>,
12529 A,
12530 B,
12531 C,
12532 D,
12533 E,
12534 F,
12535 G,
12536 H,
12537 I,
12538 J,
12539 K,
12540 L,
12541 M,
12542 N,
12543 O
12544 >(
12545 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12546 a: (
12547 _: Effect<
12548 AEff,
12549 [Eff] extends [never] ? never
12550 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12551 : never,
12552 [Eff] extends [never] ? never
12553 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12554 : never
12555 >,
12556 ...args: Args
12557 ) => A,
12558 b: (_: A, ...args: Args) => B,
12559 c: (_: B, ...args: Args) => C,
12560 d: (_: C, ...args: Args) => D,
12561 e: (_: D, ...args: Args) => E,
12562 f: (_: E, ...args: Args) => F,
12563 g: (_: F, ...args: Args) => G,
12564 h: (_: G, ...args: Args) => H,
12565 i: (_: H, ...args: Args) => I,
12566 j: (_: I, ...args: Args) => J,
12567 k: (_: J, ...args: Args) => K,
12568 l: (_: K, ...args: Args) => L,
12569 m: (_: L, ...args: Args) => M,
12570 n: (_: M, ...args: Args) => N,
12571 o: (_: N, ...args: Args) => O
12572 ): (this: Self, ...args: Args) => O
12573
12574 <
12575 Self,
12576 Eff extends Effect<any, any, any>,
12577 AEff,
12578 Args extends Array<any>,
12579 A,
12580 B,
12581 C,
12582 D,
12583 E,
12584 F,
12585 G,
12586 H,
12587 I,
12588 J,
12589 K,
12590 L,
12591 M,
12592 N,
12593 O
12594 >(
12595 options: { readonly self: Self },
12596 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12597 a: (
12598 _: Effect<
12599 AEff,
12600 [Eff] extends [never] ? never
12601 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12602 : never,
12603 [Eff] extends [never] ? never
12604 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12605 : never
12606 >,
12607 ...args: Args
12608 ) => A,
12609 b: (_: A, ...args: Args) => B,
12610 c: (_: B, ...args: Args) => C,
12611 d: (_: C, ...args: Args) => D,
12612 e: (_: D, ...args: Args) => E,
12613 f: (_: E, ...args: Args) => F,
12614 g: (_: F, ...args: Args) => G,
12615 h: (_: G, ...args: Args) => H,
12616 i: (_: H, ...args: Args) => I,
12617 j: (_: I, ...args: Args) => J,
12618 k: (_: J, ...args: Args) => K,
12619 l: (_: K, ...args: Args) => L,
12620 m: (_: L, ...args: Args) => M,
12621 n: (_: M, ...args: Args) => N,
12622 o: (_: N, ...args: Args) => O
12623 ): (...args: Args) => O
12624
12625 <
12626 Eff extends Effect<any, any, any>,
12627 AEff,
12628 Args extends Array<any>,
12629 A,
12630 B,
12631 C,
12632 D,
12633 E,
12634 F,
12635 G,
12636 H,
12637 I,
12638 J,
12639 K,
12640 L,
12641 M,
12642 N,
12643 O,
12644 P
12645 >(
12646 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12647 a: (
12648 _: Effect<
12649 AEff,
12650 [Eff] extends [never] ? never
12651 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12652 : never,
12653 [Eff] extends [never] ? never
12654 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12655 : never
12656 >,
12657 ...args: Args
12658 ) => A,
12659 b: (_: A, ...args: Args) => B,
12660 c: (_: B, ...args: Args) => C,
12661 d: (_: C, ...args: Args) => D,
12662 e: (_: D, ...args: Args) => E,
12663 f: (_: E, ...args: Args) => F,
12664 g: (_: F, ...args: Args) => G,
12665 h: (_: G, ...args: Args) => H,
12666 i: (_: H, ...args: Args) => I,
12667 j: (_: I, ...args: Args) => J,
12668 k: (_: J, ...args: Args) => K,
12669 l: (_: K, ...args: Args) => L,
12670 m: (_: L, ...args: Args) => M,
12671 n: (_: M, ...args: Args) => N,
12672 o: (_: N, ...args: Args) => O,
12673 p: (_: O, ...args: Args) => P
12674 ): (...args: Args) => P
12675 <
12676 Self,
12677 Eff extends Effect<any, any, any>,
12678 AEff,
12679 Args extends Array<any>,
12680 A,
12681 B,
12682 C,
12683 D,
12684 E,
12685 F,
12686 G,
12687 H,
12688 I,
12689 J,
12690 K,
12691 L,
12692 M,
12693 N,
12694 O,
12695 P
12696 >(
12697 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12698 a: (
12699 _: Effect<
12700 AEff,
12701 [Eff] extends [never] ? never
12702 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12703 : never,
12704 [Eff] extends [never] ? never
12705 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12706 : never
12707 >,
12708 ...args: Args
12709 ) => A,
12710 b: (_: A, ...args: Args) => B,
12711 c: (_: B, ...args: Args) => C,
12712 d: (_: C, ...args: Args) => D,
12713 e: (_: D, ...args: Args) => E,
12714 f: (_: E, ...args: Args) => F,
12715 g: (_: F, ...args: Args) => G,
12716 h: (_: G, ...args: Args) => H,
12717 i: (_: H, ...args: Args) => I,
12718 j: (_: I, ...args: Args) => J,
12719 k: (_: J, ...args: Args) => K,
12720 l: (_: K, ...args: Args) => L,
12721 m: (_: L, ...args: Args) => M,
12722 n: (_: M, ...args: Args) => N,
12723 o: (_: N, ...args: Args) => O,
12724 p: (_: O, ...args: Args) => P
12725 ): (this: Self, ...args: Args) => P
12726
12727 <
12728 Self,
12729 Eff extends Effect<any, any, any>,
12730 AEff,
12731 Args extends Array<any>,
12732 A,
12733 B,
12734 C,
12735 D,
12736 E,
12737 F,
12738 G,
12739 H,
12740 I,
12741 J,
12742 K,
12743 L,
12744 M,
12745 N,
12746 O,
12747 P
12748 >(
12749 options: { readonly self: Self },
12750 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12751 a: (
12752 _: Effect<
12753 AEff,
12754 [Eff] extends [never] ? never
12755 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12756 : never,
12757 [Eff] extends [never] ? never
12758 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12759 : never
12760 >,
12761 ...args: Args
12762 ) => A,
12763 b: (_: A, ...args: Args) => B,
12764 c: (_: B, ...args: Args) => C,
12765 d: (_: C, ...args: Args) => D,
12766 e: (_: D, ...args: Args) => E,
12767 f: (_: E, ...args: Args) => F,
12768 g: (_: F, ...args: Args) => G,
12769 h: (_: G, ...args: Args) => H,
12770 i: (_: H, ...args: Args) => I,
12771 j: (_: I, ...args: Args) => J,
12772 k: (_: J, ...args: Args) => K,
12773 l: (_: K, ...args: Args) => L,
12774 m: (_: L, ...args: Args) => M,
12775 n: (_: M, ...args: Args) => N,
12776 o: (_: N, ...args: Args) => O,
12777 p: (_: O, ...args: Args) => P
12778 ): (...args: Args) => P
12779
12780 <
12781 Eff extends Effect<any, any, any>,
12782 AEff,
12783 Args extends Array<any>,
12784 A,
12785 B,
12786 C,
12787 D,
12788 E,
12789 F,
12790 G,
12791 H,
12792 I,
12793 J,
12794 K,
12795 L,
12796 M,
12797 N,
12798 O,
12799 P,
12800 Q
12801 >(
12802 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12803 a: (
12804 _: Effect<
12805 AEff,
12806 [Eff] extends [never] ? never
12807 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12808 : never,
12809 [Eff] extends [never] ? never
12810 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12811 : never
12812 >,
12813 ...args: Args
12814 ) => A,
12815 b: (_: A, ...args: Args) => B,
12816 c: (_: B, ...args: Args) => C,
12817 d: (_: C, ...args: Args) => D,
12818 e: (_: D, ...args: Args) => E,
12819 f: (_: E, ...args: Args) => F,
12820 g: (_: F, ...args: Args) => G,
12821 h: (_: G, ...args: Args) => H,
12822 i: (_: H, ...args: Args) => I,
12823 j: (_: I, ...args: Args) => J,
12824 k: (_: J, ...args: Args) => K,
12825 l: (_: K, ...args: Args) => L,
12826 m: (_: L, ...args: Args) => M,
12827 n: (_: M, ...args: Args) => N,
12828 o: (_: N, ...args: Args) => O,
12829 p: (_: O, ...args: Args) => P,
12830 q: (_: P, ...args: Args) => Q
12831 ): (...args: Args) => Q
12832 <
12833 Self,
12834 Eff extends Effect<any, any, any>,
12835 AEff,
12836 Args extends Array<any>,
12837 A,
12838 B,
12839 C,
12840 D,
12841 E,
12842 F,
12843 G,
12844 H,
12845 I,
12846 J,
12847 K,
12848 L,
12849 M,
12850 N,
12851 O,
12852 P,
12853 Q
12854 >(
12855 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12856 a: (
12857 _: Effect<
12858 AEff,
12859 [Eff] extends [never] ? never
12860 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12861 : never,
12862 [Eff] extends [never] ? never
12863 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12864 : never
12865 >,
12866 ...args: Args
12867 ) => A,
12868 b: (_: A, ...args: Args) => B,
12869 c: (_: B, ...args: Args) => C,
12870 d: (_: C, ...args: Args) => D,
12871 e: (_: D, ...args: Args) => E,
12872 f: (_: E, ...args: Args) => F,
12873 g: (_: F, ...args: Args) => G,
12874 h: (_: G, ...args: Args) => H,
12875 i: (_: H, ...args: Args) => I,
12876 j: (_: I, ...args: Args) => J,
12877 k: (_: J, ...args: Args) => K,
12878 l: (_: K, ...args: Args) => L,
12879 m: (_: L, ...args: Args) => M,
12880 n: (_: M, ...args: Args) => N,
12881 o: (_: N, ...args: Args) => O,
12882 p: (_: O, ...args: Args) => P,
12883 q: (_: P, ...args: Args) => Q
12884 ): (this: Self, ...args: Args) => Q
12885
12886 <
12887 Self,
12888 Eff extends Effect<any, any, any>,
12889 AEff,
12890 Args extends Array<any>,
12891 A,
12892 B,
12893 C,
12894 D,
12895 E,
12896 F,
12897 G,
12898 H,
12899 I,
12900 J,
12901 K,
12902 L,
12903 M,
12904 N,
12905 O,
12906 P,
12907 Q
12908 >(
12909 options: { readonly self: Self },
12910 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12911 a: (
12912 _: Effect<
12913 AEff,
12914 [Eff] extends [never] ? never
12915 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12916 : never,
12917 [Eff] extends [never] ? never
12918 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12919 : never
12920 >,
12921 ...args: Args
12922 ) => A,
12923 b: (_: A, ...args: Args) => B,
12924 c: (_: B, ...args: Args) => C,
12925 d: (_: C, ...args: Args) => D,
12926 e: (_: D, ...args: Args) => E,
12927 f: (_: E, ...args: Args) => F,
12928 g: (_: F, ...args: Args) => G,
12929 h: (_: G, ...args: Args) => H,
12930 i: (_: H, ...args: Args) => I,
12931 j: (_: I, ...args: Args) => J,
12932 k: (_: J, ...args: Args) => K,
12933 l: (_: K, ...args: Args) => L,
12934 m: (_: L, ...args: Args) => M,
12935 n: (_: M, ...args: Args) => N,
12936 o: (_: N, ...args: Args) => O,
12937 p: (_: O, ...args: Args) => P,
12938 q: (_: P, ...args: Args) => Q
12939 ): (...args: Args) => Q
12940
12941 <
12942 Eff extends Effect<any, any, any>,
12943 AEff,
12944 Args extends Array<any>,
12945 A,
12946 B,
12947 C,
12948 D,
12949 E,
12950 F,
12951 G,
12952 H,
12953 I,
12954 J,
12955 K,
12956 L,
12957 M,
12958 N,
12959 O,
12960 P,
12961 Q,
12962 R
12963 >(
12964 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
12965 a: (
12966 _: Effect<
12967 AEff,
12968 [Eff] extends [never] ? never
12969 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
12970 : never,
12971 [Eff] extends [never] ? never
12972 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
12973 : never
12974 >,
12975 ...args: Args
12976 ) => A,
12977 b: (_: A, ...args: Args) => B,
12978 c: (_: B, ...args: Args) => C,
12979 d: (_: C, ...args: Args) => D,
12980 e: (_: D, ...args: Args) => E,
12981 f: (_: E, ...args: Args) => F,
12982 g: (_: F, ...args: Args) => G,
12983 h: (_: G, ...args: Args) => H,
12984 i: (_: H, ...args: Args) => I,
12985 j: (_: I, ...args: Args) => J,
12986 k: (_: J, ...args: Args) => K,
12987 l: (_: K, ...args: Args) => L,
12988 m: (_: L, ...args: Args) => M,
12989 n: (_: M, ...args: Args) => N,
12990 o: (_: N, ...args: Args) => O,
12991 p: (_: O, ...args: Args) => P,
12992 q: (_: P, ...args: Args) => Q,
12993 r: (_: Q, ...args: Args) => R
12994 ): (...args: Args) => R
12995 <
12996 Self,
12997 Eff extends Effect<any, any, any>,
12998 AEff,
12999 Args extends Array<any>,
13000 A,
13001 B,
13002 C,
13003 D,
13004 E,
13005 F,
13006 G,
13007 H,
13008 I,
13009 J,
13010 K,
13011 L,
13012 M,
13013 N,
13014 O,
13015 P,
13016 Q,
13017 R
13018 >(
13019 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
13020 a: (
13021 _: Effect<
13022 AEff,
13023 [Eff] extends [never] ? never
13024 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
13025 : never,
13026 [Eff] extends [never] ? never
13027 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
13028 : never
13029 >,
13030 ...args: Args
13031 ) => A,
13032 b: (_: A, ...args: Args) => B,
13033 c: (_: B, ...args: Args) => C,
13034 d: (_: C, ...args: Args) => D,
13035 e: (_: D, ...args: Args) => E,
13036 f: (_: E, ...args: Args) => F,
13037 g: (_: F, ...args: Args) => G,
13038 h: (_: G, ...args: Args) => H,
13039 i: (_: H, ...args: Args) => I,
13040 j: (_: I, ...args: Args) => J,
13041 k: (_: J, ...args: Args) => K,
13042 l: (_: K, ...args: Args) => L,
13043 m: (_: L, ...args: Args) => M,
13044 n: (_: M, ...args: Args) => N,
13045 o: (_: N, ...args: Args) => O,
13046 p: (_: O, ...args: Args) => P,
13047 q: (_: P, ...args: Args) => Q,
13048 r: (_: Q, ...args: Args) => R
13049 ): (this: Self, ...args: Args) => R
13050
13051 <
13052 Self,
13053 Eff extends Effect<any, any, any>,
13054 AEff,
13055 Args extends Array<any>,
13056 A,
13057 B,
13058 C,
13059 D,
13060 E,
13061 F,
13062 G,
13063 H,
13064 I,
13065 J,
13066 K,
13067 L,
13068 M,
13069 N,
13070 O,
13071 P,
13072 Q,
13073 R
13074 >(
13075 options: { readonly self: Self },
13076 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
13077 a: (
13078 _: Effect<
13079 AEff,
13080 [Eff] extends [never] ? never
13081 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
13082 : never,
13083 [Eff] extends [never] ? never
13084 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
13085 : never
13086 >,
13087 ...args: Args
13088 ) => A,
13089 b: (_: A, ...args: Args) => B,
13090 c: (_: B, ...args: Args) => C,
13091 d: (_: C, ...args: Args) => D,
13092 e: (_: D, ...args: Args) => E,
13093 f: (_: E, ...args: Args) => F,
13094 g: (_: F, ...args: Args) => G,
13095 h: (_: G, ...args: Args) => H,
13096 i: (_: H, ...args: Args) => I,
13097 j: (_: I, ...args: Args) => J,
13098 k: (_: J, ...args: Args) => K,
13099 l: (_: K, ...args: Args) => L,
13100 m: (_: L, ...args: Args) => M,
13101 n: (_: M, ...args: Args) => N,
13102 o: (_: N, ...args: Args) => O,
13103 p: (_: O, ...args: Args) => P,
13104 q: (_: P, ...args: Args) => Q,
13105 r: (_: Q, ...args: Args) => R
13106 ): (...args: Args) => R
13107
13108 <
13109 Eff extends Effect<any, any, any>,
13110 AEff,
13111 Args extends Array<any>,
13112 A,
13113 B,
13114 C,
13115 D,
13116 E,
13117 F,
13118 G,
13119 H,
13120 I,
13121 J,
13122 K,
13123 L,
13124 M,
13125 N,
13126 O,
13127 P,
13128 Q,
13129 R,
13130 S
13131 >(
13132 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
13133 a: (
13134 _: Effect<
13135 AEff,
13136 [Eff] extends [never] ? never
13137 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
13138 : never,
13139 [Eff] extends [never] ? never
13140 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
13141 : never
13142 >,
13143 ...args: Args
13144 ) => A,
13145 b: (_: A, ...args: Args) => B,
13146 c: (_: B, ...args: Args) => C,
13147 d: (_: C, ...args: Args) => D,
13148 e: (_: D, ...args: Args) => E,
13149 f: (_: E, ...args: Args) => F,
13150 g: (_: F, ...args: Args) => G,
13151 h: (_: G, ...args: Args) => H,
13152 i: (_: H, ...args: Args) => I,
13153 j: (_: I, ...args: Args) => J,
13154 k: (_: J, ...args: Args) => K,
13155 l: (_: K, ...args: Args) => L,
13156 m: (_: L, ...args: Args) => M,
13157 n: (_: M, ...args: Args) => N,
13158 o: (_: N, ...args: Args) => O,
13159 p: (_: O, ...args: Args) => P,
13160 q: (_: P, ...args: Args) => Q,
13161 r: (_: Q, ...args: Args) => R,
13162 s: (_: R, ...args: Args) => S
13163 ): (...args: Args) => S
13164 <
13165 Self,
13166 Eff extends Effect<any, any, any>,
13167 AEff,
13168 Args extends Array<any>,
13169 A,
13170 B,
13171 C,
13172 D,
13173 E,
13174 F,
13175 G,
13176 H,
13177 I,
13178 J,
13179 K,
13180 L,
13181 M,
13182 N,
13183 O,
13184 P,
13185 Q,
13186 R,
13187 S
13188 >(
13189 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
13190 a: (
13191 _: Effect<
13192 AEff,
13193 [Eff] extends [never] ? never
13194 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
13195 : never,
13196 [Eff] extends [never] ? never
13197 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
13198 : never
13199 >,
13200 ...args: Args
13201 ) => A,
13202 b: (_: A, ...args: Args) => B,
13203 c: (_: B, ...args: Args) => C,
13204 d: (_: C, ...args: Args) => D,
13205 e: (_: D, ...args: Args) => E,
13206 f: (_: E, ...args: Args) => F,
13207 g: (_: F, ...args: Args) => G,
13208 h: (_: G, ...args: Args) => H,
13209 i: (_: H, ...args: Args) => I,
13210 j: (_: I, ...args: Args) => J,
13211 k: (_: J, ...args: Args) => K,
13212 l: (_: K, ...args: Args) => L,
13213 m: (_: L, ...args: Args) => M,
13214 n: (_: M, ...args: Args) => N,
13215 o: (_: N, ...args: Args) => O,
13216 p: (_: O, ...args: Args) => P,
13217 q: (_: P, ...args: Args) => Q,
13218 r: (_: Q, ...args: Args) => R,
13219 s: (_: R, ...args: Args) => S
13220 ): (this: Self, ...args: Args) => S
13221
13222 <
13223 Self,
13224 Eff extends Effect<any, any, any>,
13225 AEff,
13226 Args extends Array<any>,
13227 A,
13228 B,
13229 C,
13230 D,
13231 E,
13232 F,
13233 G,
13234 H,
13235 I,
13236 J,
13237 K,
13238 L,
13239 M,
13240 N,
13241 O,
13242 P,
13243 Q,
13244 R,
13245 S
13246 >(
13247 options: { readonly self: Self },
13248 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
13249 a: (
13250 _: Effect<
13251 AEff,
13252 [Eff] extends [never] ? never
13253 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
13254 : never,
13255 [Eff] extends [never] ? never
13256 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
13257 : never
13258 >,
13259 ...args: Args
13260 ) => A,
13261 b: (_: A, ...args: Args) => B,
13262 c: (_: B, ...args: Args) => C,
13263 d: (_: C, ...args: Args) => D,
13264 e: (_: D, ...args: Args) => E,
13265 f: (_: E, ...args: Args) => F,
13266 g: (_: F, ...args: Args) => G,
13267 h: (_: G, ...args: Args) => H,
13268 i: (_: H, ...args: Args) => I,
13269 j: (_: I, ...args: Args) => J,
13270 k: (_: J, ...args: Args) => K,
13271 l: (_: K, ...args: Args) => L,
13272 m: (_: L, ...args: Args) => M,
13273 n: (_: M, ...args: Args) => N,
13274 o: (_: N, ...args: Args) => O,
13275 p: (_: O, ...args: Args) => P,
13276 q: (_: P, ...args: Args) => Q,
13277 r: (_: Q, ...args: Args) => R,
13278 s: (_: R, ...args: Args) => S
13279 ): (...args: Args) => S
13280
13281 <
13282 Eff extends Effect<any, any, any>,
13283 AEff,
13284 Args extends Array<any>,
13285 A,
13286 B,
13287 C,
13288 D,
13289 E,
13290 F,
13291 G,
13292 H,
13293 I,
13294 J,
13295 K,
13296 L,
13297 M,
13298 N,
13299 O,
13300 P,
13301 Q,
13302 R,
13303 S,
13304 T
13305 >(
13306 body: (this: unassigned, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
13307 a: (
13308 _: Effect<
13309 AEff,
13310 [Eff] extends [never] ? never
13311 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
13312 : never,
13313 [Eff] extends [never] ? never
13314 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
13315 : never
13316 >,
13317 ...args: Args
13318 ) => A,
13319 b: (_: A, ...args: Args) => B,
13320 c: (_: B, ...args: Args) => C,
13321 d: (_: C, ...args: Args) => D,
13322 e: (_: D, ...args: Args) => E,
13323 f: (_: E, ...args: Args) => F,
13324 g: (_: F, ...args: Args) => G,
13325 h: (_: G, ...args: Args) => H,
13326 i: (_: H, ...args: Args) => I,
13327 j: (_: I, ...args: Args) => J,
13328 k: (_: J, ...args: Args) => K,
13329 l: (_: K, ...args: Args) => L,
13330 m: (_: L, ...args: Args) => M,
13331 n: (_: M, ...args: Args) => N,
13332 o: (_: N, ...args: Args) => O,
13333 p: (_: O, ...args: Args) => P,
13334 q: (_: P, ...args: Args) => Q,
13335 r: (_: Q, ...args: Args) => R,
13336 s: (_: R, ...args: Args) => S,
13337 t: (_: S, ...args: Args) => T
13338 ): (...args: Args) => T
13339 <
13340 Self,
13341 Eff extends Effect<any, any, any>,
13342 AEff,
13343 Args extends Array<any>,
13344 A,
13345 B,
13346 C,
13347 D,
13348 E,
13349 F,
13350 G,
13351 H,
13352 I,
13353 J,
13354 K,
13355 L,
13356 M,
13357 N,
13358 O,
13359 P,
13360 Q,
13361 R,
13362 S,
13363 T
13364 >(
13365 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
13366 a: (
13367 _: Effect<
13368 AEff,
13369 [Eff] extends [never] ? never
13370 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
13371 : never,
13372 [Eff] extends [never] ? never
13373 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
13374 : never
13375 >,
13376 ...args: Args
13377 ) => A,
13378 b: (_: A, ...args: Args) => B,
13379 c: (_: B, ...args: Args) => C,
13380 d: (_: C, ...args: Args) => D,
13381 e: (_: D, ...args: Args) => E,
13382 f: (_: E, ...args: Args) => F,
13383 g: (_: F, ...args: Args) => G,
13384 h: (_: G, ...args: Args) => H,
13385 i: (_: H, ...args: Args) => I,
13386 j: (_: I, ...args: Args) => J,
13387 k: (_: J, ...args: Args) => K,
13388 l: (_: K, ...args: Args) => L,
13389 m: (_: L, ...args: Args) => M,
13390 n: (_: M, ...args: Args) => N,
13391 o: (_: N, ...args: Args) => O,
13392 p: (_: O, ...args: Args) => P,
13393 q: (_: P, ...args: Args) => Q,
13394 r: (_: Q, ...args: Args) => R,
13395 s: (_: R, ...args: Args) => S,
13396 t: (_: S, ...args: Args) => T
13397 ): (this: Self, ...args: Args) => T
13398
13399 <
13400 Self,
13401 Eff extends Effect<any, any, any>,
13402 AEff,
13403 Args extends Array<any>,
13404 A,
13405 B,
13406 C,
13407 D,
13408 E,
13409 F,
13410 G,
13411 H,
13412 I,
13413 J,
13414 K,
13415 L,
13416 M,
13417 N,
13418 O,
13419 P,
13420 Q,
13421 R,
13422 S,
13423 T
13424 >(
13425 options: { readonly self: Self },
13426 body: (this: Self, ...args: Args) => Generator<Eff, AEff, never> | (Eff & Effect<AEff, any, any>),
13427 a: (
13428 _: Effect<
13429 AEff,
13430 [Eff] extends [never] ? never
13431 : [Eff] extends [Effect<infer _A, infer E, infer _R>] ? E
13432 : never,
13433 [Eff] extends [never] ? never
13434 : [Eff] extends [Effect<infer _A, infer _E, infer R>] ? R
13435 : never
13436 >,
13437 ...args: Args
13438 ) => A,
13439 b: (_: A, ...args: Args) => B,
13440 c: (_: B, ...args: Args) => C,
13441 d: (_: C, ...args: Args) => D,
13442 e: (_: D, ...args: Args) => E,
13443 f: (_: E, ...args: Args) => F,
13444 g: (_: F, ...args: Args) => G,
13445 h: (_: G, ...args: Args) => H,
13446 i: (_: H, ...args: Args) => I,
13447 j: (_: I, ...args: Args) => J,
13448 k: (_: J, ...args: Args) => K,
13449 l: (_: K, ...args: Args) => L,
13450 m: (_: L, ...args: Args) => M,
13451 n: (_: M, ...args: Args) => N,
13452 o: (_: N, ...args: Args) => O,
13453 p: (_: O, ...args: Args) => P,
13454 q: (_: P, ...args: Args) => Q,
13455 r: (_: Q, ...args: Args) => R,
13456 s: (_: R, ...args: Args) => S,
13457 t: (_: S, ...args: Args) => T
13458 ): (...args: Args) => T
13459 }
13460}
13461
13462/**
13463 * Creates an Effect-returning function without tracing.
13464 *
13465 * **When to use**
13466 *
13467 * Use when you are defining a reusable Effect function whose implementation
13468 * would otherwise be a normal function returning {@link gen}, especially when
13469 * tracing spans or stack-frame capture are not needed.
13470 *
13471 * **Details**
13472 *
13473 * Compared to a plain function that returns {@link gen}, `Effect.fnUntraced`
13474 * reuses the generator body instead of allocating a fresh generator closure
13475 * around the arguments on every call. It does not record an Effect stack-frame
13476 * boundary and does not create tracing spans. Use {@link fn} when you need
13477 * those stack frames or spans. Additional arguments after the generator body
13478 * act like `pipe` transforms: each transform receives the previous result and
13479 * the original function arguments. Annotate the generator return type with
13480 * `Effect.fn.Return<A, E, R>` when the produced `Effect` type needs to be
13481 * stated explicitly.
13482 *
13483 * **Example** (Defining untraced effect functions)
13484 *
13485 * ```ts import.meta.vitest
13486 * import { Effect } from "effect"
13487 *
13488 * const f = Effect.fnUntraced(function*(
13489 * value: string
13490 * ) {
13491 * return yield* Effect.succeed(value.length)
13492 * })
13493 *
13494 * // ┌─── Effect.Effect<number>
13495 * // ▼
13496 * const program = f("hello")
13497 * Effect.runSync(program) // => 5
13498 * ```
13499 *
13500 * **Example** (Transforming the returned Effect)
13501 *
13502 * ```ts import.meta.vitest
13503 * import { Effect } from "effect"
13504 *
13505 * const f = Effect.fnUntraced(
13506 * function*(value: string) {
13507 * return yield* Effect.succeed(value.length)
13508 * },
13509 * (effect, value) =>
13510 * effect.pipe(Effect.map((length) => `${value}: ${length}`))
13511 * )
13512 *
13513 * // ┌─── Effect.Effect<string>
13514 * // ▼
13515 * const program = f("hello")
13516 * Effect.runSync(program) // => "hello: 5"
13517 * ```
13518 *
13519 * **Example** (Annotating an untraced non-parametric function)
13520 *
13521 * ```ts import.meta.vitest
13522 * import { Effect } from "effect"
13523 *
13524 * const f = Effect.fnUntraced(function*(
13525 * value: string
13526 * ): Effect.fn.Return<number> {
13527 * return yield* Effect.succeed(value.length)
13528 * })
13529 *
13530 * // ┌─── Effect.Effect<number>
13531 * // ▼
13532 * const program = f("hello")
13533 * Effect.runSync(program) // => 5
13534 * ```
13535 *
13536 * **Example** (Annotating an untraced parametric function)
13537 *
13538 * ```ts import.meta.vitest
13539 * import { Effect } from "effect"
13540 *
13541 * const f = Effect.fnUntraced(function*<A>(
13542 * value: A
13543 * ): Effect.fn.Return<A> {
13544 * return yield* Effect.succeed(value)
13545 * })
13546 *
13547 * // ┌─── Effect.Effect<string>
13548 * // ▼
13549 * const program = f("hello")
13550 * Effect.runSync(program) // => "hello"
13551 * ```
13552 *
13553 * @category constructors
13554 * @since 3.12.0
13555 */
13556export const fnUntraced: fn.Untraced = internal.fnUntraced
13557
13558/**
13559 * Creates a reusable traced function from an Effect body.
13560 *
13561 * **When to use**
13562 *
13563 * Use when you are defining a reusable Effect function whose implementation
13564 * would otherwise be a normal function returning {@link gen}, and you want
13565 * tracing spans or stack-frame capture.
13566 *
13567 * **Details**
13568 *
13569 * Compared to a plain function that returns {@link gen}, `Effect.fn` reuses the
13570 * generator body instead of allocating a fresh generator closure around the
13571 * arguments on every call. Call `Effect.fn(body, ...)` for a generic
13572 * stack-frame boundary without creating a span. Call
13573 * `Effect.fn("operationName", options?)(body, ...)` when that boundary should
13574 * have a readable operation name and the returned `Effect` should create a
13575 * tracing span when run. {@link SpanOptionsNoTrace} configures span metadata
13576 * such as attributes, links, parent or root selection, kind, sampling, and log
13577 * level. Additional arguments after the generator body act like `pipe`
13578 * transforms: each transform receives the previous result and the original
13579 * function arguments. When those transforms return an `Effect`, the returned
13580 * effect includes stack-frame metadata and, for the named form, a tracing span.
13581 * Generator bodies may declare a `this` parameter; pass `{ self }` before the
13582 * body to bind `this` when the function is created.
13583 *
13584 * **Example** (Defining traced effect functions)
13585 *
13586 * ```ts import.meta.vitest
13587 * import { Effect } from "effect"
13588 *
13589 * const f = Effect.fn("calculateLength")(function*(value: string) {
13590 * return yield* Effect.succeed(value.length)
13591 * })
13592 *
13593 * // ┌─── Effect.Effect<number>
13594 * // ▼
13595 * const program = f("hello")
13596 * Effect.runSync(program) // => 5
13597 * ```
13598 *
13599 * **Example** (Transforming the returned Effect)
13600 *
13601 * ```ts import.meta.vitest
13602 * import { Effect } from "effect"
13603 *
13604 * const f = Effect.fn("formatLength")(
13605 * function*(value: string) {
13606 * return yield* Effect.succeed(value.length)
13607 * },
13608 * (effect, value) =>
13609 * effect.pipe(Effect.map((length) => `${value}: ${length}`))
13610 * )
13611 *
13612 * // ┌─── Effect.Effect<string>
13613 * // ▼
13614 * const program = f("hello")
13615 * Effect.runSync(program) // => "hello: 5"
13616 * ```
13617 *
13618 * **Example** (Binding this)
13619 *
13620 * ```ts import.meta.vitest
13621 * import { Effect } from "effect"
13622 *
13623 * class Counter {
13624 * count = 0
13625 *
13626 * increment = Effect.fn("Counter.increment")(
13627 * { self: this },
13628 * function*(this: Counter, by: number) {
13629 * this.count += by
13630 * return yield* Effect.succeed(this.count)
13631 * }
13632 * )
13633 * }
13634 *
13635 * const counter = new Counter()
13636 *
13637 * // ┌─── Effect.Effect<number>
13638 * // ▼
13639 * const program = counter.increment(1)
13640 * Effect.runSync(program) // => 1
13641 * ```
13642 *
13643 * **Example** (Annotating a traced non-parametric function)
13644 *
13645 * ```ts import.meta.vitest
13646 * import { Effect } from "effect"
13647 *
13648 * const f = Effect.fn("calculateLength")(function*(
13649 * value: string
13650 * ): Effect.fn.Return<number> {
13651 * return yield* Effect.succeed(value.length)
13652 * })
13653 *
13654 * // ┌─── Effect.Effect<number>
13655 * // ▼
13656 * const program = f("hello")
13657 * Effect.runSync(program) // => 5
13658 * ```
13659 *
13660 * **Example** (Annotating a traced parametric function)
13661 *
13662 * ```ts import.meta.vitest
13663 * import { Effect } from "effect"
13664 *
13665 * const f = Effect.fn("succeed")(function*<A>(
13666 * value: A
13667 * ): Effect.fn.Return<A> {
13668 * return yield* Effect.succeed(value)
13669 * })
13670 *
13671 * // ┌─── Effect.Effect<string>
13672 * // ▼
13673 * const program = f("hello")
13674 * Effect.runSync(program) // => "hello"
13675 * ```
13676 *
13677 * @category constructors
13678 * @since 3.11.0
13679 */
13680export const fn: fn.Traced & {
13681 (name: string, options?: SpanOptionsNoTrace): fn.Traced
13682} = internal.fn
13683
13684// ========================================================================
13685// Clock
13686// ========================================================================
13687
13688/**
13689 * Retrieves the `Clock` service from the context and provides it to the
13690 * specified effectful function.
13691 *
13692 * **Example** (Accessing the Clock service)
13693 *
13694 * ```ts import.meta.vitest
13695 * import { Effect } from "effect"
13696 *
13697 * const program = Effect.clockWith((clock) =>
13698 * clock.currentTimeMillis.pipe(
13699 * Effect.map(() => "Clock is available")
13700 * )
13701 * )
13702 *
13703 * Effect.runSync(program) // => "Clock is available"
13704 * ```
13705 *
13706 * @category accessors
13707 * @since 2.0.0
13708 */
13709export const clockWith: <A, E, R>(
13710 f: (clock: Clock) => Effect<A, E, R>
13711) => Effect<A, E, R> = internal.clockWith
13712
13713// ========================================================================
13714// Logging
13715// ========================================================================
13716
13717/**
13718 * Creates a logger function that logs at the specified level.
13719 *
13720 * **Details**
13721 *
13722 * If no level is provided, the logger uses the fiber's current log level and
13723 * extracts any `Cause` values from the message list.
13724 *
13725 * **Example** (Logging at a dynamic level)
13726 *
13727 * ```ts import.meta.vitest
13728 * import { Effect, Logger, References } from "effect"
13729 * const output: Array<unknown> = []
13730 *
13731 * const logWarn = Effect.logWithLevel("Warn")
13732 *
13733 * const program = Effect.gen(function*() {
13734 * yield* logWarn("Cache miss")
13735 * })
13736 * const logger = Logger.make<unknown, void>(({ logLevel, message }) => {
13737 * void output.push(`${logLevel}: ${Array.isArray(message) ? message.map(String).join(" ") : String(message)}`)
13738 * })
13739 * const runnable = program.pipe(
13740 * Effect.provideService(References.MinimumLogLevel, "Debug"),
13741 * Effect.provide(Logger.layer([logger]))
13742 * )
13743 * Effect.runSync(runnable)
13744 * output // => ["Warn: Cache miss"]
13745 * ```
13746 *
13747 * @category logging
13748 * @since 2.0.0
13749 */
13750export const logWithLevel: (level?: Severity) => (...message: ReadonlyArray<any>) => Effect<void> =
13751 internal.logWithLevel
13752
13753/**
13754 * Logs one or more messages using the default log level.
13755 *
13756 * **Example** (Logging at the default level)
13757 *
13758 * ```ts import.meta.vitest
13759 * import { Effect, Logger } from "effect"
13760 * const output: Array<unknown> = []
13761 *
13762 * const program = Effect.gen(function*() {
13763 * const result = 2 + 2
13764 * yield* Effect.log("Result:", result)
13765 * return result
13766 * })
13767 *
13768 * const logger = Logger.make<unknown, void>(({ logLevel, message }) => {
13769 * void output.push(`${logLevel}: ${Array.isArray(message) ? message.map(String).join(" ") : String(message)}`)
13770 * })
13771 * const runnable = Effect.provide(program, Logger.layer([logger]))
13772 * void output.push(Effect.runSync(runnable))
13773 * output // => ["Info: Result: 4", 4]
13774 * ```
13775 *
13776 * @category logging
13777 * @since 2.0.0
13778 */
13779export const log: (...message: ReadonlyArray<any>) => Effect<void> = internal.logWithLevel()
13780
13781/**
13782 * Logs one or more messages at the FATAL level.
13783 *
13784 * **Example** (Logging fatal messages)
13785 *
13786 * ```ts import.meta.vitest
13787 * import { Effect, Logger } from "effect"
13788 * const output: Array<unknown> = []
13789 *
13790 * const program = Effect.gen(function*() {
13791 * yield* Effect.logFatal("Critical system failure")
13792 * })
13793 *
13794 * const logger = Logger.make<unknown, void>(({ logLevel, message }) => {
13795 * void output.push(`${logLevel}: ${Array.isArray(message) ? message.map(String).join(" ") : String(message)}`)
13796 * })
13797 * const runnable = Effect.provide(program, Logger.layer([logger]))
13798 * Effect.runSync(runnable)
13799 * output // => ["Fatal: Critical system failure"]
13800 * ```
13801 *
13802 * @category logging
13803 * @since 2.0.0
13804 */
13805export const logFatal: (...message: ReadonlyArray<any>) => Effect<void> = internal.logWithLevel("Fatal")
13806
13807/**
13808 * Logs one or more messages at the WARNING level.
13809 *
13810 * **Example** (Logging warnings)
13811 *
13812 * ```ts import.meta.vitest
13813 * import { Effect, Logger } from "effect"
13814 * const output: Array<unknown> = []
13815 *
13816 * const program = Effect.gen(function*() {
13817 * yield* Effect.logWarning("API rate limit approaching")
13818 * })
13819 *
13820 * const logger = Logger.make<unknown, void>(({ logLevel, message }) => {
13821 * void output.push(`${logLevel}: ${Array.isArray(message) ? message.map(String).join(" ") : String(message)}`)
13822 * })
13823 * Effect.runSync(Effect.provide(program, Logger.layer([logger])))
13824 * output // => ["Warn: API rate limit approaching"]
13825 * ```
13826 *
13827 * @category logging
13828 * @since 2.0.0
13829 */
13830export const logWarning: (...message: ReadonlyArray<any>) => Effect<void> = internal.logWithLevel("Warn")
13831
13832/**
13833 * Logs one or more messages at the ERROR level.
13834 *
13835 * **Example** (Logging errors)
13836 *
13837 * ```ts import.meta.vitest
13838 * import { Effect, Logger } from "effect"
13839 * const output: Array<unknown> = []
13840 *
13841 * const program = Effect.gen(function*() {
13842 * yield* Effect.logError("Database connection failed")
13843 * })
13844 *
13845 * const logger = Logger.make<unknown, void>(({ logLevel, message }) => {
13846 * void output.push(`${logLevel}: ${Array.isArray(message) ? message.map(String).join(" ") : String(message)}`)
13847 * })
13848 * Effect.runSync(Effect.provide(program, Logger.layer([logger])))
13849 * output // => ["Error: Database connection failed"]
13850 * ```
13851 *
13852 * @category logging
13853 * @since 2.0.0
13854 */
13855export const logError: (...message: ReadonlyArray<any>) => Effect<void> = internal.logWithLevel("Error")
13856
13857/**
13858 * Logs one or more messages at the INFO level.
13859 *
13860 * **Example** (Logging information)
13861 *
13862 * ```ts import.meta.vitest
13863 * import { Effect, Logger } from "effect"
13864 * const output: Array<unknown> = []
13865 *
13866 * const program = Effect.gen(function*() {
13867 * yield* Effect.logInfo("Application starting up")
13868 * })
13869 *
13870 * const logger = Logger.make<unknown, void>(({ logLevel, message }) => {
13871 * void output.push(`${logLevel}: ${Array.isArray(message) ? message.map(String).join(" ") : String(message)}`)
13872 * })
13873 * Effect.runSync(Effect.provide(program, Logger.layer([logger])))
13874 * output // => ["Info: Application starting up"]
13875 * ```
13876 *
13877 * @category logging
13878 * @since 2.0.0
13879 */
13880export const logInfo: (...message: ReadonlyArray<any>) => Effect<void> = internal.logWithLevel("Info")
13881
13882/**
13883 * Logs one or more messages at the DEBUG level.
13884 *
13885 * **Example** (Logging debug messages)
13886 *
13887 * ```ts import.meta.vitest
13888 * import { Effect, Logger, References } from "effect"
13889 * const output: Array<unknown> = []
13890 *
13891 * const program = Effect.gen(function*() {
13892 * yield* Effect.logDebug("Debug mode enabled")
13893 * })
13894 *
13895 * const logger = Logger.make<unknown, void>(({ logLevel, message }) => {
13896 * void output.push(`${logLevel}: ${Array.isArray(message) ? message.map(String).join(" ") : String(message)}`)
13897 * })
13898 * const runnable = program.pipe(
13899 * Effect.provideService(References.MinimumLogLevel, "Debug"),
13900 * Effect.provide(Logger.layer([logger]))
13901 * )
13902 * Effect.runSync(runnable)
13903 * output // => ["Debug: Debug mode enabled"]
13904 * ```
13905 *
13906 * @category logging
13907 * @since 2.0.0
13908 */
13909export const logDebug: (...message: ReadonlyArray<any>) => Effect<void> = internal.logWithLevel("Debug")
13910
13911/**
13912 * Logs one or more messages at the TRACE level.
13913 *
13914 * **Example** (Logging trace messages)
13915 *
13916 * ```ts import.meta.vitest
13917 * import { Effect, Logger, References } from "effect"
13918 * const output: Array<unknown> = []
13919 *
13920 * const program = Effect.gen(function*() {
13921 * yield* Effect.logTrace("Entering function processData")
13922 * })
13923 *
13924 * const logger = Logger.make<unknown, void>(({ logLevel, message }) => {
13925 * void output.push(`${logLevel}: ${Array.isArray(message) ? message.map(String).join(" ") : String(message)}`)
13926 * })
13927 * const runnable = program.pipe(
13928 * Effect.provideService(References.MinimumLogLevel, "Trace"),
13929 * Effect.provide(Logger.layer([logger]))
13930 * )
13931 * Effect.runSync(runnable)
13932 * output // => ["Trace: Entering function processData"]
13933 * ```
13934 *
13935 * @category logging
13936 * @since 2.0.0
13937 */
13938export const logTrace: (...message: ReadonlyArray<any>) => Effect<void> = internal.logWithLevel("Trace")
13939
13940/**
13941 * Adds a logger to the set of loggers which will output logs for this effect.
13942 *
13943 * **Example** (Adding a logger to an effect)
13944 *
13945 * ```ts import.meta.vitest
13946 * import { Effect, Logger } from "effect"
13947 * const output: Array<unknown> = []
13948 *
13949 * // Create a custom logger that logs to the console
13950 * const customLogger = Logger.make<unknown, void>(({ message }) =>
13951 * void output.push(`[CUSTOM]: ${Array.isArray(message) ? message.map(String).join(" ") : String(message)}`)
13952 * )
13953 *
13954 * const program = Effect.gen(function*() {
13955 * yield* Effect.log("This will go to both default and custom logger")
13956 * return "completed"
13957 * })
13958 *
13959 * // Add the custom logger to the effect
13960 * const programWithLogger = Effect.withLogger(program, customLogger)
13961 *
13962 * Effect.runSync(Effect.provide(programWithLogger, Logger.layer([])))
13963 * output // => ["[CUSTOM]: This will go to both default and custom logger"]
13964 * ```
13965 *
13966 * @category logging
13967 * @since 4.0.0
13968 */
13969export const withLogger: {
13970 <Output>(
13971 logger: Logger<unknown, Output>
13972 ): <A, E, R>(effect: Effect<A, E, R>) => Effect<A, E, R>
13973 <A, E, R, Output>(
13974 effect: Effect<A, E, R>,
13975 logger: Logger<unknown, Output>
13976 ): Effect<A, E, R>
13977} = dual(2, <A, E, R, Output>(
13978 effect: Effect<A, E, R>,
13979 logger: Logger<unknown, Output>
13980): Effect<A, E, R> =>
13981 internal.updateService(
13982 effect,
13983 internal.CurrentLoggers,
13984 (loggers) => new Set([...loggers, logger])
13985 ))
13986
13987/**
13988 * Adds an annotation to each log line in this effect.
13989 *
13990 * **Example** (Adding log annotations)
13991 *
13992 * ```ts import.meta.vitest
13993 * import { Effect, Logger } from "effect"
13994 * const output: Array<unknown> = []
13995 *
13996 * const program = Effect.gen(function*() {
13997 * yield* Effect.log("Starting operation")
13998 * })
13999 *
14000 * // Add annotations to all log messages
14001 * const annotatedProgram = Effect.annotateLogs(program, {
14002 * userId: "user123",
14003 * operation: "data-processing"
14004 * })
14005 *
14006 * // Also supports single key-value annotations
14007 * const singleAnnotated = Effect.annotateLogs(program, "requestId", "req-456")
14008 *
14009 * const logger = Logger.make<unknown, void>(({ message }) =>
14010 * void output.push(Array.isArray(message) ? message.join(" ") : String(message))
14011 * )
14012 * const run = (effect: Effect.Effect<void>) =>
14013 * Effect.runSync(Effect.provide(effect, Logger.layer([logger])))
14014 * run(annotatedProgram)
14015 * run(singleAnnotated)
14016 * output // => ["Starting operation", "Starting operation"]
14017 * ```
14018 *
14019 * @category logging
14020 * @since 2.0.0
14021 */
14022export const annotateLogs: {
14023 (
14024 key: string,
14025 value: unknown
14026 ): <A, E, R>(effect: Effect<A, E, R>) => Effect<A, E, R>
14027 (
14028 values: Record<string, unknown>
14029 ): <A, E, R>(effect: Effect<A, E, R>) => Effect<A, E, R>
14030 <A, E, R>(
14031 effect: Effect<A, E, R>,
14032 key: string,
14033 value: unknown
14034 ): Effect<A, E, R>
14035 <A, E, R>(
14036 effect: Effect<A, E, R>,
14037 values: Record<string, unknown>
14038 ): Effect<A, E, R>
14039} = dual(
14040 (args) => isEffect(args[0]),
14041 <A, E, R>(
14042 effect: Effect<A, E, R>,
14043 ...args: [Record<string, unknown>] | [key: string, value: unknown]
14044 ): Effect<A, E, R> =>
14045 internal.updateService(effect, CurrentLogAnnotations, (annotations) => {
14046 const newAnnotations = args.length === 1 ? { ...annotations, ...args[0] } : { ...annotations }
14047 if (args.length === 1) {
14048 return newAnnotations
14049 } else {
14050 InternalRecord.assignProperty(newAnnotations, args[0], args[1])
14051 }
14052 return newAnnotations
14053 })
14054)
14055
14056/**
14057 * Adds log annotations to the current scope.
14058 *
14059 * **When to use**
14060 *
14061 * Use to attach log annotations that last until the current scope closes.
14062 *
14063 * **Details**
14064 *
14065 * This differs from `annotateLogs`, which only annotates a specific effect.
14066 * `annotateLogsScoped` updates annotations for the entire current `Scope` and
14067 * restores the previous annotations when the scope closes.
14068 *
14069 * **Example** (Adding scoped log annotations)
14070 *
14071 * ```ts import.meta.vitest
14072 * import { Effect, Logger } from "effect"
14073 * const output: Array<unknown> = []
14074 *
14075 * const program = Effect.scoped(
14076 * Effect.gen(function*() {
14077 * yield* Effect.log("before")
14078 * yield* Effect.annotateLogsScoped({ requestId: "req-123" })
14079 * yield* Effect.log("inside scope")
14080 * })
14081 * )
14082 *
14083 * const logger = Logger.make<unknown, void>(({ message }) =>
14084 * void output.push(Array.isArray(message) ? message.join(" ") : String(message))
14085 * )
14086 * Effect.runSync(Effect.provide(program, Logger.layer([logger])))
14087 * output // => ["before", "inside scope"]
14088 * ```
14089 *
14090 * @see {@link annotateLogs} for annotating one effect
14091 *
14092 * @category logging
14093 * @since 3.1.0
14094 */
14095export const annotateLogsScoped: {
14096 (key: string, value: unknown): Effect<void, never, Scope>
14097 (values: Record<string, unknown>): Effect<void, never, Scope>
14098} = internal.annotateLogsScoped
14099
14100/**
14101 * Adds a span to each log line in this effect.
14102 *
14103 * **Example** (Adding a log span)
14104 *
14105 * ```ts import.meta.vitest
14106 * import { Effect, Logger } from "effect"
14107 * const output: Array<unknown> = []
14108 *
14109 * const databaseOperation = Effect.gen(function*() {
14110 * yield* Effect.log("Connecting to database")
14111 * yield* Effect.log("Executing query")
14112 * yield* Effect.log("Processing results")
14113 * return "data"
14114 * })
14115 *
14116 * const httpRequest = Effect.gen(function*() {
14117 * yield* Effect.log("Making HTTP request")
14118 * const data = yield* Effect.withLogSpan(databaseOperation, "db-operation")
14119 * yield* Effect.log("Sending response")
14120 * return data
14121 * })
14122 *
14123 * const program = Effect.withLogSpan(httpRequest, "http-handler")
14124 *
14125 * const logger = Logger.make<unknown, void>(({ message }) =>
14126 * void output.push(Array.isArray(message) ? message.join(" ") : String(message))
14127 * )
14128 * void output.push(Effect.runSync(Effect.provide(program, Logger.layer([logger]))))
14129 * output // => ["Making HTTP request", "Connecting to database", "Executing query", "Processing results", "Sending response", "data"]
14130 * ```
14131 *
14132 * @category logging
14133 * @since 2.0.0
14134 */
14135export const withLogSpan: {
14136 (label: string): <A, E, R>(effect: Effect<A, E, R>) => Effect<A, E, R>
14137 <A, E, R>(effect: Effect<A, E, R>, label: string): Effect<A, E, R>
14138} = dual(
14139 2,
14140 <A, E, R>(effect: Effect<A, E, R>, label: string): Effect<A, E, R> =>
14141 internal.flatMap(internal.currentTimeMillis, (now) =>
14142 internal.updateService(effect, CurrentLogSpans, (spans) => {
14143 const span: [label: string, timestamp: number] = [label, now]
14144 return [span, ...spans]
14145 }))
14146)
14147
14148// -----------------------------------------------------------------------------
14149// Metrics
14150// -----------------------------------------------------------------------------
14151
14152/**
14153 * Updates a metric after each effect execution, optionally mapping its `Exit` to
14154 * the metric's input.
14155 *
14156 * **Example** (Counting executions)
14157 *
14158 * ```ts import.meta.vitest
14159 * import { Effect, Metric } from "effect"
14160 *
14161 * const counter = Metric.counter("effect_executions", {
14162 * description: "Counts effect executions"
14163 * }).pipe(Metric.withConstantInput(1))
14164 *
14165 * const program = Effect.succeed("Hello").pipe(
14166 * Effect.track(counter)
14167 * )
14168 *
14169 * Effect.runSync(program)
14170 * Effect.runSync(Metric.value(counter)).count // => 1
14171 * ```
14172 *
14173 * **Example** (Mapping exits)
14174 *
14175 * ```ts import.meta.vitest
14176 * import { Effect, Exit, Metric } from "effect"
14177 *
14178 * const exitTracker = Metric.frequency("exit_types", {
14179 * description: "Tracks success/failure/defect counts"
14180 * })
14181 *
14182 * const mapExitToString = (exit: Exit.Exit<string, Error>) => {
14183 * if (Exit.isSuccess(exit)) return "success"
14184 * if (Exit.isFailure(exit)) return "failure"
14185 * return "defect"
14186 * }
14187 *
14188 * const effect = Effect.succeed("result").pipe(
14189 * Effect.track(exitTracker, mapExitToString)
14190 * )
14191 * Effect.runSync(effect)
14192 * Effect.runSync(Metric.value(exitTracker)).occurrences.get("success") // => 1
14193 * ```
14194 *
14195 * @category metrics
14196 * @since 4.0.0
14197 */
14198export const track: {
14199 <Input, State, E, A>(
14200 metric: Metric.Metric<Input, State>,
14201 f: (exit: Exit.Exit<A, E>) => Input
14202 ): <E2 extends E, R>(self: Effect<A, E2, R>) => Effect<A, E2, R>
14203 <State, E, A>(
14204 metric: Metric.Metric<Exit.Exit<NoInfer<A>, NoInfer<E>>, State>
14205 ): <R>(self: Effect<A, E, R>) => Effect<A, E, R>
14206 <A, E, R, Input, State>(
14207 self: Effect<A, E, R>,
14208 metric: Metric.Metric<Input, State>,
14209 f: (exit: Exit.Exit<A, E>) => Input
14210 ): Effect<A, E, R>
14211 <A, E, R, State>(
14212 self: Effect<A, E, R>,
14213 metric: Metric.Metric<Exit.Exit<NoInfer<A>, NoInfer<E>>, State>
14214 ): Effect<A, E, R>
14215} = dual(
14216 (args) => isEffect(args[0]),
14217 <A, E, R, Input, State>(
14218 self: Effect<A, E, R>,
14219 metric: Metric.Metric<Input, State>,
14220 f: (exit: Exit.Exit<A, E>) => Input
14221 ): Effect<A, E, R> =>
14222 onExit(self, (exit) => {
14223 const input = f === undefined ? exit : f(exit)
14224 return Metric.update(metric, input as any)
14225 })
14226)
14227
14228/**
14229 * Updates the provided `Metric` every time the wrapped `Effect` succeeds with
14230 * a value.
14231 *
14232 * **Details**
14233 *
14234 * Also accepts an optional function which can be used to map the success value
14235 * of the `Effect` into a valid `Input` for the `Metric`.
14236 *
14237 * **Example** (Counting successful results)
14238 *
14239 * ```ts import.meta.vitest
14240 * import { Effect, Metric } from "effect"
14241 *
14242 * const successCounter = Metric.counter("successes").pipe(
14243 * Metric.withConstantInput(1)
14244 * )
14245 *
14246 * const program = Effect.succeed(42).pipe(
14247 * Effect.trackSuccesses(successCounter)
14248 * )
14249 *
14250 * Effect.runSync(program)
14251 * Effect.runSync(Metric.value(successCounter)).count // => 1
14252 * ```
14253 *
14254 * **Example** (Mapping successes before tracking)
14255 *
14256 * ```ts import.meta.vitest
14257 * import { Effect, Metric } from "effect"
14258 *
14259 * // Track successful request sizes
14260 * const requestSizeGauge = Metric.gauge("request_size_bytes")
14261 *
14262 * const program = Effect.succeed("Hello World!").pipe(
14263 * Effect.trackSuccesses(requestSizeGauge, (value: string) => value.length)
14264 * )
14265 *
14266 * Effect.runSync(program)
14267 * Effect.runSync(Metric.value(requestSizeGauge)).value // => 12
14268 * ```
14269 *
14270 * @category metrics
14271 * @since 4.0.0
14272 */
14273export const trackSuccesses: {
14274 <Input, State, A>(
14275 metric: Metric.Metric<Input, State>,
14276 f: (value: A) => Input
14277 ): <E, R>(self: Effect<A, E, R>) => Effect<A, E, R>
14278 <State, A>(
14279 metric: Metric.Metric<NoInfer<A>, State>
14280 ): <E, R>(self: Effect<A, E, R>) => Effect<A, E, R>
14281 <A, E, R, Input, State>(
14282 self: Effect<A, E, R>,
14283 metric: Metric.Metric<Input, State>,
14284 f: (value: A) => Input
14285 ): Effect<A, E, R>
14286 <A, E, R, State>(
14287 self: Effect<A, E, R>,
14288 metric: Metric.Metric<NoInfer<A>, State>
14289 ): Effect<A, E, R>
14290} = dual(
14291 (args) => isEffect(args[0]),
14292 <A, E, R, Input, State>(
14293 self: Effect<A, E, R>,
14294 metric: Metric.Metric<Input, State>,
14295 f: ((value: A) => Input) | undefined
14296 ): Effect<A, E, R> =>
14297 tap(self, (value) => {
14298 const input = f === undefined ? value : f(value)
14299 return Metric.update(metric, input as any)
14300 })
14301)
14302
14303/**
14304 * Updates the provided `Metric` every time the wrapped `Effect` fails with an
14305 * **expected** error.
14306 *
14307 * **Details**
14308 *
14309 * Also accepts an optional function which can be used to map the error value
14310 * of the `Effect` into a valid `Input` for the `Metric`.
14311 *
14312 * **Example** (Counting expected failures)
14313 *
14314 * ```ts import.meta.vitest
14315 * import { Effect, Metric } from "effect"
14316 *
14317 * const errorCounter = Metric.counter("errors").pipe(
14318 * Metric.withConstantInput(1)
14319 * )
14320 *
14321 * const program = Effect.fail("Network timeout").pipe(
14322 * Effect.trackErrors(errorCounter)
14323 * )
14324 *
14325 * Effect.runSyncExit(program)
14326 * Effect.runSync(Metric.value(errorCounter)).count // => 1
14327 * ```
14328 *
14329 * **Example** (Mapping errors before tracking)
14330 *
14331 * ```ts import.meta.vitest
14332 * import { Data, Effect, Metric } from "effect"
14333 *
14334 * class ConnectionFailedError extends Data.TaggedError("ConnectionFailedError")<{}> {}
14335 *
14336 * // Track error types using frequency metric
14337 * const errorTypeFrequency = Metric.frequency("error_types")
14338 *
14339 * const program = Effect.fail(new ConnectionFailedError()).pipe(
14340 * Effect.trackErrors(errorTypeFrequency, (error: ConnectionFailedError) => error._tag)
14341 * )
14342 *
14343 * Effect.runSyncExit(program)
14344 * Effect.runSync(Metric.value(errorTypeFrequency)).occurrences.get("ConnectionFailedError") // => 1
14345 * ```
14346 *
14347 * @category metrics
14348 * @since 4.0.0
14349 */
14350export const trackErrors: {
14351 <Input, State, E>(
14352 metric: Metric.Metric<Input, State>,
14353 f: (error: E) => Input
14354 ): <A, R>(self: Effect<A, E, R>) => Effect<A, E, R>
14355 <State, E>(
14356 metric: Metric.Metric<NoInfer<E>, State>
14357 ): <A, R>(self: Effect<A, E, R>) => Effect<A, E, R>
14358 <A, E, R, Input, State>(
14359 self: Effect<A, E, R>,
14360 metric: Metric.Metric<Input, State>,
14361 f: (error: E) => Input
14362 ): Effect<A, E, R>
14363 <A, E, R, State>(
14364 self: Effect<A, E, R>,
14365 metric: Metric.Metric<NoInfer<E>, State>
14366 ): Effect<A, E, R>
14367} = dual(
14368 (args) => isEffect(args[0]),
14369 <A, E, R, Input, State>(
14370 self: Effect<A, E, R>,
14371 metric: Metric.Metric<Input, State>,
14372 f: ((error: E) => Input) | undefined
14373 ): Effect<A, E, R> =>
14374 tapError(self, (error) => {
14375 const input = f === undefined ? error : f(error)
14376 return Metric.update(metric, input as any)
14377 })
14378)
14379
14380/**
14381 * Updates the provided `Metric` every time the wrapped `Effect` fails with an
14382 * **unexpected** error (i.e. a defect).
14383 *
14384 * **Details**
14385 *
14386 * Also accepts an optional function which can be used to map the defect value
14387 * of the `Effect` into a valid `Input` for the `Metric`.
14388 *
14389 * **Example** (Counting defects)
14390 *
14391 * ```ts import.meta.vitest
14392 * import { Effect, Metric } from "effect"
14393 *
14394 * const defectCounter = Metric.counter("defects").pipe(
14395 * Metric.withConstantInput(1)
14396 * )
14397 *
14398 * const program = Effect.die("Critical system failure").pipe(
14399 * Effect.trackDefects(defectCounter)
14400 * )
14401 *
14402 * Effect.runSyncExit(program)
14403 * Effect.runSync(Metric.value(defectCounter)).count // => 1
14404 * ```
14405 *
14406 * **Example** (Mapping defects before tracking)
14407 *
14408 * ```ts import.meta.vitest
14409 * import { Effect, Metric } from "effect"
14410 *
14411 * // Track defect types using frequency metric
14412 * const defectTypeFrequency = Metric.frequency("defect_types")
14413 *
14414 * const program = Effect.die(new Error("Null pointer exception")).pipe(
14415 * Effect.trackDefects(defectTypeFrequency, (defect: unknown) => {
14416 * if (defect instanceof Error) return defect.constructor.name
14417 * return typeof defect
14418 * })
14419 * )
14420 *
14421 * Effect.runSyncExit(program)
14422 * Effect.runSync(Metric.value(defectTypeFrequency)).occurrences.get("Error") // => 1
14423 * ```
14424 *
14425 * @category metrics
14426 * @since 4.0.0
14427 */
14428export const trackDefects: {
14429 <Input, State>(
14430 metric: Metric.Metric<Input, State>,
14431 f: (defect: unknown) => Input
14432 ): <A, E, R>(self: Effect<A, E, R>) => Effect<A, E, R>
14433 <State, E>(
14434 metric: Metric.Metric<unknown, State>
14435 ): <A, R>(self: Effect<A, E, R>) => Effect<A, E, R>
14436 <A, E, R, Input, State>(
14437 self: Effect<A, E, R>,
14438 metric: Metric.Metric<Input, State>,
14439 f: (defect: unknown) => Input
14440 ): Effect<A, E, R>
14441 <A, E, R, State>(
14442 self: Effect<A, E, R>,
14443 metric: Metric.Metric<unknown, State>
14444 ): Effect<A, E, R>
14445} = dual(
14446 (args) => isEffect(args[0]),
14447 (self, metric, f) =>
14448 tapDefect(self, (defect) => {
14449 const input = f === undefined ? defect : f(defect)
14450 return Metric.update(metric, input)
14451 })
14452)
14453
14454/**
14455 * Updates the provided `Metric` with the `Duration` of time (in nanoseconds)
14456 * that the wrapped `Effect` took to complete.
14457 *
14458 * **Details**
14459 *
14460 * Also accepts an optional function which can be used to map the `Duration`
14461 * that the wrapped `Effect` took to complete into a valid `Input` for the
14462 * `Metric`.
14463 *
14464 * **Example** (Recording execution duration)
14465 *
14466 * ```ts import.meta.vitest
14467 * import { Effect, Metric } from "effect"
14468 *
14469 * const executionTimer = Metric.timer("execution_time")
14470 *
14471 * const program = Effect.succeed("done").pipe(
14472 * Effect.trackDuration(executionTimer)
14473 * )
14474 *
14475 * Effect.runSync(program)
14476 * Effect.runSync(Metric.value(executionTimer)).count // => 1
14477 * ```
14478 *
14479 * **Example** (Mapping duration before tracking)
14480 *
14481 * ```ts import.meta.vitest
14482 * import { Effect, Metric } from "effect"
14483 *
14484 * // Track execution time in milliseconds using custom mapping
14485 * const durationGauge = Metric.gauge("execution_millis")
14486 *
14487 * const program = Effect.succeed("done").pipe(
14488 * Effect.trackDuration(durationGauge, () => 1)
14489 * )
14490 *
14491 * Effect.runSync(program)
14492 * Effect.runSync(Metric.value(durationGauge)).value // => 1
14493 * ```
14494 *
14495 * @category metrics
14496 * @since 4.0.0
14497 */
14498export const trackDuration: {
14499 <Input, State>(
14500 metric: Metric.Metric<Input, State>,
14501 f: (duration: Duration.Duration) => Input
14502 ): <A, E, R>(self: Effect<A, E, R>) => Effect<A, E, R>
14503 <State, E>(
14504 metric: Metric.Metric<Duration.Duration, State>
14505 ): <A, R>(self: Effect<A, E, R>) => Effect<A, E, R>
14506 <A, E, R, Input, State>(
14507 self: Effect<A, E, R>,
14508 metric: Metric.Metric<Input, State>,
14509 f: (duration: Duration.Duration) => Input
14510 ): Effect<A, E, R>
14511 <A, E, R, State>(
14512 self: Effect<A, E, R>,
14513 metric: Metric.Metric<Duration.Duration, State>
14514 ): Effect<A, E, R>
14515} = dual(
14516 (args) => isEffect(args[0]),
14517 <A, E, R, Input, State>(
14518 self: Effect<A, E, R>,
14519 metric: Metric.Metric<Input, State>,
14520 f: ((duration: Duration.Duration) => Input) | undefined
14521 ): Effect<A, E, R> =>
14522 clockWith((clock) => {
14523 const startTime = clock.monotonicTimeNanosUnsafe()
14524 return onExit(self, () => {
14525 const endTime = clock.monotonicTimeNanosUnsafe()
14526 const duration = Duration.subtract(
14527 Duration.fromInputUnsafe(endTime),
14528 Duration.fromInputUnsafe(startTime)
14529 )
14530 const input = f === undefined ? duration : f(duration)
14531 return Metric.update(metric, input as any)
14532 })
14533 })
14534)
14535
14536// -----------------------------------------------------------------------------
14537// Transactions
14538// -----------------------------------------------------------------------------
14539
14540/**
14541 * Service that holds the current transaction state.
14542 *
14543 * **Details**
14544 *
14545 * It includes a journal that stores non-committed changes to `TxRef` values and
14546 * a retry flag that records whether the transaction should be retried.
14547 *
14548 * **Example** (Building transactions)
14549 *
14550 * ```ts import.meta.vitest
14551 * import { Effect } from "effect"
14552 *
14553 * // Transaction class for software transactional memory operations
14554 * const txEffect = Effect.gen(function*() {
14555 * const tx = yield* Effect.Transaction
14556 * // Use transaction for coordinated state changes
14557 * return "Transaction complete"
14558 * })
14559 *
14560 * const runnable = Effect.provideService(txEffect, Effect.Transaction, {
14561 * retry: false,
14562 * journal: new Map()
14563 * })
14564 * Effect.runSync(runnable) // => "Transaction complete"
14565 * ```
14566 *
14567 * @category transactions
14568 * @since 4.0.0
14569 */
14570export class Transaction extends Context.Service<
14571 Transaction,
14572 {
14573 retry: boolean
14574 readonly journal: Map<
14575 TxRef<any>,
14576 {
14577 readonly version: number
14578 value: any
14579 written: boolean
14580 }
14581 >
14582 }
14583>()("effect/Effect/Transaction") {}
14584
14585/**
14586 * Defines a transaction boundary. Transactions are "all or nothing" with respect to changes
14587 * made to transactional values (i.e. TxRef) that occur within the transaction body.
14588 *
14589 * **Details**
14590 *
14591 * If called inside an active transaction, `tx` composes with the current transaction and reuses
14592 * its journal and retry state instead of creating a nested boundary.
14593 *
14594 * Effect transactions are optimistic with retry. A transaction is retried when
14595 * its body explicitly calls `Effect.txRetry` and any accessed transactional
14596 * value changes, or when any accessed transactional value changes because a
14597 * different transaction commits before the current one.
14598 *
14599 * The outermost `tx` call creates the transaction boundary and commits or rolls back the full
14600 * composed transaction.
14601 *
14602 * **Example** (Running a transaction)
14603 *
14604 * ```ts import.meta.vitest
14605 * import { Effect, TxRef } from "effect"
14606 * const output: Array<unknown> = []
14607 *
14608 * const program = Effect.gen(function*() {
14609 * const ref1 = yield* TxRef.make(0)
14610 * const ref2 = yield* TxRef.make(0)
14611 *
14612 * // Nested tx calls compose into the same transaction
14613 * yield* Effect.tx(Effect.gen(function*() {
14614 * yield* TxRef.set(ref1, 10)
14615 * yield* Effect.tx(TxRef.set(ref2, 20))
14616 * const sum = (yield* TxRef.get(ref1)) + (yield* TxRef.get(ref2))
14617 * void output.push(`Transaction sum: ${sum}`)
14618 * }))
14619 *
14620 * void output.push(`Final ref1: ${yield* TxRef.get(ref1)}`)
14621 * void output.push(`Final ref2: ${yield* TxRef.get(ref2)}`)
14622 * })
14623 *
14624 * Effect.runSync(program)
14625 * output // => ["Transaction sum: 30", "Final ref1: 10", "Final ref2: 20"]
14626 * ```
14627 *
14628 * @category transactions
14629 * @since 4.0.0
14630 */
14631export const tx = <A, E, R>(
14632 effect: Effect<A, E, R>
14633): Effect<A, E, Exclude<R, Transaction>> =>
14634 withFiber((fiber) => {
14635 let state = Context.getOrUndefined(fiber.context, Transaction)
14636 if (state) {
14637 return effect as Effect<A, E, Exclude<R, Transaction>>
14638 }
14639 // Create transaction state only at the outermost boundary
14640 state = { journal: new Map(), retry: false }
14641 let result: Exit.Exit<A, E> | undefined
14642 return uninterruptibleMask((restore) =>
14643 flatMap(
14644 whileLoop({
14645 while: () => !result,
14646 body: constant(
14647 restore(effect).pipe(
14648 provideService(Transaction, state),
14649 tapCause(() => {
14650 if (!state.retry) return void_
14651 return restore(awaitPendingTransaction(state))
14652 }),
14653 exit
14654 )
14655 ),
14656 step(exit: Exit.Exit<A, E>) {
14657 if (state.retry || !isTransactionConsistent(state)) {
14658 return clearTransaction(state)
14659 }
14660 if (Exit.isSuccess(exit)) {
14661 commitTransaction(fiber, state)
14662 } else {
14663 clearTransaction(state)
14664 }
14665 result = exit
14666 }
14667 }),
14668 () => result!
14669 )
14670 )
14671 })
14672
14673const isTransactionConsistent = (state: Transaction["Service"]) => {
14674 for (const [ref, { version }] of state.journal) {
14675 if (ref.version !== version) {
14676 return false
14677 }
14678 }
14679 return true
14680}
14681
14682const awaitPendingTransaction = (state: Transaction["Service"]) =>
14683 callback<void>((resume) => {
14684 // Validate the read set and register the waiter in one synchronous step.
14685 // A commit that landed after the reads has already signalled its waiters
14686 // and will not signal this one, so a stale read set reruns immediately.
14687 if (!isTransactionConsistent(state)) {
14688 return resume(void_)
14689 }
14690 const key = {}
14691 const refs = Array.from(state.journal.keys())
14692 const clearPending = () => {
14693 for (const clear of refs) {
14694 clear.pending.delete(key)
14695 }
14696 }
14697 const onCall = () => {
14698 clearPending()
14699 resume(void_)
14700 }
14701 for (const ref of refs) {
14702 ref.pending.set(key, onCall)
14703 }
14704 return sync(clearPending)
14705 })
14706
14707function commitTransaction(fiber: Fiber<unknown, unknown>, state: Transaction["Service"]) {
14708 for (const [ref, { value, written }] of state.journal) {
14709 if (!written) continue
14710 if (!Object.is(value, ref.value)) {
14711 ref.version = ref.version + 1
14712 ref.value = value
14713 }
14714 for (const pending of ref.pending.values()) {
14715 fiber.currentDispatcher.scheduleTask(pending, 0)
14716 }
14717 ref.pending.clear()
14718 }
14719}
14720
14721function clearTransaction(state: Transaction["Service"]) {
14722 state.retry = false
14723 state.journal.clear()
14724}
14725
14726/**
14727 * Retries the current transaction by signaling that it must be retried.
14728 *
14729 * **Details**
14730 *
14731 * NOTE: the transaction retries on any change to transactional values (i.e. TxRef) accessed in its body.
14732 *
14733 * **Example** (Retrying transactions)
14734 *
14735 * ```ts import.meta.vitest
14736 * import { Deferred, Effect, TxRef } from "effect"
14737 *
14738 * const program = Effect.gen(function*() {
14739 * const ref = yield* TxRef.make(0)
14740 * const update = yield* Deferred.make<void>()
14741 *
14742 * yield* Effect.forkChild(
14743 * Deferred.await(update).pipe(Effect.andThen(Effect.tx(TxRef.set(ref, 1))))
14744 * )
14745 *
14746 * return yield* Effect.tx(Effect.gen(function*() {
14747 * const value = yield* TxRef.get(ref)
14748 * if (value === 0) {
14749 * yield* Deferred.succeed(update, undefined)
14750 * return yield* Effect.txRetry
14751 * }
14752 * return value
14753 * }))
14754 * })
14755 *
14756 * await Effect.runPromise(program) // => 1
14757 * ```
14758 *
14759 * @category transactions
14760 * @since 4.0.0
14761 */
14762export const txRetry: Effect<never, never, Transaction> = flatMap(
14763 Transaction,
14764 (state) => {
14765 state.retry = true
14766 return interrupt
14767 }
14768)
14769/**
14770 * Type helpers for converting callback-based functions into `Effect` functions.
14771 *
14772 * @category converting
14773 * @since 4.0.0
14774 */
14775export declare namespace Effectify {
14776 interface Callback<E, A> {
14777 (err: E, a?: A): void
14778 }
14779
14780 type ArgsWithCallback<Args extends Array<any>, E, A> = [...args: Args, cb: Callback<E, A>]
14781
14782 type WithoutNull<A> = unknown extends A ? void : Exclude<A, null | undefined>
14783
14784 /**
14785 * Converts a callback-based function type into an `Effect`-returning function type.
14786 *
14787 * @category utility types
14788 * @since 4.0.0
14789 */
14790 export type Effectify<T, E> = T extends {
14791 (...args: ArgsWithCallback<infer Args1, infer _E1, infer A1>): infer _R1
14792 (...args: ArgsWithCallback<infer Args2, infer _E2, infer A2>): infer _R2
14793 (...args: ArgsWithCallback<infer Args3, infer _E3, infer A3>): infer _R3
14794 (...args: ArgsWithCallback<infer Args4, infer _E4, infer A4>): infer _R4
14795 (...args: ArgsWithCallback<infer Args5, infer _E5, infer A5>): infer _R5
14796 (...args: ArgsWithCallback<infer Args6, infer _E6, infer A6>): infer _R6
14797 (...args: ArgsWithCallback<infer Args7, infer _E7, infer A7>): infer _R7
14798 (...args: ArgsWithCallback<infer Args8, infer _E8, infer A8>): infer _R8
14799 (...args: ArgsWithCallback<infer Args9, infer _E9, infer A9>): infer _R9
14800 (...args: ArgsWithCallback<infer Args10, infer _E10, infer A10>): infer _R10
14801 } ? {
14802 (...args: Args1): Effect<WithoutNull<A1>, E>
14803 (...args: Args2): Effect<WithoutNull<A2>, E>
14804 (...args: Args3): Effect<WithoutNull<A3>, E>
14805 (...args: Args4): Effect<WithoutNull<A4>, E>
14806 (...args: Args5): Effect<WithoutNull<A5>, E>
14807 (...args: Args6): Effect<WithoutNull<A6>, E>
14808 (...args: Args7): Effect<WithoutNull<A7>, E>
14809 (...args: Args8): Effect<WithoutNull<A8>, E>
14810 (...args: Args9): Effect<WithoutNull<A9>, E>
14811 (...args: Args10): Effect<WithoutNull<A10>, E>
14812 }
14813 : T extends {
14814 (...args: ArgsWithCallback<infer Args1, infer _E1, infer A1>): infer _R1
14815 (...args: ArgsWithCallback<infer Args2, infer _E2, infer A2>): infer _R2
14816 (...args: ArgsWithCallback<infer Args3, infer _E3, infer A3>): infer _R3
14817 (...args: ArgsWithCallback<infer Args4, infer _E4, infer A4>): infer _R4
14818 (...args: ArgsWithCallback<infer Args5, infer _E5, infer A5>): infer _R5
14819 (...args: ArgsWithCallback<infer Args6, infer _E6, infer A6>): infer _R6
14820 (...args: ArgsWithCallback<infer Args7, infer _E7, infer A7>): infer _R7
14821 (...args: ArgsWithCallback<infer Args8, infer _E8, infer A8>): infer _R8
14822 (...args: ArgsWithCallback<infer Args9, infer _E9, infer A9>): infer _R9
14823 } ? {
14824 (...args: Args1): Effect<WithoutNull<A1>, E>
14825 (...args: Args2): Effect<WithoutNull<A2>, E>
14826 (...args: Args3): Effect<WithoutNull<A3>, E>
14827 (...args: Args4): Effect<WithoutNull<A4>, E>
14828 (...args: Args5): Effect<WithoutNull<A5>, E>
14829 (...args: Args6): Effect<WithoutNull<A6>, E>
14830 (...args: Args7): Effect<WithoutNull<A7>, E>
14831 (...args: Args8): Effect<WithoutNull<A8>, E>
14832 (...args: Args9): Effect<WithoutNull<A9>, E>
14833 }
14834 : T extends {
14835 (...args: ArgsWithCallback<infer Args1, infer _E1, infer A1>): infer _R1
14836 (...args: ArgsWithCallback<infer Args2, infer _E2, infer A2>): infer _R2
14837 (...args: ArgsWithCallback<infer Args3, infer _E3, infer A3>): infer _R3
14838 (...args: ArgsWithCallback<infer Args4, infer _E4, infer A4>): infer _R4
14839 (...args: ArgsWithCallback<infer Args5, infer _E5, infer A5>): infer _R5
14840 (...args: ArgsWithCallback<infer Args6, infer _E6, infer A6>): infer _R6
14841 (...args: ArgsWithCallback<infer Args7, infer _E7, infer A7>): infer _R7
14842 (...args: ArgsWithCallback<infer Args8, infer _E8, infer A8>): infer _R8
14843 } ? {
14844 (...args: Args1): Effect<WithoutNull<A1>, E>
14845 (...args: Args2): Effect<WithoutNull<A2>, E>
14846 (...args: Args3): Effect<WithoutNull<A3>, E>
14847 (...args: Args4): Effect<WithoutNull<A4>, E>
14848 (...args: Args5): Effect<WithoutNull<A5>, E>
14849 (...args: Args6): Effect<WithoutNull<A6>, E>
14850 (...args: Args7): Effect<WithoutNull<A7>, E>
14851 (...args: Args8): Effect<WithoutNull<A8>, E>
14852 }
14853 : T extends {
14854 (...args: ArgsWithCallback<infer Args1, infer _E1, infer A1>): infer _R1
14855 (...args: ArgsWithCallback<infer Args2, infer _E2, infer A2>): infer _R2
14856 (...args: ArgsWithCallback<infer Args3, infer _E3, infer A3>): infer _R3
14857 (...args: ArgsWithCallback<infer Args4, infer _E4, infer A4>): infer _R4
14858 (...args: ArgsWithCallback<infer Args5, infer _E5, infer A5>): infer _R5
14859 (...args: ArgsWithCallback<infer Args6, infer _E6, infer A6>): infer _R6
14860 (...args: ArgsWithCallback<infer Args7, infer _E7, infer A7>): infer _R7
14861 } ? {
14862 (...args: Args1): Effect<WithoutNull<A1>, E>
14863 (...args: Args2): Effect<WithoutNull<A2>, E>
14864 (...args: Args3): Effect<WithoutNull<A3>, E>
14865 (...args: Args4): Effect<WithoutNull<A4>, E>
14866 (...args: Args5): Effect<WithoutNull<A5>, E>
14867 (...args: Args6): Effect<WithoutNull<A6>, E>
14868 (...args: Args7): Effect<WithoutNull<A7>, E>
14869 }
14870 : T extends {
14871 (...args: ArgsWithCallback<infer Args1, infer _E1, infer A1>): infer _R1
14872 (...args: ArgsWithCallback<infer Args2, infer _E2, infer A2>): infer _R2
14873 (...args: ArgsWithCallback<infer Args3, infer _E3, infer A3>): infer _R3
14874 (...args: ArgsWithCallback<infer Args4, infer _E4, infer A4>): infer _R4
14875 (...args: ArgsWithCallback<infer Args5, infer _E5, infer A5>): infer _R5
14876 (...args: ArgsWithCallback<infer Args6, infer _E6, infer A6>): infer _R6
14877 } ? {
14878 (...args: Args1): Effect<WithoutNull<A1>, E>
14879 (...args: Args2): Effect<WithoutNull<A2>, E>
14880 (...args: Args3): Effect<WithoutNull<A3>, E>
14881 (...args: Args4): Effect<WithoutNull<A4>, E>
14882 (...args: Args5): Effect<WithoutNull<A5>, E>
14883 (...args: Args6): Effect<WithoutNull<A6>, E>
14884 }
14885 : T extends {
14886 (...args: ArgsWithCallback<infer Args1, infer _E1, infer A1>): infer _R1
14887 (...args: ArgsWithCallback<infer Args2, infer _E2, infer A2>): infer _R2
14888 (...args: ArgsWithCallback<infer Args3, infer _E3, infer A3>): infer _R3
14889 (...args: ArgsWithCallback<infer Args4, infer _E4, infer A4>): infer _R4
14890 (...args: ArgsWithCallback<infer Args5, infer _E5, infer A5>): infer _R5
14891 } ? {
14892 (...args: Args1): Effect<WithoutNull<A1>, E>
14893 (...args: Args2): Effect<WithoutNull<A2>, E>
14894 (...args: Args3): Effect<WithoutNull<A3>, E>
14895 (...args: Args4): Effect<WithoutNull<A4>, E>
14896 (...args: Args5): Effect<WithoutNull<A5>, E>
14897 }
14898 : T extends {
14899 (...args: ArgsWithCallback<infer Args1, infer _E1, infer A1>): infer _R1
14900 (...args: ArgsWithCallback<infer Args2, infer _E2, infer A2>): infer _R2
14901 (...args: ArgsWithCallback<infer Args3, infer _E3, infer A3>): infer _R3
14902 (...args: ArgsWithCallback<infer Args4, infer _E4, infer A4>): infer _R4
14903 } ? {
14904 (...args: Args1): Effect<WithoutNull<A1>, E>
14905 (...args: Args2): Effect<WithoutNull<A2>, E>
14906 (...args: Args3): Effect<WithoutNull<A3>, E>
14907 (...args: Args4): Effect<WithoutNull<A4>, E>
14908 }
14909 : T extends {
14910 (...args: ArgsWithCallback<infer Args1, infer _E1, infer A1>): infer _R1
14911 (...args: ArgsWithCallback<infer Args2, infer _E2, infer A2>): infer _R2
14912 (...args: ArgsWithCallback<infer Args3, infer _E3, infer A3>): infer _R3
14913 } ? {
14914 (...args: Args1): Effect<WithoutNull<A1>, E>
14915 (...args: Args2): Effect<WithoutNull<A2>, E>
14916 (...args: Args3): Effect<WithoutNull<A3>, E>
14917 }
14918 : T extends {
14919 (...args: ArgsWithCallback<infer Args1, infer _E1, infer A1>): infer _R1
14920 (...args: ArgsWithCallback<infer Args2, infer _E2, infer A2>): infer _R2
14921 } ? {
14922 (...args: Args1): Effect<WithoutNull<A1>, E>
14923 (...args: Args2): Effect<WithoutNull<A2>, E>
14924 }
14925 : T extends {
14926 (...args: ArgsWithCallback<infer Args1, infer _E1, infer A1>): infer _R1
14927 } ? {
14928 (...args: Args1): Effect<WithoutNull<A1>, E>
14929 }
14930 : never
14931
14932 /**
14933 * Extracts the callback error type from a callback-based function type.
14934 *
14935 * @category utility types
14936 * @since 4.0.0
14937 */
14938 export type EffectifyError<T> = T extends {
14939 (...args: ArgsWithCallback<infer _Args1, infer E1, infer _A1>): infer _R1
14940 (...args: ArgsWithCallback<infer _Args2, infer E2, infer _A2>): infer _R2
14941 (...args: ArgsWithCallback<infer _Args3, infer E3, infer _A3>): infer _R3
14942 (...args: ArgsWithCallback<infer _Args4, infer E4, infer _A4>): infer _R4
14943 (...args: ArgsWithCallback<infer _Args5, infer E5, infer _A5>): infer _R5
14944 (...args: ArgsWithCallback<infer _Args6, infer E6, infer _A6>): infer _R6
14945 (...args: ArgsWithCallback<infer _Args7, infer E7, infer _A7>): infer _R7
14946 (...args: ArgsWithCallback<infer _Args8, infer E8, infer _A8>): infer _R8
14947 (...args: ArgsWithCallback<infer _Args9, infer E9, infer _A9>): infer _R9
14948 (...args: ArgsWithCallback<infer _Args10, infer E10, infer _A10>): infer _R10
14949 } ? NonNullable<E1 | E2 | E3 | E4 | E5 | E6 | E7 | E8 | E9 | E10>
14950 : T extends {
14951 (...args: ArgsWithCallback<infer _Args1, infer E1, infer _A1>): infer _R1
14952 (...args: ArgsWithCallback<infer _Args2, infer E2, infer _A2>): infer _R2
14953 (...args: ArgsWithCallback<infer _Args3, infer E3, infer _A3>): infer _R3
14954 (...args: ArgsWithCallback<infer _Args4, infer E4, infer _A4>): infer _R4
14955 (...args: ArgsWithCallback<infer _Args5, infer E5, infer _A5>): infer _R5
14956 (...args: ArgsWithCallback<infer _Args6, infer E6, infer _A6>): infer _R6
14957 (...args: ArgsWithCallback<infer _Args7, infer E7, infer _A7>): infer _R7
14958 (...args: ArgsWithCallback<infer _Args8, infer E8, infer _A8>): infer _R8
14959 (...args: ArgsWithCallback<infer _Args9, infer E9, infer _A9>): infer _R9
14960 } ? NonNullable<E1 | E2 | E3 | E4 | E5 | E6 | E7 | E8 | E9>
14961 : T extends {
14962 (...args: ArgsWithCallback<infer _Args1, infer E1, infer _A1>): infer _R1
14963 (...args: ArgsWithCallback<infer _Args2, infer E2, infer _A2>): infer _R2
14964 (...args: ArgsWithCallback<infer _Args3, infer E3, infer _A3>): infer _R3
14965 (...args: ArgsWithCallback<infer _Args4, infer E4, infer _A4>): infer _R4
14966 (...args: ArgsWithCallback<infer _Args5, infer E5, infer _A5>): infer _R5
14967 (...args: ArgsWithCallback<infer _Args6, infer E6, infer _A6>): infer _R6
14968 (...args: ArgsWithCallback<infer _Args7, infer E7, infer _A7>): infer _R7
14969 (...args: ArgsWithCallback<infer _Args8, infer E8, infer _A8>): infer _R8
14970 } ? NonNullable<E1 | E2 | E3 | E4 | E5 | E6 | E7 | E8>
14971 : T extends {
14972 (...args: ArgsWithCallback<infer _Args1, infer E1, infer _A1>): infer _R1
14973 (...args: ArgsWithCallback<infer _Args2, infer E2, infer _A2>): infer _R2
14974 (...args: ArgsWithCallback<infer _Args3, infer E3, infer _A3>): infer _R3
14975 (...args: ArgsWithCallback<infer _Args4, infer E4, infer _A4>): infer _R4
14976 (...args: ArgsWithCallback<infer _Args5, infer E5, infer _A5>): infer _R5
14977 (...args: ArgsWithCallback<infer _Args6, infer E6, infer _A6>): infer _R6
14978 (...args: ArgsWithCallback<infer _Args7, infer E7, infer _A7>): infer _R7
14979 } ? NonNullable<E1 | E2 | E3 | E4 | E5 | E6 | E7>
14980 : T extends {
14981 (...args: ArgsWithCallback<infer _Args1, infer E1, infer _A1>): infer _R1
14982 (...args: ArgsWithCallback<infer _Args2, infer E2, infer _A2>): infer _R2
14983 (...args: ArgsWithCallback<infer _Args3, infer E3, infer _A3>): infer _R3
14984 (...args: ArgsWithCallback<infer _Args4, infer E4, infer _A4>): infer _R4
14985 (...args: ArgsWithCallback<infer _Args5, infer E5, infer _A5>): infer _R5
14986 (...args: ArgsWithCallback<infer _Args6, infer E6, infer _A6>): infer _R6
14987 } ? NonNullable<E1 | E2 | E3 | E4 | E5 | E6>
14988 : T extends {
14989 (...args: ArgsWithCallback<infer _Args1, infer E1, infer _A1>): infer _R1
14990 (...args: ArgsWithCallback<infer _Args2, infer E2, infer _A2>): infer _R2
14991 (...args: ArgsWithCallback<infer _Args3, infer E3, infer _A3>): infer _R3
14992 (...args: ArgsWithCallback<infer _Args4, infer E4, infer _A4>): infer _R4
14993 (...args: ArgsWithCallback<infer _Args5, infer E5, infer _A5>): infer _R5
14994 } ? NonNullable<E1 | E2 | E3 | E4 | E5>
14995 : T extends {
14996 (...args: ArgsWithCallback<infer _Args1, infer E1, infer _A1>): infer _R1
14997 (...args: ArgsWithCallback<infer _Args2, infer E2, infer _A2>): infer _R2
14998 (...args: ArgsWithCallback<infer _Args3, infer E3, infer _A3>): infer _R3
14999 (...args: ArgsWithCallback<infer _Args4, infer E4, infer _A4>): infer _R4
15000 } ? NonNullable<E1 | E2 | E3 | E4>
15001 : T extends {
15002 (...args: ArgsWithCallback<infer _Args1, infer E1, infer _A1>): infer _R1
15003 (...args: ArgsWithCallback<infer _Args2, infer E2, infer _A2>): infer _R2
15004 (...args: ArgsWithCallback<infer _Args3, infer E3, infer _A3>): infer _R3
15005 } ? NonNullable<E1 | E2 | E3>
15006 : T extends {
15007 (...args: ArgsWithCallback<infer _Args1, infer E1, infer _A1>): infer _R1
15008 (...args: ArgsWithCallback<infer _Args2, infer E2, infer _A2>): infer _R2
15009 } ? NonNullable<E1 | E2>
15010 : T extends {
15011 (...args: ArgsWithCallback<infer _Args1, infer E1, infer _A1>): infer _R1
15012 } ? NonNullable<E1>
15013 : never
15014}
15015
15016type EffectifyArgs<F extends (...args: Array<any>) => any> = Parameters<F> extends [...infer Args, any] ? Args
15017 : Parameters<F>
15018
15019/**
15020 * Converts an error-first callback API into a function that returns an
15021 * `Effect`.
15022 *
15023 * **Details**
15024 *
15025 * The original function is called with the supplied arguments plus a final
15026 * callback. A non-null callback error fails the returned effect, while a
15027 * successful callback value becomes the effect success. Use `onError` to map
15028 * callback errors and `onSyncError` to turn synchronous throws into typed
15029 * failures; otherwise synchronous throws become defects.
15030 *
15031 * **Example** (Converting callbacks to effects)
15032 *
15033 * ```ts import.meta.vitest
15034 * import { Effect } from "effect"
15035 *
15036 * const uppercase = (
15037 * input: string,
15038 * callback: (error: Error | null, value?: string) => void
15039 * ) => queueMicrotask(() => callback(null, input.toUpperCase()))
15040 *
15041 * const effectfulUppercase = Effect.effectify(uppercase)
15042 * const program = effectfulUppercase("hello")
15043 *
15044 * await Effect.runPromise(program) // => "HELLO"
15045 * ```
15046 *
15047 * **Example** (Mapping callback errors to typed failures)
15048 *
15049 * ```ts import.meta.vitest
15050 * import { Effect } from "effect"
15051 *
15052 * const fail = (
15053 * input: string,
15054 * callback: (error: Error | null, value?: string) => void
15055 * ) => queueMicrotask(() => callback(new Error("unavailable")))
15056 *
15057 * const effectfulFail = Effect.effectify(
15058 * fail,
15059 * (error, args) => new Error(`Failed to process ${args[0]}: ${error.message}`)
15060 * )
15061 *
15062 * const program = Effect.flip(effectfulFail("hello"))
15063 *
15064 * const error = await Effect.runPromise(program)
15065 * error.message // => "Failed to process hello: unavailable"
15066 * ```
15067 *
15068 * @category converting
15069 * @since 4.0.0
15070 */
15071export const effectify: {
15072 <F extends (...args: Array<any>) => any>(fn: F): Effectify.Effectify<F, Effectify.EffectifyError<F>>
15073 <F extends (...args: Array<any>) => any, E>(
15074 fn: F,
15075 onError: (error: Effectify.EffectifyError<F>, args: EffectifyArgs<F>) => E
15076 ): Effectify.Effectify<F, E>
15077 <F extends (...args: Array<any>) => any, E, E2>(
15078 fn: F,
15079 onError: (error: Effectify.EffectifyError<F>, args: EffectifyArgs<F>) => E,
15080 onSyncError: (error: unknown, args: EffectifyArgs<F>) => E2
15081 ): Effectify.Effectify<F, E | E2>
15082} =
15083 (<A>(fn: Function, onError?: (e: any, args: any) => any, onSyncError?: (e: any, args: any) => any) =>
15084 (...args: Array<any>) =>
15085 callback<A, globalThis.Error>((resume) => {
15086 try {
15087 fn(...args, (err: globalThis.Error | null, result: A) => {
15088 if (err) {
15089 resume(fail(onError ? onError(err, args) : err))
15090 } else {
15091 resume(succeed(result))
15092 }
15093 })
15094 } catch (err) {
15095 resume(onSyncError ? fail(onSyncError(err, args)) : die(err))
15096 }
15097 })) as any
15098
15099// -----------------------------------------------------------------------------
15100// Type constraints
15101// -----------------------------------------------------------------------------
15102
15103/**
15104 * Ensures that an effect's success type extends a given type `A`.
15105 *
15106 * **Details**
15107 *
15108 * This helper is checked at compile time and does not change the effect's
15109 * runtime behavior.
15110 *
15111 * **Example** (Constraining the success type)
15112 *
15113 * ```ts import.meta.vitest
15114 * import { Effect } from "effect"
15115 *
15116 * // Define a constraint that the success type must be a number
15117 * const satisfiesNumber = Effect.satisfiesSuccessType<number>()
15118 *
15119 * // This works - Effect<42, never, never> extends Effect<number, never, never>
15120 * const validEffect = satisfiesNumber(Effect.succeed(42))
15121 * Effect.runSync(validEffect) // => 42
15122 *
15123 * // This would cause a TypeScript compilation error:
15124 * // const invalidEffect = satisfiesNumber(Effect.succeed("string"))
15125 * // ^^^^^^^^^^^^^^^^^^^^^^
15126 * // Type 'string' is not assignable to type 'number'
15127 * ```
15128 *
15129 * @category utility types
15130 * @since 4.0.0
15131 */
15132export const satisfiesSuccessType = <A>() => <A2 extends A, E, R>(effect: Effect<A2, E, R>): Effect<A2, E, R> => effect
15133
15134/**
15135 * Ensures that an effect's error type extends a given type `E`.
15136 *
15137 * **Details**
15138 *
15139 * This helper is checked at compile time and does not change the effect's
15140 * runtime behavior.
15141 *
15142 * **Example** (Constraining the error type)
15143 *
15144 * ```ts import.meta.vitest
15145 * import { Data, Effect } from "effect"
15146 *
15147 * class ValidationError extends Data.TaggedError("ValidationError")<{}> {}
15148 *
15149 * // Define a constraint that the error type must be a ValidationError
15150 * const satisfiesError = Effect.satisfiesErrorType<ValidationError>()
15151 *
15152 * // This works - Effect<number, ValidationError, never> extends the constrained type
15153 * const validEffect = satisfiesError(Effect.fail(new ValidationError()))
15154 * Effect.runSync(Effect.flip(validEffect))._tag // => "ValidationError"
15155 *
15156 * // This would cause a TypeScript compilation error:
15157 * // const invalidEffect = satisfiesError(Effect.fail("string error"))
15158 * // ^^^^^^^^^^^^^^^^^^^^^^^^^^^
15159 * // Type 'string' is not assignable to type 'ValidationError'
15160 * ```
15161 *
15162 * @category utility types
15163 * @since 4.0.0
15164 */
15165export const satisfiesErrorType = <E>() => <A, E2 extends E, R>(effect: Effect<A, E2, R>): Effect<A, E2, R> => effect
15166
15167/**
15168 * Ensures that an effect's requirements type extends a given type `R`.
15169 *
15170 * **Details**
15171 *
15172 * This helper is checked at compile time and does not change the effect's
15173 * runtime behavior.
15174 *
15175 * **Example** (Constraining the services type)
15176 *
15177 * ```ts import.meta.vitest
15178 * import { Effect } from "effect"
15179 *
15180 * // Define a constraint that requires a string as the requirements type
15181 * const satisfiesStringServices = Effect.satisfiesServicesType<string>()
15182 *
15183 * // This works - effect requires string
15184 * const validEffect: Effect.Effect<number, never, "config"> = Effect.succeed(42)
15185 * const constrainedEffect = satisfiesStringServices(validEffect)
15186 *
15187 * // This would cause a TypeScript compilation error if uncommented:
15188 * // const invalidEffect: Effect.Effect<number, never, number> = Effect.succeed(42)
15189 * // const constrainedInvalid = satisfiesStringServices(invalidEffect)
15190 * ```
15191 *
15192 * @category utility types
15193 * @since 4.0.0
15194 */
15195export const satisfiesServicesType = <R>() => <A, E, R2 extends R>(effect: Effect<A, E, R2>): Effect<A, E, R2> => effect
15196
15197/**
15198 * Applies `map` eagerly when an effect is already resolved.
15199 *
15200 * **When to use**
15201 *
15202 * Use when an already-resolved effect should apply a success transformation
15203 * immediately while pending effects still use regular mapping.
15204 *
15205 * **Details**
15206 *
15207 * Success effects apply the mapping function immediately. Failure effects pass
15208 * through unchanged, and pending effects fall back to regular `map` behavior.
15209 *
15210 * **Example** (Mapping already completed effects)
15211 *
15212 * ```ts import.meta.vitest
15213 * import { Effect } from "effect"
15214 *
15215 * // For resolved effects, the mapping is applied immediately
15216 * const resolved = Effect.succeed(5)
15217 * const mapped = Effect.mapEager(resolved, (n) => n * 2) // Applied eagerly
15218 *
15219 * // For pending effects, behaves like regular map
15220 * const pending = Effect.delay(Effect.succeed(5), 0)
15221 * const mappedPending = Effect.mapEager(pending, (n) => n * 2) // Uses regular map
15222 *
15223 * await Effect.runPromise(Effect.all([mapped, mappedPending])) // => [10, 10]
15224 * ```
15225 *
15226 * @category mapping
15227 * @since 4.0.0
15228 */
15229export const mapEager: {
15230 <A, B>(f: (a: A) => B): <E, R>(self: Effect<A, E, R>) => Effect<B, E, R>
15231 <A, E, R, B>(self: Effect<A, E, R>, f: (a: A) => B): Effect<B, E, R>
15232} = internal.mapEager
15233
15234/**
15235 * Applies `mapError` eagerly when an effect is already resolved.
15236 *
15237 * **When to use**
15238 *
15239 * Use when an already-resolved failed effect should apply an error
15240 * transformation immediately while pending effects still use regular error
15241 * mapping.
15242 *
15243 * **Details**
15244 *
15245 * Success effects pass through unchanged because there is no error to
15246 * transform. Failure effects apply the mapping function immediately, and
15247 * pending effects fall back to regular `mapError` behavior.
15248 *
15249 * **Example** (Mapping errors eagerly when possible)
15250 *
15251 * ```ts import.meta.vitest
15252 * import { Effect } from "effect"
15253 * const output: Array<unknown> = []
15254 *
15255 * // For resolved failure effects, the error mapping is applied immediately
15256 * const failed = Effect.fail("original error")
15257 * const mapped = Effect.mapErrorEager(failed, (err: string) => `mapped: ${err}`) // Applied eagerly
15258 *
15259 * // For pending effects, behaves like regular mapError
15260 * const pending = Effect.delay(Effect.fail("error"), 0)
15261 * const mappedPending = Effect.mapErrorEager(
15262 * pending,
15263 * (err: string) => `mapped: ${err}`
15264 * ) // Uses regular mapError
15265 *
15266 * void output.push(await Effect.runPromise(Effect.all([
15267 * Effect.flip(mapped),
15268 * Effect.flip(mappedPending)
15269 * ])))
15270 * output // => [['mapped: original error', 'mapped: error']]
15271 * ```
15272 *
15273 * @category error handling
15274 * @since 4.0.0
15275 */
15276export const mapErrorEager: {
15277 <E, E2>(f: (e: E) => E2): <A, R>(self: Effect<A, E, R>) => Effect<A, E2, R>
15278 <A, E, R, E2>(self: Effect<A, E, R>, f: (e: E) => E2): Effect<A, E2, R>
15279} = internal.mapErrorEager
15280
15281/**
15282 * Applies `mapBoth` eagerly when an effect is already resolved.
15283 *
15284 * **When to use**
15285 *
15286 * Use when an already-resolved effect should transform either success or
15287 * failure immediately while pending effects still use regular channel mapping.
15288 *
15289 * **Details**
15290 *
15291 * Success effects apply `onSuccess` immediately, and failure effects apply
15292 * `onFailure` immediately. Pending effects fall back to regular `mapBoth`
15293 * behavior.
15294 *
15295 * **Example** (Mapping both channels eagerly when possible)
15296 *
15297 * ```ts import.meta.vitest
15298 * import { Effect } from "effect"
15299 * const output: Array<unknown> = []
15300 *
15301 * // For resolved effects, the appropriate mapping is applied immediately
15302 * const success = Effect.succeed(5)
15303 * const mapped = Effect.mapBothEager(success, {
15304 * onFailure: (err: string) => `Failed: ${err}`,
15305 * onSuccess: (n: number) => n * 2
15306 * }) // onSuccess applied eagerly
15307 *
15308 * const failure = Effect.fail("error")
15309 * const mappedError = Effect.mapBothEager(failure, {
15310 * onFailure: (err: string) => `Failed: ${err}`,
15311 * onSuccess: (n: number) => n * 2
15312 * }) // onFailure applied eagerly
15313 *
15314 * void output.push(Effect.runSync(mapped))
15315 * void output.push(Effect.runSync(Effect.flip(mappedError)))
15316 * output // => [10, "Failed: error"]
15317 * ```
15318 *
15319 * @category mapping
15320 * @since 4.0.0
15321 */
15322export const mapBothEager: {
15323 <E, E2, A, A2>(
15324 options: { readonly onFailure: (e: E) => E2; readonly onSuccess: (a: A) => A2 }
15325 ): <R>(self: Effect<A, E, R>) => Effect<A2, E2, R>
15326 <A, E, R, E2, A2>(
15327 self: Effect<A, E, R>,
15328 options: { readonly onFailure: (e: E) => E2; readonly onSuccess: (a: A) => A2 }
15329 ): Effect<A2, E2, R>
15330} = internal.mapBothEager
15331
15332/**
15333 * Applies `flatMap` eagerly when an effect is already resolved.
15334 *
15335 * **When to use**
15336 *
15337 * Use when an already-resolved successful effect should bind immediately to the
15338 * next effect while pending effects still use regular flat mapping.
15339 *
15340 * **Details**
15341 *
15342 * Success effects apply the flatMap function immediately. Failure effects pass
15343 * through unchanged, and pending effects fall back to regular `flatMap`
15344 * behavior.
15345 *
15346 * **Example** (Flat mapping eagerly when possible)
15347 *
15348 * ```ts import.meta.vitest
15349 * import { Effect } from "effect"
15350 *
15351 * // For resolved effects, the flatMap is applied immediately
15352 * const resolved = Effect.succeed(5)
15353 * const flatMapped = Effect.flatMapEager(resolved, (n) => Effect.succeed(n * 2)) // Applied eagerly
15354 *
15355 * // For pending effects, behaves like regular flatMap
15356 * const pending = Effect.delay(Effect.succeed(5), 0)
15357 * const flatMappedPending = Effect.flatMapEager(
15358 * pending,
15359 * (n) => Effect.succeed(n * 2)
15360 * ) // Uses regular flatMap
15361 *
15362 * await Effect.runPromise(Effect.all([flatMapped, flatMappedPending])) // => [10, 10]
15363 * ```
15364 *
15365 * @category sequencing
15366 * @since 4.0.0
15367 */
15368export const flatMapEager: {
15369 <A, B, E2, R2>(f: (a: A) => Effect<B, E2, R2>): <E, R>(self: Effect<A, E, R>) => Effect<B, E | E2, R | R2>
15370 <A, E, R, B, E2, R2>(self: Effect<A, E, R>, f: (a: A) => Effect<B, E2, R2>): Effect<B, E | E2, R | R2>
15371} = internal.flatMapEager
15372
15373/**
15374 * Applies `catch` eagerly when an effect is already resolved.
15375 *
15376 * **When to use**
15377 *
15378 * Use when an already-resolved failed effect should recover immediately while
15379 * pending effects still use regular error recovery.
15380 *
15381 * **Details**
15382 *
15383 * Success effects pass through unchanged because there is no error to catch.
15384 * Failure effects apply the catch function immediately, and pending effects
15385 * fall back to regular `catch` behavior.
15386 *
15387 * **Example** (Catching failures eagerly when possible)
15388 *
15389 * ```ts import.meta.vitest
15390 * import { Effect } from "effect"
15391 * const output: Array<unknown> = []
15392 *
15393 * // For resolved failure effects, the catch function is applied immediately
15394 * const failed = Effect.fail("original error")
15395 * const recovered = Effect.catchEager(
15396 * failed,
15397 * (err: string) => Effect.succeed(`recovered from: ${err}`)
15398 * ) // Applied eagerly
15399 *
15400 * // For success effects, returns success as-is
15401 * const success = Effect.succeed(42)
15402 * const unchanged = Effect.catchEager(
15403 * success,
15404 * (err: string) => Effect.succeed(`recovered from: ${err}`)
15405 * ) // Returns success as-is
15406 *
15407 * // For pending effects, behaves like regular catch
15408 * const pending = Effect.delay(Effect.fail("error"), 0)
15409 * const recoveredPending = Effect.catchEager(
15410 * pending,
15411 * (err: string) => Effect.succeed(`recovered from: ${err}`)
15412 * ) // Uses regular catch
15413 *
15414 * void output.push(await Effect.runPromise(Effect.all([
15415 * recovered,
15416 * unchanged,
15417 * recoveredPending
15418 * ])))
15419 * output // => [['recovered from: original error', 42, 'recovered from: error']]
15420 * ```
15421 *
15422 * @category error handling
15423 * @since 4.0.0
15424 */
15425export const catchEager: {
15426 <E, B, E2, R2>(
15427 f: (e: NoInfer<E>) => Effect<B, E2, R2>
15428 ): <A, R>(self: Effect<A, E, R>) => Effect<A | B, E2, R | R2>
15429 <A, E, R, B, E2, R2>(
15430 self: Effect<A, E, R>,
15431 f: (e: NoInfer<E>) => Effect<B, E2, R2>
15432 ): Effect<A | B, E2, R | R2>
15433} = internal.catchEager
15434
15435/**
15436 * Creates untraced function effects with eager evaluation optimization.
15437 *
15438 * **Details**
15439 *
15440 * Executes generator functions eagerly when all yielded effects are synchronous,
15441 * stopping at the first async effect and deferring to normal execution.
15442 *
15443 * **Example** (Defining eager untraced effect functions)
15444 *
15445 * ```ts import.meta.vitest
15446 * import { Effect } from "effect"
15447 *
15448 * const computation = Effect.fnUntracedEager(function*() {
15449 * yield* Effect.succeed(1)
15450 * yield* Effect.succeed(2)
15451 * return "computed eagerly"
15452 * })
15453 *
15454 * const effect = computation() // Executed immediately if all effects are sync
15455 * Effect.runSync(effect) // => "computed eagerly"
15456 * ```
15457 *
15458 * @category constructors
15459 * @since 4.0.0
15460 */
15461export const fnUntracedEager: fn.Untraced = internal.fnUntracedEager