开发者问题收集

Angular-在订阅推送元素到数组中

2022-11-09
1225

我正在制作 Angular 应用程序,其中我有一个空数组,如下所示:

orders: Order[];
order_details: Product[];

然后我在 ngOnInit 中进行服务调用,将数据存储到订单数组和 order_details 数组中,

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

这是 getOrders() 函数,它应该获取每个订单。 Order 对象具有 order_id、product_id 列表,其中包含所订购产品的所有产品 ID 和 order_time

getOrders() {
    this.order_service.getOrderList().subscribe({
      next: (data) => {
        this.orders = data;
        for (let order of this.orders) {
          for (let val of order.product_ids) {
            this.product_service.getProductById(val).subscribe({
              next: (data) => {this.order_details.push(data);}
            });
          }
        }
      },
    });
    console.log(this.order_details);
  }

getOrderList() 使用 api 返回所有订单

getOrderList(): Observable<Order[]> {
    return this.http_client.get<Order[]>(`${this.baseURL}`);
  }

getProductById() 使用 api 按 id 返回产品

getProductById(id: number): Observable<Product> {
    return this.http_client.get<Product>(`${this.baseURL}/${id}`);
  }

Order 对象和 Product 对象具有如下字段

export class Order{
    order_id: number;
    product_ids: number[];
    order_time: String;
}
export class Product{
    product_id: number;
    product_name: String;
    product_image: String;
    product_description: String;
    product_price: String;
}

我正在尝试使用 getOrders() 函数获取每个订单,并从每个订单中访问产品 ID 数组并通过 id 查找每个产品,然后使用 push() 用这些产品填充 order_details 数组

所以我期望 order_details 数组中的产品与订单中提到的每个订单的 product_ids 相对应数组

但是这样做会引发错误并且 order_details 数组未定义

错误 TypeError:无法读取未定义的属性(读取“推送”)

3个回答

您尚未初始化空数组。

order_details: Product[] = [];

您应该在 tsconfig.json 中启用严格模式。严格模式可在编译器阶段防止此类错误。

Jan Schab
2022-11-09
  1. 您可以编辑
this.product_service.getProductById(val).subscribe({
              next: (data) => {this.order_details.push(data);}
            });

至:

this.product_service.getProductById(val).subscribe({
              next: (dataId) => {this.order_details.push(dataId);}
            });

注意:data --> dataId

  1. 您应该在组件 order_details 中初始化:Product[] = [];
  2. 您必须检查 if(data) 然后推送
Đỗ văn Thắng
2022-11-09

实际上,我认为您在这里遇到了另一个问题,因为我假设您希望 order_details 数组与 orders 数组的顺序相同。您的实现方式无法保证一定有效。

我的建议是执行以下操作:

  1. 删除 order_details 变量并调整 Product 类,如下所示:
export class Order{
    order_id: number;
    product_ids: number[];
    order_time: String;
    details?: Product[];
}
  1. 将订单定义为可观察对象:
orders$: Observable<Order[]>;
  1. 使用 rxjs 运算符在并行 HTTP 请求中“丰富”数据(使用 forkJoin ):
this.orders$ = this.order_service
      .getOrderList()
      .pipe(
        switchMap((orders) =>
          forkJoin(
            orders.map((order) =>
              forkJoin(
                order.product_ids.map((product_id) =>
                  this.product_service.getProductById(product_id)
                )
              ).pipe(map((products) => ({ ...order, details: products })))
            )
          )
        )
      );

这将导致 order 对象的 details 属性通过来自以下数据进行“丰富” this.product_service.getProductById(product_id)

  1. 使用 async 管道监听 orders$ observable 的输出。
Fabian Strathaus
2022-11-09