Reown · AsyncAPI Specification

Reown / WalletConnect v2 Relay

Version 2.0

AsyncAPI description of the Reown (formerly WalletConnect) v2 Relay WebSocket protocol. The relay is a JSON-RPC over WebSocket transport that routes end-to-end encrypted messages between paired peers (typically a dApp and a wallet) on a publish/subscribe basis. Two layers of JSON-RPC traffic flow over the same WebSocket: 1. Relay RPC (`irn_*`): client <-> relay server methods to publish, subscribe, unsubscribe, and deliver messages on opaque topics. 2. Sign / Pairing protocol RPC (`wc_*`): end-to-end encrypted JSON-RPC messages exchanged between peers. The relay never sees plaintext; payloads are carried in `irn_publish.message` / `irn_subscription.data.message`. Pairing is bootstrapped by an out-of-band `wc:` URI (e.g. via QR code or deep link) containing the pairing topic, symmetric key, supported methods, relay protocol (`irn`), and optional expiry timestamp.

View Spec View on GitHub Web3WalletsWalletConnectAppKitRPCAsyncAPIWebhooksEvents

Channels

/
publish clientToRelay
Messages sent from client (dApp or wallet) to the relay.
The single WebSocket endpoint over which all relay JSON-RPC messages flow. Each direction is a stream of JSON-RPC 2.0 frames; correlation uses the standard JSON-RPC `id` field.

Messages

IrnPublishRequest
irn_publish (request)
Publish an encrypted message to a topic.
IrnPublishResponse
irn_publish (response)
IrnSubscribeRequest
irn_subscribe (request)
Subscribe to a single topic; returns a subscriptionId.
IrnSubscribeResponse
irn_subscribe (response)
IrnUnsubscribeRequest
irn_unsubscribe (request)
Unsubscribe a previous subscription on a topic.
IrnUnsubscribeResponse
irn_unsubscribe (response)
IrnBatchSubscribeRequest
irn_batchSubscribe (request)
Subscribe to many topics in one call.
IrnBatchSubscribeResponse
irn_batchSubscribe (response)
IrnBatchUnsubscribeRequest
irn_batchUnsubscribe (request)
Unsubscribe many (topic, subscriptionId) pairs at once.
IrnBatchUnsubscribeResponse
irn_batchUnsubscribe (response)
IrnSubscriptionRequest
irn_subscription (server push)
Server-initiated delivery of a published message to a subscribed client. The `data.message` payload is an encrypted envelope whose plaintext, once decrypted with the pairing/session symmetric key, is a JSON-RPC 2.0 frame using one of the `wc_*` methods below.
IrnSubscriptionResponse
irn_subscription (ack)
Client acknowledgement that the pushed message was received.

Servers

wss
production relay.walletconnect.com
Reown / WalletConnect public relay. Clients connect with a project ID issued via Reown Cloud and (for authenticated sessions) a signed JWT.

AsyncAPI Specification

Raw ↑
asyncapi: '2.6.0'
info:
  title: Reown / WalletConnect v2 Relay
  version: '2.0'
  description: |
    AsyncAPI description of the Reown (formerly WalletConnect) v2 Relay
    WebSocket protocol. The relay is a JSON-RPC over WebSocket transport
    that routes end-to-end encrypted messages between paired peers (typically
    a dApp and a wallet) on a publish/subscribe basis.

    Two layers of JSON-RPC traffic flow over the same WebSocket:

      1. Relay RPC (`irn_*`): client <-> relay server methods to publish,
         subscribe, unsubscribe, and deliver messages on opaque topics.
      2. Sign / Pairing protocol RPC (`wc_*`): end-to-end encrypted JSON-RPC
         messages exchanged between peers. The relay never sees plaintext;
         payloads are carried in `irn_publish.message` / `irn_subscription.data.message`.

    Pairing is bootstrapped by an out-of-band `wc:` URI (e.g. via QR code or
    deep link) containing the pairing topic, symmetric key, supported methods,
    relay protocol (`irn`), and optional expiry timestamp.
  contact:
    name: Reown
    url: https://reown.com/
  license:
    name: Apache-2.0
  tags:
    - name: Web3
    - name: Wallets
    - name: WalletConnect
    - name: Relay
    - name: WebSocket

defaultContentType: application/json

servers:
  production:
    url: relay.walletconnect.com
    protocol: wss
    description: |
      Reown / WalletConnect public relay. Clients connect with a project ID
      issued via Reown Cloud and (for authenticated sessions) a signed JWT.
    variables:
      projectId:
        description: Project ID from cloud.reown.com.
        default: YOUR_PROJECT_ID
    bindings:
      ws:
        query:
          type: object
          properties:
            projectId:
              type: string
              description: Reown Cloud project identifier (required).
            auth:
              type: string
              description: |
                Optional client-signed JWT (Ed25519) identifying the client.
            ua:
              type: string
              description: |
                Optional user-agent string of the form `<protocol>-<sdk>-<version>`.

channels:
  /:
    description: |
      The single WebSocket endpoint over which all relay JSON-RPC messages
      flow. Each direction is a stream of JSON-RPC 2.0 frames; correlation
      uses the standard JSON-RPC `id` field.
    publish:
      operationId: clientToRelay
      summary: Messages sent from client (dApp or wallet) to the relay.
      message:
        oneOf:
          - $ref: '#/components/messages/IrnPublishRequest'
          - $ref: '#/components/messages/IrnSubscribeRequest'
          - $ref: '#/components/messages/IrnUnsubscribeRequest'
          - $ref: '#/components/messages/IrnBatchSubscribeRequest'
          - $ref: '#/components/messages/IrnBatchUnsubscribeRequest'
          - $ref: '#/components/messages/IrnSubscriptionResponse'
    subscribe:
      operationId: relayToClient
      summary: Messages delivered from the relay to a client.
      message:
        oneOf:
          - $ref: '#/components/messages/IrnSubscriptionRequest'
          - $ref: '#/components/messages/IrnPublishResponse'
          - $ref: '#/components/messages/IrnSubscribeResponse'
          - $ref: '#/components/messages/IrnUnsubscribeResponse'
          - $ref: '#/components/messages/IrnBatchSubscribeResponse'
          - $ref: '#/components/messages/IrnBatchUnsubscribeResponse'

components:
  messages:

    IrnPublishRequest:
      name: irn_publish
      title: irn_publish (request)
      summary: Publish an encrypted message to a topic.
      payload:
        $ref: '#/components/schemas/IrnPublishRequest'

    IrnPublishResponse:
      name: irn_publish_response
      title: irn_publish (response)
      payload:
        $ref: '#/components/schemas/BooleanResponse'

    IrnSubscribeRequest:
      name: irn_subscribe
      title: irn_subscribe (request)
      summary: Subscribe to a single topic; returns a subscriptionId.
      payload:
        $ref: '#/components/schemas/IrnSubscribeRequest'

    IrnSubscribeResponse:
      name: irn_subscribe_response
      title: irn_subscribe (response)
      payload:
        $ref: '#/components/schemas/SubscriptionIdResponse'

    IrnUnsubscribeRequest:
      name: irn_unsubscribe
      title: irn_unsubscribe (request)
      summary: Unsubscribe a previous subscription on a topic.
      payload:
        $ref: '#/components/schemas/IrnUnsubscribeRequest'

    IrnUnsubscribeResponse:
      name: irn_unsubscribe_response
      title: irn_unsubscribe (response)
      payload:
        $ref: '#/components/schemas/BooleanResponse'

    IrnBatchSubscribeRequest:
      name: irn_batchSubscribe
      title: irn_batchSubscribe (request)
      summary: Subscribe to many topics in one call.
      payload:
        $ref: '#/components/schemas/IrnBatchSubscribeRequest'

    IrnBatchSubscribeResponse:
      name: irn_batchSubscribe_response
      title: irn_batchSubscribe (response)
      payload:
        $ref: '#/components/schemas/SubscriptionIdsResponse'

    IrnBatchUnsubscribeRequest:
      name: irn_batchUnsubscribe
      title: irn_batchUnsubscribe (request)
      summary: Unsubscribe many (topic, subscriptionId) pairs at once.
      payload:
        $ref: '#/components/schemas/IrnBatchUnsubscribeRequest'

    IrnBatchUnsubscribeResponse:
      name: irn_batchUnsubscribe_response
      title: irn_batchUnsubscribe (response)
      payload:
        $ref: '#/components/schemas/BooleanResponse'

    IrnSubscriptionRequest:
      name: irn_subscription
      title: irn_subscription (server push)
      summary: |
        Server-initiated delivery of a published message to a subscribed
        client. The `data.message` payload is an encrypted envelope whose
        plaintext, once decrypted with the pairing/session symmetric key, is
        a JSON-RPC 2.0 frame using one of the `wc_*` methods below.
      payload:
        $ref: '#/components/schemas/IrnSubscriptionRequest'

    IrnSubscriptionResponse:
      name: irn_subscription_response
      title: irn_subscription (ack)
      summary: Client acknowledgement that the pushed message was received.
      payload:
        $ref: '#/components/schemas/BooleanResponse'

  schemas:

    JsonRpcId:
      type: integer
      format: int64
      description: JSON-RPC 2.0 correlation id.

    JsonRpcVersion:
      type: string
      enum: ['2.0']

    IrnPublishRequest:
      type: object
      required: [id, jsonrpc, method, params]
      properties:
        id: { $ref: '#/components/schemas/JsonRpcId' }
        jsonrpc: { $ref: '#/components/schemas/JsonRpcVersion' }
        method:
          type: string
          enum: [irn_publish]
        params:
          type: object
          required: [topic, message, ttl, tag]
          properties:
            topic:
              type: string
              description: Hex-encoded topic identifier.
            message:
              type: string
              description: Encrypted envelope (UTF-8 / base64) carrying a wc_* payload.
            attestation:
              type: string
              description: Optional client attestation string.
            ttl:
              type: integer
              description: Time-to-live in seconds.
            tag:
              type: integer
              description: |
                Protocol message tag (e.g. 1100 = wc_sessionPropose request,
                1101 = wc_sessionPropose response, 1108 = wc_sessionRequest,
                etc.). Tags are defined per `wc_*` method in the Reown specs.
            prompt:
              type: boolean
              description: Whether the recipient should be prompted via push.

    IrnSubscribeRequest:
      type: object
      required: [id, jsonrpc, method, params]
      properties:
        id: { $ref: '#/components/schemas/JsonRpcId' }
        jsonrpc: { $ref: '#/components/schemas/JsonRpcVersion' }
        method:
          type: string
          enum: [irn_subscribe]
        params:
          type: object
          required: [topic]
          properties:
            topic:
              type: string

    IrnUnsubscribeRequest:
      type: object
      required: [id, jsonrpc, method, params]
      properties:
        id: { $ref: '#/components/schemas/JsonRpcId' }
        jsonrpc: { $ref: '#/components/schemas/JsonRpcVersion' }
        method:
          type: string
          enum: [irn_unsubscribe]
        params:
          type: object
          required: [topic, id]
          properties:
            topic:
              type: string
            id:
              type: string
              description: Subscription id previously returned by irn_subscribe.

    IrnBatchSubscribeRequest:
      type: object
      required: [id, jsonrpc, method, params]
      properties:
        id: { $ref: '#/components/schemas/JsonRpcId' }
        jsonrpc: { $ref: '#/components/schemas/JsonRpcVersion' }
        method:
          type: string
          enum: [irn_batchSubscribe]
        params:
          type: object
          required: [topics]
          properties:
            topics:
              type: array
              items: { type: string }

    IrnBatchUnsubscribeRequest:
      type: object
      required: [id, jsonrpc, method, params]
      properties:
        id: { $ref: '#/components/schemas/JsonRpcId' }
        jsonrpc: { $ref: '#/components/schemas/JsonRpcVersion' }
        method:
          type: string
          enum: [irn_batchUnsubscribe]
        params:
          type: object
          required: [subscriptions]
          properties:
            subscriptions:
              type: array
              items:
                type: object
                required: [topic, id]
                properties:
                  topic: { type: string }
                  id:    { type: string }

    IrnSubscriptionRequest:
      type: object
      required: [id, jsonrpc, method, params]
      properties:
        id: { $ref: '#/components/schemas/JsonRpcId' }
        jsonrpc: { $ref: '#/components/schemas/JsonRpcVersion' }
        method:
          type: string
          enum: [irn_subscription]
        params:
          type: object
          required: [id, data]
          properties:
            id:
              type: string
              description: Subscription id this message is being delivered for.
            data:
              type: object
              required: [topic, message]
              properties:
                topic:       { type: string }
                message:     { type: string, description: Encrypted wc_* envelope. }
                attestation: { type: string }
                publishedAt: { type: integer, description: Unix ms timestamp. }
                tag:         { type: integer }

    BooleanResponse:
      type: object
      required: [id, jsonrpc, result]
      properties:
        id: { $ref: '#/components/schemas/JsonRpcId' }
        jsonrpc: { $ref: '#/components/schemas/JsonRpcVersion' }
        result:
          type: boolean

    SubscriptionIdResponse:
      type: object
      required: [id, jsonrpc, result]
      properties:
        id: { $ref: '#/components/schemas/JsonRpcId' }
        jsonrpc: { $ref: '#/components/schemas/JsonRpcVersion' }
        result:
          type: string
          description: Newly issued subscription identifier.

    SubscriptionIdsResponse:
      type: object
      required: [id, jsonrpc, result]
      properties:
        id: { $ref: '#/components/schemas/JsonRpcId' }
        jsonrpc: { $ref: '#/components/schemas/JsonRpcVersion' }
        result:
          type: array
          items: { type: string }

    # --------------------------------------------------------------------
    # Inner WalletConnect protocol payloads (wc_*) carried inside the
    # encrypted `message` field of irn_publish / irn_subscription. The relay
    # itself never inspects these; they are documented here for completeness.
    # --------------------------------------------------------------------

    WcSessionPropose:
      type: object
      description: |
        wc_sessionPropose — sent by the dApp (proposer) on the pairing topic
        (Topic A) to request a session. The wallet (responder) replies with
        its public key and chosen relay; both peers then derive Topic B.
      required: [id, jsonrpc, method, params]
      properties:
        id: { $ref: '#/components/schemas/JsonRpcId' }
        jsonrpc: { $ref: '#/components/schemas/JsonRpcVersion' }
        method: { type: string, enum: [wc_sessionPropose] }
        params:
          type: object
          properties:
            relays:
              type: array
              items:
                type: object
                properties:
                  protocol: { type: string, example: irn }
                  data:     { type: string }
            proposer:
              type: object
              properties:
                publicKey: { type: string }
                metadata:  { $ref: '#/components/schemas/AppMetadata' }
            requiredNamespaces:
              type: object
              additionalProperties: { $ref: '#/components/schemas/Namespace' }
            optionalNamespaces:
              type: object
              additionalProperties: { $ref: '#/components/schemas/Namespace' }
            sessionProperties:
              type: object
              additionalProperties: { type: string }
            expiryTimestamp:
              type: integer

    WcSessionSettle:
      type: object
      description: |
        wc_sessionSettle — sent by the responder on Topic B to finalize the
        session with agreed namespaces, accounts, methods, events and expiry.
      required: [id, jsonrpc, method, params]
      properties:
        id: { $ref: '#/components/schemas/JsonRpcId' }
        jsonrpc: { $ref: '#/components/schemas/JsonRpcVersion' }
        method: { type: string, enum: [wc_sessionSettle] }
        params:
          type: object
          properties:
            relay:
              type: object
              properties:
                protocol: { type: string }
                data:     { type: string }
            controller:
              type: object
              properties:
                publicKey: { type: string }
                metadata:  { $ref: '#/components/schemas/AppMetadata' }
            namespaces:
              type: object
              additionalProperties: { $ref: '#/components/schemas/SettledNamespace' }
            sessionProperties:
              type: object
              additionalProperties: { type: string }
            expiry:
              type: integer

    WcSessionUpdate:
      type: object
      description: wc_sessionUpdate — updates the agreed namespaces of an active session.
      properties:
        method: { type: string, enum: [wc_sessionUpdate] }
        params:
          type: object
          properties:
            namespaces:
              type: object
              additionalProperties: { $ref: '#/components/schemas/SettledNamespace' }

    WcSessionExtend:
      type: object
      description: wc_sessionExtend — pushes the session expiry forward.
      properties:
        method: { type: string, enum: [wc_sessionExtend] }
        params:
          type: object
          properties:
            expiry: { type: integer }

    WcSessionRequest:
      type: object
      description: |
        wc_sessionRequest — dApp asks the wallet to execute a JSON-RPC method
        scoped to a CAIP-2 chain (e.g. eth_sendTransaction on eip155:1).
      properties:
        method: { type: string, enum: [wc_sessionRequest] }
        params:
          type: object
          properties:
            request:
              type: object
              properties:
                method: { type: string }
                params: {}
                expiryTimestamp: { type: integer }
            chainId: { type: string, description: CAIP-2 chain identifier. }

    WcSessionEvent:
      type: object
      description: wc_sessionEvent — peer-emitted event (e.g. chainChanged, accountsChanged).
      properties:
        method: { type: string, enum: [wc_sessionEvent] }
        params:
          type: object
          properties:
            event:
              type: object
              properties:
                name: { type: string }
                data: {}
            chainId: { type: string }

    WcSessionPing:
      type: object
      description: wc_sessionPing — liveness probe with a 30s timeout.
      properties:
        method: { type: string, enum: [wc_sessionPing] }
        params:
          type: object

    WcSessionDelete:
      type: object
      description: wc_sessionDelete — terminate a session.
      properties:
        method: { type: string, enum: [wc_sessionDelete] }
        params:
          type: object
          properties:
            code:    { type: integer }
            message: { type: string }

    WcSessionAuthenticate:
      type: object
      description: |
        wc_sessionAuthenticate — request a CAIP-74 (CACAO) authentication
        signature, optionally also settling a session.
      properties:
        method: { type: string, enum: [wc_sessionAuthenticate] }
        params:
          type: object
          properties:
            requester:
              type: object
              properties:
                publicKey: { type: string }
                metadata:  { $ref: '#/components/schemas/AppMetadata' }
            authPayload: { type: object }
            expiryTimestamp: { type: integer }

    WcPairingPing:
      type: object
      description: wc_pairingPing — liveness probe on the pairing topic.
      properties:
        method: { type: string, enum: [wc_pairingPing] }
        params:
          type: object

    WcPairingDelete:
      type: object
      description: wc_pairingDelete — close and delete a pairing.
      properties:
        method: { type: string, enum: [wc_pairingDelete] }
        params:
          type: object
          properties:
            code:    { type: integer }
            message: { type: string }

    AppMetadata:
      type: object
      properties:
        name:        { type: string }
        description: { type: string }
        url:         { type: string }
        icons:
          type: array
          items: { type: string }

    Namespace:
      type: object
      properties:
        chains:
          type: array
          items: { type: string, description: CAIP-2 chain id, e.g. eip155:1. }
        methods:
          type: array
          items: { type: string }
        events:
          type: array
          items: { type: string }

    SettledNamespace:
      type: object
      properties:
        accounts:
          type: array
          items: { type: string, description: CAIP-10 account id. }
        methods:
          type: array
          items: { type: string }
        events:
          type: array
          items: { type: string }
        chains:
          type: array
          items: { type: string }