代码之家  ›  专栏  ›  技术社区  ›  hswner

RxJS和角度HttpClient:如何异步转换值?

  •  2
  • hswner  · 技术社区  · 7 年前

    我想对可观察对象发出的值应用异步转换函数。

    @Injectable
    export class ApiService{
        constructor(private http: HttpClient){}
    
        getSomething(url): Observable<any>{
            return this.http.get(url);
        }
    }
    

    在上面的代码中,我想应用一个转换函数 myFunc ,返回一个承诺,该承诺基于 this.http.get(url) .

    通常我会使用RxJS的map操作符,但由于转换函数返回承诺,我找不到处理它的方法。

    例如,我的函数是:

    function myFunc(value){
        return new Promise((resolve, reject) => {
            // modify the value async
    
            resolve(modifiedValue);
    
            // ...
        });
    }
    

    有没有合适的方法来处理这项任务?我认为以下是不合适的,对吗?

    return this.http.get(url).map(myFunc);

    任何帮助都将不胜感激。

    注: 我使用的是RxJS 5.5.2

    1 回复  |  直到 7 年前
        1
  •  3
  •   rawkfist0215    7 年前

    使用 mergeMap 运算符获取响应值,通过另一个可观察的操作异步执行一些修改,然后返回修改后的值。该操作符将合并HttpClient和修改器Observable发出的值,并返回一个发出变异值的Observable。

    编辑 :包括 Observable.fromPromise 从@bygrace的评论中获得更完整的答案。

    编辑 :对于RxJs v5.5+

    import { pipe } from 'rxjs/util/pipe';
    import { mergeMap } from 'rxjs/operators';
    
    
        @Injectable
        export class ApiService{
            constructor(private http: HttpClient){}
    
            getSomething(url): Observable<any>{
                return this.http.get(url).pipe( 
                                            mergeMap(myFunc) 
                                          );
            }
    
            private myFunc(x): Observable<any> {
                // do some asynchronous modification that returns an Observable
                return Observable.fromPromise(x);
            }
        }
    

    RxJs v5.5之前版本

    @Injectable
    export class ApiService{
        constructor(private http: HttpClient){}
    
        getSomething(url): Observable<any>{
            return this.http.get(url)
                   .mergeMap(data => {
                       // do some asynchronous modification that returns an Observable
                       return Observable.fromPromise(data);
                    });
        }
    }
    

    请参见: http://reactivex.io/rxjs/class/es6/Observable.js~Observable.html#instance-method-mergeMap