让我们说你有两种文件类型,客户和订单.客户文件包含名称,地址等基本信息,订单每次客户订购时都包含所有订单信息.存储文档时,type = order或type = customer.
如果我在一组10个客户和30个订单中做一个地图函数,它将输出40行.一些行将成为客户,有些将会是订单.
问题是,如何编写reduce,以便订单信息被“填充”到具有客户信息的行内部?所以它会返回10行(10个客户),但每个客户的所有相关订单.
基本上我不想在输出上单独记录,我想把它们(订单分成一个客户行),我认为减少是一种方式?
解决方法
这被称为视图排序规则,它是非常有用的CouchDB技术.
幸运的是,你甚至不需要减少步骤.只需使用地图将客户和他们的订单“团结起来”在一起.
建立
关键在于,您需要为每位客户提供一个唯一的ID,并且必须从客户文档和订单文档中都知道.
示例客户:
{ "_id": "customer me@example.com","type": "customer","name": "Jason" }
示例订单:
{ "_id": "abcdef123456","type": "order","for_customer": "customer me@example.com" }
我方便地使用客户ID作为文档_id,但重要的是两个文档都知道客户的身份.
付清
目标是一个地图查询,如果您指定?key =“customer me@example.com”,那么您将首先回到(1)客户信息,和(2)任何和所有订单.
这个地图函数会这样做:
function(doc) { var CUSTOMER_VAL = 1; var ORDER_VAL = 2; var key; if(doc.type === "customer") { key = [doc._id,CUSTOMER_VAL]; emit(key,doc); } if(doc.type === "order") { key = [doc.for_customer,ORDER_VAL]; emit(key,doc); } }
所有行将主要根据客户的文档进行排序,“tiebreaker”排序是整数1或2.这使得客户文档总是排在其对应的订单文档之上.
["customer me@example.com",1],...customer doc... ["customer me@example.com",2],...customer's order... ["customer me@example.com",...customer's other order. ... etc... ["customer another@customer.com",... different customer... ["customer another@customer.com",... different customer's order
附:如果您遵循所有这些:而不是1和2,更好的值可能为客户的null,然后订单的订单时间戳.它们将像以前一样进行排序,但现在您有按时间顺序排列的列表.