【问题标题】:How to do actions when MongoDB Realm Web SDK change stream closes or times out?MongoDB Realm Web SDK 更改流关闭或超时时如何执行操作?
【发布时间】:2021-12-08 18:57:28
【问题描述】:

当用户停止观看来自 React 客户端的更改流时,我想删除集合中的所有用户插入。为此,我正在使用 Realm Web SDK。

这是我的代码的摘要以及我想要在其末尾执行的操作:

import * as Realm from "realm-web";

const realmApp: Realm.App = new Realm.App({ id: realmAppId });
const credentials = Realm.Credentials.anonymous();
const user: Realm.User = await realmApp.logIn(credentials);

const mongodb = realmApp?.currentUser?.mongoClient("mongodb-atlas");
const users = mongodb?.db("users").collection("users");

const changeStream = users.watch();

for await (const change of changeStream) {
  switch (change.operationType) {
    case "insert": {
      ...
      break;
    }
    case ...
  }
}

// This pseudo-code shows what I want to do
changeStream.on("close", () => // delete all user's inserts)

changeStream.on("timeout", () => // delete all user's inserts)

changeStream.on("user closes app thus also closing stream", () => ... )

Realm Web SDK 模式似乎与NodeJS ones 有很大不同,并且似乎不包括关闭流或在关闭时运行回调的方法。无论如何,它们不适合我的用例。

这些 MongoDB Realm Web docs 导致更多关于 Realm 的 docs。除非我错过了它,否则两组都不会讨论如何监视从 Realm Web SDK 实例化的更改流观察器的关闭和超时,以及当它发生时如何做某事。

我认为另一种方法是在 Realm 的触发器中。但从他们的docs 看来不太可能。

这甚至可以从前端客户端完成吗?有没有办法以“无服务器”的方式在 MongoDB 本身上执行此操作?

【问题讨论】:

  • 出于好奇 - 您能否分享一些有关该用例的更多细节?
  • @oblivion02 我正在收集用户的 GPS 坐标,以便向他们发送附近其他人的不重要数据。但我不需要保留任何内容,因此我想在他们关闭连接时将其删除。

标签: mongodb realm


【解决方案1】:

如果您想在更改流的(客户端)侦听器停止侦听时专门删除插入,则必须在客户端实现一些逻辑。即使在 Mongodb Realm 中,目前也无法获得此类通知。

由于应用程序/浏览器已关闭,因此可能会关闭观察者,我建议不要在您的客户端上运行删除逻辑。而是通知服务器(或调用 Mongodb Realm 函数/http 端点)进行删除。

您可以使用Beacon API 可靠地发送请求以触发删除,即使在窗口卸载时也是如此。

Client side

const inserts = [];
for await (const change of changeStream) {
  switch (change.operationType) {
    case 'insert': inserts.push(change);
  }
}
// This point is only reached if the generator returns / stream closes
navigator.sendBeacon('url/to/endpoint', JSON.stringify(inserts));

// Might also add a handler to catch users closing the app.
window.addEventListener('unload', sendBeacon);

请注意unload 事件不可靠MDN。但是有一些替代方案可能对您的用例来说已经足够好了。

realm function 中,您可以删除文档。

话虽如此,也许有更好的方法来实现您想要实现的目标。真的是更改流侦听器的超时必须触发删除或其他一些用户事件吗?

【讨论】:

  • 我认为,由于各种限制,包括 MongoDB HTTPS 端点需要标头,我无法让 Beacon API 和“卸载”事件在这种情况下工作。 sendBeacon 失败,但 curl 使用标头。所以我认为你是对的。我将不得不使用服务器。也许我会每天运行一个 cron 工作。谢谢!
  • Http 端点要求您在应用设置中的“允许的来源”下添加客户端域。是的,这是 CORS 的事情。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-01-07
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多