首页 > 解决方案 > Angular 使用 Promise 和 Promise 中的泛型

问题描述

我需要在我的应用程序中交错承诺:

  protected scroll<T>(path: string, pageSize: number, filter: string, data: T[]): Promise<T[]> {    
            let promise = new Promise<T[]>(function(resolve, reject) {
                this.httpClient
                    .get<T[]>(this.appConfigService.buildApiUrl(path), { params })
                    .toPromise<T[]>()
                    .then(result => {
                        if (result) {
                            resolve(data.concat(result));
                        }
                    })
                    .catch(function(e) {
                        reject(e);
                    });
            });

            return promise;
        }

我的问题是我收到以下消息:'无类型函数调用可能不接受类型参数'

我将如何解决这个问题?

更新:

我不应该从示例中删除 if 条件:

  if (!filter) {
            const params = new HttpParams()
                .set('searchText', '')
                .set('skip', data.length.toString())
                .set('take', pageSize.toString());

            const promise = new Promise<T[]>((resolve, reject) => {
                this.httpClient
                    .get<T>(this.appConfigService.buildApiUrl(path), { params })
                    .toPromise<any>()
                    .then(result => {
                        if (result) {
                            resolve(data.concat(result));
                        }
                        resolve(data);
                    })
                    .catch(e => reject(e));
            });

            return promise;
        }
        // also returning a promise
        return this.filter<T>(data, pageSize, filter, path);

标签: javascriptangularpromise

解决方案


那里有几个问题。

  1. 错误消息是因为您使用的是<T[]>ongettoPromise,它们不是通用函数。只需在处理程序中应用类型T即可。resultthen

  2. 你陷入了承诺创建反模式。你已经有一个承诺(来自this.httpClient),所以你不需要new Promise.

  3. 您正在为new Promise回调使用传统函数,但随后this在其中使用它,就好像它仍然引用您的类实例一样。如果要保留new Promise,则需要一个箭头功能,因此它会关闭this

相反(见***评论):

protected scroll<T>(path: string, pageSize: number, filter: string, data: T[]): Promise<T[]> {    
    // *** Return the result of calling `then` on the promise from `toPromise`
    return this.httpClient
        // *** Don't use <T[]> on `get` and `toPromise`
        .get(this.appConfigService.buildApiUrl(path), { params })
        .toPromise()
        .then((result: T) => { // *** <== Note the `T`
            // *** If it's really possible that `result` will be falsy and you don't want that
            // to be valid, you can do this:
            if (!result) {
                throw new Error("appropriate error here");
            }
            return data.concat(result);
        });
}

在操场上


更新:

我不应该从示例中删除 if 条件:

没关系,把上面的body放入ifblock中即可:

protected scroll<T>(path: string, pageSize: number, filter: string, data: T[]): Promise<T[]> {    
    if (!filter) {
        const params = new HttpParams()
           .set('searchText', '')
           .set('skip', data.length.toString())
           .set('take', pageSize.toString());

        return this.httpClient
            // *** Don't use <T[]> on `get` and `toPromise`
            .get(this.appConfigService.buildApiUrl(path), { params })
            .toPromise()
            .then((result: T) => { // *** <== Note the `T`
                // *** If it's really possible that `result` will be falsy and you don't want that
                // to be valid, you can do this:
                if (!result) {
                    throw new Error("appropriate error here");
                }
                return data.concat(result);
            });
    }
    return this.filter<T>(data, pageSize, filter, path);
}

推荐阅读