Return data from Nested Get/Post methods


#1

Hello,

The server generating a token for every response.
So, I have a function to get token.

TokenRequest() {
    let body = "grant_type=password&username=kaan&password=123";
    let headers = new Headers();
    headers.append('Content-Type', 'application/x-www-form-urlencoded');
    headers.append('Accept', 'application/json');

    return this.http.post(this.rootURL+'token', body, { headers: headers })
        .map(res => res.json())

 }

for example; I want to sign in. First, I should generate a token key, later should check user using token key.

CheckLogin (username: string, password:string):Observable<Response> {

    this.TokenRequest().subscribe((token: any) => {

        let header = new Headers();
        header.append('Content-Type', 'application/x-www-form-urlencoded');
        header.append('Accept', 'application/json');
        header.append('Authorization', "Bearer " + token.access_token);

        let options = new RequestOptions({
            headers: header
        });

        let loading = this.loadingCtrl.create({
            content: 'Doğrulama yapılıyor...',
            spinner: 'dots'
        });
        loading.present();

          this.response = this.http.get(this.apiURL + 'user/basiclogincheck?username=' + username + '&password=' + password, options)
            .map(res => res.json());
    
            return this.response;

    }, (err) => {
        this.toastService.SendToastMessage("Token oluşturulamadı.", "top", 3)
    });

return this.response;
}

So, I have to use nested post/get methods.

but theese methods working async so it’s trying to return the second request without waiting for the answer. then it always returns null data before the answer comes.

how can i return the second request data


#2

Makes no sense. The function returns sync but the sideeffect of the function, the second subscribe, has not completed by then (http is async). An advanced version of async hell u are in

If u insist to do a return then the proper pattern is to remove all the subscribes in the functions and use rxjs operators to concat/merge the consecutive observable streams.

The subscribe should be in the consumer of the function which returns the above observable

Dunno by heart which operator to use, but that is the optimal pattern

Alternatively, if u insist in subscribing in a aubacription, then dont rely on a return in the last.subscribing in a subscription is poor programming though


#3

I believe what you’re looking for is flatMap, which in simplified terms is the Observable equivalent of a promises then.


#4

yup


#5

In addition to flatmap, you can use switchmap, which is my preference when getting past an auth gate.

getToken.switchMap(token => doSomethingWithTheToken)

To emphasize what others are saying, don’t use subscribe like that, and don’t nest http calls, You never have to nest, and it’s always wrong.