如何格式化和显示从 AngularFire 返回的 Firestore 数据?
How can I format and display Firestore data returned from AngularFire?
我有一个简单的团队列表,首先我将每个团队都放在一个 firebase 文档中,当查询集合时,可以直接将它们显示在 HTML 和 *ngFor
中。非常简单的例子:
<ion-card *ngFor="let t of (team|async)" >
<ion-card-header>
<ion-card-title>name: {{t.name}} </ion-card-title>
{{t.pic}}
score = {{t.score}}
</ion-card-header>
</ion-card>
然后,我决定使用地图类型 (json object) 测试将所有团队放在一个 Firebase 文档中。但是现在 *ngFor
将不起作用。 (我明白了why的本质,但是解决不了):
这是数据库文档:
假设这是新查询:
this.teams= this._db.collection('teams').doc("allteams").valueChanges();
然后我尝试将响应设为数组:(否则 *ngFor
会显示错误)
this.team= this.teams.pipe(map((res: Response) => {return [res]}));
这样做之后,在 HTML 中我只能访问一个值,例如:
<ion-card *ngFor="let t of (team|async)" >
<ion-card-header>
<ion-card-title>name: {{t.team1.name}} </ion-card-title>
</ion-card-header>
</ion-card>
但我真的无法像以前那样展示:
<ion-card *ngFor="let t of (team|async)" >
<ion-card-header>
<ion-card-title>name: {{t.name}} </ion-card-title>
{{t.pic}}
score = {{t.score}}
</ion-card-header>
</ion-card>
我知道响应只是一个数组,但无法将其转换成有效的东西。
我也尝试过类似的东西:
this.team= this.teams.pipe(map((res: Response)=> {for(let r in res){return r}}));
但这只会 console.log: team1, team2, team3
。所有其他数据都不存在。
衷心感谢您的帮助! :)
您上次的尝试非常接近,但在这种情况下您实际上只是return输入了密钥(这是您观察到的行为)。
因为当您在文档上调用 valueChanges
时 Angular 仅触发 return 原始文档值,您可以像直接操作对象一样操作它。由于您想要 return 给定键的值,因此您只需将其从对象中拉出即可。
试试这个:
this.team = this.teams.pipe(map(res => {
return Object.keys(res).map(x => res[x]);
}));
此代码映射对象上的所有键,returns 是这些键的所有值的数组。 Angular / Ionic 模板应该能够以您期望的方式处理这个问题。
旁注:我已切换到 Object.keys
,因为 tslint 喜欢 以获得未过滤的 for x in obj
。
我也不太确定这里的 Response
是什么,所以为了清楚起见,我省略了类型——这段代码实际上并不依赖于类型。
当然,上面的代码并没有保留密钥。如果你想这样做,你可以:
this.team = this.teams.pipe(map(res => {
return Object.keys(res).map(x => {
const output = res[x];
output._key = x;
return output;
});
}));
只需确保您使用的 属性(在本例中为 _key
)不会存在于您的对象中,否则它将被覆盖:)
我有一个简单的团队列表,首先我将每个团队都放在一个 firebase 文档中,当查询集合时,可以直接将它们显示在 HTML 和 *ngFor
中。非常简单的例子:
<ion-card *ngFor="let t of (team|async)" >
<ion-card-header>
<ion-card-title>name: {{t.name}} </ion-card-title>
{{t.pic}}
score = {{t.score}}
</ion-card-header>
</ion-card>
然后,我决定使用地图类型 (json object) 测试将所有团队放在一个 Firebase 文档中。但是现在 *ngFor
将不起作用。 (我明白了why的本质,但是解决不了):
这是数据库文档:
假设这是新查询:
this.teams= this._db.collection('teams').doc("allteams").valueChanges();
然后我尝试将响应设为数组:(否则 *ngFor
会显示错误)
this.team= this.teams.pipe(map((res: Response) => {return [res]}));
这样做之后,在 HTML 中我只能访问一个值,例如:
<ion-card *ngFor="let t of (team|async)" >
<ion-card-header>
<ion-card-title>name: {{t.team1.name}} </ion-card-title>
</ion-card-header>
</ion-card>
但我真的无法像以前那样展示:
<ion-card *ngFor="let t of (team|async)" >
<ion-card-header>
<ion-card-title>name: {{t.name}} </ion-card-title>
{{t.pic}}
score = {{t.score}}
</ion-card-header>
</ion-card>
我知道响应只是一个数组,但无法将其转换成有效的东西。
我也尝试过类似的东西:
this.team= this.teams.pipe(map((res: Response)=> {for(let r in res){return r}}));
但这只会 console.log: team1, team2, team3
。所有其他数据都不存在。
衷心感谢您的帮助! :)
您上次的尝试非常接近,但在这种情况下您实际上只是return输入了密钥(这是您观察到的行为)。
因为当您在文档上调用 valueChanges
时 Angular 仅触发 return 原始文档值,您可以像直接操作对象一样操作它。由于您想要 return 给定键的值,因此您只需将其从对象中拉出即可。
试试这个:
this.team = this.teams.pipe(map(res => {
return Object.keys(res).map(x => res[x]);
}));
此代码映射对象上的所有键,returns 是这些键的所有值的数组。 Angular / Ionic 模板应该能够以您期望的方式处理这个问题。
旁注:我已切换到 Object.keys
,因为 tslint 喜欢 for x in obj
。
我也不太确定这里的 Response
是什么,所以为了清楚起见,我省略了类型——这段代码实际上并不依赖于类型。
当然,上面的代码并没有保留密钥。如果你想这样做,你可以:
this.team = this.teams.pipe(map(res => {
return Object.keys(res).map(x => {
const output = res[x];
output._key = x;
return output;
});
}));
只需确保您使用的 属性(在本例中为 _key
)不会存在于您的对象中,否则它将被覆盖:)