如何确保 if 循环在按顺序运行下一个 if 循环之前等待并接收结果



我有一个javascript函数,其中if循环不按顺序相互跟随。我需要他们一个接一个地运行。在第一个循环完成之前,第二个循环不应运行,因为它处理第一个循环的输出。

  1. 我使用 if 循环(循环 1(调用子 iframe 中的函数(此帧包含映射元素,我无法合理地将其与父帧组合(。这部分正在按预期工作。

  2. iframe 中的函数被触发,它调用外部服务,并等待响应。当它收到响应时,它会使用"return"函数将"error"或"ok"传递回父函数。这部分正在按预期工作。

  3. 父级接收响应,设置一个变量,然后继续执行执行其他操作的下一个 if 语句(循环 2(。

实际发生的是循环 1 运行,然后循环 2也运行,循环 2 在循环 1 之前返回结果 - 这搞砸了,因为循环 2 旨在处理循环 1 的结果。

jQuery(document).on('click', '.gv-button-delete', function (e) {
e.preventDefault();  //prevent submission
console.log('Intercepted delete button request');
var delLoc = "";
(function ($) {
var delLoc2 = $('.gv-button-delete').attr("href"); //capture default action, because we need the time-valid nonce
delLoc = delLoc2;
}(jQuery));
var objID = document.getElementById("input_4_40").value;
objID = parseInt(objID);
var iframe = document.getElementById("MapFrame1");
var result = "";
if (iframe) { //1st if loop that collects the answer
var iframeContent = (iframe.contentWindow || iframe.contentDocument);
var result = iframeContent.WriteLog(objID); //call the function from the iframe, and hopefully wait for a result. 
console.log(result);
}
if (result == "error") { //the second if loop
console.log("Step 5")
console.log("There was an error with removing the feature");
} else if (result == "ok") {
console.log("Step 5")
console.log("The spatial delete completed correctly");
} else {
console.log("Step 5")
console.log("unexpected result of spatial delete")
}
});

iframe 代码,因为它对上下文很有用。

function WriteLog(objID){
var retireFeatureID = hotspots.getFeature(objID);
var successStatus = "";
retireFeatureID.feature.properties["SystemStatus"] = "Deleted";
hotspots.updateFeature(retireFeatureID.feature, function (err, response) { //This is a syncronous call to another service
if (err) {
console.log("Step 3")
console.log(err);
successStatus = "error";
console.log("successStatus is: " + successStatus);
} else {
console.log("Step 3")
console.log(response);
successStatus = "ok";
console.log("successStatus is: " + successStatus);
}
});
console.log("Step 4")
console.log("Updated the status of feature: " + objID);
console.log("child iframe has variable successStatus as: " + successStatus);
return successStatus;
}

实际发生的是控制台结果如下所示:

步骤 4

步骤 5

步骤 3

第二个循环在第一个循环完成并返回结果之前返回。

async-await可能是您问题的答案。

这是它的工作原理。

您定义了一个函数,该函数发送具有一定延迟的响应(可能是因为网络调用或其他原因(。

async function f() {
// Make network call and return value
return value;
}

然后你用一个等待来调用这个函数。

var valueRequired = await f();
if(valueRequired == something) {
doSomeWork();
}

我希望这是清楚的。

参考: MDN

请注意,这在较旧的浏览器中不兼容,因为这是一个相当现代的JS结构。

这可能是由于回调和 javascript 事件循环通常的工作方式,步骤 4 和 5 将在步骤 3 之前首先执行。

函数响应回调将放在调用堆栈的末尾,这会导致执行剩余代码(步骤 4 开始和第二个 if 循环(,而无需等待回调完成,尽管其他服务代码是同步的。

我建议您要么将服务函数转换为具有直接返回的函数,并且如果可能的话不使用回调,要么通过添加回调参数并在获得来自其他服务的响应后调用它来将WriteLog函数更改为回调函数。

JavaScript 事件循环解释

你为什么不添加一个标志。此标志可以在console.log(result)之后直接出现。第二个 if 块可以位于不允许代码在true此标志之前继续的while内。这可以确保您的第二次if不会在第一次之前发生。

最新更新