2009-09-22 15 views
34

¿Cómo actualizo la variable returnHtml desde la función de éxito anónimo?jQuery ajax success función anónima 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; 
} 

Respuesta

54

Ese es el enfoque equivocado. La primera A en AJAX es asincrónica. Esa función regresa antes de que la llamada AJAX regrese (o al menos pueda). Entonces este no es un problema de alcance. Es una cuestión de ordenar. Sólo hay dos opciones:

  1. hacer que el sincrónica llamada AJAX (No recomendado) con la opción async: false; o
  2. Cambie su forma de pensar. En lugar de devolver HTML desde la función, necesita pasar una devolución de llamada para que se llame cuando la llamada AJAX tenga éxito.

Como ejemplo de (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 - pensé que tengo que hacer eso. pero ¿y si tuviera que hacerlo? –

+0

Es difícil responder eso sin saber cómo pretendía utilizar el método getPrice(). ¿Para qué se usa? ¿Cómo se usa? Es un código en ese nivel "externo" que tendrá que ajustarse. – cletus

+0

Ok, lo tengo. No me di cuenta de que productId y storeId estarían en el alcance y puedo pasar esas cosas en la devolución de llamada. –

11

Su función anónima no hace tienen acceso a la variable returnHtml en su alcance, por lo que el código no funciona realmente como desee esperar. Donde probablemente esté fallando está en su declaración de devolución.

Recuerde que el Un en AJAX representa asynchronous, lo que significa que no sucede al mismo tiempo. Por esa razón, la línea returnHtml = html está sucediendo en realidad después de llama al return returnHtml;, por lo que returnHtml sigue siendo una cadena vacía.

Es difícil decir lo que debe hacer para conseguir este trabajo como desee sin ver el resto de su código, pero lo que podría hacer es añadir otra devolución de llamada a la función:

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

Respuesta corta, no puede, la primera A en AJAX significa Asincrónico, lo que significa que la solicitud aún se está ejecutando cuando llega a la declaración de devolución.

Usted puede hacerlo con una petición síncrona (no asíncrono), pero es generalmente una mala cosa Algo

como la siguiente oughta devolver los datos.

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; 
} 

PERO

A menos que realmente realmente necesita para ser capaz de utilizar el valor de retorno de la prueba de inmediato, se le mucho mejor pasar una devolución de llamada en la prueba. Algo así como

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 
} 

Editar UH, ustedes son más rápidos que decir lo que dije :-)

+0

¿Configurará la página de bloque 'async: false' el navegador? –

+0

@Ramswaroop Creo que sí, sí –

Cuestiones relacionadas