Observable Continue calling API and changing parameters based on condition

对着背影说爱祢 提交于 2019-11-29 11:07:56
martin

I don't think repeat() is a good operator for this. If I understand you correctly you want to repeat the HTTP request based on the response of the previous request. Operator repeat() is good if you wanted to repeat the same request multiple times.

I'd use concatMap() and recursively call itself until the reqMode is eqaul to "done":

See live demo: http://plnkr.co/edit/w0DdepslTaKrLSB3aIkA

import {Observable, Subject} from 'rxjs';

const result = new Subject();
const closeBuffer = new Subject();
const buffer = result.buffer(closeBuffer.asObservable());

function sendHttpRequest(reqMode) {
  return Observable.of('{"reqMode":' + reqMode + '}')
    .map(response => JSON.parse(response))
    .concatMap(data => {
      console.log('HTTP Response:', data);
      // Add data to the buffer of results
      result.next(data);

      if (data.reqMode == 'done') {
        // Return an empty value wrapped as an Observable so concatMap can work
        // with it and emit onNext when it completes (which is immediately
        // thanks to the `.of()` operator).
        return Observable.of(null);
      } else {
        // Simulate that the next call returns 'done'
        return sendHttpRequest('"done"');

        // Uncomment this for real usage
        //return sendHttpRequest(data.reqMode);
      }
    });
}

// Subscribe to the buffer where I'll receive the value.
buffer.subscribe(val => console.log('Next: ', val));

// Simulate HTTP request with reqMode = 42
sendHttpRequest(42).subscribe(() => {
  console.log('done');
  // Emit values from the buffer.
  closeBuffer.next(null);
  closeBuffer.complete();
});

I use of() operator to simulate a request and to return a value wrapped as an Observable. I also use Subject to hold all responses that are buffered using buffer() operator. The I subscribe to the buffer to get the final array of responses (If you wrap this code into a function you'll most likely return the buffer where you can subscribe later).

The response is following:

HTTP Response: Object {reqMode: 42}
HTTP Response: Object {reqMode: "done"}
Next:  [Object, Object]

See similar question: Angular 2 + rxjs - how return stream of objects fetched with several subsequent http requests

So I made an example on how you can do this by using a wrapping observer and using .repeat().

All the logic is in app.component.ts

Checkout this plunker

I left comments in the code, but essentially it will make an http request, it will increment a count, and then will make another request with a different query number. It will repeat until it reaches 5.

You will have to modify it so the "repeat condition" represents your logic.

Hope that helps!

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!