2009-09-22 14 views
34

Come si aggiorna la variabile returnHtml dall'interno della funzione anonima di successo?jQuery ajax successo funzione anonima scope

function getPrice(productId, storeId) { 
    var returnHtml = ''; 

    jQuery.ajax({ 
     url: "/includes/unit.jsp?" + params, 
     cache: false, 
     dataType: "html", 
     success: function(html){ 
      returnHtml = html; 
     } 
    }); 

    return returnHtml; 
} 

risposta

54

Questo è l'approccio sbagliato. Il primo A in AJAX è Asincrono. Questa funzione ritorna prima che la chiamata AJAX ritorni (o almeno possa farlo). Quindi questo non è un problema di ambito. È un problema di ordinazione. Ci sono solo due opzioni:

  1. effettuare la chiamata sincrona AJAX (non raccomandato) con l'opzione async: false; oppure
  2. Cambia il tuo modo di pensare. Invece di restituire HTML dalla funzione è necessario passare una richiamata per essere chiamata quando la chiamata AJAX ha esito positivo.

Come esempio di (2):

function findPrice(productId, storeId, callback) { 
    jQuery.ajax({ 
     url: "/includes/unit.jsp?" + params, 
     cache: false, 
     dataType: "html", 
     success: function(html) { 
      callback(productId, storeId, html); 
     } 
    }); 
} 

function receivePrice(productId, storeId, html) { 
    alert("Product " + productId + " for storeId " + storeId + " received HTML " + html); 
} 

findPrice(23, 334, receive_price); 
+1

Gotchya - ho pensato che devo farlo. ma cosa succede se dovessi farlo? –

+0

È difficile rispondere a questo senza sapere come intendevi usare il metodo getPrice(). A cosa serve? Come viene usato? È il codice a quel livello "esterno" che dovrà essere aggiustato. – cletus

+0

Ok ho capito. Non mi ero reso conto che productId e storeId sarebbero stati inclusi nel campo di applicazione e posso effettivamente passare quella roba nella chiamata. –

11

tua funzione anonima ci fa hanno accesso alla variabile returnHtml nel suo campo di applicazione, e quindi il codice non è in realtà lavorando come ci si aspettarsi. Dove probabilmente stai andando male è nella tua dichiarazione di ritorno.

ricordare che il Un in AJAX sta per asynchronous, il che significa che non avviene allo stesso tempo. Per questo motivo, la linea returnHtml = html sta effettivamente accadendo dopo il, si chiama return returnHtml;, quindi returnHtml è ancora una stringa vuota.

E 'difficile dire che cosa si dovrebbe fare per ottenere questo lavoro come si desidera senza vedere il resto del codice, ma quello che si potrebbe fare è aggiungere un altro richiamo alla funzione:

function getPrice(productId, storeId, callback) { 
    jQuery.ajax({ 
     url: "/includes/unit.jsp?" + params, 
     cache: false, 
     dataType: "html", 
     success: callback 
    }); 
} 

getPrice(5, 1, function(html) { 
    alert(html); 
}); 
13

Risposta breve, non è possibile, il primo A in AJAX sta per Asincrono, il che significa che la richiesta è ancora in corso quando si arriva alla dichiarazione di ritorno.

È può farlo con un (non asincrona) richiesta sincrona, ma è generalmente una Qualcosa Bad Thing

simile al seguente oughta restituire i dati.

function getPrice(productId, storeId) { 
    var returnHtml = ''; 

    jQuery.ajax({ 
    url: "/includes/unit.jsp?" + params, 
    async: false, 
    cache: false, 
    dataType: "html", 
    success: function(html){ 
     returnHtml = html; 
    } 
    }); 

    return returnHtml; 
} 

MA

A meno che non si ha realmente realmente bisogno di essere in grado di utilizzare il valore restituito da prova subito, sarete molto meglio il superamento di un callback in prova. Qualcosa di simile

function getPrice(productId, storeId, callback) { 
    jQuery.ajax({ 
    url: "/includes/unit.jsp?" + params, 
    async: true, 
    cache: false, 
    dataType: "html", 
    success: function(html){ 
     callback(html); 
    } 
    }); 
} 

//the you call it like 
getPrice(x,y, function(html) { 
    // do something with the html 
} 

Modifica Sheesh, voi siete più veloce di dire quello che ho detto :-)

+0

Imposta il rendering della pagina di blocco 'async: false' dal browser? –

+0

@Ramswaroop Credo di si, si –

Problemi correlati