如何构建CouchDB的结构示例

4
我正在寻找有关如何存储和结构化CouchDB数据的良好示例/实践。比Definitive Guide中的博客应用程序更复杂一些。
让我们想象一个像Stack Overflow这样的应用程序。
- 如何存储基本部分 - 用户、问题、答案、评论、标签、投票? - 您认为将数据分成不同的数据库是一个好主意吗?例如,将用户放在单独的数据库中...或者投票/标签? - 还是不要这样做,因为在视图中无法组合来自不同数据库的数据?
4个回答

2
在文档存储数据库中,用于结构化关系型数据库中数据的概念同样适用。唯一真正改变的是,在NoSQL数据库中通常使用联接操作进行的查询通常比较麻烦。这意味着在NoSQL数据库中,通常需要进行更多的去规范化(denormalization),以解决关系型数据库上通常通过联接来解决的一对多关系。例如,在博客文章和评论之间的典型一对多关系中,您将在评论中复制一些来自文章的数据,而不是在评论中使用外键引用文章,以避免额外的查询,并且在文章中保留评论ID列表(以及最近10个评论的内容)。

TokenMacGuy,通过外键,你是指帖子的“_id”属性吗?你会在评论对象中存储重复数据只是为了方便吗?我正在尝试使用Backbone.js来实现,所以我在准备Backbone的CRUD操作时仔细思考这个问题。 - AndrewHenderson
是的,您可以通过将父级的ID添加到子级的属性中来关联这两个文档。但是,非规范化通常不方便,它通常是出于性能考虑;但CouchDB可能会通过视图为您节省麻烦。 - SingleNegationElimination

1
我建议您将各个部分(用户、问题、答案、评论、标签、投票)作为单独的文档存储在一个数据库中。
不要将它们存储在单独的数据库中。这样会失去视图的优势,并且需要进行指数级别的HTTP请求来收集数据。

--

请看http://www.cmlenz.net/archives/2007/10/couchdb-joins,这篇文章对我启发很大。感谢Costa另一个问题中分享了链接。

虽然这篇文章使用了无处不在的博客示例,但我认为“视图聚合”是你想要的方法之一。

作为另一个文档的子文档的文档将通过父文档的“_id”属性进行链接。此外,您将为文档指定一个“类型”属性,以便在视图中返回时对它们进行排序。例如:

function(doc) {
  if (doc.type == "post") {
    map([doc._id, 0], doc);
  } else if (doc.type == "comment") {
    map([doc.post, 1], doc);
  }
}

您将获得返回的内容如下:

{
 "total_rows": 5, "offset": 0, "rows": [{
  "id": "myslug",
  "key": ["myslug", 0],
  "value": {...}
}, {
  "id": "ABCDEF",
  "key": ["myslug", 1],
  "value": {...}
}, {
  "id": "DEFABC",
  "key": ["myslug", 1],
  "value": {...}
}, {
  "id": "other_slug",
  "key": ["other_slug", 0],
  "value": {...}
}, {
  "id": "CDEFAB",
  "key": ["other_slug", 1],
  "value": {...}
}]
}

你现在已经通过一个HTTP请求获取了所有数据,包括父级和子级。此外,你可以直接通过REST API对这些文档进行CRUD操作。在我看来,这正是你想要的。
你可以将相同的方法应用于任何具有一对多或多对一关系的内容。
希望这能帮到你!

0
关于在couchdb中进行“连接”的问题:
实际上,不重复数据可能更有意义。这是我在couchdb中创建的一个视图的示例:http://wamoyo.iriscouch.com/_utils/database.html?ideageneration/_design/IdeaGeneration/_view/challengesAndIdeas 这个简单的应用程序允许人们输入挑战,然后让他们收集解决这些挑战的想法。它非常适合博客示例:挑战将成为博客文章,而想法将成为适合每篇博客文章下的评论。
我已经在这里的另一个问题中详细介绍了这个问题:Couch DB Join operations like RDBMS 关于在couchdb中构建应用程序,Jason,我也在思考同样的问题。CouchDB提供了很多灵活性,因此我不确定是否应该使用shows和lists来显示数据,还是仅编写客户端代码来完成这项工作,也许可以使用backbone,然后只使用couchdb视图来提供模型。请告诉我你最终的决定,我会非常好奇的。

你有关于这个主题的任何新发现可以分享吗? - AndrewHenderson
有很多种方式可以使用CouchDB进行结构化,这完全取决于你自己,这就是没有模式的好处/坏处。此外,从你的回答来看,你比我更了解它。 - Costa Michailidis

0

http://www.cmlenz.net/archives/2007/10/couchdb-joins中演示的模型有助于理解结构,但我对使用博客主题作为文档ID的方法有一个评论。如果两个用户具有相同的博客标题,则会导致冲突。虽然我新手couchdb,但似乎文档ID和文档标题应该是分开的,尽管存在通过/blogName加载博客的挑战。是否可以通过以下结构实现:
{_id:6377738426gdjjsb,_rev:1-hsusubsvh6377,title:blogName,authorName:shakespeareND5}


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接