I just launched a mobile app that uses Firebase as the data store, and I have a RTDB collection that looks like:
classes:{
"-Kv4KCJM4rHbwqF-pMxN":
{
"added" : 1515114635871,
"admins" : {
"wgKCoCZj4IaWuiwGKwygpEZ3sg02" : true
},
"allowConversations" : false,
"grade" : 998,
"name" : "Some Name",
"pageContent" : "Possibly VERY LARGE field",
"school" : "-KufLJxgD8DE2FnutPbs"
},
"-KvEpubNdVvlnSsKJ4Z9": {
"added" : 1515114635871,
"admins" : {
"wgKCoCZj4IaWuiwGKwygpEZ3sg02" : true
},
"allowConversations" : false,
"grade" : 998,
"name" : "Name",
"pageContent" : "Possibly VERY LARGE field",
"school" : "-KufLJxgD8DE2FnutPbs"
}
...
}
And I need to load this collection for the sole purpose building a list of links in a mobile app. The problem is pageContent turns out to possibly be very large, a few MB, due to base64 images being inline. Ultimately I'll be moving pageContent out into a separate collection, but I need a short term fix, because this is eating up GB of bandwidth from Firebase each day!
To build a list of links, I need the id(key), name, and grade fields only. I'm using angularfire2, so I'm doing this:
getClasses2(): Promise<any> {
let _thee = this;
return new Promise((resolve, reject) => {
if (Object.keys(_thee._classesData).length > 0) {
return resolve(_thee._classesData);
}
let classList = _thee.afDB.list(`/schools/${this.schoolid}/classes`).valueChanges();
classList.subscribe(aClass => {
console.log(aClass);
aClass.forEach((c: string, i) => {
_thee._classesData[c].id = c;
this.afDB
.object(`/classes/${c}/grade`)
.valueChanges()
.subscribe(grade => {
_thee._classesData[c].grade = grade;
});
this.afDB
.object(`/classes/${c}/name`)
.valueChanges()
.subscribe(name => {
_thee._classesData[c].name = name;
});
if (i + 1 === aClass.length) {
return resolve(_thee._classesData);
}
});
});
});
}
The issue is handling those two Observables inside a promise. Ideally, the observables just do their thing, and update the appropriate objects in _classesData totally asynchronously, and when the for loop finishes, I resolve the promise, and _classesData 'may' still be getting updated by the observables, but that's fine. The trouble is this looks like garbage, is garbage, and even though this is very short term and will be replaced in a few days, I still need to control bandwidth usage by several hundred mobile devices accessing 50-60Mb of data a few hundred times a day.
Is there an elegant way to properly access two properties in an object while staying somewhat synchronized, using AngularFire2 methods?