You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何编写Promise等待JavaScript中变量的值发生变化?

解决方案

你之前的写法无效的原因很明确:

  • 第一个Promise创建后立即调用resolve(AJAXvariable),此时变量还没被AJAX请求赋值,直接返回了初始的undefined或空值,后续变量变化不会影响已resolve的Promise。
  • 第二个写法里await的不是Promise对象,AJAXvariable !== ""是普通布尔表达式,await会直接返回它的结果,根本不会等待变量变化。

要实现“等变量值变化后再resolve Promise”,有两种可行思路:

思路1:直接把AJAX请求包装成Promise(推荐)

这是最合理的方式,变量变化本质是AJAX请求完成的结果,没必要绕弯监听变量,直接在请求回调里控制Promise状态。

原生AJAX的Promise封装示例:

function fetchDBData() {
  return new Promise((resolve, reject) => {
    const xhr = new XMLHttpRequest();
    xhr.open('GET', '你的数据库接口地址');
    xhr.onload = function() {
      if (xhr.status >= 200 && xhr.status < 300) {
        const AJAXvariable = JSON.parse(xhr.responseText);
        resolve(AJAXvariable);
      } else {
        reject(new Error('请求失败'));
      }
    };
    xhr.onerror = function() {
      reject(new Error('网络错误'));
    };
    xhr.send();
  });
}

// 使用方式
async function useData() {
  try {
    const data = await fetchDBData();
    // 这里直接使用获取到的数据库数据
    console.log(data);
  } catch (err) {
    console.error('获取数据失败:', err);
  }
}

useData();

如果用jQuery的$.ajax,代码可以更简洁:

function fetchDBData() {
  return $.ajax({
    url: '你的数据库接口地址',
    type: 'GET'
  });
}

// 使用方式和上面一致
async function useData() {
  try {
    const data = await fetchDBData();
    console.log(data);
  } catch (err) {
    console.error(err);
  }
}

思路2:监听变量的变化(仅当无法修改AJAX请求代码时使用)

如果受限于现有代码,不能修改AJAX请求逻辑,必须通过监听变量变化触发Promise,可以用Object.defineProperty给变量设置setter,拦截赋值操作并resolve Promise。

示例代码:

// 初始化变量
let AJAXvariable = "";
// 存储Promise的resolve函数
let resolveFn;

// 创建等待变量变化的Promise
const waitForData = new Promise((resolve) => {
  resolveFn = resolve;
});

// 给变量设置setter,赋值时触发resolve
Object.defineProperty(window, 'AJAXvariable', {
  set: function(newValue) {
    AJAXvariable = newValue;
    // 变量变为有效数据时resolve
    if (newValue !== "" && newValue !== undefined) {
      resolveFn(newValue);
    }
  },
  get: function() {
    return AJAXvariable;
  }
});

// 模拟原有AJAX请求(假设无法修改这段代码)
setTimeout(() => {
  AJAXvariable = { id: 1, name: "测试数据" };
}, 30);

// 使用方式
async function useData() {
  const data = await waitForData;
  console.log('拿到数据:', data);
}

useData();

注意:如果变量可能被多次赋值,可添加标记位避免重复resolve。

内容的提问来源于stack exchange,提问作者Mark Lamprey

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.23 21:37:16