Ionic5/Angular渲染Firebase子集合时报错仅允许数组及可迭代对象
错误原因
Error trying to diff '[object Object]'. Only arrays and iterables are allowed报错的核心是Angular的*ngFor指令仅支持遍历数组/可迭代类型,你直接将Firestore返回的querySnapshot对象赋值给了storedData,该对象不是可遍历的数组结构,因此UI渲染失败,但循环打印单条文档数据可以正常输出。
修复方案
1. 修改TS文件fetchBookings方法
需要先把querySnapshot中的所有文档数据提取出来组装成数组,再赋值给storedData,同时可优化获取userId后自动触发数据拉取的逻辑:
import { Component, OnInit } from '@angular/core'; import { AuthService } from '../services/auth.service'; import { Router } from '@angular/router'; import { AngularFirestore } from '@angular/fire/compat/firestore'; @Component({ selector: 'app-my-reservations', templateUrl: './my-reservations.page.html', styleUrls: ['./my-reservations.page.scss'], }) export class MyReservationsPage implements OnInit { user: any; userId: string; storedData: any = []; constructor( private auth: AuthService, private router: Router, private afs: AngularFirestore ) {} ngOnInit() { this.auth.user$.subscribe((user) => { this.userId = user.userId; // 拿到用户ID后自动拉取预约数据 this.fetchBookings(); }); } fetchBookings() { this.afs .collection('user') .doc(this.userId) .collection('BookingHistory') .get() .subscribe((querySnapshot) => { // 清空历史数据避免重复累加 this.storedData = []; querySnapshot.forEach((doc) => { console.log(doc.id, ' => ', doc.data()); // 将单条文档数据推入数组 this.storedData.push(doc.data()); }); }); } }
2. 优化HTML渲染逻辑
新增空状态判断,同时增加可选链操作避免字段不存在时报错:
<ng-container *ngIf="storedData.length > 0; else emptyTpl"> <ion-item *ngFor="let data of storedData"> <ion-label>{{data?.TimeSlot}}</ion-label> <ion-label>{{data?.BookedAt}}</ion-label> <ion-label>{{data?.BookingDate}}</ion-label> </ion-item> </ng-container> <!-- 无数据时的提示模板 --> <ng-template #emptyTpl> <ion-item> <ion-label class="ion-text-center">暂无预约记录</ion-label> </ion-item> </ng-template>
额外注意点
- 记得及时取消RxJS订阅避免内存泄漏,可使用takeUntil、async管道等方案处理
- 如果使用OnPush变更检测策略,赋值后可手动触发一次变更检测保证UI更新
内容的提问来源于stack exchange,提问作者Victor Nem
相关产品推荐
相关产品推荐

