typescript - Angular 2 - Returnera data direkt från en Observable


Jag har slagit mitt huvud mot den här hela tiden för att försöka lista ut det, och ingen mängd dokumentation jag har kunnat läsa har gett mig ett svar på min fråga.

Jag har en tjänst som kommunicerar direkt med ett API och returnerar ett observerbart event som under normala omständigheter skulle abonnera på och göra vad jag vill med datan, men i en sekundär tjänst som använder förfrågningarna från den RESTful-tjänsten behöver jag kunna returnera värden från förfrågningen.

getSomething() {
    return this._restService.addRequest('object', 'method').run()
        .subscribe(
            res => {
                res;
            },
            err => {
                console.error(err);
            }
        );
}

returnSomething() {
    return this.getSomething();
}

I det snabba exemplet ovan vill jag veta om det finns något sätt att returnera res från getSomething() inom returnSomething(). Om det inte är möjligt på detta sätt, vad är alternativet? Jag vill tillägga att _restService används mycket och jag vill egentligen inte börja ändra på det.

Svar #1

Eftersom HTTP-anrop och liknande är asynkrona får du ett Observable istället för ett synkront värde som returneras. Du måste prenumerera på det, och i callbacken därinne får du datan. Det finns inget sätt att kringgå det.

Ett alternativ skulle vara att placera din logik i subscribe-anropet

getSomething() {
    return this._restService.addRequest('object', 'method').run()
        .subscribe(
            res => {
                // do something here
                res;
            },
            err => {
                console.error(err);
            }
        );
}

Men det sätt jag gillar att göra det på är att lägga till en callback, för att injicera logiken från utsidan (kanske en komponent, kanske en annan tjänst):

getSomething(callback: (data) => void) {
    return this._restService.addRequest('object', 'method').run()
        .subscribe(
            res => {
                callback(res);
            },
            err => {
                console.error(err);
            }
        );
}

Och i din komponent eller var som helst:

this._yourService.getSomething((data) => {
    // do something here
    console.log(data);
});

Svar #2

Jag hade ett liknande problem. Min lösning var att konvertera observablen till ett löfte med .toPromise() (och använda async - await för att returnera det och fånga fel). Du kan konvertera din kod till något liknande:

 async getSomething() {
     try{
         return await this._restService.addRequest('object', 'method').run().toPromise()
      } catch (err){
       console.error(err);
	  }
  }

Relaterade artiklar