gpt4 book ai didi

javascript - 在为下一个成员运行循环之前完成任务

转载 作者:行者123 更新时间:2023-11-29 10:57:31 26 4
gpt4 key购买 nike

我有一个简单而简短的网站 javascript 代码:

db.collection("classes").doc(data.readGrades).get().then(function(doc) {
if (doc.exists) {
const data = doc.data();
const members = data.members;

members.forEach(el => {

db.collection("users").doc(el).collection("grades").get().then(function(querySnapshot) {
querySnapshot.forEach(function(doc) {
const data = doc.data();

//some stuff

});
});
})

} else {
console.log("No such document!");
}
}).catch(function(error) {
console.log("Error getting document:", error);
});

如您所见,我需要运行两个 Firebase Firestore 任务。重要的是首先运行 db.collection("classes").doc(data.readGrades).get().then(function(doc) { 并且对于每个成员,此任务如下db.collection("users").doc(el).collection("grades").get().then(function(querySnapshot) {(注意:第二个任务需要第一个,因为var el)。所以我的问题是我必须等待完成第二个任务,然后才能继续下一个成员的循环。

这正是我的问题:如何在为下一个成员运行循环之前完成第二个任务?

编辑:
我像这样修改了我的 Javascript 代码:

db.collection("classes").doc(data.readGrades).get().then(function(doc) {
if (doc.exists) {
const data = doc.data();
const members = data.members;

members.reduce((chain, el) => {

table_number++;
const html = fillTemplate("grade_table" + table_number, member_name);
document.getElementById("main_padding").insertAdjacentHTML('beforeend', html);

return chain.then(() =>
db.collection("users").doc(el).collection("grades").get().then(function(querySnapshot) {
querySnapshot.forEach(function(doc) {
const data = doc.data();

addToTable("grade_table" + table_number, doc.id, data.mdl, data.klu);
});
})
)
}, Promise.resolve());
} else {
console.log("No such document!");
}
}).catch(function(error) {
console.log("Error getting document:", error);
});

function fillTemplate(table_name, id) {
console.log("ID OF TABLES " + table_name);
return `
<div class="noten_tabelle_permission" id="noten_tabelle_permission">
<h1 id="member_name">${id}</h1>
<table id="${table_name}" style="width:100%">
<tr>
<th>Fach</th>
<th>mündlich</th>
<th>Klausur</th>
</tr>
<!-- Make content with js code -->
</table>
</div>
`;
}

function addToTable(table_name, subject, mdl, klu) {

var subject_name = getSubjectByNumber(subject);
var short_subject = getSubjectShortByNumber(subject);

//Zeile erstellen

console.log("addToTable " + table_name);

var y = document.createElement([short_subject]);
y.setAttribute("id", [short_subject]);
document.getElementById([table_name]).appendChild(y);

//Spalten in einer Zeile

var y = document.createElement("TR");
y.setAttribute("id", [short_subject]);

//Spalten in einer Zeile

var cE = document.createElement("TD");
var tE = document.createTextNode([subject_name]);
cE.appendChild(tE);
y.appendChild(cE);

var a = document.createElement("TD");
var b = document.createTextNode([mdl]);
a.appendChild(b);
y.appendChild(a);

var c = document.createElement("TD");
var d = document.createTextNode([klu]);
c.appendChild(d);
y.appendChild(c);


document.getElementById(table_name).appendChild(y);
}

因此 promise 有效。但是现在我遇到了 promise 错误的问题。如您所见,我想为每个成员运行一个 Firestore(Database) 任务。所以 promise 应该解雇每个新成员。但 promise 将在最后首先解雇。

背景知识:我从数据库的 ArrayList 中获取成员,对于每个成员,我需要获取基于该成员的特定值。当加载成员的值时,我将它们添加到一个表中,该表为上一个任务中的每个成员(如您所见)填充。正如我所说, promise 将在最后解雇。 因此不会将值添加到成员的特定表中。它们将被添加到最后一个表中。

编辑 2:这是编辑后的代码:

members.reduce((chain, el) => {

db.collection("users").doc(el).collection("user_data").doc("u").get().then(function (doc) {
const data = doc.data();
var member_name = data.name;

table_number++;
const html = fillTemplate("grade_table" + table_number, member_name);
document.getElementById("main_padding").insertAdjacentHTML('beforeend', html);
})


return chain.then(((table_num) => {
return db.collection("users").doc(el).collection("grades").get().then(function (querySnapshot) {
querySnapshot.forEach(function (doc) {
const data = doc.data();

addToTable("grade_table" + table_num, doc.id, data.mdl, data.klu);

});
})
}).bind(null, table_number))
}, Promise.resolve());

所以这里的问题是我获取 member_name 的任务是异步运行的,而另一部分则不是。所以我只能在加载所有内容时运行整个任务。因为如您所见,我还需要 member_name。那么如何对其进行重新编码,使任务在仅加载所有内容(member_name/grades)时运行。

最佳答案

您可以使用 reduce 而不是 forEach 并将空的 Promise 作为初始值传递,以便按顺序处理成员:

db.collection("classes").doc(data.readGrades).get().then(function(doc) {
if (doc.exists) {
const data = doc.data();
const members = data.members;

members.reduce((chain, el) => {
return chain.then(() =>
db.collection("users").doc(el).collection("grades").get().then(function(querySnapshot) {
querySnapshot.forEach(function(doc) {
const data = doc.data();
//some stuff
});
})
)
}, Promise.resolve());
} else {
console.log("No such document!");
}
}).catch(function(error) {
console.log("Error getting document:", error);
});

更新#1:

考虑到更新后的问题,数据可能被添加到最后一个表中,因为在 promise 解决时所有减少迭代都已完成(因此 table_name 变量保留最后一个表的值迭代)。您可以通过 binding table_name 值到在 promise 解析上调用的回调来解决它:

members.reduce((chain, el) => {

table_number++;
const html = fillTemplate("grade_table" + table_number, doc.id);
document.getElementById("main_padding").insertAdjacentHTML('beforeend', html);

return chain.then(((table_num) => {
return db.collection("users").doc(el).collection("grades").get().then(function (querySnapshot) {
querySnapshot.forEach(function (doc) {
const data = doc.data();

addToTable("grade_table" + table_num, doc.id, data.mdl, data.klu);
});
})
}).bind(null, table_number))
}, Promise.resolve());

更新#2:为了在单个 reduce 迭代中随后运行多个异步操作,请尝试使用 Promise 的 then 方法将它们链接起来:

members.reduce((chain, el) => {

return chain
.then(() => db.collection("users").doc(el).collection("user_data").doc("u").get())
.then(doc => {
const data = doc.data();
var member_name = data.name;

table_number++;
const html = fillTemplate("grade_table" + table_number, member_name);
document.getElementById("main_padding").insertAdjacentHTML('beforeend', html);
return table_number;
})
.then(table_num => {
return db.collection("users").doc(el).collection("grades").get().then(function (querySnapshot) {
querySnapshot.forEach(function (doc) {
const data = doc.data();

addToTable("grade_table" + table_num, doc.id, data.mdl, data.klu);

});
})
})

}, Promise.resolve());

关于javascript - 在为下一个成员运行循环之前完成任务,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54366941/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com