jquery - return value using ajax result on success

I have a small problem with jQuery $.ajax() function.

I have a form where every click on the radio button or selection from the dropdown menu creates a session variable with the selected value.

Now - I have one of the dropdown menus which have 4 options - the first one (with label None) has a value="" other have their ids.

What I want to happen is to None option (with blank value) to remove the session and other to create one, but only if session with this specific select name doesn't already exist - as all other options have the same amount assigned to it - it's just indicating which one was selected.

I'm not sure if that makes sense - but have a look at the code - perhaps this will make it clearer:

$("#add_ons select").change(function() {
// get current price of the addons
var order_price_addon = $(".order_price_addon").text();
// get price of the clicked radio button from the rel attribute
var add = $(this).children('option').attr('label');
var name = $(this).attr('name');
var val = $(this).val();
        

        

if(val == "") {
var price = parseInt(order_price_addon) - parseInt(add);
removeSession(name);
} else {
if(isSession(name) == 0) {
var price = parseInt(order_price_addon) + parseInt(add);
}
setSession(name, val);
}
        

$(".order_price_addon").html(price);
setSession('order_price_addon', price);
updateTotal();
});

so - first of all when the #add_ons select menu triggers "change" we get some values from a few elements for calculations.

we get the label attribute of the option from our select which stores the value to be added to the total, name of the select to create session with this name and value to later check which one was selected.

now - we check whether the val == "" (which would indicate that None option has been selected) and we deduct the amount from the total as well as remove the session with the select's name.

After this is where the problem starts - else statement.

Else - we want to check whether the isSession() function with the name of our selector returns 0 or 1 - if it returns 0 then we add to the total the value stored in the label attribute, but if it returns 1 - that would suggest that session already exists - then we only change the value of this session by recreating it - but the amount isn't added to it.

Now isSession function looks like this:

function isSession(selector) {
$.ajax({
type: "POST",
url: '/order.html',
data: ({ issession : 1, selector: selector }),
dataType: "html",
success: function(data) {
return data;
},
error: function() {
alert('Error occured');
}
});
}

Now - the problem is - that I don't know whether using return will return the result from the function - as it doesn't seem to work - however, if I put the "data" in the success: section into the alert() - it does seem to return the right value.

Does anyone know how to return the value from the function and then compare it in the next statement?


Thanks guys - I've tried it in the following way:

function isSession(selector) {
$.ajax({
type: "POST",
url: '/order.html',
data: ({ issession : 1, selector: selector }),
dataType: "html",
success: function(data) {
updateResult(data);
},
error: function() {
alert('Error occured');
}
});
}

then the updateResult() function:

function updateResult(data) {
result = data;
}

result - is the global variable - which I'm then trying to read:

$("#add_ons select").change(function() {
// get current price of the addons
var order_price_addon = $(".order_price_addon").text();
// get price of the clicked radio button from the rel attribute
var add = $(this).children('option').attr('label');
var name = $(this).attr('name');
var val = $(this).val();
        

        

if(val == "") {
var price = parseInt(order_price_addon) - parseInt(add);
removeSession(name);
} else {
isSession(name);
if(result == 0) {
var price = parseInt(order_price_addon) + parseInt(add);
}
setSession(name, val);
}
        

$(".order_price_addon").html(price);
setSession('order_price_addon', price);
updateTotal();
});

but for some reason - it doesn't work - any idea?

604806 次浏览

The trouble is that you can not return a value from an asynchronous call, like an AJAX request, and expect it to work.

The reason is that the code waiting for the response has already executed by the time the response is received.

这个问题的解决方案是运行必要的代码 在里面 success:回调。这样,它只有在 data可用时才访问它。

function isSession(selector) {
$.ajax({
type: "POST",
url: '/order.html',
data: ({ issession : 1, selector: selector }),
dataType: "html",
success: function(data) {
// Run the code here that needs
//    to access the data returned
return data;
},
error: function() {
alert('Error occured');
}
});
}

另一种可能性(实际上是相同的)是在 success:回调中调用一个函数,该函数在数据可用时传递数据。

function isSession(selector) {
$.ajax({
type: "POST",
url: '/order.html',
data: ({ issession : 1, selector: selector }),
dataType: "html",
success: function(data) {
// Call this function on success
someFunction( data );
return data;
},
error: function() {
alert('Error occured');
}
});
}


function someFunction( data ) {
// Do something with your data
}

获得 jQuery AJAX 响应的方法有很多,我将与你们分享两种常见的方法:

第一:

使用 异步 = 虚假并在函数中返回 ajax-object,然后获取 响应 ajax-object. response seText

/**
* jQuery ajax method with async = false, to return response
* @param  {mix}  selector - your selector
* @return {mix}           - your ajax response/error
*/
function isSession(selector) {
return $.ajax({
type: "POST",
url: '/order.html',
data: {
issession: 1,
selector: selector
},
dataType: "html",
async: !1,
error: function() {
alert("Error occured")
}
});
}
// global param
var selector = !0;
// get return ajax object
var ajaxObj = isSession(selector);
// store ajax response in var
var ajaxResponse = ajaxObj.responseText;
// check ajax response
console.log(ajaxResponse);
// your ajax callback function for success
ajaxObj.success(function(response) {
alert(response);
});

第二:

use $.extend 方法,并创建一个像 ajax 的新函数

/**
* xResponse function
*
* xResponse method is made to return jQuery ajax response
*
* @param  {string} url   [your url or file]
* @param  {object} your ajax param
* @return {mix}       [ajax response]
*/
$.extend({
xResponse: function(url, data) {
// local var
var theResponse = null;
// jQuery ajax
$.ajax({
url: url,
type: 'POST',
data: data,
dataType: "html",
async: false,
success: function(respText) {
theResponse = respText;
}
});
// Return the response text
return theResponse;
}
});


// set ajax response in var
var xData = $.xResponse('temp.html', {issession: 1,selector: true});


// see response in console
console.log(xData);

你想做多大就做多大。

编辑: 这是相当古老和丑陋的,不要这样做。你应该使用回调: https://stackoverflow.com/a/5316755/591257

编辑2: 请参见 < a href = “ https://developer.mozilla.org/en-US/docs/Web/API/Fetch _ API”rel = “ nofollow norefrer”> get API

遇到了同样的问题,这样解决了,使用了一个全局变量。不知道是不是最好的,但肯定管用。如果出现错误,就会得到一个空字符串(myVar =”) ,这样就可以根据需要进行处理。

var myVar = '';
function isSession(selector) {
$.ajax({
'type': 'POST',
'url': '/order.html',
'data': {
'issession': 1,
'selector': selector
},
'dataType': 'html',
'success': function(data) {
myVar = data;
},
'error': function() {
alert('Error occured');
}
});
return myVar;
}
// Common ajax caller
function AjaxCall(url,successfunction){
var targetUrl=url;
$.ajax({
'url': targetUrl,
'type': 'GET',
'dataType': 'json',
'success': successfunction,
'error': function() {
alert("error");
}
});
}


// Calling Ajax
$(document).ready(function() {
AjaxCall("productData.txt",ajaxSuccessFunction);
});


// Function details of success function
function ajaxSuccessFunction(d){
alert(d.Pioneer.Product[0].category);
}

它可能会有帮助,创建一个通用的 ajax 调用函数,并附加一个函数,当 Ajax 调用成功时调用,参见示例

Add async: false to your attributes list. This forces the javascript thread to wait until the return value is retrieved before moving on. Obviously, you wouldn't want to do this in every circumstance, but if a value is needed before proceeding, this will do it.

Hi try async:false in your ajax call..

我在这里看到了答案,尽管很有帮助,但它们并不是我想要的,因为我不得不修改很多代码。

对我有效的方法,就是这样做:

function isSession(selector) {
//line added for the var that will have the result
var result = false;
$.ajax({
type: "POST",
url: '/order.html',
data: ({ issession : 1, selector: selector }),
dataType: "html",
//line added to get ajax response in sync
async: false,
success: function(data) {
//line added to save ajax response in var result
result = data;
},
error: function() {
alert('Error occured');
}
});
//line added to return ajax response
return result;
}

Hope helps someone

阿纳金

尽管所有关于使用 async: false的方法都不太好,因为它不适用,并且在请求返回之前一直停留在页面上。因此,这里有两种方法可以做到这一点:

1st: Return whole ajax response in a function and then make use of done function to capture the response when the request is completed.(RECOMMENDED, THE BEST WAY)

function getAjax(url, data){
return $.ajax({
type: 'POST',
url : url,
data: data,
dataType: 'JSON',
//async: true,  //NOT NEEDED
success: function(response) {
//Data = response;
}
});
}

像这样称呼上面的人:

getAjax(youUrl, yourData).done(function(response){
console.log(response);
});

使用 $.when进行多次 AJAX 调用:

$.when( getAjax(youUrl, yourData), getAjax2(yourUrl2, yourData2) ).done(function(response){
console.log(response);
});

第二步: 将响应存储在 cookie 中,然后在 ajax 调用之外获取 cookie 值。(不推荐)

        $.ajax({
type: 'POST',
url : url,
data: data,
//async: false,    // No need to use this
success: function(response) {
Cookies.set(name, response);
}
});


// Outside of the ajax call
var response = Cookies.get(name);

注意: 在上面的例子中使用了 jquery cookies库,它非常轻量级,工作起来非常快捷。这里有一个链接 < a href = “ https://github.com/js-cookie/js-cookie”rel = “ norefrer”> https://github.com/js-cookie/js-cookie

给你的帮助下

function get_result(some_value) {
var ret_val = {};
$.ajax({
url: '/some/url/to/fetch/from',
type: 'GET',
data: {'some_key': some_value},
async: false,
dataType: 'json'
}).done(function (response) {
ret_val = response;
}).fail(function (jqXHR, textStatus, errorThrown) {
ret_val = null;
});
return ret_val;
}

希望这对某些人有所帮助。

function get_rows(param) {
var rows = '';
$.ajax({
url: 'https://www.exmple.com/test.php',
type: 'POST',
data: {'key': value},
async: false,
dataType: 'html'
}).done(function (data) {
rows = data;
}).fail(function (jqXHR, textStatus, errorThrown) {
rows = '';
});
return rows;
}

我建议使用 async: false。它非常非常有帮助。