gpt4 book ai didi

javascript - 如何在 sapper 的 svelte 组件中运行服务器发送的事件

转载 作者:行者123 更新时间:2023-12-04 01:10:45 25 4
gpt4 key购买 nike

我有一个名为 [symbol].svelte 的精简组件,我想在其中启动与流服务的连接以接收服务器发送的事件。我还没有找到成功的方法。

由于 EventSource 只在浏览器中运行,所以我在 onMount 函数中将其初始化如下:

<script>
export let quote;

let sse = {};

onMount(async () => {
sse = new EventSource(`https://myurl.com?symbol=${quote.symbol}`);
sse.onmessage = (event) => {
let response = JSON.parse(event.data);
if(!response.length) return;
quote = response[0];
}
});

onDestroy(() => {
if(sse.readyState && sse.readyState === 1) {
sse.close();
}
})
</script>

<div>{quote.symbol}</div>

这很好用,除非我导航到使用相同组件的另一条路线 - 因为组件不会卸载和重新安装,onMount() 不会触发,因此不会实例化新的 SSE 请求。我不知道有什么方法可以轻松地强制重新安装组件,这将是最简单的(相关 github 问题 here)

另一个尝试是使用这样的响应式语句:

<script>
export let quote;

let sse = {};

$: {
if(process.browser === true) { //again, this stuff won't run on the server
if(sse.readyState && sse.readyState === 1) {
sse.close();
}
sse = new EventSource(`https://myurl.com?symbol=${quote.symbol}`);
}
}

sse.onmessage = (event) => {
let response = JSON.parse(event.data);
quote = response[0];
console.log(quote);
}
</script>

<div>{quote.symbol}</div>

当更改路由时,quote 变量发生了变化,从而触发了响应式语句来杀死现有的 SSE 并实例化一个新的。除了 onmessage 处理程序不会触发,可能是因为 onmessage 处理程序在创建事件源对象之前被附加。

最后是尝试在响应式语句中使用 onmessage 处理程序,如下所示:

<script>
export let quote;

let sse = {};

$: {
if(process.browser === true) { //again, this stuff won't run on the server
if(sse.readyState && sse.readyState === 1) {
sse.close();
}
sse = new EventSource(`https://myurl.com?symbol=${quote.symbol}`);
sse.onmessage = (event) => {
let response = JSON.parse(event.data);
quote = response[0];
console.log(quote);
}
}
}
</script>

<div>{quote.symbol}</div>

这里的问题是,由于 quote 被重新分配为 onmessage 处理程序的产品,因此响应式语句不断循环触发。

此时我不知所措,任何意见将不胜感激!

最佳答案

听起来你想使用 {#key ...},这会导致其内容在值更改时被拆除并重新创建,包括组件:

{#key quote}
<!-- destroyed and recreated whenever `quote` changes -->
<Quote {quote}/>
{/key}

这里的文档:https://svelte.dev/docs#key

顺便说一句,如果 onDestroy 仅用于清理发生在 onMount 中的工作,则无需使用它:

onMount(() => {
const sse = new EventSource(`https://myurl.com?symbol=${quote.symbol}`);
sse.onmessage = (event) => {
let response = JSON.parse(event.data);
if(!response.length) return;
quote = response[0];
}
};

return () => {
if(sse.readyState === 1) {
sse.close();
}
});
});

这样更好,因为你没有顶级的 sse 变量,并且因为返回的清理函数只需要在浏览器中,你不需要占位符 ssr = {} 赋值或检查 sse.readyState

关于javascript - 如何在 sapper 的 svelte 组件中运行服务器发送的事件,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/64921224/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com