【问题标题】:when jquery really updates values in input fields after ajax call?当 ajax 调用后 jquery 真正更新输入字段中的值时?
【发布时间】:2014-05-26 10:11:36
【问题描述】:

我使用 jquery 通过 ajax 请求检索我用来填充输入字段的一些值。 检索这些字段后,我需要在另一个 ajax 调用中使用它们的新值,但我发现我得到了在我的 ajax 调用之前字段中的值。

$("#clickme").function(e) {
   e.preventDefault()
   retrieveValues()
   compareValues()
}

function retrieveValues {
    paramList = {}

    ..... snip .....

    $.ajax({
    url: myControllerAction,
        type: "POST",
        dataType: "json",
        data: JSON.stringify(paramList),
        contentType: "application/json; charset=utf-8",
        success: function (result) {
                $("#myFieldOne").val(result["myFieldOne"]);
                $("#myFieldOne").val(result["myFieldOne"]);
                $("#myFieldThree").val(result["myFieldThree"]);
            }
        },
        error: function () {
            alert("error");
        }
    });

function compareValues {
    paramList = {}
    paramList["myFieldOne"] = $("#myFieldOne").val();
    paramList["myFieldTwo"] = $("#myFieldTwo").val();
    paramList["myFieldThree"] = $("#myFieldThree").val();
    paramList = {}

    ..... snip ....

    $.ajax({
    url: myOtherControllerAction,
        type: "POST",
        dataType: "json",
        data: JSON.stringify(paramList),
        contentType: "application/json; charset=utf-8",
        success: function (result) {

            .....
            some Business Logic
            .....

            }
        },
        error: function () {
            alert("error");
        }
    });
}

在点击“clickme”之前我有

<input name="myFieldOne" id="myFieldOne" value="default value #1">
<input name="myFieldTwo" id="myFieldTwo" value="default value #2">
<input name="myFieldThree" id="myFieldThree" value="default value #3">

并且函数 retrieveValues 应该用新值“New Value #1”、“New Value #2”、“New Value #3”设置这三个字段。

从retrieveValues() 返回后,我调用了compareValues(),但是Jquery 对象仍然包含默认值。我似乎只有在点击事件结束后才实际更改字段值。 函数 compareValues() 在第一次点击时发送错误的数据,值比较错误,然后如果我再次点击“clickme”,则比较正确。

有什么方法可以纠正这个问题并让 jquery 即时识别我在输入字段中的新值?

弗朗切斯科

【问题讨论】:

  • Ajax 是异步的,一旦 ajax 完成,您应该调用 compareValues(),例如从 ajax 成功回调中调用它
  • ajax 调用是异步的。因此,当您运行 compareValues 时,来自 retrieveValues 的 ajax 调用尚未完成,因此您仍会在字段中看到旧值。

标签: jquery ajax input-field


【解决方案1】:

Ajax 调用默认是异步的。要在retrieveValues 之后使用compareValues 函数,您可以在成功处理程序中调用compareValues 检索或通过设置ajax 选项async:false 使retrieveValues 同步(默认为:true

示例一:使用回调函数

function retrieveValues (callback) {
    paramList = {}

    ..... snip .....

    $.ajax({
    url: myControllerAction,
        type: "POST",
        dataType: "json",
        data: JSON.stringify(paramList),
        contentType: "application/json; charset=utf-8",
        success: function (result) {
                $("#myFieldOne").val(result["myFieldOne"]);
                $("#myFieldOne").val(result["myFieldOne"]);
                $("#myFieldThree").val(result["myFieldThree"]);

                //CALL callback function.
                if(typeof callback === 'function') callback();
            }
        },
        error: function () {
            alert("error");
        }
    });

}

示例 2:将 ajax 选项 async 设置为 false

function retrieveValues () {
paramList = {}

..... snip .....

$.ajax({
url: myControllerAction,
    type: "POST",
    async:false //SET ASYNC TO FALSE
    dataType: "json",
    data: JSON.stringify(paramList),
    contentType: "application/json; charset=utf-8",
    success: function (result) {
            $("#myFieldOne").val(result["myFieldOne"]);
            $("#myFieldOne").val(result["myFieldOne"]);
            $("#myFieldThree").val(result["myFieldThree"]);
        }
    },
    error: function () {
        alert("error");
    }
});

【讨论】:

  • 我接受在成功处理程序中调用 compareValues 的解决方案。无论如何,我并不完全理解 ajax 调用的“异步性”。如果我在 Chrome 中调试整个过程,我可以看到只有在退出“点击”处理程序后才会填充字段值;所以看起来它实际上是同步的,事情只发生在最后,而不是“一旦 ajax 调用完成”......这如何解释?
【解决方案2】:

这是因为 Ajax 调用是异步的。因此,当您调用 compareValues 时,retrieveValues 尚未完成。

$("#clickme").function(e) {
   e.preventDefault();
   retrieveValues(); // just called, ajax not finished
   compareValues(); // called right after retrieveValues
}

您可以更改您的代码,以便retrieveValues 返回Promise

function retrieveValues {
    paramList = {}

    ..... snip .....
    // RETURN an Ajax Promise
    return $.ajax({
    url: myControllerAction,
        type: "POST",
        dataType: "json",
        data: JSON.stringify(paramList),
        contentType: "application/json; charset=utf-8",
        success: function (result) {
                $("#myFieldOne").val(result["myFieldOne"]);
                $("#myFieldOne").val(result["myFieldOne"]);
                $("#myFieldThree").val(result["myFieldThree"]);
            }
        },
        error: function () {
            alert("error");
        }
    });
}

现在您可以在retrieveValues 的返回值上使用.done()

retrieveValues().done(function() { compareValues(); });

【讨论】:

    【解决方案3】:

    问题是由于 ajax 调用的异步响应造成的。在其他函数获取值时,ajax 调用不会返回更新的值,因此会读取过时的值。

    解决此问题的一种方法是使调用同步:

    $.ajax({
        url: myControllerAction,
            type: "POST",
            dataType: "json",
            async:false,
             --- rest of the code ----
    

    【讨论】:

      猜你喜欢
      • 2020-03-04
      • 2016-06-20
      • 2018-07-16
      • 2017-10-09
      • 1970-01-01
      • 2014-11-24
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多