Skip to content

Subscribe EVENT

You can use RxNostr's use() method to subscribe EVENT messages.

The general flow of EVENT message subscription process is as follows:

  1. Create a RxNostr object by createRxNostr().
  2. Create a RxReq object by createRxForwardReq() or createRxBackwardReq().
  3. Do rxNostr.use(rxReq).subscribe(callback) to register a listener and get a Subscription object as the return value.
  4. Emit REQ messages by rxReq.emit(filter).
  5. When you are done with what you need to do, do subscription.unsubscribe() to finish the subscription.

Getting Started explains this process with concrete code for reference.

The difference between createRxForwardReq() and createRxBackwardReq() is the difference of REQ Strategy.

REQ Strategy

REQ Strategy is a read-only value that defines how RxNostr handles ReqPackets or issues EventPackets and is assigned to each RxReq object. When rxNostr.use(rxReq) is called, RxNostr reads rxReq.strategy and determines the REQ strategy according to that value.

Note

To avoid confusion between Subscription as defined in NIP-01 and Subscription in the sense of unsubscribe()-able objects returned by rxNostr.use(), we use the terms REQ subscription / Rx subscriptions in this document. In fact, the latter is strictly equivalent to Subscription in RxJS.

Forward Strategy

Forward Strategy is a strategy to listen to future events. The RxReq generated by createRxForwardReq() is based on this strategy. Under this strategy:

  • Each ReqPacket establishes REQ subscriptions that have the same subId. That is, old REQ subscriptions are overwritten, and always one or less REQ subscription is held.
  • REQ subscriptions will be CLOSE'd if any of the following occur:
    • When Rx subscription is explicitly unsubscribe()'d.
    • When CLOSE message is received for a reason other than an AUTH request.
    • When RxNostr is explicitly dispose()'d.

Note

To avoid duplicate retrieval of past events, it is recommended to adjust the since and limit of the ReqPacket to be sent out after the second time.

Backward Strategy

Backward Strategy is a strategy to listen to past events. The RxReq generated by createRxBackwardReq() is based on this strategy. Under this strategy:

  • Each ReqPacket establishes REQ subscriptions that have different subIds from each other. That is, multiple REQ subscriptions may run concurrently.
  • REQ subscriptions will be CLOSE'd if any of the following occur:
    • When an EOSE message is received.
    • When EVENT messages cannot be received for a certain period of time.
    • When Rx subscription is explicitly unsubscribe()'d.
    • When CLOSE message is received for a reason other than an AUTH request.
    • When RxNostr is explicitly dispose()'d.

WARNING

Since the Backward Strategy works assuming all REQs to return EOSE, you should adjust until etc. to avoid capturing future events.

Otherwise, REQ subscriptions may remain until the Rx subscriptions are explicitly unsubscribe().

Note

By default, it is CLOSE'd after 30 seconds of no EVENT messages being received. This time can be changed with the eoseTimeout option of createRxNostr().

over()

When issuing multiple REQs based on the Backward Strategy, it is sometimes useful to be able to wait for all of them to complete. The rxReq.over() function is only available with the Backward Strategy in such cases.

rxReq.over() tells rx-nostr that no more rxReq.emit() calls will be made on the same rxReq. After rxReq.over() is called, rxNostr.use() completes when the EOSE associated with all ReqPackets already sent out are confirmed (or immediately if all EOSE have already been confirmed). The completion process can be registered as follows:

ts
const rxReq = createRxBackwardReq();

rxNostr.use(rxReq).subscribe({
  next: (packet) => {
    console.log("Received:", packet);
  },
  complete: () => {
    console.log("Completed!");
  },
});

rxReq.emit({ ids: ["..."] });
rxReq.over();

RxJS Tips

The concept of completion here is identical to the concept of Observable's completion in RxJS. Observable based on the Forward Strategy will never be completed (unless RxNostr is dispose()).

REQ Queue

Normally, relays are capped on the number of concurrent REQ subscriptions they can have, and these limits are exposed according to NIP-11. rx-nostr automatically reads this information and queues REQ requests so as not to violate the concurrency limit.

For more information, see NIP-11 Registry.