在从 RDBMS 切换之前需要 MongoDB 专家/开发人员的建议

Posted

技术标签:

【中文标题】在从 RDBMS 切换之前需要 MongoDB 专家/开发人员的建议【英文标题】:Need advice from MongoDB experts/developers before on switching from RDBMS 【发布时间】:2011-03-29 19:46:40 【问题描述】:

我们在 SQL2005 中有这些表:

专辑:视频专辑详细信息(类别、标题、标签、日期、作者、 喜欢、观看等 标签:专辑标签和按字母顺序排序(查找所有带 特定标签) ratings:存储给专辑评分的用户的id(防止 重复评级) cmets:存储相册中的所有cmets comment_ratings:评价评论的用户ID(防止重复 评分) comment_replies:对评论的所有回复,带有日期和海报 信息 comment_reply_ratings:评价回复的用户的 ID(防止 重复评级)

这种类型的结构可以在 MongoDB 中创建吗? 以下操作/查询具有相同/更好的性能?

1) 获取前 10 名最喜欢的专辑(标题、缩略图、浏览量、点赞数、 作者和日期)与分页。 如果用户点击下一个,则获得下一个 10 个最喜欢的专辑等等

2) 通过分页获取前 10 个观看次数最多的专辑。

3) 通过分页获取前 10 个讨论最多的专辑。

4) 获取最近创建的带有分页但最多 100 个专辑的列表 专辑

5) 获取给定用户的所有相册(标题、缩略图、查看次数、喜欢的次数、 作者和日期)

6) 获取特定专辑的详细信息并仅显示前 10 名 分页。 Next 将加载接下来的 10 个 cmets,依此类推。

7) 获取相关专辑列表。关系将通过专辑标签或 专辑名称

8) 按关键字搜索会搜索专辑的标题或标签字段。

9) 当有人点击一个标签时,获取所有带有该标签的专辑列表

10)当有人点击一个分类链接时,获取10个分类的列表 专辑

11) 获取按评级、日期等排序的 cmets

12)文档中新条目的顺序可以是 控制?

感谢阅读。上帝保佑。

【问题讨论】:

我已经从不同的 rdbms 移动了两个应用程序(第一个大约 100 个 sql 表,第二个大约 60 个)。这两个应用程序都可以使用 mongodb 快速运行。因此,将您的项目移动到 mongodb 是一个很好的解决方案(至少在项目上方,因为对于某些项目仍然使用 sql 至关重要)。 Bugai,我无法告诉您我多么感谢您的回复。非常感谢。 【参考方案1】:

我建议如下结构:

Album 
   Id,
   UserId,
   Title,
   Category,
   Tags (list of tag names for fast access and for searching),
   Ratings (user ids, use $addToSet),
   Likes (user ids, use $addToSet),  
   ViewsCount, (probably just integer value,)
   RatingsCount (use $inc to increment this field once someone vote for album),
   CommentsCount (use $inc everytime when someone post comment),
   LikesCount (use $inc everytime when someone click 'Like it')


Comment 
   Id,
   AlbumId,
   Text,
   CreatedDate,
   Ratings,
   RatingsCount,
   Replies  (collection of comment replies)
      Text,
      CreatedDate,
      Ratings,
      RatingsCount
   


Tag 
   Id,
   TagName,
   AlbumsCount (use $inc: 1 when new album created with this tag
                 and $inc:-1 - once deleted)

我已将 cmets 移动到单独的集合中(而不是将其嵌入到相册中),因为目前在 mongodb 中很难更新具有一层以上嵌套的文档。

现在查询:

1) 通过分页获取前 10 个最喜欢的专辑(标题、缩略图、视图、喜欢、作者和日期)。如果用户点击下一个,则获得下一个 10 个最喜欢的专辑等等

db.albums.find().skip(0).limit(10).sort(  RatingsCount: -1  );

2) 通过分页获取前 10 个观看次数最多的专辑。

db.albums.find().skip(0).limit(10).sort(  ViewsCount: -1  );

3) 通过分页获取前 10 个讨论最多的专辑。

db.albums.find().skip(0).limit(10).sort(  CommentsCount: -1  );

4) 获取最近创建的带有分页但最多 100 个相册的相册列表

db.albums.find().skip(0).limit(100).sort(  CreatedDate: -1  );

5) 获取给定用户的所有专辑(标题、缩略图、视图、喜欢、作者和日期)

db.albums.find(UserId: someUserId)

6) 获取特定专辑的详细信息并通过分页仅显示前 10 个 cmets。 Next 将加载接下来的 10 个 cmets,依此类推。

album = db.albums.find(_id: someAlbumId);
comments = db.comments.find(AlbumId: someAlbumId ).skip(0)
                 .limit(10).sort(  RatingsCount: -1 ,CreateDate: -1  );

7) 获取相关专辑列表。关系将通过专辑标签或专辑标题完成

请澄清

8) 按关键字搜索会搜索专辑的标题或标签字段。

db.albums.find(  $or : [  Title : searchKey  ,  Tags : searchKey  ]  )

注意:可能需要存储两次标签:小写用于搜索,原样用于显示

9) 当有人点击一个标签时,获取所有带有该标签的专辑列表

db.albums.find( Tags :  $in: [tagName1, tagName2] ]  )

注意:使用 $in 运算符可以按多个标签名称进行搜索。

10)当有人点击分类链接时,获取10个分类相册的列表

db.albums.find(Category: val ).skip(0).limit(10).sort(  CreatedDate: -1  );

11) 获取按评级、日期等排序的 cmets

db.comments.skip(0).limit(10).sort(  RatingsCount: -1  );

12)可以控制文档中新条目的顺序吗?

请澄清

我认为现在您看到您可以将关系数据库迁移到 MongoDB,并相信您的应用程序使用 mongodb 及以上架构会非常快;)。

希望对您有所帮助。

P.S:如果 sql 2005 比我想你使用一些 .net 语言?

【讨论】:

您推荐哪个 c# 驱动程序?我一个在 MongoDB 网站上,另一个在此处列出:github.com/samus/mongodb-csharp/downloads 如果您有首选的 C# 驱动程序,请告诉我。否则,我会选择github.com/samus/mongodb-csharp @Projapati:我建议你使用官方的 mongodb c# 驱动程序(github.com/mongodb/mongo-csharp-driver/downloads)。它支持10gen。 此驱动程序中没有 LINQ dll。来自 samus(社区驱动)的驱动程序具有 linq.dll。有什么意见吗? @Projapati:你的意思是官方驱动不支持linq?是的,就是这样。但只有官方驱动是稳定的,并且包含所有最新的 mongodb 功能。我在所有项目中都使用官方驱动程序,我可以不用 linq ;)。做出你的选择。【参考方案2】:

我看到网络上出现了各种各样的问题。您会发现最常见的答案是为每项工作使用正确的“工具”,因此 Mongo 和标准 RDBMS 都不会比其他数据库更适合每个应用程序,但在我看来,您绝对应该投入一些时间学习这个新的“工具”,因为它会让你更好地了解什么更适合你的思维方式和编程风格。

在使用 SQL 数据库多年后,我最近也开始使用 MongoDB,我可以告诉你这是值得的体验。你可以用 Mongo 做几乎所有事情,绝对是你在列表中描述的所有事情,但要准备好在这个过程中做出一些权衡。不知道你用的是什么语言。我使用 php,我认为 MongoDB 比任何 SQL 数据库更适合 PHP,因为它以 JSON 格式组织数据,这对于 PHP(数组、类等)树状结构来说更“自然”,几乎可以将整个数组或其中的一部分转储到数据库中,而无需进行大量“映射”并在需要时将其取回。此外,无shema 设计可以让您在如何组织(或不组织:))数据方面更加灵活。此外,如果您想开发大型应用程序,MongoDB 将比大多数 SQL 数据库更容易扩展。

但对于更“严格”的应用程序,其中数据“一致性”和“持久性”更重要,我可能会选择老式 RDMBS 数据库之一,例如 PostgreSQL。 事实上,如果必须的话,没有什么能阻止您在同一个项目中使用这两种工具。 希望这会有所帮助!

【讨论】:

数据一致性不是所有网络应用程序都必须的吗?我知道它在某些应用程序(例如银行系统)中很重要,但总的来说,它对于像这样的网站也很重要。只要我可以使用 NoSQL 类型的数据库进行上述查询,我​​就很乐意搬到新领域。我正在花一些时间做一些好事。我已经准备好进行一些取舍了。谢谢你的帖子。 不完全是,因为 Mongo 是为扩展环境设计的,它们确实提供了所谓的“最终”数据一致性,这意味着您的数据最终将在每个节点上更新,这对于大多数 Web 应用程序来说都很好.例如,如果您在博客上创建帖子,它应该“最终”出现在您的浏览器上,这可能是在您按下帖子按钮后 2-5 秒,而不是“即时”!它们还支持“原子”操作以及 FSYNC,它允许您在更新一定数量的副本后获得响应,这是足够好的一致性。 在实践中,Mongo 非常快,这种延迟通常比 2 秒小很多,更像是几毫秒,但这是我所说的小权衡之一,但好处对于许多应用程序而言,使用 Mongo 的缺点远远超过了缺点。

以上是关于在从 RDBMS 切换之前需要 MongoDB 专家/开发人员的建议的主要内容,如果未能解决你的问题,请参考以下文章

社区阿杜:Restful Spring Boot with MongoDB

如何解决 MongoDB 中缺少事务的问题?

MongoDB与RDBMS之优势对比

MongoDB

修改从 RDBMS 到 MongoDB 的查询 [关闭]

在从付费应用切换到应用内购买时需要帮助