2017-02-15 102 views
1

我有一個[可能是愚蠢]的問題,但我已經搜索和搜索,仍然沒有找到答案。如何與httprequest同步執行Javascript

我創建了一個函數,將我的httprequest調用存放到我的服務器,並將POST方法的webservice URL和參數傳遞給函數。我的事件處理函數調用該網頁必須對響應做些事情。

不幸的是,調用Web調用函數之後的代碼在我有需要的值之前正在執行,這會導致巨大的錯誤。我的代碼如下所示:

function process_stuff() { 
    do_stuff; 
    var d = webcall(link, params); 
    if (d == "OK") { 
     do_stuff2; 
    } 
} 

function webcall(link, params) { 
    //httprequest...; 
    return responseText; 

} 

該d檢查,因爲它是d填充之前執行if語句失敗,所以d仍然未定義或爲空。請幫助。如何讓代碼等到d填充來自webcall的值?

編輯:

下面的代碼按你的意見:

function checker() { 
var d; // declare d here so it is global among process_logic() and give_alert()  
    function process_logic(callback) { 

    var params = "func=" + encodeURIComponent("webcalls"); 
    params += "&text=" + encodeURIComponent("yadda"); 

    var linker = "http://www.wigital.co.za/test/test.php"; 
    d = webcall(params, linker, callback); 
    alert(d + ' on line 63'); 

} 

function give_alert(d) { 

    if (d == "OK") { 
     alert("Success"); 
    } else { 
     alert("not so sure... " + d); 
    } 

} 

//process_logic(give_alert(d)); 
process_logic(give_alert()); 

} 


function webcall(a, link) { 
// a = paramaters string, link is the URL of the web service 
//alert(callback); 
var d; 
var x = new XMLHttpRequest(); 

/* What to do when server responds - define this before sending to server */ 
x.onreadystatechange = function() { 
    /* Error check */ 
    if (x.readyState === 4 && x.status !== 200) { 
     return("PROBLEM: " + x.response); 
    } 
    /* Process response */ 
    if (x.readyState === 4 && x.status === 200) { 
     //alert("I have a return value"); 
     return x.responseText; 
     //alert(x.responseText); 
     //d = x.responseText; 
    } 
}; 


/* send to server */ 
x.open("POST", link, true); 
x.setRequestHeader("Content-type", "application/x-www-form-urlencoded"); 
x.send(a); 

/* 
if (typeof callback === 'function') { 
    callback(d); 
}*/ 

} 

我想在功能give_alert變量d()來填充。它目前未定義爲give_alert()在webcall()完成之前執行並返回一個值...

+2

如果您希望我們能夠查找問題,您可能需要向我們顯示您的完整代碼而不是'// httprequest ...;'。 –

+0

這是一堆模式解決它的一個常見問題。如果沒有更多的代碼,很難提出針對您的特定問題的解決方案,但試着研究JavaScript'Promises'作爲一種可能的解決方案。 – GSP

+2

在這種情況下,程序這個詞是不正確的,你正在尋找一個同步執行。 看你是否面臨錯誤或錯誤的實現,你將不得不顯示你用來執行http請求的代碼。一般來說,你將不得不使用回調,或者最優的承諾。 參考承諾:https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise – omerkarj

回答

0

我強烈建議將回調函數傳遞到Web請求中。

function process_stuff() { 
    do_stuff; 
    webcall(link, params, callback); 
} 

function callback(data){ 
    do_stuff2; 
} 

function webcall(link, params, callback) { 
    //httprequest...; 

    //on success 
    callback(response) 

} 
0

Mozilla的文檔是clear。儘管您可以執行請求,例如:

var request = new XMLHttpRequest(); 
request.open('GET', '/bar/foo.txt', false); // `false` makes the request synchronous 
request.send(null); 

if (request.status === 200) { 
    console.log(request.responseText); 
} 

使用request.open(..., false)可以發出同步請求。如註釋所示,使用方法promise(不要阻止腳本執行)。