我使用fetch来填充一个带有html的页面,后端服务器是自托管的,使用cloudflare的dns和nginx,在node,express和ejs上运行,但是昨天突然在fetch的整个主体完成之前它开始移动。
下面是我在前端用来获取和解码html的函数
function fetchWindow(element) {
let link = element.getAttribute('data-nav-link');
let checked = element.checked;
console.log('fetchWindow');
console.log(link, checked);
//adds a loading animation
document.querySelector('.render-content').innerHTML = `<div class='loader'><div class="line-wobble"></div></div>`;
//gets inner html based on checked state
if(checked) {
//gets html from link
fetch(`./dashboard/${link}`, {
method: 'GET',
credentials: 'same-origin'
}).then((res) => {
// makes a toast if the response is not ok
if(!res.ok) {
M.toast({html: `Error ${res.status}: ${res.headers.get('err')}`, classes: `red darken-4`});
return;
}
//reads the response body
res.body.getReader().read().then((data) => {
let html = new TextDecoder("utf-8").decode(data.value);
document.querySelector('.render-content').innerHTML = html;
init();
}).catch((err) => {
console.log(err);
});
}).catch((err) => {
console.log(err);
});
}
}
我检查了端点,它正在生成并发送完整的html,浏览器也正在接收完整的html,尽管inspect的network选项卡也显示fetch在实际完成之前已经完成,并且列出的大小和真实的的身体大小相差四倍。我试过只使用setTimeout,但效果并不一致。我也试过在这两种状态下使用proxy_buffering,但没有任何意义的区别,我在另一篇文章中读到,可能是数据延迟并发送一个空的主体,导致浏览器认为提取完成。
1条答案
按热度按时间dw1jzc5e1#
.read().then()
获取下一个数据块,不一定是所有数据。参见示例here。所以,你必须设置它来读取所有的块,而不仅仅是第一个。在上面的MDN参考中示出了如何这样做的示例。
这也可以解释为什么数据的大小是关闭的(因为您只阅读了第一个块,而不是所有数据)。