我在下面的代码中使用派生存储。感觉像是一个奇怪的构造,因为我仅将派生构造用于动态$ session依赖关系并获取normData。但是不是$ norm。我仅使用$ norm一次即可启动派生商店。
尽管如此,它似乎工作正常。但是如果$ session更改,我必须续订。是否可以在不先取消订阅的情况下更新RxFire / RxJs订阅?
let normDocRef = null;
let normData = null;
let normSubscription = null;
const norm = derived(
session,
$session => {
normDocRef = db.doc(`uploads/${$session.a_id}_${$session.year}`);
// renew the subscription if $session changes
if (normSubscription)
normSubscription.unsubscribe();
normSubscription = doc(normDocRef).subscribe(snapshot => {
if (snapshot.exists) {
normData = snapshot.data();
} else {
normData = null;
};
});
},
);
$norm; // kick off the derived store to monitor $session
// show the data and updates
$: console.log(normData);
onDestroy(() => {
if (normSubscription) normSubscription.unsubscribe();
});
Update:我可以使用派生商店的set和return选项在真实的$ norm Svelte商店中更改$ norm。下面是我自己的答案中的代码。
但是真正的问题是:我可以更新订阅。更改订阅而不取消订阅吗?
好吧,大致了解一下您想要在此处描述的内容。
当变量/存储区更改时,您实际上可以使用reactive declaration执行代码。
在这种情况下是执行重新订阅方法:
let normDocRef = null;
let normData = null;
let normSubscription = null;
$: {
normDocRef = db.doc(`uploads/${$session.a_id}_${$session.year}`);
// renew the subscription if $session changes
if (normSubscription) {
normSubscription.unsubscribe();
normSubscription = doc(normDocRef).subscribe(snapshot => {
if (snapshot.exists) {
normData = snapshot.data();
} else {
normData = null;
};
});
}
}
onDestroy(() => {
if (normSubscription) normSubscription.unsubscribe();
});
这里的关键是,当编译此代码时,Svelte知道该块取决于$session
,因此,每当$session
更改时,它将重新执行代码块。
如果您想将其重构为另一个函数,则需要确保Svelte知道该函数取决于$session
,即:
$: resubscribe_norm($session);
[Svelte可以告诉您,如果$session
更改,则需要再次调用resubscribe_norm
。
我已经有了答案,但没有意识到。
在带有set()和return()选项的派生商店代码下面。当会话更改时,return()将自动退订。所以仍然是退订,而不是更新...但是感觉很好。不错!
let normDocRef = null;
let normSubscription = null
const norm = derived(
session,
($session, set) => {
normDocRef = db.doc(`uploads/${$session.a_id}_${$session.year}`);
normSubscription = doc(normDocRef).subscribe(snapshot => {
if (snapshot.exists) {
set(snapshot.data());
} else {
set({}); // clear
};
});
return () => {
normSubscription.unsubscribe();
};
}, {} // initial value
);
$: console.log('$norm', $norm); // Now it is a real store
onDestroy(() => {
if (normSubscription) {
normSubscription.unsubscribe();
}
});