【发布时间】:2020-05-09 01:42:56
【问题描述】:
我有许多不同的猫鼬模式通过 id 字符串相互引用。
我正在使用 redis 来缓存 mongoose 文档。
例如,getUser(id) 将返回一个先前缓存的用户对象(如果存在),否则它会调用 mongoose find。
使用 mongoose 引用并使用填充会感觉更美观。
但是,据我了解,它只是 find 的语法糖,没有任何缓存层。
主要问题
什么时候应该使用 mongoose 填充而不是缓存层,在使用 mongoose 的稳定高流量应用程序中的最佳实践是什么?
指导子问题
- 猫鼬填充真的适合高流量应用吗?
- 使用填充而不是缓存文档有什么好处 我自己?
- 自己缓存模型(例如使用 redis)在性能方面是否可以忽略不计?
- 最佳做法是什么?使用什么大型应用程序公司 猫鼬呢?
- 你会混合填充猫鼬引用和缓存层吗 取决于不同的用例,或者你会选择一个并成为 符合吗?
示例用例
这是我的应用程序中的一个常见的简单示例。
我有 3 个集合:用户、应用程序、研究所。
- 用户有一个 App 的引用
- 应用有一个对 Institute 的引用
现在我是:
- 从缓存层获取用户,其中包含一个 app_id
- 从缓存层获取应用,其中包含 Institute_id
- 从缓存层获取机构
给定一个用户,从缓存层获取应用程序和机构实际上是 O(1)。
但是,如果我选择进行纯猫鼬填充,则需要对数据库进行 2 次额外的查找调用 - 用于应用程序,然后用于研究所。
我需要用户在向服务器发送的每个经过身份验证的请求中填充应用程序和机构。
当然还有更复杂的用例,但这是最常见的一种。
我最简单的请求平均需要填充 4 个引用,而更复杂的请求可以填充更多。
【问题讨论】:
-
取决于你如何“烹饪”你的模型 :) 根据我的经验,我每秒可以向 mongodb 插入 100 000 个文档,但我承认服务器有 32 gigs 的 ram 和 8 个线程(4 核) .还取决于业务逻辑您可以自定义
_id(字符串),这可以帮助通过id获取文档而不是通过条件查询。 (例如:users collection: _id = "someusername"不在username字段上创建索引) -
如果您想要最佳实践,请更好地分享您的模型(架构)和用例。这将帮助 SO 成员提供最佳解决方案。
-
听起来很多,但它确实是一台强大的机器。就您而言,您是否使用填充?在我的业务逻辑中,我实际上对普通的旧自动生成的 ID 感到满意。我在原始问题中添加了一个简单的用例。
-
一切都取决于用例。关于您的用例:无论如何您正在向缓存层发出请求,所以如果缓存层不能承受高负载怎么办? :) 通过 id 获取文档也比通过某些字段获取文档更快(即使它已被索引)。复杂的用例:我认为与其拥有缓存层,不如拥有 Elastic Search 来响应变化并准备好使用包含必要数据的搜索索引。我使用消息总线(事件总线)并通过收集和存储将所有关系数据保存在 CouchBase 中的数据集来对更改做出反应
-
在任何情况下,如果是通过_id 获取文档,对数据库进行额外查询或对缓存进行第二次查询都不是什么大问题。考虑在某个文件夹中打开一些名称类似于 _id 的文件。但是对于复杂的用例,请使用 ElasticSearch 或自己的工作人员,这些工作人员将预取数据并将其放在单独的地方以加快访问速度。附言不要忘记放置适当的索引以提高查找速度(可能会花费额外的存储空间)