nats-architecture-and-design icon indicating copy to clipboard operation
nats-architecture-and-design copied to clipboard

AckNext

Open aricart opened this issue 3 years ago • 1 comments

AckNext functionality

The server API has always supported the ability to ack and next using a single response. This functionality seems to work correctly on the server, and we are getting requests for clients to implement them.

As a short reminder, the acknext has a signature like this:

/**
   * next() combines ack() and pull(), requires the subject for a
   * subscription processing to process a message is provided
   * (can be the same) however, because the ability to specify
   * how long to keep the request open can be specified, this
   * functionality doesn't work well with iterators, as an error
   * (408s) are expected and needed to re-trigger a pull in case
   * there was a timeout. In an iterator, the error will close
   * the iterator, requiring a subscription to be reset.
   */
  next(subj: string, ro?: Partial<PullOptions>): void;

The JavaScript implementation does this:

  next(subj: string, opts: Partial<PullOptions> = { batch: 1 }) {
    const args: Partial<PullOptions> = {};
   // `batch` is defaulted to 1, can be tweaked with all the supported PullOptions.
    args.batch = opts.batch || 1;
    // `no_wait` is defaulted to false
    args.no_wait = opts.no_wait || false;
    // if an expires is provided JavaScript converts millis to nanos
    if (opts.expires && opts.expires > 0) {
      args.expires = nanos(opts.expires);
    }
    // the args are then serialized to a JSON
    const data = JSONCodec().encode(args);
    // NXT is `+NXT`
    // final payload is `+NXT {"batch": 1, "no_wait": false}`
    const payload = DataBuffer.concat(NXT, SPACE, data);
    // subj is the subject where the pull subscription is receiving messages
    // the request is sent to the reply subject of the msg getting ack'ed.
    const reqOpts = subj ? { reply: subj } as RequestOptions : undefined;
    this.msg.respond(payload, reqOpts);
  }

The behavior is documented in ADR-X.

Clients and Tools

  • [ ] Go @piotrpio
  • [ ] Java @scottf
  • [x] JavaScript @aricart
  • [ ] .Net @scottf
  • [ ] C @levb
  • [ ] Python @wallyqs
  • [ ] Ruby @wallyqs
  • [ ] Rust @Jarema

Other Tasks

  • [ ] docs.nats.io updated @jnmoyne
  • [ ] Update ADR to Implemented
  • [ ] Update client features spreadsheet

Client authors please update with your progress. If you open issues in your own repositories as a result of this request, please link them to this one by pasting the issue URL in a comment or main issue description.

aricart avatar Jul 26 '22 14:07 aricart

I think this needs to be better baked and not a client parity priority. There are other ways to make the pulls more efficient, there is concern about behavior against pulls with expiration, and the inherent inefficiency of pull size of 1 against small messages has been repeatedly been demonstrated.

scottf avatar Aug 01 '22 16:08 scottf