如何在提交按钮上使addEventListener连续流



我正试图使用javascript和html将json对象列表从服务器端点流式传输到前端。下面是我的代码。目前,当我点击表单按钮时,addEventListener工作得很好(下面还添加了HTML供参考(。这是我的问题:

我的服务器端点返回的对象列表是一个单独的列表,该列表不断地将对象附加到列表中。所以我希望我的前端每秒自动刷新一次,以显示最新版本。因此,我正在为我的addEventListener找到一种方法,每次在清除它正在推送的HTML后重新运行该函数。目前,我必须点击我的按钮才能实现这一点,而之前推送的HTML也没有被清除。因此,每次单击该按钮,我都会获得与单击该按钮一样多次显示的所有现有HTML(旧版本(以及我的端点数据的最新版本。

我想要实现的解决方案是能够点击一次我的启动流按钮,并在每次清除旧数据后每隔X秒运行一次该功能,只显示fetch返回的最新列表。

const startStream = document.querySelector('form')
const messageOne = document.querySelector('#message-1')
startStream.addEventListener('submit', (e) => {
e.preventDefault()
messageOne.textContent = 'Streaming...'
function fetchData() {
fetch('http://localhost:1337/dashboard')
.then(response => {
if (!response.ok) {
throw Error('ERROR')
}
response.json().then(events => {
events.forEach(event => {
const html = `<div class="event">
Event: ${event.name}
</div>
`
let div = document.createElement('div');
div.setAttribute("id", "app");
div.innerHTML = html;
document.body.appendChild(div);
})
})
.catch(error => {
console.log(error)
})
})
}
fetchData()
});
<h1>Dashboard</h1>
<form>
<button>Start Stream</button>
</form>
<p id="message-1"></p>

问题只是如何每X秒运行一个函数吗?如果是这样的话,您要查找的函数是setInterval,它与setTimeout类似,但它会不断地运行。例如:

setInterval( () => console.log("hello"), 100 )

将记录";你好";每100ms 一次

这是一个详细的例子,但尝试这种方法,它可能对您有效任何更正都会很好:

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Repeating Event example</title>
</head>
<body>
<div>
<button id="start-stream-btn">Start Streaming</button>
<p id="message-section"></p>
<div id="app-data-div"></div>
</div>
<script>
window.onload = function () {
var streamButton = document.getElementById("start-stream-btn");
var messageContainer = document.getElementById("message-section");
var appDataContainer = document.getElementById("app-data-div");
function handleFetchError(appDataContainerRef, messageContainerRef) {
messageContainerRef.innerText = "There was an Error fetching data!";
// optional clear previous data or leave it by commenting the line below
appDataContainerRef.innerHTML = "";
}
// Define the function that fetches our data
function fetchData(appDataContainerRef, messageContainerRef, timerRef) {
fetch('http://localhost:1337/dashboard')
.then(response => {
if (!response.ok) {
throw Error('ERROR')
}
response.json().then(events => {
events.forEach(event => {
// Create your string here with a loop
const htmlString = `<div class="event">
Event: ${event.name}
</div>`;
// Set your string here - replacing any previous
appDataContainerRef.innerHTML = htmlString;
})
})
.catch(error => {
console.log(error);
handleFetchError(appDataContainerRef, messageContainerRef);
// optional clear timer on error, you can comment this out if you want the timer to continue
clearInterval(timerRef);
});
}).catch(error => {
console.log(error);
handleFetchError(appDataContainerRef, messageContainerRef);
// optional clear timer on error, you can comment this out if you want the timer to continue
clearInterval(timerRef);
});
}
var timerRef;
// Attach event listener to your button
streamButton.addEventListener("click", function (e) {
e.preventDefault(); //if it is in a form or if you have any form on your current page
messageContainer.innerText = "Streaming...";
timerRef = setInterval(function () {
// check and clear your timer before adding another timer here on click
if (!!timerRef) clearInterval(timerRef);
fetchData(appDataContainer, messageContainer, timerRef);
}, 1000); // X seconds intervals i.e. for now 1s = 1000ms
});
}
</script>
</body>
</html>

最新更新