"use strict";

Object.defineProperty(exports, "__esModule", {
  value: true
});
exports.zipWithOptions = exports.zipRightOptions = exports.zipOptions = exports.zipLeftOptions = exports.withTracerScoped = exports.withSpanScoped = exports.withRuntimeFlagsScoped = exports.withParentSpanScoped = exports.withEarlyRelease = exports.withConfigProviderScoped = exports.withClockScoped = exports.validateWith = exports.validateFirst = exports.validateAllParDiscard = exports.validateAllPar = exports.validateAll = exports.validate = exports.using = exports.useSpanScoped = exports.unsome = exports.unsafeMakeChildFiber = exports.unsafeFork = exports.tracerLogger = exports.tagMetricsScoped = exports.sequentialFinalizers = exports.scopedEffect = exports.scopeWith = exports.scopeUse = exports.scopeTag = exports.scopeMake = exports.scopeExtend = exports.scope = exports.runtimeFiberVariance = exports.replicateEffect = exports.replicate = exports.releaseMapReleaseAll = exports.reduceEffect = exports.raceWith = exports.raceFibersWith = exports.raceAll = exports.race = exports.partition = exports.parallelFinalizers = exports.mergeAll = exports.logFmtLogger = exports.labelMetricsScopedSet = exports.labelMetricsScoped = exports.invokeWithInterrupt = exports.interruptWhenPossible = exports.forkWithErrorHandler = exports.forkDaemon = exports.fork = exports.forEachParUnboundedDiscard = exports.forEachParUnbounded = exports.forEachParNDiscard = exports.forEachParN = exports.forEachOptions = exports.filterMinimumLogLevel = exports.filter = exports.fiberSuccesses = exports.fiberStarted = exports.fiberScoped = exports.fiberRefUnsafeMakeSupervisor = exports.fiberRefMakeWith = exports.fiberRefMakeRuntimeFlags = exports.fiberRefMakeContext = exports.fiberRefMake = exports.fiberRefLocallyScopedWith = exports.fiberRefLocallyScoped = exports.fiberLifetimes = exports.fiberJoinAll = exports.fiberInterruptFork = exports.fiberFailures = exports.fiberAwaitAll = exports.fiberAll = exports.fiberActive = exports.exists = exports.ensuring = exports.disconnect = exports.defaultLogger = exports.daemonChildren = exports.currentSupervisor = exports.currentRuntimeFlags = exports.currentMinimumLogLevel = exports.currentLoggers = exports.allWith = exports.allSuccesses = exports.all = exports.addFinalizer = exports.acquireReleaseInterruptible = exports.acquireRelease = exports.FiberRuntime = void 0;
var Boolean = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/data/Boolean"));
var Chunk = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/data/Chunk"));
var Context = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/data/Context"));
var _Function = /*#__PURE__*/require("@effect/data/Function");
var HashSet = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/data/HashSet"));
var List = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/data/List"));
var MRef = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/data/MutableRef"));
var Option = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/data/Option"));
var _Pipeable = /*#__PURE__*/require("@effect/data/Pipeable");
var Predicate = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/data/Predicate"));
var RA = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/data/ReadonlyArray"));
var Deferred = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/Deferred"));
var FiberId = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/Fiber/Id"));
var RuntimeFlagsPatch = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/Fiber/Runtime/Flags/Patch"));
var FiberStatus = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/Fiber/Status"));
var FiberRefsPatch = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/FiberRefs/Patch"));
var _RequestBlock = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/blockedRequests"));
var internalCause = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/cause"));
var clock = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/clock"));
var _completedRequestMap = /*#__PURE__*/require("@effect/io/internal/completedRequestMap");
var concurrency = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/concurrency"));
var _configProvider = /*#__PURE__*/require("@effect/io/internal/configProvider");
var core = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/core"));
var defaultServices = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/defaultServices"));
var internalEffect = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/effect"));
var executionStrategy = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/executionStrategy"));
var internalFiber = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/fiber"));
var FiberMessage = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/fiberMessage"));
var fiberRefs = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/fiberRefs"));
var fiberScope = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/fiberScope"));
var internalLogger = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/logger"));
var metric = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/metric"));
var metricBoundaries = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/metric/boundaries"));
var metricLabel = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/metric/label"));
var OpCodes = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/opCodes/effect"));
var _request = /*#__PURE__*/require("@effect/io/internal/request");
var _runtimeFlags = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/runtimeFlags"));
var supervisor = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/supervisor"));
var SupervisorPatch = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/supervisor/patch"));
var tracer = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/internal/tracer"));
var LogLevel = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/Logger/Level"));
var Ref = /*#__PURE__*/_interopRequireWildcard( /*#__PURE__*/require("@effect/io/Ref"));
function _getRequireWildcardCache(nodeInterop) { if (typeof WeakMap !== "function") return null; var cacheBabelInterop = new WeakMap(); var cacheNodeInterop = new WeakMap(); return (_getRequireWildcardCache = function (nodeInterop) { return nodeInterop ? cacheNodeInterop : cacheBabelInterop; })(nodeInterop); }
function _interopRequireWildcard(obj, nodeInterop) { if (!nodeInterop && obj && obj.__esModule) { return obj; } if (obj === null || typeof obj !== "object" && typeof obj !== "function") { return { default: obj }; } var cache = _getRequireWildcardCache(nodeInterop); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var key in obj) { if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } newObj.default = obj; if (cache) { cache.set(obj, newObj); } return newObj; }
var _a, _b;
/** @internal */
const fiberStarted = /*#__PURE__*/metric.counter("effect_fiber_started");
/** @internal */
exports.fiberStarted = fiberStarted;
const fiberActive = /*#__PURE__*/metric.counter("effect_fiber_active");
/** @internal */
exports.fiberActive = fiberActive;
const fiberSuccesses = /*#__PURE__*/metric.counter("effect_fiber_successes");
/** @internal */
exports.fiberSuccesses = fiberSuccesses;
const fiberFailures = /*#__PURE__*/metric.counter("effect_fiber_failures");
/** @internal */
exports.fiberFailures = fiberFailures;
const fiberLifetimes = /*#__PURE__*/metric.histogram("effect_fiber_lifetimes", /*#__PURE__*/metricBoundaries.exponential({
  start: 1.0,
  factor: 2.0,
  count: 100
}));
/** @internal */
exports.fiberLifetimes = fiberLifetimes;
const EvaluationSignalContinue = "Continue";
/** @internal */
const EvaluationSignalDone = "Done";
/** @internal */
const EvaluationSignalYieldNow = "Yield";
/** @internal */
const runtimeFiberVariance = {
  _E: _ => _,
  _A: _ => _
};
exports.runtimeFiberVariance = runtimeFiberVariance;
const absurd = _ => {
  throw new Error(`BUG: FiberRuntime - ${JSON.stringify(_)} - please report an issue at https://github.com/Effect-TS/io/issues`);
};
const contOpSuccess = {
  [OpCodes.OP_ON_SUCCESS]: (_, cont, value) => {
    return cont.i1(value);
  },
  ["OnStep"]: (_, cont, value) => {
    return cont.i1(core.exitSucceed(value));
  },
  [OpCodes.OP_ON_SUCCESS_AND_FAILURE]: (_, cont, value) => {
    return cont.i2(value);
  },
  [OpCodes.OP_REVERT_FLAGS]: (self, cont, value) => {
    self.patchRuntimeFlags(self._runtimeFlags, cont.patch);
    if (_runtimeFlags.interruptible(self._runtimeFlags) && self.isInterrupted()) {
      return core.exitFailCause(self.getInterruptedCause());
    } else {
      return core.exitSucceed(value);
    }
  },
  [OpCodes.OP_WHILE]: (self, cont, value) => {
    cont.i2(value);
    if (cont.i0()) {
      self.pushStack(cont);
      return cont.i1();
    } else {
      return core.unit;
    }
  }
};
const drainQueueWhileRunningTable = {
  [FiberMessage.OP_INTERRUPT_SIGNAL]: (self, runtimeFlags, cur, message) => {
    self.processNewInterruptSignal(message.cause);
    return _runtimeFlags.interruptible(runtimeFlags) ? core.exitFailCause(message.cause) : cur;
  },
  [FiberMessage.OP_RESUME]: (_self, _runtimeFlags, _cur, _message) => {
    throw new Error("It is illegal to have multiple concurrent run loops in a single fiber");
  },
  [FiberMessage.OP_STATEFUL]: (self, runtimeFlags, cur, message) => {
    message.onFiber(self, FiberStatus.running(runtimeFlags));
    return cur;
  },
  [FiberMessage.OP_YIELD_NOW]: (_self, _runtimeFlags, cur, _message) => {
    return core.flatMap(core.yieldNow(), () => cur);
  }
};
/**
 * Executes all requests, submitting requests to each data source in parallel.
 */
const runBlockedRequests = self => core.forEachSequentialDiscard(_RequestBlock.flatten(self), requestsByRequestResolver => forEachParUnboundedDiscard(_RequestBlock.sequentialCollectionToChunk(requestsByRequestResolver), ([dataSource, sequential]) => {
  const map = new Map();
  for (const block of sequential) {
    for (const entry of block) {
      map.set(entry.request, entry);
    }
  }
  return core.fiberRefLocally(invokeWithInterrupt(dataSource.runAll(sequential), sequential.flat()), _completedRequestMap.currentRequestMap, map);
}, false));
/** @internal */
class FiberRuntime {
  pipe() {
    return (0, _Pipeable.pipeArguments)(this, arguments);
  }
  constructor(fiberId, fiberRefs0, runtimeFlags0) {
    this[_a] = internalFiber.fiberVariance;
    this[_b] = runtimeFiberVariance;
    this._queue = new Array();
    this._children = null;
    this._observers = new Array();
    this._running = false;
    this._stack = [];
    this._asyncInterruptor = null;
    this._asyncBlockingOn = null;
    this._exitValue = null;
    this._steps = [false];
    this.run = () => {
      this.drainQueueOnCurrentThread();
    };
    this._runtimeFlags = runtimeFlags0;
    this._fiberId = fiberId;
    this._fiberRefs = fiberRefs0;
    this._supervisor = this.getFiberRef(currentSupervisor);
    if (_runtimeFlags.runtimeMetrics(runtimeFlags0)) {
      const tags = this.getFiberRef(core.currentMetricLabels);
      fiberStarted.unsafeUpdate(1, tags);
      fiberActive.unsafeUpdate(1, tags);
    }
  }
  /**
   * The identity of the fiber.
   */
  id() {
    return this._fiberId;
  }
  /**
   * Begins execution of the effect associated with this fiber on in the
   * background. This can be called to "kick off" execution of a fiber after
   * it has been created.
   */
  resume(effect) {
    this.tell(FiberMessage.resume(effect));
  }
  /**
   * The status of the fiber.
   */
  status() {
    return this.ask((_, status) => status);
  }
  /**
   * Gets the fiber runtime flags.
   */
  runtimeFlags() {
    return this.ask((state, status) => {
      if (FiberStatus.isDone(status)) {
        return state._runtimeFlags;
      }
      return status.runtimeFlags;
    });
  }
  /**
   * Returns the current `FiberScope` for the fiber.
   */
  scope() {
    return fiberScope.unsafeMake(this);
  }
  /**
   * Retrieves the immediate children of the fiber.
   */
  children() {
    return this.ask(fiber => Array.from(fiber.getChildren()));
  }
  /**
   * Gets the fiber's set of children.
   */
  getChildren() {
    if (this._children === null) {
      this._children = new Set();
    }
    return this._children;
  }
  /**
   * Retrieves the interrupted cause of the fiber, which will be `Cause.empty`
   * if the fiber has not been interrupted.
   *
   * **NOTE**: This method is safe to invoke on any fiber, but if not invoked
   * on this fiber, then values derived from the fiber's state (including the
   * log annotations and log level) may not be up-to-date.
   */
  getInterruptedCause() {
    return this.getFiberRef(core.currentInterruptedCause);
  }
  /**
   * Retrieves the whole set of fiber refs.
   */
  fiberRefs() {
    return this.ask(fiber => fiber.unsafeGetFiberRefs());
  }
  /**
   * Returns an effect that will contain information computed from the fiber
   * state and status while running on the fiber.
   *
   * This allows the outside world to interact safely with mutable fiber state
   * without locks or immutable data.
   */
  ask(f) {
    return core.suspend(() => {
      const deferred = core.deferredUnsafeMake(this._fiberId);
      this.tell(FiberMessage.stateful((fiber, status) => {
        core.deferredUnsafeDone(deferred, core.sync(() => f(fiber, status)));
      }));
      return core.deferredAwait(deferred);
    });
  }
  /**
   * Adds a message to be processed by the fiber on the fiber.
   */
  tell(message) {
    this._queue.push(message);
    if (!this._running) {
      this._running = true;
      this.drainQueueLaterOnExecutor();
    }
  }
  await() {
    return core.async(resume => {
      const cb = exit => resume(core.succeed(exit));
      this.tell(FiberMessage.stateful((fiber, _) => {
        if (fiber._exitValue !== null) {
          cb(this._exitValue);
        } else {
          fiber.unsafeAddObserver(cb);
        }
      }));
      return core.sync(() => this.tell(FiberMessage.stateful((fiber, _) => {
        fiber.unsafeRemoveObserver(cb);
      })));
    }, this.id());
  }
  inheritAll() {
    return core.withFiberRuntime((parentFiber, parentStatus) => {
      const parentFiberId = parentFiber.id();
      const parentFiberRefs = parentFiber.unsafeGetFiberRefs();
      const parentRuntimeFlags = parentStatus.runtimeFlags;
      const childFiberRefs = this.unsafeGetFiberRefs();
      const updatedFiberRefs = fiberRefs.joinAs(parentFiberRefs, parentFiberId, childFiberRefs);
      parentFiber.setFiberRefs(updatedFiberRefs);
      const updatedRuntimeFlags = parentFiber.getFiberRef(currentRuntimeFlags);
      const patch = RuntimeFlagsPatch.exclude(_runtimeFlags.WindDown)(
      // Do not inherit WindDown or Interruption!
      RuntimeFlagsPatch.exclude(_runtimeFlags.Interruption)(_runtimeFlags.diff(parentRuntimeFlags, updatedRuntimeFlags)));
      return core.updateRuntimeFlags(patch);
    });
  }
  /**
   * Tentatively observes the fiber, but returns immediately if it is not
   * already done.
   */
  poll() {
    return core.sync(() => Option.fromNullable(this._exitValue));
  }
  /**
   * Unsafely observes the fiber, but returns immediately if it is not
   * already done.
   */
  unsafePoll() {
    return this._exitValue;
  }
  /**
   * In the background, interrupts the fiber as if interrupted from the specified fiber.
   */
  interruptAsFork(fiberId) {
    return core.sync(() => this.tell(FiberMessage.interruptSignal(internalCause.interrupt(fiberId))));
  }
  /**
   * Adds an observer to the list of observers.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  unsafeAddObserver(observer) {
    if (this._exitValue !== null) {
      observer(this._exitValue);
    } else {
      this._observers.push(observer);
    }
  }
  /**
   * Removes the specified observer from the list of observers that will be
   * notified when the fiber exits.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  unsafeRemoveObserver(observer) {
    this._observers = this._observers.filter(o => o !== observer);
  }
  /**
   * Retrieves all fiber refs of the fiber.
   *
   * **NOTE**: This method is safe to invoke on any fiber, but if not invoked
   * on this fiber, then values derived from the fiber's state (including the
   * log annotations and log level) may not be up-to-date.
   */
  unsafeGetFiberRefs() {
    this.setFiberRef(currentRuntimeFlags, this._runtimeFlags);
    return this._fiberRefs;
  }
  /**
   * Deletes the specified fiber ref.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  unsafeDeleteFiberRef(fiberRef) {
    this._fiberRefs = fiberRefs.delete_(this._fiberRefs, fiberRef);
  }
  /**
   * Retrieves the state of the fiber ref, or else its initial value.
   *
   * **NOTE**: This method is safe to invoke on any fiber, but if not invoked
   * on this fiber, then values derived from the fiber's state (including the
   * log annotations and log level) may not be up-to-date.
   */
  getFiberRef(fiberRef) {
    if (this._fiberRefs.locals.has(fiberRef)) {
      return this._fiberRefs.locals.get(fiberRef)[0][1];
    }
    return fiberRef.initial;
  }
  /**
   * Sets the fiber ref to the specified value.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  setFiberRef(fiberRef, value) {
    this._fiberRefs = fiberRefs.updatedAs(this._fiberRefs, {
      fiberId: this._fiberId,
      fiberRef,
      value
    });
    // @ts-expect-error
    if (fiberRef === currentSupervisor) {
      // @ts-expect-error
      this._supervisor = value;
    }
  }
  /**
   * Wholesale replaces all fiber refs of this fiber.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  setFiberRefs(fiberRefs) {
    this._fiberRefs = fiberRefs;
    this._supervisor = this.getFiberRef(currentSupervisor);
  }
  /**
   * Adds a reference to the specified fiber inside the children set.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  addChild(child) {
    this.getChildren().add(child);
  }
  /**
   * Removes a reference to the specified fiber inside the children set.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  removeChild(child) {
    this.getChildren().delete(child);
  }
  /**
   * On the current thread, executes all messages in the fiber's inbox. This
   * method may return before all work is done, in the event the fiber executes
   * an asynchronous operation.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  drainQueueOnCurrentThread() {
    let recurse = true;
    while (recurse) {
      let evaluationSignal = EvaluationSignalContinue;
      const prev = globalThis[internalFiber.currentFiberURI];
      globalThis[internalFiber.currentFiberURI] = this;
      try {
        while (evaluationSignal === EvaluationSignalContinue) {
          evaluationSignal = this._queue.length === 0 ? EvaluationSignalDone : this.evaluateMessageWhileSuspended(this._queue.splice(0, 1)[0]);
        }
      } finally {
        this._running = false;
        globalThis[internalFiber.currentFiberURI] = prev;
      }
      // Maybe someone added something to the queue between us checking, and us
      // giving up the drain. If so, we need to restart the draining, but only
      // if we beat everyone else to the restart:
      if (this._queue.length > 0 && !this._running) {
        this._running = true;
        if (evaluationSignal === EvaluationSignalYieldNow) {
          this.drainQueueLaterOnExecutor();
          recurse = false;
        } else {
          recurse = true;
        }
      } else {
        recurse = false;
      }
    }
  }
  /**
   * Schedules the execution of all messages in the fiber's inbox.
   *
   * This method will return immediately after the scheduling
   * operation is completed, but potentially before such messages have been
   * executed.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  drainQueueLaterOnExecutor() {
    this.getFiberRef(core.currentScheduler).scheduleTask(this.run, this.getFiberRef(core.currentSchedulingPriority));
  }
  /**
   * Drains the fiber's message queue while the fiber is actively running,
   * returning the next effect to execute, which may be the input effect if no
   * additional effect needs to be executed.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  drainQueueWhileRunning(runtimeFlags, cur0) {
    let cur = cur0;
    while (this._queue.length > 0) {
      const message = this._queue.splice(0, 1)[0];
      // @ts-expect-error
      cur = drainQueueWhileRunningTable[message._tag](this, runtimeFlags, cur, message);
    }
    return cur;
  }
  /**
   * Determines if the fiber is interrupted.
   *
   * **NOTE**: This method is safe to invoke on any fiber, but if not invoked
   * on this fiber, then values derived from the fiber's state (including the
   * log annotations and log level) may not be up-to-date.
   */
  isInterrupted() {
    return !internalCause.isEmpty(this.getFiberRef(core.currentInterruptedCause));
  }
  /**
   * Adds an interruptor to the set of interruptors that are interrupting this
   * fiber.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  addInterruptedCause(cause) {
    const oldSC = this.getFiberRef(core.currentInterruptedCause);
    this.setFiberRef(core.currentInterruptedCause, internalCause.sequential(oldSC, cause));
  }
  /**
   * Processes a new incoming interrupt signal.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  processNewInterruptSignal(cause) {
    this.addInterruptedCause(cause);
    this.sendInterruptSignalToAllChildren();
  }
  /**
   * Interrupts all children of the current fiber, returning an effect that will
   * await the exit of the children. This method will return null if the fiber
   * has no children.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  sendInterruptSignalToAllChildren() {
    if (this._children === null || this._children.size === 0) {
      return false;
    }
    let told = false;
    for (const child of this._children) {
      child.tell(FiberMessage.interruptSignal(internalCause.interrupt(this.id())));
      told = true;
    }
    return told;
  }
  /**
   * Interrupts all children of the current fiber, returning an effect that will
   * await the exit of the children. This method will return null if the fiber
   * has no children.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  interruptAllChildren() {
    if (this.sendInterruptSignalToAllChildren()) {
      const it = this._children.values();
      this._children = null;
      let isDone = false;
      const body = () => {
        const next = it.next();
        if (!next.done) {
          return core.asUnit(next.value.await());
        } else {
          return core.sync(() => {
            isDone = true;
          });
        }
      };
      return core.whileLoop({
        while: () => !isDone,
        body,
        step: () => {
          //
        }
      });
    }
    return null;
  }
  reportExitValue(exit) {
    if (_runtimeFlags.runtimeMetrics(this._runtimeFlags)) {
      const tags = this.getFiberRef(core.currentMetricLabels);
      fiberActive.unsafeUpdate(-1, tags);
      switch (exit._tag) {
        case OpCodes.OP_SUCCESS:
          {
            fiberSuccesses.unsafeUpdate(1, tags);
            break;
          }
        case OpCodes.OP_FAILURE:
          {
            fiberFailures.unsafeUpdate(1, tags);
            break;
          }
      }
    }
    if (exit._tag === "Failure") {
      const level = this.getFiberRef(core.currentUnhandledErrorLogLevel);
      if (!internalCause.isInterruptedOnly(exit.cause) && level._tag === "Some") {
        this.log("Fiber terminated with a non handled error", exit.cause, level);
      }
    }
  }
  setExitValue(exit) {
    this._exitValue = exit;
    if (_runtimeFlags.runtimeMetrics(this._runtimeFlags)) {
      const tags = this.getFiberRef(core.currentMetricLabels);
      const startTimeMillis = this.id().startTimeMillis;
      const endTimeMillis = new Date().getTime();
      fiberLifetimes.unsafeUpdate((endTimeMillis - startTimeMillis) / 1000.0, tags);
    }
    this.reportExitValue(exit);
    for (let i = this._observers.length - 1; i >= 0; i--) {
      this._observers[i](exit);
    }
  }
  getLoggers() {
    return this.getFiberRef(currentLoggers);
  }
  log(message, cause, overrideLogLevel) {
    const logLevel = Option.isSome(overrideLogLevel) ? overrideLogLevel.value : this.getFiberRef(core.currentLogLevel);
    const minimumLogLevel = this.getFiberRef(currentMinimumLogLevel);
    if (LogLevel.greaterThan(minimumLogLevel, logLevel)) {
      return;
    }
    const spans = this.getFiberRef(core.currentLogSpan);
    const annotations = this.getFiberRef(core.currentLogAnnotations);
    const loggers = this.getLoggers();
    const contextMap = this.unsafeGetFiberRefs();
    if (HashSet.size(loggers) > 0) {
      const clockService = Context.get(this.getFiberRef(defaultServices.currentServices), clock.clockTag);
      const date = new Date(clockService.unsafeCurrentTimeMillis());
      for (const logger of loggers) {
        logger.log({
          fiberId: this.id(),
          logLevel,
          message,
          cause,
          context: contextMap,
          spans,
          annotations,
          date
        });
      }
    }
  }
  /**
   * Evaluates a single message on the current thread, while the fiber is
   * suspended. This method should only be called while evaluation of the
   * fiber's effect is suspended due to an asynchronous operation.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  evaluateMessageWhileSuspended(message) {
    switch (message._tag) {
      case FiberMessage.OP_YIELD_NOW:
        {
          return EvaluationSignalYieldNow;
        }
      case FiberMessage.OP_INTERRUPT_SIGNAL:
        {
          this.processNewInterruptSignal(message.cause);
          if (this._asyncInterruptor !== null) {
            this._asyncInterruptor(core.exitFailCause(message.cause));
            this._asyncInterruptor = null;
          }
          return EvaluationSignalContinue;
        }
      case FiberMessage.OP_RESUME:
        {
          this._asyncInterruptor = null;
          this._asyncBlockingOn = null;
          this.evaluateEffect(message.effect);
          return EvaluationSignalContinue;
        }
      case FiberMessage.OP_STATEFUL:
        {
          message.onFiber(this, this._exitValue !== null ? FiberStatus.done : FiberStatus.suspended(this._runtimeFlags, this._asyncBlockingOn));
          return EvaluationSignalContinue;
        }
      default:
        {
          return absurd(message);
        }
    }
  }
  /**
   * Evaluates an effect until completion, potentially asynchronously.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  evaluateEffect(effect0) {
    this._supervisor.onResume(this);
    try {
      let effect = _runtimeFlags.interruptible(this._runtimeFlags) && this.isInterrupted() ? core.exitFailCause(this.getInterruptedCause()) : effect0;
      while (effect !== null) {
        try {
          const eff = effect;
          const exit = this.runLoop(eff);
          this._runtimeFlags = _runtimeFlags.enable(_runtimeFlags.WindDown)(this._runtimeFlags);
          const interruption = this.interruptAllChildren();
          if (interruption !== null) {
            effect = core.flatMap(interruption, () => exit);
          } else {
            if (this._queue.length === 0) {
              // No more messages to process, so we will allow the fiber to end life:
              this.setExitValue(exit);
            } else {
              // There are messages, possibly added by the final op executed by
              // the fiber. To be safe, we should execute those now before we
              // allow the fiber to end life:
              this.tell(FiberMessage.resume(exit));
            }
            effect = null;
          }
        } catch (e) {
          if (core.isEffect(e)) {
            if (e._tag === OpCodes.OP_YIELD) {
              if (_runtimeFlags.cooperativeYielding(this._runtimeFlags)) {
                this.tell(FiberMessage.yieldNow());
                this.tell(FiberMessage.resume(core.exitUnit));
                effect = null;
              } else {
                effect = core.exitUnit;
              }
            } else if (e._tag === OpCodes.OP_ASYNC) {
              // Terminate this evaluation, async resumption will continue evaluation:
              effect = null;
            }
          } else {
            throw e;
          }
        }
      }
    } finally {
      this._supervisor.onSuspend(this);
    }
  }
  /**
   * Begins execution of the effect associated with this fiber on the current
   * thread. This can be called to "kick off" execution of a fiber after it has
   * been created, in hopes that the effect can be executed synchronously.
   *
   * This is not the normal way of starting a fiber, but it is useful when the
   * express goal of executing the fiber is to synchronously produce its exit.
   */
  start(effect) {
    if (!this._running) {
      this._running = true;
      const prev = globalThis[internalFiber.currentFiberURI];
      globalThis[internalFiber.currentFiberURI] = this;
      try {
        this.evaluateEffect(effect);
      } finally {
        this._running = false;
        globalThis[internalFiber.currentFiberURI] = prev;
        // Because we're special casing `start`, we have to be responsible
        // for spinning up the fiber if there were new messages added to
        // the queue between the completion of the effect and the transition
        // to the not running state.
        if (this._queue.length > 0) {
          this.drainQueueLaterOnExecutor();
        }
      }
    } else {
      this.tell(FiberMessage.resume(effect));
    }
  }
  /**
   * Begins execution of the effect associated with this fiber on in the
   * background, and on the correct thread pool. This can be called to "kick
   * off" execution of a fiber after it has been created, in hopes that the
   * effect can be executed synchronously.
   */
  startFork(effect) {
    this.tell(FiberMessage.resume(effect));
  }
  /**
   * Takes the current runtime flags, patches them to return the new runtime
   * flags, and then makes any changes necessary to fiber state based on the
   * specified patch.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  patchRuntimeFlags(oldRuntimeFlags, patch) {
    const newRuntimeFlags = _runtimeFlags.patch(oldRuntimeFlags, patch);
    globalThis[internalFiber.currentFiberURI] = this;
    this._runtimeFlags = newRuntimeFlags;
    return newRuntimeFlags;
  }
  /**
   * Initiates an asynchronous operation, by building a callback that will
   * resume execution, and then feeding that callback to the registration
   * function, handling error cases and repeated resumptions appropriately.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  initiateAsync(runtimeFlags, asyncRegister) {
    let alreadyCalled = false;
    const callback = effect => {
      if (!alreadyCalled) {
        alreadyCalled = true;
        this.tell(FiberMessage.resume(effect));
      }
    };
    if (_runtimeFlags.interruptible(runtimeFlags)) {
      this._asyncInterruptor = callback;
    }
    try {
      asyncRegister(callback);
    } catch (e) {
      callback(core.failCause(internalCause.die(e)));
    }
  }
  pushStack(cont) {
    this._stack.push(cont);
    if (cont._tag === "OnStep") {
      this._steps.push(true);
    }
    if (cont._tag === "RevertFlags") {
      this._steps.push(false);
    }
  }
  popStack() {
    const item = this._stack.pop();
    if (item) {
      if (item._tag === "OnStep" || item._tag === "RevertFlags") {
        this._steps.pop();
      }
      return item;
    }
    return;
  }
  getNextSuccessCont() {
    let frame = this.popStack();
    while (frame) {
      if (frame._tag !== OpCodes.OP_ON_FAILURE) {
        return frame;
      }
      frame = this.popStack();
    }
  }
  getNextFailCont() {
    let frame = this.popStack();
    while (frame) {
      if (frame._tag !== OpCodes.OP_ON_SUCCESS && frame._tag !== OpCodes.OP_WHILE) {
        return frame;
      }
      frame = this.popStack();
    }
  }
  [(_a = internalFiber.FiberTypeId, _b = internalFiber.RuntimeFiberTypeId, OpCodes.OP_TAG)](op) {
    return core.map(core.fiberRefGet(core.currentContext), context => {
      try {
        return Context.unsafeGet(context, op);
      } catch (e) {
        console.log(e);
        throw e;
      }
    });
  }
  ["Left"](op) {
    return core.exitFail(op.i0);
  }
  ["None"](_) {
    return core.exitFail(internalCause.NoSuchElementException());
  }
  ["Right"](op) {
    return core.exitSucceed(op.i0);
  }
  ["Some"](op) {
    return core.exitSucceed(op.i0);
  }
  [OpCodes.OP_SYNC](op) {
    const value = op.i0();
    const cont = this.getNextSuccessCont();
    if (cont !== undefined) {
      if (!(cont._tag in contOpSuccess)) {
        // @ts-expect-error
        absurd(cont);
      }
      // @ts-expect-error
      return contOpSuccess[cont._tag](this, cont, value);
    } else {
      throw core.exitSucceed(value);
    }
  }
  [OpCodes.OP_SUCCESS](op) {
    const oldCur = op;
    const cont = this.getNextSuccessCont();
    if (cont !== undefined) {
      if (!(cont._tag in contOpSuccess)) {
        // @ts-expect-error
        absurd(cont);
      }
      // @ts-expect-error
      return contOpSuccess[cont._tag](this, cont, oldCur.i0);
    } else {
      throw oldCur;
    }
  }
  [OpCodes.OP_FAILURE](op) {
    const span = this.getFiberRef(core.currentTracerSpan);
    const cause = List.isNil(span) || span.head._tag === "ExternalSpan" ? op.i0 : internalCause.annotated(op.i0, internalCause.makeSpanAnnotation(span.head));
    const cont = this.getNextFailCont();
    if (cont !== undefined) {
      switch (cont._tag) {
        case OpCodes.OP_ON_FAILURE:
        case OpCodes.OP_ON_SUCCESS_AND_FAILURE:
          {
            if (!(_runtimeFlags.interruptible(this._runtimeFlags) && this.isInterrupted())) {
              return cont.i1(cause);
            } else {
              return core.exitFailCause(internalCause.stripFailures(cause));
            }
          }
        case "OnStep":
          {
            if (!(_runtimeFlags.interruptible(this._runtimeFlags) && this.isInterrupted())) {
              return cont.i1(core.exitFailCause(cause));
            } else {
              return core.exitFailCause(internalCause.stripFailures(cause));
            }
          }
        case OpCodes.OP_REVERT_FLAGS:
          {
            this.patchRuntimeFlags(this._runtimeFlags, cont.patch);
            if (_runtimeFlags.interruptible(this._runtimeFlags) && this.isInterrupted()) {
              return core.exitFailCause(internalCause.sequential(cause, this.getInterruptedCause()));
            } else {
              return core.exitFailCause(cause);
            }
          }
        default:
          {
            absurd(cont);
          }
      }
    } else {
      throw core.exitFailCause(cause);
    }
  }
  [OpCodes.OP_WITH_RUNTIME](op) {
    return op.i0(this, FiberStatus.running(this._runtimeFlags));
  }
  ["Blocked"](op) {
    if (this._steps[this._steps.length - 1]) {
      const nextOp = this.popStack();
      if (nextOp) {
        switch (nextOp._tag) {
          case "OnStep":
            {
              return nextOp.i1(op);
            }
          case "OnSuccess":
            {
              return core.blocked(op.i0, core.flatMap(op.i1, nextOp.i1));
            }
          case "OnSuccessAndFailure":
            {
              return core.blocked(op.i0, core.matchCauseEffect(op.i1, {
                onFailure: nextOp.i1,
                onSuccess: nextOp.i2
              }));
            }
          case "OnFailure":
            {
              return core.blocked(op.i0, core.catchAllCause(op.i1, nextOp.i1));
            }
          case "While":
            {
              return core.blocked(op.i0, core.flatMap(op.i1, a => {
                nextOp.i2(a);
                if (nextOp.i0()) {
                  return core.whileLoop({
                    while: nextOp.i0,
                    body: nextOp.i1,
                    step: nextOp.i2
                  });
                }
                return core.unit;
              }));
            }
          case "RevertFlags":
            {
              this.pushStack(nextOp);
              break;
            }
        }
      }
    }
    return core.uninterruptibleMask(restore => core.flatMap(fork(core.runRequestBlock(op.i0)), () => restore(op.i1)));
  }
  ["RunBlocked"](op) {
    return runBlockedRequests(op.i0);
  }
  [OpCodes.OP_UPDATE_RUNTIME_FLAGS](op) {
    const updateFlags = op.i0;
    const oldRuntimeFlags = this._runtimeFlags;
    const newRuntimeFlags = _runtimeFlags.patch(oldRuntimeFlags, updateFlags);
    // One more chance to short circuit: if we're immediately going
    // to interrupt. Interruption will cause immediate reversion of
    // the flag, so as long as we "peek ahead", there's no need to
    // set them to begin with.
    if (_runtimeFlags.interruptible(newRuntimeFlags) && this.isInterrupted()) {
      return core.exitFailCause(this.getInterruptedCause());
    } else {
      // Impossible to short circuit, so record the changes
      this.patchRuntimeFlags(this._runtimeFlags, updateFlags);
      if (op.i1) {
        // Since we updated the flags, we need to revert them
        const revertFlags = _runtimeFlags.diff(newRuntimeFlags, oldRuntimeFlags);
        this.pushStack(new core.RevertFlags(revertFlags, op));
        return op.i1(oldRuntimeFlags);
      } else {
        return core.exitUnit;
      }
    }
  }
  [OpCodes.OP_ON_SUCCESS](op) {
    this.pushStack(op);
    return op.i0;
  }
  ["OnStep"](op) {
    this.pushStack(op);
    return op.i0;
  }
  [OpCodes.OP_ON_FAILURE](op) {
    this.pushStack(op);
    return op.i0;
  }
  [OpCodes.OP_ON_SUCCESS_AND_FAILURE](op) {
    this.pushStack(op);
    return op.i0;
  }
  [OpCodes.OP_ASYNC](op) {
    this._asyncBlockingOn = op.i1;
    this.initiateAsync(this._runtimeFlags, op.i0);
    throw op;
  }
  [OpCodes.OP_YIELD](op) {
    throw op;
  }
  [OpCodes.OP_WHILE](op) {
    const check = op.i0;
    const body = op.i1;
    if (check()) {
      this.pushStack(op);
      return body();
    } else {
      return core.exitUnit;
    }
  }
  [OpCodes.OP_COMMIT](op) {
    return op.commit();
  }
  /**
   * The main run-loop for evaluating effects.
   *
   * **NOTE**: This method must be invoked by the fiber itself.
   */
  runLoop(effect0) {
    let cur = effect0;
    let ops = 0;
    // eslint-disable-next-line no-constant-condition
    while (true) {
      if ((this._runtimeFlags & _runtimeFlags.OpSupervision) !== 0) {
        this._supervisor.onEffect(this, cur);
      }
      if (this._queue.length > 0) {
        cur = this.drainQueueWhileRunning(this._runtimeFlags, cur);
      }
      ops += 1;
      if (ops >= this.getFiberRef(core.currentMaxFiberOps)) {
        ops = 0;
        const oldCur = cur;
        cur = core.flatMap(core.yieldNow(), () => oldCur);
      }
      try {
        if (!(cur._tag in this)) {
          if (typeof cur === "function") {
            console.log(cur());
          }
          // @ts-expect-error
          absurd(cur);
        }
        // @ts-expect-error
        cur = this._supervisor.onRun(
        // @ts-expect-error
        () => this[cur._tag](cur), this);
      } catch (e) {
        if (core.isEffect(e)) {
          if (e._tag === OpCodes.OP_YIELD || e._tag === OpCodes.OP_ASYNC) {
            throw e;
          }
          if (e._tag === OpCodes.OP_SUCCESS || e._tag === OpCodes.OP_FAILURE) {
            return e;
          }
        } else {
          if (core.isEffectError(e)) {
            cur = core.exitFailCause(e.cause);
          } else if (internalCause.isInterruptedException(e)) {
            cur = core.exitFailCause(internalCause.sequential(internalCause.die(e), internalCause.interrupt(FiberId.none)));
          } else {
            cur = core.exitFailCause(internalCause.die(e));
          }
        }
      }
    }
  }
}
// circular with Logger
/** @internal */
exports.FiberRuntime = FiberRuntime;
const currentMinimumLogLevel = /*#__PURE__*/core.fiberRefUnsafeMake( /*#__PURE__*/LogLevel.fromLiteral("Info"));
/** @internal */
exports.currentMinimumLogLevel = currentMinimumLogLevel;
const defaultLogger = /*#__PURE__*/internalLogger.makeLogger(options => {
  const formatted = internalLogger.stringLogger.log(options);
  globalThis.console.log(formatted);
});
/** @internal */
exports.defaultLogger = defaultLogger;
const filterMinimumLogLevel = /*#__PURE__*/internalLogger.makeLogger(options => {
  const formatted = internalLogger.stringLogger.log(options);
  globalThis.console.log(formatted);
});
/** @internal */
exports.filterMinimumLogLevel = filterMinimumLogLevel;
const logFmtLogger = /*#__PURE__*/internalLogger.makeLogger(options => {
  const formatted = internalLogger.logfmtLogger.log(options);
  globalThis.console.log(formatted);
});
/** @internal */
exports.logFmtLogger = logFmtLogger;
const tracerLogger = /*#__PURE__*/internalLogger.makeLogger(({
  annotations,
  cause,
  context,
  fiberId,
  logLevel,
  message
}) => {
  const span = Option.flatMap(fiberRefs.get(context, core.currentTracerSpan), List.head);
  const clockService = Option.map(fiberRefs.get(context, defaultServices.currentServices), _ => Context.get(_, clock.clockTag));
  if (span._tag === "None" || span.value._tag === "ExternalSpan" || clockService._tag === "None") {
    return;
  }
  const attributes = Object.fromEntries(annotations);
  attributes["effect.fiberId"] = FiberId.threadName(fiberId);
  attributes["effect.logLevel"] = logLevel.label;
  if (cause !== null && cause !== internalCause.empty) {
    attributes["effect.cause"] = internalCause.pretty(cause);
  }
  span.value.event(String(message), clockService.value.unsafeCurrentTimeNanos(), attributes);
});
/** @internal */
exports.tracerLogger = tracerLogger;
const currentLoggers = /*#__PURE__*/core.fiberRefUnsafeMakeHashSet( /*#__PURE__*/HashSet.make(defaultLogger, tracerLogger));
// circular with Effect
/* @internal */
exports.currentLoggers = currentLoggers;
const acquireRelease = /*#__PURE__*/(0, _Function.dual)(args => core.isEffect(args[0]), (acquire, release) => {
  return core.uninterruptible(core.tap(acquire, a => addFinalizer(exit => release(a, exit))));
});
/* @internal */
exports.acquireRelease = acquireRelease;
const acquireReleaseInterruptible = /*#__PURE__*/(0, _Function.dual)(args => core.isEffect(args[0]), (acquire, release) => {
  return ensuring(acquire, addFinalizer(exit => release(exit)));
});
/* @internal */
exports.acquireReleaseInterruptible = acquireReleaseInterruptible;
const addFinalizer = finalizer => core.withFiberRuntime(runtime => {
  const acquireRefs = runtime.unsafeGetFiberRefs();
  return core.flatMap(scope, scope => core.scopeAddFinalizerExit(scope, exit => core.withFiberRuntime(runtimeFinalizer => {
    const pre = runtimeFinalizer.unsafeGetFiberRefs();
    const patch = FiberRefsPatch.diff(pre, acquireRefs);
    const inverse = FiberRefsPatch.diff(acquireRefs, pre);
    runtimeFinalizer.setFiberRefs(FiberRefsPatch.patch(patch, runtimeFinalizer.id(), acquireRefs));
    return ensuring(finalizer(exit), core.sync(() => {
      runtimeFinalizer.setFiberRefs(FiberRefsPatch.patch(inverse, runtimeFinalizer.id(), runtimeFinalizer.unsafeGetFiberRefs()));
    }));
  })));
});
/* @internal */
exports.addFinalizer = addFinalizer;
const daemonChildren = self => {
  const forkScope = core.fiberRefLocally(core.currentForkScopeOverride, Option.some(fiberScope.globalScope));
  return forkScope(self);
};
/** @internal */
exports.daemonChildren = daemonChildren;
const _existsParFound = /*#__PURE__*/Symbol("@effect/io/Effect/existsPar/found");
/* @internal */
const exists = /*#__PURE__*/(0, _Function.dual)(args => Predicate.isIterable(args[0]), (elements, f, options) => concurrency.matchSimple(options, () => core.suspend(() => existsLoop(elements[Symbol.iterator](), 0, f)), () => core.matchEffect(forEachOptions(elements, (a, i) => core.if_(f(a, i), {
  onTrue: core.fail(_existsParFound),
  onFalse: core.unit
}), options), {
  onFailure: e => e === _existsParFound ? core.succeed(true) : core.fail(e),
  onSuccess: () => core.succeed(false)
})));
exports.exists = exists;
const existsLoop = (iterator, index, f) => {
  const next = iterator.next();
  if (next.done) {
    return core.succeed(false);
  }
  return core.flatMap(f(next.value, index), b => b ? core.succeed(b) : existsLoop(iterator, index + 1, f));
};
/* @internal */
const filter = /*#__PURE__*/(0, _Function.dual)(args => Predicate.isIterable(args[0]), (elements, f, options) => {
  const predicate = options?.negate ? (a, i) => core.map(f(a, i), Boolean.not) : f;
  return concurrency.matchSimple(options, () => core.suspend(() => RA.fromIterable(elements).reduceRight((effect, a, i) => core.zipWith(effect, core.suspend(() => predicate(a, i)), (list, b) => b ? [a, ...list] : list), core.sync(() => new Array()))), () => core.map(forEachOptions(elements, (a, i) => core.map(predicate(a, i), b => b ? Option.some(a) : Option.none()), options), RA.compact));
});
// === all
exports.filter = filter;
const allResolveInput = input => {
  if (Array.isArray(input) || Predicate.isIterable(input)) {
    return [input, Option.none()];
  }
  const keys = Object.keys(input);
  const size = keys.length;
  return [keys.map(k => input[k]), Option.some(values => {
    const res = {};
    for (let i = 0; i < size; i++) {
      ;
      res[keys[i]] = values[i];
    }
    return res;
  })];
};
const allValidate = (effects, reconcile, options) => {
  const eitherEffects = [];
  for (const effect of effects) {
    eitherEffects.push(core.either(effect));
  }
  return core.flatMap(forEachOptions(eitherEffects, _Function.identity, {
    concurrency: options?.concurrency,
    batching: options?.batching
  }), eithers => {
    const none = Option.none();
    const size = eithers.length;
    const errors = new Array(size);
    const successes = new Array(size);
    let errored = false;
    for (let i = 0; i < size; i++) {
      const either = eithers[i];
      if (either._tag === "Left") {
        errors[i] = Option.some(either.left);
        errored = true;
      } else {
        successes[i] = either.right;
        errors[i] = none;
      }
    }
    if (errored) {
      return reconcile._tag === "Some" ? core.fail(reconcile.value(errors)) : core.fail(errors);
    } else if (options?.discard) {
      return core.unit;
    }
    return reconcile._tag === "Some" ? core.succeed(reconcile.value(successes)) : core.succeed(successes);
  });
};
const allEither = (effects, reconcile, options) => {
  const eitherEffects = [];
  for (const effect of effects) {
    eitherEffects.push(core.either(effect));
  }
  if (options?.discard) {
    return forEachOptions(eitherEffects, _Function.identity, {
      concurrency: options?.concurrency,
      batching: options?.batching,
      discard: true
    });
  }
  return core.map(forEachOptions(eitherEffects, _Function.identity, {
    concurrency: options?.concurrency,
    batching: options?.batching
  }), eithers => reconcile._tag === "Some" ? reconcile.value(eithers) : eithers);
};
/* @internal */
const all = (arg, options) => {
  const [effects, reconcile] = allResolveInput(arg);
  if (options?.mode === "validate") {
    return allValidate(effects, reconcile, options);
  } else if (options?.mode === "either") {
    return allEither(effects, reconcile, options);
  }
  return reconcile._tag === "Some" ? core.map(forEachOptions(effects, _Function.identity, options), reconcile.value) : forEachOptions(effects, _Function.identity, options);
};
/* @internal */
exports.all = all;
const allWith = options => arg => all(arg, options);
/* @internal */
exports.allWith = allWith;
const allSuccesses = (elements, options) => core.map(all(RA.fromIterable(elements).map(core.exit), options), RA.filterMap(exit => core.exitIsSuccess(exit) ? Option.some(exit.i0) : Option.none()));
/* @internal */
exports.allSuccesses = allSuccesses;
const replicate = /*#__PURE__*/(0, _Function.dual)(2, (self, n) => Array.from({
  length: n
}, () => self));
/* @internal */
exports.replicate = replicate;
const replicateEffect = /*#__PURE__*/(0, _Function.dual)(args => core.isEffect(args[0]), (self, n, options) => all(replicate(n)(self), options));
// @ts-expect-error
exports.replicateEffect = replicateEffect;
const forEachOptions = /*#__PURE__*/(0, _Function.dual)(args => Predicate.isIterable(args[0]), (self, f, options) => core.withFiberRuntime(r => {
  const requestBatchingEnabled = options?.batching === true || options?.batching === "inherit" && r.getFiberRef(core.currentRequestBatching);
  if (options?.discard) {
    return concurrency.match(options, () => requestBatchingEnabled ? forEachBatchedDiscard(self, f) : core.forEachSequentialDiscard(self, f), () => forEachParUnboundedDiscard(self, f, requestBatchingEnabled), n => forEachParNDiscard(self, n, f, requestBatchingEnabled));
  }
  return concurrency.match(options, () => requestBatchingEnabled ? forEachParN(self, 1, f, true) : core.forEachSequential(self, f), () => forEachParUnbounded(self, f, requestBatchingEnabled), n => forEachParN(self, n, f, requestBatchingEnabled));
}));
/* @internal */
exports.forEachOptions = forEachOptions;
const forEachParUnbounded = (self, f, batching) => core.suspend(() => {
  const as = RA.fromIterable(self);
  const array = new Array(as.length);
  const fn = (a, i) => core.flatMap(f(a, i), b => core.sync(() => array[i] = b));
  return core.zipRight(forEachParUnboundedDiscard(as, fn, batching), core.succeed(array));
});
exports.forEachParUnbounded = forEachParUnbounded;
const forEachBatchedDiscard = (self, f) => core.suspend(() => {
  const as = RA.fromIterable(self);
  const size = as.length;
  if (size === 0) {
    return core.unit;
  } else if (size === 1) {
    return core.asUnit(f(as[0], 0));
  }
  const effects = as.map(f);
  const blocked = new Array();
  const loop = i => i === effects.length ? core.suspend(() => {
    if (blocked.length > 0) {
      const requests = blocked.map(b => b.i0).reduce(_RequestBlock.par);
      return core.blocked(requests, forEachBatchedDiscard(blocked.map(b => b.i1), _Function.identity));
    }
    return core.unit;
  }) : core.flatMapStep(effects[i], s => {
    if (s._tag === "Blocked") {
      blocked.push(s);
      return loop(i + 1);
    } else if (s._tag === "Failure") {
      return core.suspend(() => {
        if (blocked.length > 0) {
          const requests = blocked.map(b => b.i0).reduce(_RequestBlock.par);
          return core.blocked(requests, core.flatMap(forEachBatchedDiscard(blocked.map(b => b.i1), _Function.identity), () => s));
        }
        return core.unit;
      });
    } else {
      return loop(i + 1);
    }
  });
  return loop(0);
});
/* @internal */
const forEachParUnboundedDiscard = (self, f, batching) => core.suspend(() => {
  const as = RA.fromIterable(self);
  const size = as.length;
  if (size === 0) {
    return core.unit;
  } else if (size === 1) {
    return core.asUnit(f(as[0], 0));
  }
  return core.uninterruptibleMask(restore => {
    const deferred = core.deferredUnsafeMake(FiberId.none);
    let ref = 0;
    const residual = [];
    const joinOrder = [];
    const process = core.transplant(graft => core.forEachSequential(as, (a, i) => core.map(fiber => {
      fiber.unsafeAddObserver(() => {
        joinOrder.push(fiber);
      });
      return fiber;
    })(forkDaemon(graft(core.flatMap(exit => {
      switch (exit._tag) {
        case "Failure":
          {
            if (residual.length > 0) {
              const requests = residual.map(blocked => blocked.i0).reduce(_RequestBlock.par);
              const _continue = forEachParUnboundedDiscard(residual, blocked => blocked.i1, batching);
              return core.blocked(requests, core.matchCauseEffect(_continue, {
                onFailure: cause => core.zipRight(core.deferredFail(deferred, void 0), core.failCause(internalCause.parallel(cause, exit.cause))),
                onSuccess: () => core.zipRight(core.deferredFail(deferred, void 0), core.failCause(exit.cause))
              }));
            }
            return core.zipRight(core.deferredFail(deferred, void 0), core.failCause(exit.cause));
          }
        default:
          {
            if (exit._tag === "Blocked") {
              residual.push(exit);
            }
            if (ref + 1 === size) {
              if (residual.length > 0) {
                const requests = residual.map(blocked => blocked.i0).reduce(_RequestBlock.par);
                const _continue = forEachParUnboundedDiscard(residual, blocked => blocked.i1, batching);
                return core.deferredSucceed(deferred, core.blocked(requests, _continue));
              } else {
                core.deferredUnsafeDone(deferred, core.exitSucceed(core.exitUnit));
              }
            } else {
              ref = ref + 1;
            }
            return core.unit;
          }
      }
    })(core.suspend(() => restore((batching ? core.step : core.exit)(f(a, i))))))))));
    return core.flatMap(process, fibers => core.matchCauseEffect(restore(core.deferredAwait(deferred)), {
      onFailure: cause => core.flatMap(forEachParUnbounded(fibers, core.interruptFiber, batching), exits => {
        const exit = core.exitCollectAll(exits, {
          parallel: true
        });
        if (exit._tag === "Some" && core.exitIsFailure(exit.value)) {
          return core.failCause(internalCause.parallel(internalCause.stripFailures(cause), exit.value.i0));
        } else {
          return core.failCause(internalCause.stripFailures(cause));
        }
      }),
      onSuccess: rest => core.flatMap(rest, () => core.forEachSequentialDiscard(joinOrder, f => f.inheritAll()))
    }));
  });
});
/* @internal */
exports.forEachParUnboundedDiscard = forEachParUnboundedDiscard;
const forEachParN = (self, n, f, batching) => core.suspend(() => {
  const as = RA.fromIterable(self);
  const array = new Array(as.length);
  const fn = (a, i) => core.map(f(a, i), b => array[i] = b);
  return core.zipRight(forEachParNDiscard(as, n, fn, batching), core.succeed(array));
});
/* @internal */
exports.forEachParN = forEachParN;
const forEachParNDiscard = (self, n, f, batching) => core.suspend(() => {
  let i = 0;
  const iterator = self[Symbol.iterator]();
  const residual = [];
  const worker = core.flatMap(core.sync(() => iterator.next()), next => next.done ? core.unit : core.flatMap((batching ? core.step : core.exit)(core.asUnit(f(next.value, i++))), res => {
    switch (res._tag) {
      case "Blocked":
        {
          residual.push(res);
          return worker;
        }
      case "Failure":
        {
          return res;
        }
      case "Success":
        return worker;
    }
  }));
  const effects = [];
  for (let i = 0; i < n; i++) {
    effects.push(worker);
  }
  return core.flatMap(core.exit(forEachParUnboundedDiscard(effects, _Function.identity, batching)), exit => {
    if (residual.length === 0) {
      return exit;
    }
    const requests = residual.map(blocked => blocked.i0).reduce(_RequestBlock.par);
    const _continue = forEachParNDiscard(residual, n, blocked => blocked.i1, batching);
    if (exit._tag === "Failure") {
      return core.blocked(requests, core.matchCauseEffect(_continue, {
        onFailure: cause => core.exitFailCause(internalCause.parallel(exit.cause, cause)),
        onSuccess: () => exit
      }));
    }
    return core.blocked(requests, _continue);
  });
});
/* @internal */
exports.forEachParNDiscard = forEachParNDiscard;
const fork = self => core.withFiberRuntime((state, status) => core.succeed(unsafeFork(self, state, status.runtimeFlags)));
/* @internal */
exports.fork = fork;
const forkDaemon = self => forkWithScopeOverride(self, fiberScope.globalScope);
/* @internal */
exports.forkDaemon = forkDaemon;
const forkWithErrorHandler = /*#__PURE__*/(0, _Function.dual)(2, (self, handler) => fork(core.onError(self, cause => {
  const either = internalCause.failureOrCause(cause);
  switch (either._tag) {
    case "Left":
      {
        return handler(either.left);
      }
    case "Right":
      {
        return core.failCause(either.right);
      }
  }
})));
/** @internal */
exports.forkWithErrorHandler = forkWithErrorHandler;
const unsafeFork = (effect, parentFiber, parentRuntimeFlags, overrideScope = null) => {
  const childFiber = unsafeMakeChildFiber(effect, parentFiber, parentRuntimeFlags, overrideScope);
  childFiber.resume(effect);
  return childFiber;
};
/** @internal */
exports.unsafeFork = unsafeFork;
const unsafeMakeChildFiber = (effect, parentFiber, parentRuntimeFlags, overrideScope = null) => {
  const childId = FiberId.unsafeMake();
  const parentFiberRefs = parentFiber.unsafeGetFiberRefs();
  const childFiberRefs = fiberRefs.forkAs(parentFiberRefs, childId);
  const childFiber = new FiberRuntime(childId, childFiberRefs, parentRuntimeFlags);
  const childContext = fiberRefs.getOrDefault(childFiberRefs, core.currentContext);
  const supervisor = childFiber._supervisor;
  supervisor.onStart(childContext, effect, Option.some(parentFiber), childFiber);
  childFiber.unsafeAddObserver(exit => supervisor.onEnd(exit, childFiber));
  const parentScope = overrideScope !== null ? overrideScope : Option.getOrElse(() => parentFiber.scope())(parentFiber.getFiberRef(core.currentForkScopeOverride));
  parentScope.add(parentRuntimeFlags, childFiber);
  return childFiber;
};
/* @internal */
exports.unsafeMakeChildFiber = unsafeMakeChildFiber;
const forkWithScopeOverride = (self, scopeOverride) => core.withFiberRuntime((parentFiber, parentStatus) => core.succeed(unsafeFork(self, parentFiber, parentStatus.runtimeFlags, scopeOverride)));
/* @internal */
const mergeAll = /*#__PURE__*/(0, _Function.dual)(args => Predicate.isIterable(args[0]), (elements, zero, f, options) => concurrency.matchSimple(options, () => RA.fromIterable(elements).reduce((acc, a, i) => core.zipWith(acc, a, (acc, a) => f(acc, a, i)), core.succeed(zero)), () => core.flatMap(Ref.make(zero), acc => core.flatMap(forEachOptions(elements, (effect, i) => core.flatMap(effect, a => Ref.update(acc, b => f(b, a, i))), options), () => Ref.get(acc)))));
/* @internal */
exports.mergeAll = mergeAll;
const partition = /*#__PURE__*/(0, _Function.dual)(args => Predicate.isIterable(args[0]), (elements, f, options) => core.map(chunk => core.partitionMap(chunk, _Function.identity))(forEachOptions(elements, (a, i) => core.either(f(a, i)), options)));
/* @internal */
exports.partition = partition;
const validateAll = /*#__PURE__*/(0, _Function.dual)(args => Predicate.isIterable(args[0]), (elements, f, options) => core.flatMap(partition(elements, f, {
  concurrency: options?.concurrency,
  batching: options?.batching
}), ([es, bs]) => es.length === 0 ? options?.discard ? core.unit : core.succeed(bs) : core.fail(es)));
/* @internal */
exports.validateAll = validateAll;
const raceAll = all => {
  const list = Chunk.fromIterable(all);
  if (!Chunk.isNonEmpty(list)) {
    return core.dieSync(() => internalCause.IllegalArgumentException(`Received an empty collection of effects`));
  }
  const self = Chunk.headNonEmpty(list);
  const effects = Chunk.tailNonEmpty(list);
  const inheritAll = res => core.as(res[0])(internalFiber.inheritAll(res[1]));
  return core.flatMap(done => core.flatMap(fails => core.uninterruptibleMask(restore => core.flatMap(head => core.flatMap(fibers => core.onInterrupt(() => RA.reduce(core.unit, (effect, fiber) => core.zipLeft(core.interruptFiber(fiber))(effect))(fibers))(restore(core.flatMap(inheritAll)(Deferred.await(done)))))(core.tap(fibers => RA.reduce(core.unit, (effect, fiber) => core.zipRight(core.asUnit(fork(core.flatMap(raceAllArbiter(fibers, fiber, done, fails))(internalFiber._await(fiber)))))(effect))(fibers))(core.map(tail => Chunk.prepend(head)(tail))(core.map(Chunk.unsafeFromArray)(core.forEachSequential(effect => fork(core.interruptible(effect)))(effects))))))(fork(core.interruptible(self)))))(Ref.make(effects.length)))(core.deferredMake());
};
/* @internal */
exports.raceAll = raceAll;
const raceAllArbiter = (fibers, winner, deferred, fails) => exit => core.exitMatchEffect(exit, {
  onFailure: cause => core.flatten(Ref.modify(fails, fails => [fails === 0 ? core.asUnit(core.deferredFailCause(deferred, cause)) : core.unit, fails - 1])),
  onSuccess: value => core.flatMap(set => set ? RA.reduce(core.unit, (effect, fiber) => fiber === winner ? effect : core.zipLeft(core.interruptFiber(fiber))(effect))(Chunk.fromIterable(fibers)) : core.unit)(core.deferredSucceed(deferred, [value, winner]))
});
/* @internal */
const reduceEffect = /*#__PURE__*/(0, _Function.dual)(args => Predicate.isIterable(args[0]), (elements, zero, f, options) => concurrency.matchSimple(options, () => RA.fromIterable(elements).reduce((acc, a, i) => core.zipWith(acc, a, (acc, a) => f(acc, a, i)), zero), () => core.suspend(() => core.map(option => {
  switch (option._tag) {
    case "None":
      {
        throw new Error("BUG: Effect.reduceEffect - please report an issue at https://github.com/Effect-TS/io/issues");
      }
    case "Some":
      {
        return option.value;
      }
  }
})(mergeAll([zero, ...elements], Option.none(), (acc, elem, i) => {
  switch (acc._tag) {
    case "None":
      {
        return Option.some(elem);
      }
    case "Some":
      {
        return Option.some(f(acc.value, elem, i));
      }
  }
}, options)))));
/* @internal */
exports.reduceEffect = reduceEffect;
const parallelFinalizers = self => core.flatMap(scope, outerScope => core.flatMap(scopeMake(executionStrategy.parallel), innerScope => core.zipRight(scopeExtend(self, innerScope))(outerScope.addFinalizer(exit => innerScope.close(exit)))));
/* @internal */
exports.parallelFinalizers = parallelFinalizers;
const scopeWith = f => core.flatMap(scopeTag, f);
/* @internal */
exports.scopeWith = scopeWith;
const scopedEffect = effect => core.flatMap(scopeMake(), scope => scopeUse(scope)(effect));
/* @internal */
exports.scopedEffect = scopedEffect;
const sequentialFinalizers = self => scopeWith(scope => core.flatMap(scope => scopeExtend(scope)(self))(core.scopeFork(scope, executionStrategy.sequential)));
/* @internal */
exports.sequentialFinalizers = sequentialFinalizers;
const tagMetricsScoped = (key, value) => labelMetricsScoped([metricLabel.make(key, value)]);
/* @internal */
exports.tagMetricsScoped = tagMetricsScoped;
const labelMetricsScoped = labels => labelMetricsScopedSet(HashSet.fromIterable(labels));
/* @internal */
exports.labelMetricsScoped = labelMetricsScoped;
const labelMetricsScopedSet = labels => fiberRefLocallyScopedWith(core.currentMetricLabels, set => HashSet.union(labels)(set));
/* @internal */
exports.labelMetricsScopedSet = labelMetricsScopedSet;
const using = /*#__PURE__*/(0, _Function.dual)(2, (self, use) => core.acquireUseRelease(scopeMake(), scope => core.flatMap(scopeExtend(self, scope), use), (scope, exit) => core.scopeClose(scope, exit)));
/* @internal */
exports.using = using;
const unsome = self => core.matchEffect(self, {
  onFailure: option => {
    switch (option._tag) {
      case "None":
        {
          return core.succeed(Option.none());
        }
      case "Some":
        {
          return core.fail(option.value);
        }
    }
  },
  onSuccess: a => core.succeed(Option.some(a))
});
/** @internal */
exports.unsome = unsome;
const validate = /*#__PURE__*/(0, _Function.dual)(args => core.isEffect(args[1]), (self, that, options) => validateWith(self, that, (a, b) => [a, b], options));
/** @internal */
exports.validate = validate;
const validateWith = /*#__PURE__*/(0, _Function.dual)(args => core.isEffect(args[1]), (self, that, f, options) => core.flatten(zipWithOptions(core.exit(self), core.exit(that), (ea, eb) => core.exitZipWith(ea, eb, {
  onSuccess: f,
  onFailure: (ca, cb) => options?.concurrent ? internalCause.parallel(ca, cb) : internalCause.sequential(ca, cb)
}), options)));
/* @internal */
exports.validateWith = validateWith;
const validateAllPar = /*#__PURE__*/(0, _Function.dual)(2, (elements, f) => core.flatMap(partition(elements, f), ([es, bs]) => es.length === 0 ? core.succeed(bs) : core.fail(es)));
/* @internal */
exports.validateAllPar = validateAllPar;
const validateAllParDiscard = /*#__PURE__*/(0, _Function.dual)(2, (elements, f) => core.flatMap(partition(elements, f), ([es, _]) => es.length === 0 ? core.unit : core.fail(es)));
/* @internal */
exports.validateAllParDiscard = validateAllParDiscard;
const validateFirst = /*#__PURE__*/(0, _Function.dual)(args => Predicate.isIterable(args[0]), (elements, f, options) => core.flip(forEachOptions(elements, (a, i) => core.flip(f(a, i)), options)));
/* @internal */
exports.validateFirst = validateFirst;
const withClockScoped = value => fiberRefLocallyScopedWith(defaultServices.currentServices, Context.add(clock.clockTag, value));
/* @internal */
exports.withClockScoped = withClockScoped;
const withConfigProviderScoped = value => fiberRefLocallyScopedWith(defaultServices.currentServices, Context.add(_configProvider.configProviderTag, value));
/* @internal */
exports.withConfigProviderScoped = withConfigProviderScoped;
const withEarlyRelease = self => scopeWith(parent => core.flatMap(core.scopeFork(parent, executionStrategy.sequential), child => core.map(value => [core.fiberIdWith(fiberId => core.scopeClose(child, core.exitInterrupt(fiberId))), value])(scopeExtend(child)(self))));
/** @internal */
exports.withEarlyRelease = withEarlyRelease;
const zipOptions = /*#__PURE__*/(0, _Function.dual)(args => core.isEffect(args[1]), (self, that, options) => zipWithOptions(self, that, (a, b) => [a, b], options));
/** @internal */
exports.zipOptions = zipOptions;
const zipLeftOptions = /*#__PURE__*/(0, _Function.dual)(args => core.isEffect(args[1]), (self, that, options) => zipWithOptions(self, that, (a, _) => a, options));
/** @internal */
exports.zipLeftOptions = zipLeftOptions;
const zipRightOptions = /*#__PURE__*/(0, _Function.dual)(args => core.isEffect(args[1]), (self, that, options) => zipWithOptions(self, that, (_, b) => b, options));
/** @internal */
exports.zipRightOptions = zipRightOptions;
const zipWithOptions = /*#__PURE__*/(0, _Function.dual)(args => core.isEffect(args[1]), (self, that, f, options) => core.map(all([self, that], {
  concurrency: options?.concurrent ? 2 : 1,
  batching: options?.batching
}), ([a, a2]) => f(a, a2)));
/* @internal */
exports.zipWithOptions = zipWithOptions;
const withRuntimeFlagsScoped = update => {
  if (update === RuntimeFlagsPatch.empty) {
    return core.unit;
  }
  return core.uninterruptible(core.flatMap(runtimeFlags => {
    const updatedRuntimeFlags = _runtimeFlags.patch(runtimeFlags, update);
    const revertRuntimeFlags = _runtimeFlags.diff(updatedRuntimeFlags, runtimeFlags);
    return core.asUnit(core.zipRight(addFinalizer(() => core.updateRuntimeFlags(revertRuntimeFlags)))(core.updateRuntimeFlags(update)));
  })(core.runtimeFlags));
};
// circular with ReleaseMap
/* @internal */
exports.withRuntimeFlagsScoped = withRuntimeFlagsScoped;
const releaseMapReleaseAll = (strategy, exit) => self => core.suspend(() => {
  switch (self.state._tag) {
    case "Exited":
      {
        return core.unit;
      }
    case "Running":
      {
        const finalizersMap = self.state.finalizers;
        const update = self.state.update;
        const finalizers = Array.from(finalizersMap.keys()).sort((a, b) => b - a).map(key => finalizersMap.get(key));
        self.state = {
          _tag: "Exited",
          nextKey: self.state.nextKey,
          exit,
          update
        };
        return executionStrategy.isSequential(strategy) ? core.flatMap(results => Option.getOrElse(() => core.exitUnit)(Option.map(core.exitAsUnit)(core.exitCollectAll(results))))(core.forEachSequential(fin => core.exit(update(fin)(exit)))(finalizers)) : executionStrategy.isParallel(strategy) ? core.flatMap(results => Option.getOrElse(() => core.exitUnit)(Option.map(core.exitAsUnit)(core.exitCollectAll(results, {
          parallel: true
        }))))(forEachParUnbounded(finalizers, fin => core.exit(update(fin)(exit)), false)) : core.flatMap(results => Option.getOrElse(() => core.exitUnit)(Option.map(core.exitAsUnit)(core.exitCollectAll(results, {
          parallel: true
        }))))(forEachParN(finalizers, strategy.parallelism, fin => core.exit(update(fin)(exit)), false));
      }
  }
});
// circular with Scope
/** @internal */
exports.releaseMapReleaseAll = releaseMapReleaseAll;
const scopeTag = /*#__PURE__*/Context.Tag(core.ScopeTypeId);
/* @internal */
exports.scopeTag = scopeTag;
const scope = scopeTag;
/* @internal */
exports.scope = scope;
const scopeMake = (strategy = executionStrategy.sequential) => core.map(core.releaseMapMake, rm => ({
  [core.ScopeTypeId]: core.ScopeTypeId,
  [core.CloseableScopeTypeId]: core.CloseableScopeTypeId,
  pipe() {
    return (0, _Pipeable.pipeArguments)(this, arguments);
  },
  fork: strategy => core.uninterruptible(core.flatMap(scope => core.as(scope)(core.tap(fin => core.scopeAddFinalizerExit(scope, fin))(core.releaseMapAdd(rm, exit => core.scopeClose(scope, exit)))))(scopeMake(strategy))),
  close: exit => core.asUnit(releaseMapReleaseAll(strategy, exit)(rm)),
  addFinalizer: fin => core.asUnit(core.releaseMapAdd(fin)(rm))
}));
/* @internal */
exports.scopeMake = scopeMake;
const scopeExtend = /*#__PURE__*/(0, _Function.dual)(2, (effect, scope) => core.mapInputContext(effect,
// @ts-expect-error
Context.merge(Context.make(scopeTag, scope))));
/* @internal */
exports.scopeExtend = scopeExtend;
const scopeUse = /*#__PURE__*/(0, _Function.dual)(2, (effect, scope) => core.onExit(exit => scope.close(exit))(scopeExtend(scope)(effect)));
// circular with Supervisor
/** @internal */
exports.scopeUse = scopeUse;
const fiberRefUnsafeMakeSupervisor = initial => core.fiberRefUnsafeMakePatch(initial, {
  differ: SupervisorPatch.differ,
  fork: SupervisorPatch.empty
});
// circular with FiberRef
/* @internal */
exports.fiberRefUnsafeMakeSupervisor = fiberRefUnsafeMakeSupervisor;
const fiberRefLocallyScoped = /*#__PURE__*/(0, _Function.dual)(2, (self, value) => core.asUnit(acquireRelease(core.flatMap(core.fiberRefGet(self), oldValue => core.as(core.fiberRefSet(self, value), oldValue)), oldValue => core.fiberRefSet(self, oldValue))));
/* @internal */
exports.fiberRefLocallyScoped = fiberRefLocallyScoped;
const fiberRefLocallyScopedWith = /*#__PURE__*/(0, _Function.dual)(2, (self, f) => core.fiberRefGetWith(self, a => fiberRefLocallyScoped(self, f(a))));
/* @internal */
exports.fiberRefLocallyScopedWith = fiberRefLocallyScopedWith;
const fiberRefMake = (initial, options) => fiberRefMakeWith(() => core.fiberRefUnsafeMake(initial, options));
/* @internal */
exports.fiberRefMake = fiberRefMake;
const fiberRefMakeWith = ref => acquireRelease(core.tap(core.sync(ref), ref => core.fiberRefUpdate(ref, _Function.identity)), fiberRef => core.fiberRefDelete(fiberRef));
/* @internal */
exports.fiberRefMakeWith = fiberRefMakeWith;
const fiberRefMakeContext = initial => fiberRefMakeWith(() => core.fiberRefUnsafeMakeContext(initial));
/* @internal */
exports.fiberRefMakeContext = fiberRefMakeContext;
const fiberRefMakeRuntimeFlags = initial => fiberRefMakeWith(() => core.fiberRefUnsafeMakeRuntimeFlags(initial));
/** @internal */
exports.fiberRefMakeRuntimeFlags = fiberRefMakeRuntimeFlags;
const currentRuntimeFlags = /*#__PURE__*/core.fiberRefUnsafeMakeRuntimeFlags(_runtimeFlags.none);
/** @internal */
exports.currentRuntimeFlags = currentRuntimeFlags;
const currentSupervisor = /*#__PURE__*/fiberRefUnsafeMakeSupervisor(supervisor.none);
// circular with Fiber
/* @internal */
exports.currentSupervisor = currentSupervisor;
const fiberAwaitAll = fibers => core.asUnit(internalFiber._await(fiberAll(fibers)));
/** @internal */
exports.fiberAwaitAll = fiberAwaitAll;
const fiberAll = fibers => ({
  [internalFiber.FiberTypeId]: internalFiber.fiberVariance,
  id: () => RA.fromIterable(fibers).reduce((id, fiber) => FiberId.combine(id, fiber.id()), FiberId.none),
  await: () => core.exit(forEachParUnbounded(fibers, fiber => core.flatten(fiber.await()), false)),
  children: () => core.map(forEachParUnbounded(fibers, fiber => fiber.children(), false), RA.flatten),
  inheritAll: () => core.forEachSequentialDiscard(fibers, fiber => fiber.inheritAll()),
  poll: () => core.map(core.forEachSequential(fibers, fiber => fiber.poll()), RA.reduceRight(Option.some(core.exitSucceed(new Array())), (optionB, optionA) => {
    switch (optionA._tag) {
      case "None":
        {
          return Option.none();
        }
      case "Some":
        {
          switch (optionB._tag) {
            case "None":
              {
                return Option.none();
              }
            case "Some":
              {
                return Option.some(core.exitZipWith(optionA.value, optionB.value, {
                  onSuccess: (a, chunk) => [a, ...chunk],
                  onFailure: internalCause.parallel
                }));
              }
          }
        }
    }
  })),
  interruptAsFork: fiberId => core.forEachSequentialDiscard(fibers, fiber => fiber.interruptAsFork(fiberId)),
  pipe() {
    return (0, _Pipeable.pipeArguments)(this, arguments);
  }
});
/* @internal */
exports.fiberAll = fiberAll;
const fiberInterruptFork = self => core.asUnit(forkDaemon(core.interruptFiber(self)));
/* @internal */
exports.fiberInterruptFork = fiberInterruptFork;
const fiberJoinAll = fibers => core.asUnit(internalFiber.join(fiberAll(fibers)));
/* @internal */
exports.fiberJoinAll = fiberJoinAll;
const fiberScoped = self => acquireRelease(core.succeed(self), core.interruptFiber);
//
// circular race
//
/** @internal */
exports.fiberScoped = fiberScoped;
const raceWith = /*#__PURE__*/(0, _Function.dual)(3, (self, other, options) => raceFibersWith(self, other, {
  onSelfWin: (winner, loser) => core.flatMap(winner.await(), exit => {
    switch (exit._tag) {
      case OpCodes.OP_SUCCESS:
        {
          return core.flatMap(winner.inheritAll(), () => options.onSelfDone(exit, loser));
        }
      case OpCodes.OP_FAILURE:
        {
          return options.onSelfDone(exit, loser);
        }
    }
  }),
  onOtherWin: (winner, loser) => core.flatMap(winner.await(), exit => {
    switch (exit._tag) {
      case OpCodes.OP_SUCCESS:
        {
          return core.flatMap(winner.inheritAll(), () => options.onOtherDone(exit, loser));
        }
      case OpCodes.OP_FAILURE:
        {
          return options.onOtherDone(exit, loser);
        }
    }
  })
}));
/** @internal */
exports.raceWith = raceWith;
const disconnect = self => core.uninterruptibleMask(restore => core.fiberIdWith(fiberId => core.flatMap(forkDaemon(restore(self)), fiber => core.onInterrupt(() => internalFiber.interruptAsFork(fiberId)(fiber))(restore(internalFiber.join(fiber))))));
/** @internal */
exports.disconnect = disconnect;
const race = /*#__PURE__*/(0, _Function.dual)(2, (self, that) => core.fiberIdWith(parentFiberId => raceWith(self, that, {
  onSelfDone: (exit, right) => core.exitMatchEffect(exit, {
    onFailure: cause => internalEffect.mapErrorCause(cause2 => internalCause.parallel(cause, cause2))(internalFiber.join(right)),
    onSuccess: value => core.as(value)(core.interruptAsFiber(parentFiberId)(right))
  }),
  onOtherDone: (exit, left) => core.exitMatchEffect(exit, {
    onFailure: cause => internalEffect.mapErrorCause(cause2 => internalCause.parallel(cause2, cause))(internalFiber.join(left)),
    onSuccess: value => core.as(value)(core.interruptAsFiber(parentFiberId)(left))
  })
})));
/** @internal */
exports.race = race;
const raceFibersWith = /*#__PURE__*/(0, _Function.dual)(3, (self, other, options) => core.withFiberRuntime((parentFiber, parentStatus) => {
  const parentRuntimeFlags = parentStatus.runtimeFlags;
  const raceIndicator = MRef.make(true);
  const leftFiber = unsafeMakeChildFiber(self, parentFiber, parentRuntimeFlags, options.selfScope);
  const rightFiber = unsafeMakeChildFiber(other, parentFiber, parentRuntimeFlags, options.otherScope);
  return core.async(cb => {
    leftFiber.unsafeAddObserver(() => completeRace(leftFiber, rightFiber, options.onSelfWin, raceIndicator, cb));
    rightFiber.unsafeAddObserver(() => completeRace(rightFiber, leftFiber, options.onOtherWin, raceIndicator, cb));
    leftFiber.startFork(self);
    rightFiber.startFork(other);
  }, FiberId.combine(leftFiber.id(), rightFiber.id()));
}));
exports.raceFibersWith = raceFibersWith;
const completeRace = (winner, loser, cont, ab, cb) => {
  if (MRef.compareAndSet(true, false)(ab)) {
    cb(cont(winner, loser));
  }
};
/** @internal */
const ensuring = /*#__PURE__*/(0, _Function.dual)(2, (self, finalizer) => core.uninterruptibleMask(restore => core.matchCauseEffect(restore(self), {
  onFailure: cause1 => core.matchCauseEffect(finalizer, {
    onFailure: cause2 => core.failCause(internalCause.sequential(cause1, cause2)),
    onSuccess: () => core.failCause(cause1)
  }),
  onSuccess: a => core.as(finalizer, a)
})));
/** @internal */
exports.ensuring = ensuring;
const invokeWithInterrupt = (dataSource, all) => core.fiberIdWith(id => core.flatMap(core.flatMap(forkDaemon(core.interruptible(dataSource)), processing => core.async(cb => {
  const counts = all.map(_ => _.listeners.count);
  const checkDone = () => {
    if (counts.every(count => count === 0)) {
      cleanup.forEach(f => f());
      cb(core.interruptFiber(processing));
    }
  };
  processing.unsafeAddObserver(exit => {
    cleanup.forEach(f => f());
    cb(exit);
  });
  const cleanup = all.map((r, i) => {
    const observer = count => {
      counts[i] = count;
      checkDone();
    };
    r.listeners.addObserver(observer);
    return () => r.listeners.removeObserver(observer);
  });
  checkDone();
  return core.sync(() => {
    cleanup.forEach(f => f());
  });
})), () => core.suspend(() => {
  const residual = all.flatMap(entry => {
    if (!entry.state.completed) {
      return [entry];
    }
    return [];
  });
  return core.forEachSequentialDiscard(residual, entry => (0, _request.complete)(entry.request, core.exitInterrupt(id)));
})));
/** @internal */
exports.invokeWithInterrupt = invokeWithInterrupt;
const interruptWhenPossible = /*#__PURE__*/(0, _Function.dual)(2, (self, all) => core.fiberRefGetWith(_completedRequestMap.currentRequestMap, map => core.suspend(() => {
  const entries = RA.fromIterable(all).flatMap(_ => map.has(_) ? [map.get(_)] : []);
  return invokeWithInterrupt(self, entries);
})));
// circular Tracer
/** @internal */
exports.interruptWhenPossible = interruptWhenPossible;
const useSpanScoped = (name, options) => acquireRelease(internalEffect.makeSpan(name, options), (span, exit) => core.flatMap(internalEffect.currentTimeNanosTracing, endTime => core.sync(() => span.end(endTime, exit))));
/* @internal */
exports.useSpanScoped = useSpanScoped;
const withSpanScoped = (name, options) => core.flatMap(internalEffect.makeSpan(name, options), span => fiberRefLocallyScopedWith(core.currentTracerSpan, List.prepend(span)));
/* @internal */
exports.withSpanScoped = withSpanScoped;
const withTracerScoped = value => fiberRefLocallyScopedWith(defaultServices.currentServices, Context.add(tracer.tracerTag, value));
/* @internal */
exports.withTracerScoped = withTracerScoped;
const withParentSpanScoped = span => fiberRefLocallyScopedWith(core.currentTracerSpan, List.prepend(span));
exports.withParentSpanScoped = withParentSpanScoped;
//# sourceMappingURL=fiberRuntime.js.map