如何使用 mergeMap 和 forkJoin 在 Angular 中处理多个 API 请求

2025-06-07

如何使用 mergeMap 和 forkJoin 在 Angular 中处理多个 API 请求

在本文中,我将探讨如何在 Angular 中处理多个 API 请求。在现代 Web 开发中,处理 Angular 中的多个 API 请求是一种常见的场景。为了避免诸如嵌套订阅之类的问题,实现一个高效且可维护的解决方案至关重要。在本文中,我们将探索如何使用 Angular RxJS 库中的mergeMapforkJoin运算符来正确处理多个 API 请求

首先我来解释一下这个问题。

因为我们没有使用嵌套订阅

在现实世界中,我们的 Web 应用程序中经常会进行多个 API 调用。导航到页面时,通常需要从各种 API 中检索数据。在 Angular 中,subscribe 运算符通常用于从单个 API 调用中获取数据。但是,在处理多个 API 调用时,有更有效的方法来实现这一点。我们可以先使用subscribe运算符解决这个问题,然后再利用mergeMapforkJoin进行改进

订阅()

通常情况下,这种技术非常简单。然而,当我们为call()的 Observable 发出的每个值都触发一个新的订阅时,可能会导致创建大量未处理的 Observable 和订阅。所有这些实体都会暂时保留在内存中,从而导致潜在的问题。以下是嵌套订阅的示例。

export class DevToComponent implements OnInit {
    todoValue: string = '';
    comment: any;

    constructor(private http: HttpClient) { }

    ngOnInit(): void {

        this.retrieveDefaultData();
    }

    retrieveDefaultData(): void {
        this.http.get('https://jsonplaceholder.typicode.com/posts/1')
            .pipe(map(todo => todo[0]))
            .subscribe(
                todo => {
                    this.todoValue = todo;
                    this.http.get(`https://jsonplaceholder.typicode.com/posts/${this.todoValue}/comments`)
                        .subscribe(
                            coment => {
                                this.comment = coment;
                            }
                        );
                }
            )
    }

}
Enter fullscreen mode Exit fullscreen mode

需要注意的是,当你多次subscribe()一个 Observable 时,你的订阅者不会监听同一个源。相反,每次订阅都会触发一个已定义的Observable管道的新副本。

合并映射()

该运算符接受输入可观察值,将转换函数应用于每个发出的值,并将结果可观察值合并为单个输出可观察值。通过使用MergeMap(),我们可以避免嵌套订阅,并实现更简化、更高效的处理异步请求的方法。

当我们需要从第一个 API 请求到第二个 API 请求的数据信息时,我们可以使用 MergeMap():

export class DevToComponent implements OnInit {
    todoValue: string = '';
    comment: any;
    mergeMapResult: any;
    constructor(private http: HttpClient) { }

    ngOnInit(): void {
        this.retrieveDefaultData();
    }

    retrieveDefaultData(): void {
        this.http.get('https://jsonplaceholder.typicode.com/posts/1')
            .pipe(
                map(todo => {
                    return todo
                }),
                mergeMap(todo => this.http.get(`https://jsonplaceholder.typicode.com/posts/${todo}/comments`))
            ).subscribe(response => {
                this.mergeMapResult = response;
            })
    }

}
Enter fullscreen mode Exit fullscreen mode

使用 mergeMap 可以避免嵌套订阅,从而简化异步操作。由于操作按顺序执行,而不是嵌套多个订阅回调,因此代码更加简洁易读。

ForkJoin()

此运算符,当您有多个彼此独立的并行 API 请求,并且您想等待所有请求完成后再采取进一步操作时,您可以使用forkJoin()运算符而不是嵌套订阅。

我们可以使用 ForkJoin() 调用独立的多个 API 请求:

export class DevToComponent implements OnInit {
    todoValue: string = '';
    comment: any;
    firstApiResult: any;
    secondApiResult: any;
    constructor(private http: HttpClient) { }

    ngOnInit(): void {
        this.retrieveDefaultData();
    }

    retrieveDefaultData(): void {
        const firstAPI = this.http.get('https://jsonplaceholder.typicode.com/posts/1')
        const secondAPI = this.http.get(`https://jsonplaceholder.typicode.com/posts`)

        forkJoin([firstAPI, secondAPI]) //we can use more that 2 api request 
            .subscribe(
                result => {
                    //this will return list of array of the result
                    this.firstApiResult = result[0];
                    this.secondApiResult = result[1];
                }
            )
    }

}
Enter fullscreen mode Exit fullscreen mode

使用 forkJoin() 可以简化并行 API 请求的处理,因为它提供了一种简洁高效的方法来等待所有请求完成。它消除了嵌套订阅的需要,从而提高了代码的可读性和可维护性。

注意:如果 forkJoin() 中的任何源 Observable 在完成之前发生错误,整个 Observable 都会出错,并且不会发出任何结果。因此,在使用 forkJoin() 时,妥善处理错误情况非常重要。

结论:
通过在 RxJS 中使用 mergeMap() 和 forkJoin(),您获得了一种强大的技术来处理多个 API 请求,而无需依赖嵌套订阅。这种方法不仅提高了代码的可读性和可维护性,而且还允许高效地并行执行异步操作。

感谢您阅读整个故事❤

文章来源:https://dev.to/mana95/how-to-use-mergemap-and-forkjoin-to-handle-multiple-api-requests-in-angular-412p
PREV
GitHub 个人资料 README 展示!🔥 GitHub 个人资料 README 生成器
NEXT
Angular 变化检测和 OnPush 策略