6

I wish to create a function that returns an Observable<any> but before returning another asyncronous task must complete (an Observable<string>), in order for a value to be passed to the returned Observable.

 @Injectable()
 export class MyComponent
 {

      GetAuthToken = function() : Observable<string>
      {
           return this._storageService.GetAsString('authToken');
      }

      GetData = function(authToken) : Observable<any>
      {

           let headers = new Headers();
           headers.append('authToken', authToken);
           var getUsers = this._http.get('/api/endpoint', { headers: headers })
                 .map((resonse: Response) => resonse.json()));

           return getUsers;        
      }


      DoIt = function() : Observable<any>
      {
          this.GetAuthToken ().Subsribe(t=> {
              return GetData(t); 
          })
      }          


 }

So instead of passing the authToken parameter into the GetData function, I wish to execute the GetAuthToken function within the GetData function, wait for its completion, and then still return the http observable.

Executing the DoIt function would return the subscriber, not the GetData Observable

martin
  • 76,615
  • 21
  • 156
  • 193
gunwin
  • 2,810
  • 4
  • 31
  • 50
  • 2
    Completely unrelated question: Why are you using syntax: `GetAuthToken = function() {...}` and not `GetAuthToken() {...}` like everyone else (I know these two method definitions aren't the same though)? – martin Nov 07 '16 at 15:06
  • 1
    Use `Observable.forkJoin`, check this: https://github.com/Reactive-Extensions/RxJS/blob/master/doc/api/core/operators/forkjoin.md – dlcardozo Nov 07 '16 at 15:06
  • @Martin http://stackoverflow.com/questions/336859/javascript-function-declaration-syntax-var-fn-function-vs-function-fn – gunwin Nov 07 '16 at 15:08
  • @camaron the first observable needs to finish executing before the second begins. And I need to return the Observable from the Http service, not an amalgamation – gunwin Nov 07 '16 at 15:09
  • @gunwin I understand the difference but I really doubt you need to use it. This btw makes extending your class very complicated. It's basically the same problem as described here http://stackoverflow.com/questions/40398381/overriding-methods-from-javascript-function-based-classes-in-typescript – martin Nov 07 '16 at 15:12

2 Answers2

10

Try using concatMap():

DoIt() : Observable<any>
{
    return this.GetAuthToken()
        .concatMap(token => this.GetData(token)); 
}   
gunwin
  • 2,810
  • 4
  • 31
  • 50
martin
  • 76,615
  • 21
  • 156
  • 193
0

This is also possible using flatMap

DoIt() : Observable<any>
{
    return this.GetAuthToken()
        .flatMap(token => this.GetData(token)); 
}   
gunwin
  • 2,810
  • 4
  • 31
  • 50