Основная причина вашей проблемы заключается в том, что вы смешиваете понятие подписки на данные в вашем документе Firebase и извлечения данных в вашем документе Firebase (используя async / await). Вам нужно будет провести рефакторинг этого решения, используя один или другой шаблон (подписка или шаблон асинхронной выборки).
doSearchOnChanges() {
const col = await this.service.getLogbookEntries(this.searchDoc.id, doStuffAfterRetrieval)
function doStuffAfterRetrieval = entries => {
for (let i = 0; i < entries.length; i++) {
// Do something with entry
const entry = entries[0];
}
};
}
// Collection retrieval
getLogbookEntries(docId: string, doStuff: entry => void): void
// Retrieve sub collection and convert
const entries: LogbookEntry[] = [];
console.log("Retrieving logbook entries: ", docId);
const doc = this.db.doc(`${this.endpoint}/${docId}`);
doc.collection<Usage>("Usage").snapshotChanges()
.subscribe(async a => {
for (let i = 0; i < a.length; i++) {
let data = a[i].payload.doc.data();
let id = a[i].payload.doc.id;
console.log("Cleaning ID: ", id, " Data: ", data);
entries.push(this.toLogbookEntry(id, data);
}
doStuff(entries);
});
Это более или менее то, как вы бы преобразовали свой код в правильное использование подписки. Я не очень знаком с API Firebase, но при беглом поиске в Google, чтобы получать данные, а не подписываться на них, вам нужно использовать функцию .get()
в коллекциях. (Также ProTip: Никогда не используйте .hen, когда вы используете async / await. Это избыточно и приведет к ошибкам чаще, чем нет. Выберите один шаблон и придерживайтесь его.)
async doSearch() {
const col = await this.service.getLogbookEntries(this.searchDoc.id);
for (let i = 0; i < col.length; i++) {
// Do something with entry
const entry = entries[0];
}
}
// Collection retrieval
async getLogbookEntries(docId: string): Promise<LogbookEntry[]> {
// Retrieve sub collection and convert
// Don't create your own promises. Async/Await and the Firbase API will do this for you
const entries: LogbookEntry[] = [];
console.log("Retrieving logbook entries: ", docId);
const doc = this.db.doc(`${this.endpoint}/${docId}`);
const returnedData = await doc.collection<Usage>("Usage").get();
for (let i = 0; i < returnedData.length; i++) {
let data = returnedData[i].payload.doc.data();
let id = returnedData[i].payload.doc.id;
console.log("Cleaning ID: ", id, " Data: ", data);
entries.push(this.toLogbookEntry(id, data));
}
return entries;
}