繁体   English   中英

异步/等待不起作用?

[英]async / await not working?

我正在尝试编写 Foxfire 网络扩展。 我想要一个返回选项卡 URL 的函数。

Firefox 选项卡browser.tabs.get(id)返回一个承诺,该承诺解析为具有 URL 成员的选项卡对象。 browser.tabs.query返回一个解析为包含选项卡 ID 的选项卡数组的承诺。

计划将上面的两个调用包装在一个解析为 tab.url 的承诺中,使用 async/await 等待它解析并返回结果。

根据 MDN 文档:

“await 表达式导致异步函数执行暂停,直到 Promise 完成,即被解决或拒绝,并在完成后恢复异步函数的执行。恢复时,await 表达式的值是已完成的 Promise 的值。”

清单文件具有 tabs 权限。

所以我的代码如下:

browser.browserAction.onClicked.addListener(test);

async function test(){
  let res = await GetActiveTabURL();
  //console.log(`test ${res}`);
  return res;
}

async function test2(TabID){
  let res = await GetTabURL(TabID);
  //console.log(`test2 ${res}`);
  return res;
}

function GetActiveTabURL() {
  return new Promise((resolve, reject) => {
    browser.tabs.query({currentWindow: true, active: true})
      .then((tabs) => {
        browser.tabs.get(tabs.pop().id)
          .then((tab) => {
            //console.dir(tab);
            resolve(tab.url)
          })
      })
  })
}


function GetTabURL(TabID) {
  return new Promise((resolve, reject) => {
    browser.tabs.get(TabID)
      .then((tab) => {
        //console.dir(tab);
        resolve(tab.url)
      })
  })
}

如图所示,console.dir 和 console.log 语句被注释掉了。 我调试代码并使用命令行执行测试功能。 我(显然我错了)认为测试函数中的 await 应该等到承诺解决,然后让我返回值。

好的,如果我取消对 console.log 和 console.dir 语句的注释,从命令行运行测试会给出预期的(url)结果。 在控制台中,我看到 log/dir 语句的结果,当从命令行运行时,最终结果是选项卡的 URL(您可以从 test2 的 console.dir 获取 tab.id)。

如果我注释掉 console.dir 语句,我会在日志中看到一行,上面写着“Promise { : “pending” }”,紧接着是新行上的所需结果(url)。

如果我随后也注释掉 console.log 语句,我只会得到“Promise { : "pending" }” 行。 我从来没有得到想要的 URL。

如果有人想尝试这个,清单文件如下:

{

  "manifest_version": 2,
  "name": "TestGetURL",
  "description": "Functions returning the url",
  "version": "1.0",
  "icons": {
    "48": "icons/link-48.png"
  },

  "permissions": [
    "tabs",
    "contextMenus",
    "nativeMessaging",
    "<all_urls>",
    "webRequest",
    "downloads",
    "clipboardWrite",
    "webNavigation",
    "notifications",
    "storage",
    "cookies",
    "alarms"
  ],

  "background": {
    "scripts": ["background-script.js"]
  },


  "browser_action": {
    "browser_style":false,
    "default_icon": {
      "16": "icons/page-16.png",
      "32": "icons/page-32.png"
    }
  },


  "default_locale": "en"
}

在文档中发现异步函数必须返回一个承诺。 任何返回语句。 不包含承诺的 return 语句的值将被忽略,如上所示。 显然,函数中的最后一个承诺被返回。

因此,据我所知,您不能编写一个等待承诺从该承诺返回值的函数。

来自 let xx = await promise, xx 的值在 await 语句之后的同一函数中可用,并且可以在那里使用。 因此,与其调用函数以异步返回值,您必须使调用函数异步并根据需要使用一系列等待来获取所需的值,然后在函数中使用它。

试试这个,记住如果你有使用 async/await 的环境,那么支持过度使用 .then()。

browser.browserAction.onClicked.addListener(test);

async function test() {
    let res = await GetActiveTabURL();
    return res;
}

async function test2(TabID) {
    let res = await GetTabURL(TabID);
    return res;
}

async function GetActiveTabURL() {
    const tabs = await browser.tabs.query({
        currentWindow: true,
        active: true
    });

    const tab = browser.tabs.get(tabs.pop().id);

    return tab.url;
}

async function GetTabURL() {
    const tab = await browser.tabs.get(TabID);

    return tab.url;
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM