【发布时间】:2018-07-06 09:41:27
【问题描述】:
早上好,
我在从 firebase 加载列表并使用 AngularFire2 将其渲染到我的视图时遇到问题。
解释:
我的页面中有一个功能,允许加载帖子列表,并将帖子映射到用户数据,然后将整个列表绑定到视图:
时间线.ts:
// Get the timeline data
getTimeline() {
console.log('Get timeline data');
this.loadingProvider.show();
this.createUserData(); // create user data if accoutn just created
this.dataProvider.getCurrentUser().valueChanges().subscribe((user) => {
this.user = <any>user;
});
this.getUserFriends().then((friends) => {
this.friends = friends;
}).then(() => {
this.dataProvider.getTimelinePost().valueChanges().subscribe((posts) => {
console.log("Change in timeline");
this.timelineData = posts.slice(0).reverse().map(p => {
return this.checkPostData(p);
});
this.loadingProvider.hide();
});
});
}
// Get the friend's user so we can display only the post who are relevants for the user
getUserFriends() {
return new Promise((resolve) => {
this.dataProvider.getFriends().valueChanges().subscribe((f) => {
resolve(f)
});
});
}
// Map post data with user's info such as avatar, etc
checkPostData(currentPost) {
let postedByFriend = this.checkIfPostedByFriend(currentPost);
if (postedByFriend || currentPost.postBy === firebase.auth().currentUser.uid) {
this.dataProvider.getUser(currentPost.postBy).valueChanges().subscribe((user) => {
currentPost.avatar = user.img;
currentPost.name = user.name
});
// Liked ?
this.dataProvider.getLike(currentPost.key).valueChanges().subscribe((likes) => {
currentPost.likes = likes.length;
currentPost.isLike = this.checkIfPostIsLiked(likes);
});
// Disliked ?
this.dataProvider.getdisLike(currentPost.key).valueChanges().subscribe((dislikes) => {
currentPost.dislikes = dislikes.length;
currentPost.isdisLike = this.checkIfPostIsDislike(dislikes);
});
// Commented ?
this.dataProvider.getComments(currentPost.key).valueChanges().subscribe((comments) => {
currentPost.comments = comments.length;
currentPost.isComment = this.checkIfPostIsCommented(comments);
});
}
return currentPost;
}
时间线.html:
<ion-card *ngFor="let item of timelineData">
<ion-item >
<ion-avatar item-left>
<img src="{{item.avatar}}" >
</ion-avatar>
<h2>{{item.name}}</h2>
<p>{{item.dateCreated | DateFormat}}</p>
</ion-item>
<ion-card-content>
<p>{{item.postText}}</p>
</ion-card-content>
[...]
</ion-card>
DataProvider.ts:
// Get Timeline post
getTimelinePost(){
return this.angularDb.list<any>('/timeline');
}
我的问题如下:当我将帖子添加到时间线时,需要几秒钟,因为 Timeline.ts 页面会重新加载整个列表(这是正常的,因为有使用 getTimeLinePost() 进行的订阅)。我想知道是否可以仅检测列表中的最后更改以将它们添加到视图中,从而避免重新加载所有数据。
我已经尝试过 SnapshotChanges() 和 StateChange() 但没有成功。
我注意到当我添加一个帖子时,订阅被触发了两次:
时间线变化(2)timeline.ts:89:8
Addpost.ts 代码:
pushNewPost(url) {
this.angularDb.list('timeline').push({
dateCreated: new Date().toString(),
postBy: firebase.auth().currentUser.uid,
postText: this.postText,
image: url
})
}
使用的版本: “@angular”:“5.2.11”, "angularfire2":"^5.0.0-rc.5-next",
对此有什么想法吗?我错过了什么吗?
提前致谢
更新:
我找到了一个对渲染性能影响较小的替代方案(在视图上),但在数据库上触发更改时仍会加载所有数据:
getTimeline() {
console.log('Get timeline data');
this.loadingProvider.show();
this.createUserData();
this.dataProvider.getCurrentUser().valueChanges().subscribe((user) => {
this.user = <any>user;
});
this.getUserFriends().then((friends) => {
this.friends = friends;
}).then(() => {
this.dataProvider.getTimelinePost().snapshotChanges().map(actions =>
actions.map(a => ({ type: a.type, ...a.payload.val() }))
).subscribe(items => {
this.checkPostData(items);
this.loadingProvider.hide();
});
});
}
getUserFriends() {
return new Promise((resolve) => {
this.dataProvider.getFriends().valueChanges().subscribe((f) => {
resolve(f)
});
});
}
checkPostData(currentPost) {
// Check if whe have a child added to the timeline
if (this.timelineLoaded === true) {
currentPost.forEach(p => {
if (p.type === 'child_added') {
this.mapPost(p);
}
});
} else {
this.timelineData = [];
currentPost.map(p => {
return this.mapPost(p);
});
}
}
mapPost(currentPost) {
let postedByFriend = this.checkIfPostedByFriend(currentPost);
if (postedByFriend || currentPost.postBy === firebase.auth().currentUser.uid) {
this.dataProvider.getUser(currentPost.postBy).valueChanges().subscribe((user) => {
currentPost.avatar = user.img;
currentPost.name = user.name
});
// Liked ?
this.dataProvider.getLike(currentPost.key).valueChanges().subscribe((likes) => {
currentPost.likes = likes.length;
currentPost.isLike = this.checkIfPostIsLiked(likes);
});
// Disliked ?
this.dataProvider.getdisLike(currentPost.key).valueChanges().subscribe((dislikes) => {
currentPost.dislikes = dislikes.length;
currentPost.isdisLike = this.checkIfPostIsDislike(dislikes);
});
// Commented ?
this.dataProvider.getComments(currentPost.key).valueChanges().subscribe((comments) => {
currentPost.comments = comments.length;
currentPost.isComment = this.checkIfPostIsCommented(comments);
});
this.timelineData.unshift(currentPost);
this.timelineLoaded = true
}
return currentPost;
}
【问题讨论】:
标签: angular firebase rxjs ionic3 angularfire2