【问题标题】:Hold on callback function execution until promise is completed等待回调函数执行直到promise完成
【发布时间】:2018-01-17 10:27:16
【问题描述】:

我有一些第三方库,我正在监听它的事件。我有机会修改该库将在 UI 中附加的数据。在数据修改同步之前一切都很好。一旦我涉及 Ajax 回调/承诺,这将无法正常工作。让我举个例子来说明问题。

以下是我收听事件的方式:-

d.on('gotResults', function (data) {

  // If alter data directly it works fine.
  data.title = 'newTitle';
  // Above code alters the text correctly.

  //I want some properties to be grabbed from elsewhere so I make an Ajax call.
  $.ajax('http://someurl...', {data.id}, function (res) {
    data.someProperty = res.thatProperty;
  });
  // Above code doesn't wait for ajax call to complete, it just go away and 
  renders page without data change.


  // Yes I tried promises but doesn't help
  return fetch('http://someurl...').then(function (data) {
    data.someProperty = res.thatProperty;
    return true;
  });
  // Above code also triggers the url and gets away. Doesn't wait for then to complete.

});

我无法更改/更改第三方库。我所要做的就是监听事件并更改数据。

任何更好的解决方案。没有。我不能使用异步/等待生成器,因为我希望 ES5 浏览器支持它。

【问题讨论】:

  • 那么,您的第 3 方库需要同步响应,但您只有异步响应?那你就吃饱了。
  • 我们在谈论哪个库?是否可以不使用内置的结果转换逻辑并用您自己的处理异步的代码包装整个事情?

标签: javascript ajax promise ecmascript-5


【解决方案1】:

您不能让同步函数等待异步响应,根据定义,这根本不可能。您的选择几乎是:

  1. 坏主意:发出同步 AJAX 请求。再说一遍:坏主意。这不仅会阻止整个浏览器,而且还是一种已弃用的做法,不应该在新代码中使用,甚至永远也不应该使用。

  2. 先获取异步数据并存储在本地,以便在需要时同步使用。这显然只有在您提前知道需要哪些数据时才有效。

  3. 更改第 3 方库以添加对异步回调的支持,或请求供应商提供支持。

  4. 找到一些解决方法,您可能会先让库处理不完整的数据,然后在异步数据可用时更新它。这显然在很大程度上取决于该库的具体情况和正在完成的任务。

【讨论】:

    【解决方案2】:

    gotResults 回调函数真的需要返回 true 以外的任何内容吗?如果没有,那么你可以在这个库不知道的情况下编写常规的异步代码。让我通过重写你的伪代码来解释自己:

    d.on('gotResults', function (data) {
    
      // If alter data directly it works fine.
      data.title = 'newTitle';
      // Above code alters the text correctly.
    
      //I want some properties to be grabbed from elsewhere so I make an Ajax call.
      $.ajax('http://someurl...', {data.id}, function (res) {
        data.someProperty = res.thatProperty;
    
        // Above code doesn't wait for ajax call to complete, it just go away and 
        // EDIT: now it should render properly
        renders page without data change.
    
    
        // Yes I tried promises but doesn't help
        return fetch('http://someurl...');
        // Above code also triggers the url and gets away. Doesn't wait for then to complete.
    
    
      }).then(function (data) {
        data.someProperty = res.thatProperty;
        
        // maybe render again here?
      }).catch(function(err) { 
        handleError(err); // handle errors so the don't disappear silently
      });
      return true; // this line runs before any of the above asynchronous code but do we care?
    });

    【讨论】:

    • 这里的问题。当我有 ajax 响应时,库已经完成了渲染工作。因此,更改任何 JS 对象不会对 UI 进行任何更改。
    猜你喜欢
    • 2019-05-11
    • 2012-06-02
    • 1970-01-01
    • 1970-01-01
    • 2022-01-02
    • 2015-07-01
    • 2015-09-16
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多