将 async/await 与 promise 和 appendChild 一起使用时应用停止工作
App stops working when use async/await with promise and appendChild
我正在努力更好更深入地理解 JS,以提高我的技能。因此,我编写了一个演示应用程序,它添加了 JS、CSS 并在加载 HTML-document 后创建了 DOM 元素。
我还添加了 async/await 并保证。
当我等待我的承诺得到解决时(JSFiddle 代码中的第 31 行),应用程序停止工作。
貌似有点没看懂,但具体是什么,怎么找方向,有什么需要改进的地方,我也不知道。
所以,我需要你的建议。
这里是 fiddle:
http://jsfiddle.net/k4z86nw3/9/
现在可以使用了,但是,正如我已经提到的,如果您取消注释第 31 行,
(await wait)();
它将停止工作。
正如在 https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise 上演示的那样,它需要调用 promise 中的 resolve
函数。
'use strict';
function initAnimation() {
(new WOW()).init();
}
function addCSS() {
let cssStyleSheet = document.createElement('link');
cssStyleSheet.rel = 'stylesheet';
cssStyleSheet.href = 'https://cdnjs.cloudflare.com/ajax/libs/animate.css/3.7.0/animate.min.css';
document.head.appendChild(cssStyleSheet);
}
async function addWOW() {
let wowScriptJS = document.createElement('script');
wowScriptJS.src = 'https://cdnjs.cloudflare.com/ajax/libs/wow/1.1.2/wow.min.js';
wowScriptJS.onload = initAnimation;
document.body.appendChild(wowScriptJS);
}
(async function run() {
let res = await fetch('https://dl.dropboxusercontent.com/s/i6ckrkzscn6uuhq/data.json');
addCSS();
addWOW();
let wait = new Promise((resolve, reject) => {
setTimeout(() => {
console.log('Already waited N sec.');
resolve();
}, 1000);
});
await wait; // <<< === IF YOU UNCOMMENT THIS LINE, APP WILL STOP WORKING
let jsonData = await res.json();
let sections = jsonData.sections;
function addNewChildToParentDOMElement({
childDOMElementName,
cssClasses,
innerHTML,
src,
parentDOMNode
}) {
let childDOMElement = document.createElement(childDOMElementName);
if (cssClasses) {
childDOMElement.classList.add(...cssClasses);
}
if (innerHTML) {
childDOMElement.innerHTML = innerHTML;
}
if (src) {
childDOMElement.src = src;
}
parentDOMNode.appendChild(childDOMElement);
}
for (let i = 0; i < sections.length; i++) {
console.warn('i==', i);
let newDOMItem = document.createElement('div');
addNewChildToParentDOMElement({
childDOMElementName: 'h2',
cssClasses: ['text-centered'],
innerHTML: sections[i].title,
parentDOMNode: newDOMItem
});
addNewChildToParentDOMElement({
childDOMElementName: 'p',
cssClasses: ['text-centered', 'wow', 'bounceInUp'],
innerHTML: sections[i].desc,
parentDOMNode: newDOMItem
});
let div = document.createElement('div');
div.classList.add('img-centered');
div.classList.add('wow');
div.classList.add('flipInX');
addNewChildToParentDOMElement({
childDOMElementName: 'img',
src: sections[i].imgURL,
parentDOMNode: div
});
newDOMItem.appendChild(div);
document.body.appendChild(newDOMItem);
}
})();
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>aj_test</title>
<style>
.text-centered {
text-align: center;
}
.img-centered {
text-align: center;
}
</style>
</head>
<body>
</body>
</html>
您正在等待承诺解决(在承诺执行函数中调用 resolve
)。你应该通过像函数一样调用 resolve
(或 reject
)来解决(或在出现错误时拒绝)你的承诺:
let wait = new Promise((resolve, reject) => {
setTimeout(() => {
const someFunc = () => console.log('Already waited N sec.');
resolve(someFunc);
}, 1000);
});
(await wait)(); // in this line you are waiting result of promise resolving and then calling returned someFunc
我正在努力更好更深入地理解 JS,以提高我的技能。因此,我编写了一个演示应用程序,它添加了 JS、CSS 并在加载 HTML-document 后创建了 DOM 元素。 我还添加了 async/await 并保证。 当我等待我的承诺得到解决时(JSFiddle 代码中的第 31 行),应用程序停止工作。
貌似有点没看懂,但具体是什么,怎么找方向,有什么需要改进的地方,我也不知道。 所以,我需要你的建议。
这里是 fiddle:
http://jsfiddle.net/k4z86nw3/9/
现在可以使用了,但是,正如我已经提到的,如果您取消注释第 31 行,
(await wait)();
它将停止工作。
正如在 https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise 上演示的那样,它需要调用 promise 中的 resolve
函数。
'use strict';
function initAnimation() {
(new WOW()).init();
}
function addCSS() {
let cssStyleSheet = document.createElement('link');
cssStyleSheet.rel = 'stylesheet';
cssStyleSheet.href = 'https://cdnjs.cloudflare.com/ajax/libs/animate.css/3.7.0/animate.min.css';
document.head.appendChild(cssStyleSheet);
}
async function addWOW() {
let wowScriptJS = document.createElement('script');
wowScriptJS.src = 'https://cdnjs.cloudflare.com/ajax/libs/wow/1.1.2/wow.min.js';
wowScriptJS.onload = initAnimation;
document.body.appendChild(wowScriptJS);
}
(async function run() {
let res = await fetch('https://dl.dropboxusercontent.com/s/i6ckrkzscn6uuhq/data.json');
addCSS();
addWOW();
let wait = new Promise((resolve, reject) => {
setTimeout(() => {
console.log('Already waited N sec.');
resolve();
}, 1000);
});
await wait; // <<< === IF YOU UNCOMMENT THIS LINE, APP WILL STOP WORKING
let jsonData = await res.json();
let sections = jsonData.sections;
function addNewChildToParentDOMElement({
childDOMElementName,
cssClasses,
innerHTML,
src,
parentDOMNode
}) {
let childDOMElement = document.createElement(childDOMElementName);
if (cssClasses) {
childDOMElement.classList.add(...cssClasses);
}
if (innerHTML) {
childDOMElement.innerHTML = innerHTML;
}
if (src) {
childDOMElement.src = src;
}
parentDOMNode.appendChild(childDOMElement);
}
for (let i = 0; i < sections.length; i++) {
console.warn('i==', i);
let newDOMItem = document.createElement('div');
addNewChildToParentDOMElement({
childDOMElementName: 'h2',
cssClasses: ['text-centered'],
innerHTML: sections[i].title,
parentDOMNode: newDOMItem
});
addNewChildToParentDOMElement({
childDOMElementName: 'p',
cssClasses: ['text-centered', 'wow', 'bounceInUp'],
innerHTML: sections[i].desc,
parentDOMNode: newDOMItem
});
let div = document.createElement('div');
div.classList.add('img-centered');
div.classList.add('wow');
div.classList.add('flipInX');
addNewChildToParentDOMElement({
childDOMElementName: 'img',
src: sections[i].imgURL,
parentDOMNode: div
});
newDOMItem.appendChild(div);
document.body.appendChild(newDOMItem);
}
})();
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>aj_test</title>
<style>
.text-centered {
text-align: center;
}
.img-centered {
text-align: center;
}
</style>
</head>
<body>
</body>
</html>
您正在等待承诺解决(在承诺执行函数中调用 resolve
)。你应该通过像函数一样调用 resolve
(或 reject
)来解决(或在出现错误时拒绝)你的承诺:
let wait = new Promise((resolve, reject) => {
setTimeout(() => {
const someFunc = () => console.log('Already waited N sec.');
resolve(someFunc);
}, 1000);
});
(await wait)(); // in this line you are waiting result of promise resolving and then calling returned someFunc