扩展中的嵌套 XMLHttpRequests 不起作用

Nested XMLHttpRequests in extension not working

以下从数据库调用生成的 json 文件中读取数据。

function loadJSON(callback) {   
  var xobj = new XMLHttpRequest();
  xobj.overrideMimeType("application/json");
  xobj.open('GET', 'next.php', true);
  xobj.onreadystatechange = function () {
    if (xobj.readyState == 4 && xobj.status == "200") {
      callback(JSON.parse(xobj.responseText));
    }
  };
  xobj.send(null);  
}

下面使用上面的函数select随机url并在用户点击按钮时改变url。

var page = '';
var nextpageButton = document.getElementById('nextpage');
nextpageButton.addEventListener('click', function() {
  loadJSON(function(json) {
    var limit = json.length;
    var i = ((Math.floor(Math.random()*limit)+1) - 1);
    page = (json[i].sites);
    chrome.tabs.query({currentWindow: true, active: true}, function (tab) {
      chrome.tabs.update(tab.id, {url: page});
    });
  });
});

以上两个功能完美运行。

当用户单击按钮时,以下将数据添加到数据库中。只要我不在成功时添加嵌套的 XMLHttpRequest,这就可以完美地工作。

var like = document.getElementById('tu');
like.addEventListener('click', function() {
  var select_element = document.getElementById('cat');
  var cat = select_element.value;
  if (cat != 0) {
    chrome.tabs.query({active: true, lastFocusedWindow: true}, tabs => {
      var current_url = tabs[0].url;
      var current_title = tabs[0].title;
      var xhttp = new XMLHttpRequest();
      xhttp.open("POST", "add.php", true);
      xhttp.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
      xhttp.send("sites="+current_url+"&title="+current_title+"&vote_up=1&vote_down=0");
    });
  } else { 
   select_element.focus();
  }
});

当我在上面的代码中添加以下内容时,事情开始崩溃:

//this is the last row from above code before adding new code
xhttp.send("sites="+current_url+"&title="+current_title+"&vote_up=1&vote_down=0");

//this is new code
xhttp.onreadystatechange = function() {
  if(xhttp.readyState == 4 && xhttp.status == 200) {
    loadJSON(function(json) {
      var limit = json.length;
      var i = ((Math.floor(Math.random()*limit)+1) - 1);
      page = (json[i].sites);
      chrome.tabs[0].update(tab.id, {url: page});
    });
  }
}

当我添加上面的代码时,它应该只是调用第一个函数,我开始收到 javascript 错误 Cannot read property 'url' of undefined

问题是...如果 javascript 从上到下以线性方式读取,为什么 属性 会随着 loadJSON(function(json) 的添加而变得不确定?我可以删除该功能,一切都会重新开始。这不是由 XMLHttpRequest 定义的变量,那么为什么嵌套请求会阻止正确加载变量?

更重要的是我该如何解决这个问题?

您的问题是您以两种不同的方式使用 chrome.tabs.query。来自不可迭代的文档 chrom.tabs.query(queryInfo, callback) (Chrome Dev) takes as callback a function with a parameter of type Tab (Chrome Dev)

第一次用的不错:

// "tab" as *singular*
chrome.tabs.query({currentWindow: true, active: true}, function (tab) { // <-- here 
      chrome.tabs.update(tab.id, {url: page});
});

但是你第二次像数组一样使用它:

// "tabs" as *plural*?
chrome.tabs.query({active: true, lastFocusedWindow: true}, tabs => { // <-- here
      var current_url = tabs[0].url; // <-- tabs[0] is not defined!
      var current_title = tabs[0].title;
      var xhttp = new XMLHttpRequest();
      xhttp.open("POST", "add.php", true);
      xhttp.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
      xhttp.send("sites="+current_url+"&title="+current_title+"&vote_up=1&vote_down=0");
});

A Tab 对象没有属性 '0' 所以通过访问 tabs[0] 你实际上是在检索一个 undefined,这会在 url 上抛出错误属性 访问