在继续下一行之前,await函数未执行。 (异步/等待无效)

时间:2020-02-01 15:56:47

标签: javascript asynchronous ecmascript-6 promise async-await

<!DOCTYPE html>
<html>
    <head>
        <title>Async/Await</title>
    </head>
    <body>
        <button id="getData">getData</button>
    <script>
        document.getElementById("getData").addEventListener("click", getAll);
        function displayData(){
            return new Promise((res, rej)=>{
                fetch("https://jsonplaceholder.typicode.com/posts").then((res)=>{
                    return res.json();
                }).then((data)=>{
                    console.log(data);
                }).catch((err)=>{
                    rej(err);
                });
                fetch("https://jsonplaceholder.typicode.com/users").then((res)=>{
                    return res.json();
                }).then((res)=>{
                    console.log(res);
                }).catch((err)=>{
                    rej(err);
                })
                res();
            });
        }

        function getmoreData(){
            fetch("https://reqres.in/api/users/2").then((res)=>{
                return res.json();
            }).then((data)=>{
                console.log(data.data);
            }).catch((err)=>{
                console.log(err);
            });
        }

        async function getAll(){
            await displayData();
            getmoreData();
        }
    </script>
    </body>
</html>

我想同时调用显示功能中的两个API,获取这些数据后,我想调用另一个位于getmoreData函数中的API。这就是为什么我使用Promise和async等待的原因,但是当我单击按钮时,首先执行getmoreData,然后获取displayData函数中这两个API的数据。我的代码有什么问题吗?如果没有,为什么我没有得到期望的结果。

2 个答案:

答案 0 :(得分:3)

问题在于您正在解决displayData响应出现之前从fetch返回的承诺。

要解决此问题,您可以跳过构建新的Promise并使用Promise.all。这是一个示例:

function displayData(){
    const call1 = fetch("https://jsonplaceholder.typicode.com/posts").then((res)=>{
        return res.json();
    }).then((data)=>{
        console.log(data);
        return data;
    });
    const call2 = fetch("https://jsonplaceholder.typicode.com/users").then((res)=>{
        return res.json();
    }).then((res)=>{
        console.log(res);
        return res;
    });
    return Promise.all([call1, call2]);
}

此外,您有一些重复的代码,可以将其重构为:

function getAndPrintData(url) {
  return fetch(url)
    .then(rsp => rsp.json())
    .then(json => {
      console.log(json);
      return json;
    });
}

const base = "https://jsonplaceholder.typicode.com/";
const urls = [`${base}posts`, `${base}users`];

function displayData() {
  return PromiseAll(urls.map(getAndPrintData));
}

答案 1 :(得分:0)

(可选)您可以将第二个函数设为在第一个解析时进行回叫:

async function getAll(){
    await displayData().then( () => getmoreData() )
}