{"version":3,"file":"observable-kpFFzvou.mjs","names":[],"sources":["../src/observable/observable.ts"],"sourcesContent":["import type {\n  Observable,\n  Observer,\n  OperatorFunction,\n  TeardownLogic,\n  UnaryFunction,\n  Unsubscribable,\n} from './types';\n\n/**\n * The type of the values an observable emits.\n * @public\n */\nexport type inferObservableValue<TObservable> =\n  TObservable extends Observable<infer TValue, unknown> ? TValue : never;\n\n/**\n * Whether a value is an observable: an object with `subscribe`.\n * @public\n */\nexport function isObservable(x: unknown): x is Observable<unknown, unknown> {\n  return typeof x === 'object' && x !== null && 'subscribe' in x;\n}\n\n/**\n * Creates an observable. `subscribe` runs for each subscriber, and can\n * return a function that cleans up when it unsubscribes.\n * @example\n * ```ts\n * const ticks = observable<number>((observer) => {\n *   const timer = setInterval(() => observer.next(Date.now()), 1000);\n *   return () => clearInterval(timer);\n * });\n * ```\n * @see https://trpc.io/docs/client/links#creating-a-custom-link\n * @public\n */\nexport function observable<TValue, TError = unknown>(\n  subscribe: (observer: Observer<TValue, TError>) => TeardownLogic,\n): Observable<TValue, TError> {\n  const self: Observable<TValue, TError> = {\n    subscribe(observer) {\n      let teardownRef: TeardownLogic | null = null;\n      let isDone = false;\n      let unsubscribed = false;\n      let teardownImmediately = false;\n      let subscribing = true;\n      let thrownWhileSubscribing = null as { cause: unknown } | null;\n      function end(notify: () => void) {\n        try {\n          notify();\n        } catch (cause) {\n          // The source hasn't returned its teardown yet; rethrow once it has\n          // run.\n          if (!subscribing) throw cause;\n          thrownWhileSubscribing ??= { cause };\n        } finally {\n          unsubscribe();\n        }\n      }\n      function unsubscribe() {\n        if (teardownRef === null) {\n          teardownImmediately = true;\n          return;\n        }\n        if (unsubscribed) {\n          return;\n        }\n        unsubscribed = true;\n\n        if (typeof teardownRef === 'function') {\n          teardownRef();\n        } else if (teardownRef) {\n          teardownRef.unsubscribe();\n        }\n      }\n      teardownRef = subscribe({\n        next(value) {\n          if (isDone) {\n            return;\n          }\n          observer.next?.(value);\n        },\n        error(err) {\n          if (isDone) {\n            return;\n          }\n          isDone = true;\n          end(() => observer.error?.(err));\n        },\n        complete() {\n          if (isDone) {\n            return;\n          }\n          isDone = true;\n          end(() => observer.complete?.());\n        },\n      });\n      subscribing = false;\n      if (teardownImmediately) {\n        unsubscribe();\n      }\n      if (thrownWhileSubscribing) {\n        throw thrownWhileSubscribing.cause;\n      }\n      return {\n        unsubscribe,\n      };\n    },\n    pipe(\n      ...operations: OperatorFunction<any, any, any, any>[]\n    ): Observable<any, any> {\n      return operations.reduce(pipeReducer, self);\n    },\n  };\n  return self;\n}\n\nfunction pipeReducer(prev: any, fn: UnaryFunction<any, any>) {\n  return fn(prev);\n}\n\n/**\n * Resolves with an observable's first value. Rejects if it errors or\n * completes first. It doesn't unsubscribe after the first value.\n * @internal\n */\nexport function observableToPromise<TValue>(\n  observable: Observable<TValue, unknown>,\n) {\n  const ac = new AbortController();\n  const promise = new Promise<TValue>((resolve, reject) => {\n    let isDone = false;\n    function onDone() {\n      if (isDone) {\n        return;\n      }\n      isDone = true;\n      obs$.unsubscribe();\n    }\n    ac.signal.addEventListener('abort', () => {\n      reject(ac.signal.reason);\n    });\n    const obs$ = observable.subscribe({\n      next(data) {\n        isDone = true;\n        resolve(data);\n        onDone();\n      },\n      error(data) {\n        reject(data);\n      },\n      complete() {\n        ac.abort();\n        onDone();\n      },\n    });\n  });\n  return promise;\n}\n\n/**\n * Turns an observable into an async iterable, like Node's `events.on()`.\n * Values wait in a queue until `next()` reads them. An error rejects the\n * `next()` after the queued values, once. Completion, `return()` and aborting\n * `signal` unsubscribe and end every pending `next()` with `{ done: true }`;\n * anything the observable sends after that is ignored.\n *\n * If unsubscribing throws, `return()` rejects with the error, and completion\n * or an error from the observable rethrows it. On abort, it rejects the\n * `next()` after the queued values instead, as an error would.\n * @internal\n */\nexport function observableToAsyncIterable<TValue>(\n  observable: Observable<TValue, unknown>,\n  signal: AbortSignal,\n): AsyncIterableIterator<TValue> {\n  const values: TValue[] = [];\n  const pending: {\n    resolve: (result: IteratorResult<TValue>) => void;\n    reject: (cause: unknown) => void;\n  }[] = [];\n  let error: { cause: unknown } | null = null;\n  let finished = false;\n  let subscription: Unsubscribable | null = null;\n\n  /** Unsubscribes once, and returns what the teardown threw. */\n  function unsubscribe(): { cause: unknown } | null {\n    if (finished) {\n      return null;\n    }\n    finished = true;\n    signal.removeEventListener('abort', abort);\n    try {\n      subscription?.unsubscribe();\n      return null;\n    } catch (cause) {\n      return { cause };\n    }\n  }\n  /** Settles every pending `next()`: the first with `error` if there is one. */\n  function settle() {\n    const first = error ? pending.shift() : undefined;\n    if (error && first) {\n      const { cause } = error;\n      error = null;\n      first.reject(cause);\n    }\n    for (const promise of pending.splice(0)) {\n      promise.resolve({ value: undefined, done: true });\n    }\n  }\n  function finish() {\n    const failure = unsubscribe();\n    settle();\n    if (failure) {\n      throw failure.cause;\n    }\n  }\n  function abort() {\n    const failure = unsubscribe();\n    if (failure) {\n      error = failure;\n    }\n    settle();\n  }\n\n  subscription = observable.subscribe({\n    next(value) {\n      if (finished) {\n        return;\n      }\n      const promise = pending.shift();\n      if (promise) {\n        promise.resolve({ value, done: false });\n      } else {\n        values.push(value);\n      }\n    },\n    error(cause) {\n      if (finished) {\n        return;\n      }\n      error = { cause };\n      finish();\n    },\n    complete: finish,\n  });\n  if (finished) {\n    subscription.unsubscribe();\n  } else if (signal.aborted) {\n    abort();\n  } else {\n    signal.addEventListener('abort', abort, { once: true });\n  }\n\n  const iterator: AsyncIterableIterator<TValue> = {\n    [Symbol.asyncIterator]() {\n      return iterator;\n    },\n    async next() {\n      if (values.length > 0) {\n        return { value: values.shift() as TValue, done: false };\n      }\n      if (error) {\n        const { cause } = error;\n        error = null;\n        throw cause;\n      }\n      if (finished) {\n        return { value: undefined, done: true };\n      }\n      return new Promise((resolve, reject) => {\n        pending.push({ resolve, reject });\n      });\n    },\n    async return() {\n      values.length = 0;\n      error = null;\n      finish();\n      return { value: undefined, done: true };\n    },\n  };\n  return iterator;\n}\n"],"mappings":"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"}