{"version":3,"file":"index.mjs","names":[],"sources":["../../src/effect-rpc.ts","../../src/errors.ts","../../src/rpc.ts","../../src/service.ts","../../src/testing.ts","../../src/trace.ts"],"sourcesContent":["//\n// Copyright 2026 DXOS.org\n//\n\nimport * as RpcClient from '@effect/rpc/RpcClient';\nimport * as RpcClientError from '@effect/rpc/RpcClientError';\nimport * as RpcMessage from '@effect/rpc/RpcMessage';\nimport * as RpcSerialization from '@effect/rpc/RpcSerialization';\nimport * as RpcServer from '@effect/rpc/RpcServer';\nimport * as Duration from 'effect/Duration';\nimport * as Effect from 'effect/Effect';\nimport * as Layer from 'effect/Layer';\nimport * as Mailbox from 'effect/Mailbox';\nimport * as Option from 'effect/Option';\nimport type * as Scope from 'effect/Scope';\n\nimport { log } from '@dxos/log';\n\nimport { type RpcPort } from './rpc';\n\n/**\n * Interval at which the client re-sends the initial Ping while waiting for the server to attach.\n */\nconst HANDSHAKE_RETRY_INTERVAL = Duration.millis(50);\n\n/**\n * Effect RPC protocols over a {@link RpcPort} — a transport-agnostic, reliable, ordered,\n * binary message channel. Message envelopes are framed with msgpack; RPC payloads are expected\n * to already be binary-safe (e.g. protobuf-encoded by the payload schemas).\n */\n\nconst subscribePort = (port: RpcPort) =>\n  Effect.gen(function* () {\n    const mailbox = yield* Mailbox.make<Uint8Array>();\n    const unsubscribe = port.subscribe((message) => {\n      mailbox.unsafeOffer(message);\n    });\n    yield* Effect.addFinalizer(() =>\n      Effect.sync(() => {\n        unsubscribe?.();\n      }),\n    );\n    return mailbox;\n  });\n\nconst sendFrame = (port: RpcPort, frame: Uint8Array | string | undefined): Effect.Effect<void, Error> =>\n  frame === undefined || typeof frame === 'string'\n    ? Effect.dieMessage('rpc-port protocol requires binary frames')\n    : // Copy the frame: msgpack encoders reuse their output buffer, but RpcPort.send may be\n      // asynchronous (e.g. postMessage) and read the bytes after the encoder has overwritten them.\n      Effect.tryPromise({\n        try: async () => port.send(frame.slice()),\n        catch: (cause) => (cause instanceof Error ? cause : new Error(String(cause))),\n      });\n\n/**\n * Client-side effect-rpc protocol over an {@link RpcPort}.\n *\n * Performs a Ping/Pong handshake on construction: the server answers Pings as soon as it is\n * running, so construction blocks until the peer is reachable and fails fast under an outer\n * timeout instead of buffering requests towards a peer that never attaches.\n */\nexport const makeProtocolRpcPortClient = (\n  port: RpcPort,\n): Effect.Effect<RpcClient.Protocol['Type'], never, Scope.Scope> =>\n  RpcClient.Protocol.make(\n    Effect.fnUntraced(function* (writeResponse) {\n      const parser = RpcSerialization.msgPack.unsafeMake();\n      const mailbox = yield* subscribePort(port);\n\n      const decodeFrame = (frame: Uint8Array) =>\n        Effect.try({\n          try: () => parser.decode(frame) as ReadonlyArray<RpcMessage.FromServerEncoded>,\n          catch: (cause) => {\n            log.warn('rpc-port client: failed to decode frame', { cause });\n            return [] as ReadonlyArray<RpcMessage.FromServerEncoded>;\n          },\n        }).pipe(Effect.merge);\n\n      const send = (request: RpcMessage.FromClientEncoded): Effect.Effect<void, RpcClientError.RpcClientError> =>\n        Effect.suspend(() => sendFrame(port, parser.encode(request))).pipe(\n          Effect.mapError(\n            (cause) =>\n              new RpcClientError.RpcClientError({\n                reason: 'Protocol',\n                message: 'Failed to send message over RpcPort',\n                cause,\n              }),\n          ),\n        );\n\n      // Handshake: resend Ping until the server responds, forwarding any other early responses.\n      // Transport failures during the handshake are unrecoverable for this connection.\n      yield* Effect.gen(function* () {\n        let connected = false;\n        while (!connected) {\n          yield* send(RpcMessage.constPing);\n          const frame = yield* mailbox.take.pipe(Effect.timeoutOption(HANDSHAKE_RETRY_INTERVAL));\n          if (Option.isNone(frame)) {\n            continue;\n          }\n          for (const response of yield* decodeFrame(frame.value)) {\n            if (response._tag === 'Pong') {\n              connected = true;\n            } else {\n              yield* writeResponse(response);\n            }\n          }\n        }\n      }).pipe(Effect.orDie);\n\n      yield* mailbox.take.pipe(\n        Effect.flatMap(decodeFrame),\n        Effect.flatMap((responses) => Effect.forEach(responses, writeResponse, { discard: true })),\n        Effect.forever,\n        Effect.orDie,\n        Effect.interruptible,\n        Effect.forkScoped,\n      );\n\n      return {\n        send,\n        supportsAck: true,\n        supportsTransferables: false,\n      };\n    }),\n  );\n\nexport const layerProtocolRpcPortClient = (port: RpcPort): Layer.Layer<RpcClient.Protocol> =>\n  Layer.scoped(RpcClient.Protocol, makeProtocolRpcPortClient(port));\n\n/**\n * Server-side effect-rpc protocol over an {@link RpcPort}.\n * The port carries a single logical client for the lifetime of the protocol.\n */\nexport const makeProtocolRpcPortServer = (\n  port: RpcPort,\n): Effect.Effect<RpcServer.Protocol['Type'], never, Scope.Scope> =>\n  RpcServer.Protocol.make(\n    Effect.fnUntraced(function* (writeRequest) {\n      const parser = RpcSerialization.msgPack.unsafeMake();\n      const mailbox = yield* subscribePort(port);\n      const disconnects = yield* Mailbox.make<number>();\n      const clientId = 0;\n\n      yield* mailbox.take.pipe(\n        Effect.flatMap((frame) =>\n          Effect.try({\n            try: () => parser.decode(frame) as ReadonlyArray<RpcMessage.FromClientEncoded>,\n            catch: (cause) => {\n              log.warn('rpc-port server: failed to decode frame', { cause });\n              return [] as ReadonlyArray<RpcMessage.FromClientEncoded>;\n            },\n          }).pipe(Effect.merge),\n        ),\n        Effect.flatMap((requests) =>\n          Effect.forEach(requests, (request) => writeRequest(clientId, request), { discard: true }),\n        ),\n        Effect.forever,\n        Effect.interruptible,\n        Effect.forkScoped,\n      );\n\n      return {\n        disconnects,\n        send: (_clientId: number, response: RpcMessage.FromServerEncoded) =>\n          Effect.suspend(() => sendFrame(port, parser.encode(response))).pipe(Effect.orDie),\n        end: (_clientId: number) => Effect.void,\n        clientIds: Effect.sync(() => new Set([clientId])),\n        initialMessage: Effect.succeed(Option.none()),\n        supportsAck: true,\n        supportsTransferables: false,\n        supportsSpanPropagation: false,\n      };\n    }),\n  );\n\nexport const layerProtocolRpcPortServer = (port: RpcPort): Layer.Layer<RpcServer.Protocol> =>\n  Layer.scoped(RpcServer.Protocol, makeProtocolRpcPortServer(port));\n","//\n// Copyright 2021 DXOS.org\n//\n\nimport { StackTrace } from '@dxos/debug';\nimport { decodeError } from '@dxos/protocols';\nimport { type Error as ErrorResponse } from '@dxos/protocols/proto/dxos/error';\n\nexport const decodeRpcError = (err: ErrorResponse, rpcMethod: string): Error =>\n  decodeError(err, {\n    appendStack: `\\n    at RPC ${rpcMethod} \\n` + new StackTrace().getStack(1),\n  });\n","//\n// Copyright 2021 DXOS.org\n//\n\nimport { Trigger, asyncTimeout, synchronized } from '@dxos/async';\nimport { type Any, type ProtoCodec, type RequestOptions, Stream } from '@dxos/codec-protobuf';\nimport { type Context, ContextRpcCodec } from '@dxos/context';\nimport { StackTrace } from '@dxos/debug';\nimport { invariant } from '@dxos/invariant';\nimport { log } from '@dxos/log';\nimport { RpcClosedError, RpcNotOpenError, encodeError } from '@dxos/protocols';\nimport { schema } from '@dxos/protocols/proto';\nimport { type Request, type Response, type RpcMessage } from '@dxos/protocols/proto/dxos/rpc';\nimport { exponentialBackoffInterval } from '@dxos/util';\n\nimport { decodeRpcError } from './errors';\n\nconst DEFAULT_TIMEOUT = 30_000;\nconst BYE_SEND_TIMEOUT = 2_000;\n\nconst DEBUG_CALLS = true;\n\ntype MaybePromise<T> = Promise<T> | T;\n\nexport interface RpcPeerOptions {\n  port: RpcPort;\n\n  /**\n   * Time to wait for a response to an RPC call.\n   */\n  timeout?: number;\n\n  callHandler: (method: string, request: Any, options?: RequestOptions) => MaybePromise<Any>;\n  streamHandler?: (method: string, request: Any, options?: RequestOptions) => Stream<Any>;\n\n  /**\n   * Do not require or send handshake messages.\n   */\n  noHandshake?: boolean;\n\n  /**\n   * What options get passed to the `callHandler` and `streamHandler`.\n   */\n  handlerRpcOptions?: RequestOptions;\n}\n\n/**\n * Interface for a transport-agnostic port to send/receive binary messages.\n */\nexport interface RpcPort {\n  send: (msg: Uint8Array, timeout?: number) => MaybePromise<void>;\n  subscribe: (cb: (msg: Uint8Array) => void) => (() => void) | void;\n}\n\nconst CLOSE_TIMEOUT = 3_000;\n\nexport type CloseOptions = {\n  /**\n   * Time to wait for the other side to confirm close.\n   */\n  timeout?: number;\n};\n\nclass PendingRpcRequest {\n  constructor(\n    public readonly resolve: (response: Response) => void,\n    public readonly reject: (error?: Error) => void,\n    public readonly stream: boolean,\n  ) {}\n}\n\n// NOTE: Lazy so that code that doesn't use indexing doesn't need to load the codec (breaks in workerd).\nlet RpcMessageCodec!: ProtoCodec<RpcMessage>;\nconst getRpcMessageCodec = () => (RpcMessageCodec ??= schema.getCodecForType('dxos.rpc.RpcMessage'));\n\nenum RpcState {\n  INITIAL = 'INITIAL',\n\n  OPENING = 'OPENING',\n\n  OPENED = 'OPENED',\n\n  /**\n   * Bye message sent, waiting for the other side to close.\n   * Not possible to send requests.\n   * All pending requests will be rejected.\n   */\n  CLOSING = 'CLOSING',\n\n  /**\n   * Connection fully closed.\n   * The underlying transport can be disposed.\n   */\n  CLOSED = 'CLOSED',\n}\n\n/**\n * A remote procedure call peer.\n *\n * Provides a away to make RPC calls and get a response back as a promise.\n * Does not handle encoding/decoding and only works with byte buffers.\n * For type safe approach see `createRpcClient` and `createRpcServer`.\n *\n * Must be connected with another instance on the other side via `send`/`receive` methods.\n * Both sides must be opened before making any RPC calls.\n *\n * Errors inside the handler get serialized and sent to the other side.\n *\n * Inspired by JSON-RPC 2.0 https://www.jsonrpc.org/specification.\n */\nexport class RpcPeer {\n  private readonly _params: RpcPeerOptions;\n\n  private readonly _outgoingRequests = new Map<number, PendingRpcRequest>();\n  private readonly _localStreams = new Map<number, Stream<any>>();\n  private readonly _remoteOpenTrigger = new Trigger();\n\n  /**\n   * Triggered when the peer starts closing.\n   */\n  private readonly _closingTrigger = new Trigger();\n\n  /**\n   * Triggered when peer receives a bye message.\n   */\n  private readonly _byeTrigger = new Trigger();\n\n  private _nextId = 0;\n  private _state: RpcState = RpcState.INITIAL;\n  private _unsubscribeFromPort: (() => void) | undefined = undefined;\n  private _clearOpenInterval: (() => void) | undefined = undefined;\n\n  constructor(params: RpcPeerOptions) {\n    this._params = {\n      timeout: undefined,\n      streamHandler: undefined,\n      noHandshake: false,\n      ...params,\n    };\n  }\n\n  /**\n   * Open the peer. Required before making any calls.\n   *\n   * Will block before the other peer calls `open`.\n   */\n  @synchronized\n  async open(): Promise<void> {\n    if (this._state !== RpcState.INITIAL) {\n      return;\n    }\n\n    this._unsubscribeFromPort = this._params.port.subscribe(async (msg) => {\n      try {\n        await this._receive(msg);\n      } catch (err: any) {\n        log.catch(err);\n      }\n    }) as any;\n\n    this._state = RpcState.OPENING;\n\n    if (this._params.noHandshake) {\n      this._state = RpcState.OPENED;\n      this._remoteOpenTrigger.wake();\n      return;\n    }\n\n    log('sending open message', { state: this._state });\n    await this._sendMessage({ open: true });\n\n    if (this._state !== RpcState.OPENING) {\n      return;\n    }\n\n    // Retry sending.\n    this._clearOpenInterval = exponentialBackoffInterval(() => {\n      void this._sendMessage({ open: true }).catch((err) => log.warn(err));\n    }, 50);\n\n    await Promise.race([this._remoteOpenTrigger.wait(), this._closingTrigger.wait()]);\n\n    this._clearOpenInterval?.();\n\n    if ((this._state as RpcState) !== RpcState.OPENED) {\n      // Closed while opening.\n      return; // TODO(dmaretskyi): Throw error?\n    }\n\n    // TODO(burdon): This seems error prone.\n    // Send an \"open\" message in case the other peer has missed our first \"open\" message and is still waiting.\n    log('resending open message', { state: this._state });\n    await this._sendMessage({ openAck: true });\n  }\n\n  /**\n   * Close the peer.\n   * Stop taking or making requests.\n   * Will wait for confirmation from the other side.\n   * Any responses for RPC calls made before close will be delivered.\n   */\n  async close({ timeout = CLOSE_TIMEOUT }: CloseOptions = {}): Promise<void> {\n    if (this._state === RpcState.CLOSED) {\n      return;\n    }\n\n    this._abortRequests();\n\n    if (this._state === RpcState.OPENED && !this._params.noHandshake) {\n      try {\n        this._state = RpcState.CLOSING;\n        await this._sendMessage({ bye: {} }, BYE_SEND_TIMEOUT);\n      } catch (err: any) {\n        log('error closing peer, sending bye', { err });\n      }\n      try {\n        log('closing waiting on bye');\n        await this._byeTrigger.wait({ timeout });\n      } catch (err: any) {\n        log('error closing peer', { err });\n        return;\n      }\n    }\n\n    this._disposeAndClose();\n  }\n\n  /**\n   * Dispose the connection without waiting for the other side.\n   */\n  async abort(): Promise<void> {\n    if (this._state === RpcState.CLOSED) {\n      return;\n    }\n\n    this._abortRequests();\n    this._disposeAndClose();\n  }\n\n  private _abortRequests(): void {\n    // Abort open\n    this._clearOpenInterval?.();\n    this._closingTrigger.wake();\n\n    // Abort pending requests\n    for (const req of this._outgoingRequests.values()) {\n      req.reject(new RpcClosedError());\n    }\n    this._outgoingRequests.clear();\n  }\n\n  private _disposeAndClose(): void {\n    this._unsubscribeFromPort?.();\n    this._unsubscribeFromPort = undefined;\n    this._clearOpenInterval?.();\n    this._state = RpcState.CLOSED;\n  }\n\n  /**\n   * Handle incoming message. Should be called as the result of other peer's `send` callback.\n   */\n  private async _receive(msg: Uint8Array): Promise<void> {\n    const decoded = getRpcMessageCodec().decode(msg, { preserveAny: true });\n    DEBUG_CALLS && log.trace('received message', { type: Object.keys(decoded)[0] });\n\n    if (decoded.request) {\n      if (this._state !== RpcState.OPENED && this._state !== RpcState.OPENING) {\n        log('received request while closed');\n        await this._sendMessage({\n          response: {\n            id: decoded.request.id,\n            error: encodeError(new RpcClosedError()),\n          },\n        });\n        return;\n      }\n\n      const req = decoded.request;\n      if (req.stream) {\n        log('stream request', { method: req.method });\n        this._callStreamHandler(req, (response) => {\n          log.trace('sending stream response', {\n            method: req.method,\n            response: response.payload?.type_url,\n            error: response.error,\n            close: response.close,\n          });\n\n          void this._sendMessage({ response }).catch((err) => {\n            log.warn('failed during close', err);\n          });\n        });\n      } else {\n        DEBUG_CALLS && log.trace('requesting...', { method: req.method });\n        const response = await this._callHandler(req);\n        DEBUG_CALLS &&\n          log.trace('sending response', {\n            method: req.method,\n            response: response.payload?.type_url,\n            error: response.error,\n          });\n        await this._sendMessage({ response });\n      }\n    } else if (decoded.response) {\n      if (this._state !== RpcState.OPENED) {\n        log('received response while closed');\n        return; // Ignore when not open.\n      }\n\n      const responseId = decoded.response.id;\n      invariant(typeof responseId === 'number');\n      if (!this._outgoingRequests.has(responseId)) {\n        log.trace('received response with invalid id', { responseId });\n        return; // Ignore requests with incorrect id.\n      }\n\n      const item = this._outgoingRequests.get(responseId)!;\n      // Delete the request record if no more responses are expected.\n      if (!item.stream) {\n        this._outgoingRequests.delete(responseId);\n      }\n\n      DEBUG_CALLS && log.trace('response', { type_url: decoded.response.payload?.type_url });\n      item.resolve(decoded.response);\n    } else if (decoded.open) {\n      log('received open message', { state: this._state });\n      if (this._params.noHandshake) {\n        return;\n      }\n\n      await this._sendMessage({ openAck: true });\n    } else if (decoded.openAck) {\n      log('received openAck message', { state: this._state });\n      if (this._params.noHandshake) {\n        return;\n      }\n\n      this._state = RpcState.OPENED;\n      this._remoteOpenTrigger.wake();\n    } else if (decoded.streamClose) {\n      if (this._state !== RpcState.OPENED) {\n        log('received stream close while closed');\n        return; // Ignore when not open.\n      }\n\n      log('received stream close', { id: decoded.streamClose.id });\n      invariant(typeof decoded.streamClose.id === 'number');\n      const stream = this._localStreams.get(decoded.streamClose.id);\n      if (!stream) {\n        log('no local stream', { id: decoded.streamClose.id });\n        return; // Ignore requests with incorrect id.\n      }\n\n      this._localStreams.delete(decoded.streamClose.id);\n      await stream.close();\n    } else if (decoded.bye) {\n      this._byeTrigger.wake();\n      // If we haven't already started closing, close now.\n      if (this._state !== RpcState.CLOSING && this._state !== RpcState.CLOSED) {\n        log('replying to bye');\n        this._state = RpcState.CLOSING;\n        await this._sendMessage({ bye: {} });\n\n        this._abortRequests();\n        this._disposeAndClose();\n      }\n    } else {\n      log.error('received malformed message', { msg });\n      throw new Error('Malformed message.');\n    }\n  }\n\n  /**\n   * Make RPC call. Will trigger a handler on the other side.\n   * Peer should be open before making this call.\n   */\n  async call(method: string, request: Any, options?: RequestOptions): Promise<Any> {\n    DEBUG_CALLS && log.trace('calling...', { method });\n    throwIfNotOpen(this._state);\n\n    let response: Response;\n    try {\n      // Set-up response listener.\n      const id = this._nextId++;\n      const responseReceived = new Promise<Response>((resolve, reject) => {\n        this._outgoingRequests.set(id, new PendingRpcRequest(resolve, reject, false));\n      });\n\n      let traceContext;\n      try {\n        traceContext = options?.ctx ? ContextRpcCodec.encode(options.ctx) : undefined;\n      } catch (err) {\n        log.warn('failed to encode trace context', { err });\n      }\n\n      // Send request call.\n      const sending = this._sendMessage({\n        request: {\n          id,\n          method,\n          payload: request,\n          stream: false,\n          ...(traceContext ? { traceContext } : {}),\n        },\n      });\n\n      // Wait until send completes or throws an error (or response throws a timeout), the resume waiting.\n      const timeout = options?.timeout ?? this._params.timeout;\n      const waiting =\n        timeout === 0 ? responseReceived : asyncTimeout<any>(responseReceived, timeout ?? DEFAULT_TIMEOUT);\n\n      await Promise.race([sending, waiting]);\n      response = await waiting;\n      invariant(response.id === id);\n    } catch (err) {\n      if (err instanceof RpcClosedError) {\n        // Rethrow the error here to have the correct stack-trace.\n        const error = new RpcClosedError();\n        error.stack += `\\n\\n info: RPC client was closed at:\\n${err.stack?.split('\\n').slice(1).join('\\n')}`;\n        throw error;\n      }\n\n      throw err;\n    }\n\n    if (response.payload) {\n      return response.payload;\n    } else if (response.error) {\n      throw decodeRpcError(response.error, method);\n    } else {\n      throw new Error('Malformed response.');\n    }\n  }\n\n  /**\n   * Make RPC call with a streaming response.\n   * Will trigger a handler on the other side.\n   * Peer should be open before making this call.\n   */\n  callStream(method: string, request: Any, options?: RequestOptions): Stream<Any> {\n    throwIfNotOpen(this._state);\n    const id = this._nextId++;\n\n    return new Stream(({ ready, next, close }) => {\n      const onResponse = (response: Response) => {\n        if (response.streamReady) {\n          ready();\n        } else if (response.close) {\n          close();\n        } else if (response.error) {\n          // TODO(dmaretskyi): Stack trace might be lost because the stream producer function is called asynchronously.\n          close(decodeRpcError(response.error, method));\n        } else if (response.payload) {\n          next(response.payload);\n        } else {\n          throw new Error('Malformed response.');\n        }\n      };\n\n      const stack = new StackTrace();\n      const closeStream = (err?: Error) => {\n        if (!err) {\n          close();\n        } else {\n          err.stack += `\\n\\nError happened in the stream at:\\n${stack.getStack()}`;\n          close(err);\n        }\n      };\n\n      this._outgoingRequests.set(id, new PendingRpcRequest(onResponse, closeStream, true));\n\n      let traceContext;\n      try {\n        traceContext = options?.ctx ? ContextRpcCodec.encode(options.ctx) : undefined;\n      } catch (err) {\n        log.warn('failed to encode trace context', { err });\n      }\n\n      try {\n        this._sendMessage({\n          request: {\n            id,\n            method,\n            payload: request,\n            stream: true,\n            ...(traceContext ? { traceContext } : {}),\n          },\n        }).catch((err) => {\n          this._outgoingRequests.delete(id);\n          close(err);\n        });\n      } catch (err) {\n        this._outgoingRequests.delete(id);\n        throw err;\n      }\n\n      return () => {\n        this._sendMessage({\n          streamClose: { id },\n        }).catch((err) => {\n          log.catch(err);\n        });\n        this._outgoingRequests.delete(id);\n      };\n    });\n  }\n\n  private async _sendMessage(message: RpcMessage, timeout?: number): Promise<void> {\n    DEBUG_CALLS && log.trace('sending message', { type: Object.keys(message)[0] });\n    await this._params.port.send(getRpcMessageCodec().encode(message, { preserveAny: true }), timeout);\n  }\n\n  private _getHandlerRpcOptions(req: Request): RequestOptions | undefined {\n    let traceCtx: Context | undefined;\n    if (req.traceContext) {\n      try {\n        traceCtx = ContextRpcCodec.decode(req.traceContext);\n      } catch (err) {\n        log.warn('failed to decode trace context', { traceContext: req.traceContext, err });\n      }\n    }\n    if (!traceCtx && !this._params.handlerRpcOptions) {\n      return undefined;\n    }\n    return { ...this._params.handlerRpcOptions, ...(traceCtx ? { ctx: traceCtx } : {}) };\n  }\n\n  private async _callHandler(req: Request): Promise<Response> {\n    try {\n      invariant(typeof req.id === 'number');\n      invariant(req.payload);\n      invariant(req.method);\n\n      const response = await this._params.callHandler(req.method, req.payload, this._getHandlerRpcOptions(req));\n      return {\n        id: req.id,\n        payload: response,\n      };\n    } catch (err) {\n      return {\n        id: req.id,\n        error: encodeError(err),\n      };\n    }\n  }\n\n  private _callStreamHandler(req: Request, callback: (response: Response) => void): void {\n    try {\n      invariant(this._params.streamHandler, 'Requests with streaming responses are not supported.');\n      invariant(typeof req.id === 'number');\n      invariant(req.payload);\n      invariant(req.method);\n\n      const responseStream = this._params.streamHandler(req.method, req.payload, this._getHandlerRpcOptions(req));\n      responseStream.onReady(() => {\n        callback({\n          id: req.id,\n          streamReady: true,\n        });\n      });\n\n      responseStream.subscribe(\n        (msg) => {\n          callback({\n            id: req.id,\n            payload: msg,\n          });\n        },\n        (error) => {\n          if (error) {\n            callback({\n              id: req.id,\n              error: encodeError(error),\n            });\n          } else {\n            callback({\n              id: req.id,\n              close: true,\n            });\n          }\n        },\n      );\n\n      this._localStreams.set(req.id, responseStream);\n    } catch (err: any) {\n      callback({\n        id: req.id,\n        error: encodeError(err),\n      });\n    }\n  }\n}\n\nconst throwIfNotOpen = (state: RpcState) => {\n  switch (state) {\n    case RpcState.OPENED: {\n      return;\n    }\n    case RpcState.INITIAL: {\n      throw new RpcNotOpenError();\n    }\n    case RpcState.CLOSED: {\n      throw new RpcClosedError();\n    }\n  }\n};\n","//\n// Copyright 2021 DXOS.org\n//\n\nimport {\n  type EncodingOptions,\n  type ServiceDescriptor,\n  type ServiceHandler,\n  type ServiceProvider,\n} from '@dxos/codec-protobuf';\nimport { invariant } from '@dxos/invariant';\n\nimport { RpcPeer, type RpcPeerOptions } from './rpc';\n\n/**\n * Map of service definitions.\n */\n// TODO(burdon): Rename ServiceMap.\nexport type ServiceBundle<Services> = { [Key in keyof Services]: ServiceDescriptor<Services[Key]> };\n\nexport type ServiceHandlers<Services> = { [ServiceName in keyof Services]: ServiceProvider<Services[ServiceName]> };\n\nexport type ServiceTypesOf<Bundle extends ServiceBundle<any>> =\n  Bundle extends ServiceBundle<infer Services> ? Services : never;\n\n/**\n * Groups multiple services together to be served by a single RPC peer.\n */\nexport const createServiceBundle = <Service>(services: ServiceBundle<Service>): ServiceBundle<Service> => services;\n\n/**\n * Type-safe RPC peer.\n */\nexport class ProtoRpcPeer<Service> {\n  constructor(\n    public readonly rpc: Service,\n    private readonly _peer: RpcPeer,\n  ) {}\n\n  async open(): Promise<void> {\n    await this._peer.open();\n  }\n\n  async close(): Promise<void> {\n    await this._peer.close();\n  }\n\n  async abort(): Promise<void> {\n    await this._peer.abort();\n  }\n}\n\nexport interface ProtoRpcPeerOptions<Client, Server> extends Omit<RpcPeerOptions, 'callHandler' | 'streamHandler'> {\n  /**\n   * Services that are expected to be implemented by the counter-space.\n   */\n  // TODO(burdon): Rename proxy.\n  requested?: ServiceBundle<Client>;\n\n  /**\n   * Services exposed to the counter-space.\n   */\n  // TODO(burdon): Rename service.\n  exposed?: ServiceBundle<Server>;\n\n  /**\n   * Handlers for the exposed services\n   */\n  handlers?: ServiceHandlers<Server>;\n\n  /**\n   * Encoding options passed to the underlying proto codec.\n   */\n  encodingOptions?: EncodingOptions;\n}\n\n/**\n * Create type-safe RPC peer from a service bundle.\n * Can both handle and issue requests.\n */\n// TODO(burdon): Currently assumes that the proto service name is unique.\n//  Support multiple instances services definitions (e.g., halo/space invitations).\nexport const createProtoRpcPeer = <Client = {}, Server = {}>({\n  requested,\n  exposed,\n  handlers,\n  encodingOptions,\n  ...rest\n}: ProtoRpcPeerOptions<Client, Server>): ProtoRpcPeer<Client> => {\n  // Create map of RPCs.\n  const exposedRpcs: Record<string, ServiceHandler<any>> = {};\n  if (exposed) {\n    invariant(handlers);\n    for (const serviceName of Object.keys(exposed) as (keyof Server)[]) {\n      // Get full service name with the package name without '.' at the beginning.\n      const serviceFqn = exposed[serviceName].serviceProto.fullName.slice(1);\n      const serviceProvider = handlers[serviceName];\n      exposedRpcs[serviceFqn] = exposed[serviceName].createServer(serviceProvider, encodingOptions);\n    }\n  }\n\n  // Create peer.\n  const peer = new RpcPeer({\n    ...rest,\n\n    callHandler: (method, request, options) => {\n      const [serviceName, methodName] = parseMethodName(method);\n      if (!exposedRpcs[serviceName]) {\n        throw new Error(`Service not supported: ${serviceName}`);\n      }\n\n      return exposedRpcs[serviceName].call(methodName, request, options);\n    },\n\n    streamHandler: (method, request, options) => {\n      const [serviceName, methodName] = parseMethodName(method);\n      if (!exposedRpcs[serviceName]) {\n        throw new Error(`Service not supported: ${serviceName}`);\n      }\n\n      return exposedRpcs[serviceName].callStream(methodName, request, options);\n    },\n  });\n\n  const requestedRpcs: Client = {} as Client;\n  if (requested) {\n    for (const serviceName of Object.keys(requested) as (keyof Client)[]) {\n      // Get full service name with the package name without '.' at the beginning.\n      const serviceFqn = requested[serviceName].serviceProto.fullName.slice(1);\n\n      requestedRpcs[serviceName] = requested[serviceName].createClient(\n        {\n          call: (method, req, options) => peer.call(`${serviceFqn}.${method}`, req, options),\n          callStream: (method, req, options) => peer.callStream(`${serviceFqn}.${method}`, req, options),\n        },\n        encodingOptions,\n      );\n    }\n  }\n\n  return new ProtoRpcPeer(requestedRpcs, peer);\n};\n\nexport const parseMethodName = (method: string): [serviceName: string, methodName: string] => {\n  const separator = method.lastIndexOf('.');\n  const serviceName = method.slice(0, separator);\n  const methodName = method.slice(separator + 1);\n  if (serviceName.length === 0 || methodName.length === 0) {\n    throw new Error(`Invalid method: ${method}`);\n  }\n\n  return [serviceName, methodName];\n};\n\n//\n// TODO(burdon): Remove deprecated (only bot factory).\n//\n\n/**\n * Create a type-safe RPC client.\n * @deprecated Use createProtoRpcPeer instead.\n */\nexport const createRpcClient = <S>(\n  serviceDef: ServiceDescriptor<S>,\n  options: Omit<RpcPeerOptions, 'callHandler'>,\n): ProtoRpcPeer<S> => {\n  const peer = new RpcPeer({\n    ...options,\n    callHandler: () => {\n      throw new Error('Requests to client are not supported.');\n    },\n  });\n\n  const client = serviceDef.createClient({\n    call: peer.call.bind(peer),\n    callStream: peer.callStream.bind(peer),\n  });\n\n  return new ProtoRpcPeer(client, peer);\n};\n\n/**\n * @deprecated\n */\nexport interface RpcServerOptions<S> extends Omit<RpcPeerOptions, 'callHandler'> {\n  service: ServiceDescriptor<S>;\n  handlers: S;\n}\n\n/**\n * Create a type-safe RPC server.\n * @deprecated Use createProtoRpcPeer instead.\n */\nexport const createRpcServer = <S>({ service, handlers, ...rest }: RpcServerOptions<S>): RpcPeer => {\n  const server = service.createServer(handlers);\n  return new RpcPeer({\n    ...rest,\n    callHandler: server.call.bind(server),\n    streamHandler: server.callStream.bind(server),\n  });\n};\n\n/**\n * Create type-safe RPC client from a service bundle.\n * @deprecated Use createProtoRpcPeer instead.\n */\nexport const createBundledRpcClient = <S>(\n  descriptors: ServiceBundle<S>,\n  options: Omit<RpcPeerOptions, 'callHandler' | 'streamHandler'>,\n): ProtoRpcPeer<S> => {\n  return createProtoRpcPeer({\n    requested: descriptors,\n    ...options,\n  });\n};\n\n/**\n * @deprecated\n */\nexport interface RpcBundledServerOptions<S> extends Omit<RpcPeerOptions, 'callHandler'> {\n  services: ServiceBundle<S>;\n  handlers: S;\n}\n\n/**\n * Create type-safe RPC server from a service bundle.\n * @deprecated Use createProtoRpcPeer instead.\n */\n// TODO(burdon): Support late-binding via providers.\nexport const createBundledRpcServer = <S>({ services, handlers, ...rest }: RpcBundledServerOptions<S>): RpcPeer => {\n  const rpc: Record<string, ServiceHandler<any>> = {};\n  for (const serviceName of Object.keys(services) as (keyof S)[]) {\n    // Get full service name with the package name without '.' at the beginning.\n    const serviceFqn = services[serviceName].serviceProto.fullName.slice(1);\n    rpc[serviceFqn] = services[serviceName].createServer(handlers[serviceName] as any);\n  }\n\n  return new RpcPeer({\n    ...rest,\n\n    callHandler: (method, request) => {\n      const [serviceName, methodName] = parseMethodName(method);\n      if (!rpc[serviceName]) {\n        throw new Error(`Service not supported: ${serviceName}`);\n      }\n\n      return rpc[serviceName].call(methodName, request);\n    },\n\n    streamHandler: (method, request) => {\n      const [serviceName, methodName] = parseMethodName(method);\n      if (!rpc[serviceName]) {\n        throw new Error(`Service not supported: ${serviceName}`);\n      }\n\n      return rpc[serviceName].callStream(methodName, request);\n    },\n  });\n};\n","//\n// Copyright 2021 DXOS.org\n//\n\nimport { isNode } from '@dxos/util';\n\nimport { type RpcPort } from './rpc';\n\nexport type CreateLinkedPortsOptions = {\n  delay?: number;\n};\n\n/**\n * Create bi-directionally linked ports.\n */\nexport const createLinkedPorts = ({ delay }: CreateLinkedPortsOptions = {}): [RpcPort, RpcPort] => {\n  let port1Received: RpcPort['send'] | undefined;\n  let port2Received: RpcPort['send'] | undefined;\n\n  const send = (handler: RpcPort['send'] | undefined, msg: Uint8Array) => {\n    if (delay) {\n      setTimeout(() => handler?.(msg), delay);\n    } else {\n      void handler?.(msg);\n    }\n  };\n\n  const port1: RpcPort = {\n    send: (msg) => send(port2Received, msg),\n    subscribe: (cb) => {\n      port1Received = cb;\n    },\n  };\n\n  const port2: RpcPort = {\n    send: (msg) => send(port1Received, msg),\n    subscribe: (cb) => {\n      port2Received = cb;\n    },\n  };\n\n  return [port1, port2];\n};\n\nexport const encodeMessage = (msg: string): Uint8Array => (isNode() ? Buffer.from(msg) : new TextEncoder().encode(msg));\n","//\n// Copyright 2021 DXOS.org\n//\n\nimport { Event } from '@dxos/async';\nimport { MessageTrace } from '@dxos/protocols/proto/dxos/rpc';\n\nimport { type RpcPort } from './rpc';\n\nexport class PortTracer {\n  readonly message = new Event<MessageTrace>();\n\n  private readonly _port: RpcPort;\n\n  constructor(private readonly _wrappedPort: RpcPort) {\n    this._port = {\n      send: (msg: Uint8Array) => {\n        this.message.emit({\n          direction: MessageTrace.Direction.OUTGOING,\n          data: msg,\n        });\n\n        return this._wrappedPort.send(msg);\n      },\n      subscribe: (cb: (msg: Uint8Array) => void) => {\n        return this._wrappedPort.subscribe((msg) => {\n          this.message.emit({\n            direction: MessageTrace.Direction.INCOMING,\n            data: msg,\n          });\n          cb(msg);\n        });\n      },\n    };\n  }\n\n  public get port() {\n    return this._port;\n  }\n}\n"],"mappings":"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"}