CouchDB - 过滤复制 - 速度可以提高吗?

时间:2012-11-02 12:30:54

标签: couchdb replication

我有一个数据库(300MB和42,924个文档),包含来自约200个用户的大约20种不同类型的文档。这些文档的大小范围从几个字节到几千字节(150KB左右)。

卸载服务器时,以下复制过滤器功能大约需要2.5分钟才能完成。 加载服务器时,大约需要10分钟。

任何人都可以评论这些时间是否是预期的,如果没有,建议我如何优化事物 获得更好的表现?

function(doc, req) {
    acceptedDate = true;
    if(doc.date) {
        var docDate = new Date();
        var dateKey = doc.date;
        docDate.setFullYear(dateKey[0], dateKey[1], dateKey[2]);

        var reqYear = req.query.year;
        var reqMonth = req.query.month;
        var reqDay = req.query.day;
        var reqDate = new Date();
        reqDate.setFullYear(reqYear, reqMonth, reqDay);

        acceptedDate = docDate.getTime() >= reqDate.getTime();
    }

    return doc.user_id && doc.user_id == req.query.userid && doc._id.indexOf("_design") != 0 && acceptedDate; 
}

1 个答案:

答案 0 :(得分:10)

过滤后的复制工作很慢,因为每个获取的文档都会运行复杂的逻辑来决定是否复制它:

  1. CouchDB获取下一个文档;
  2. 因为必须应用过滤器功能,所以文档会转换为JSON;
  3. JSONifyed文档通过stdio传递给查询服务器;
  4. 查询服务器处理文档并从JSON解码;
  5. 现在,查询服务器查找并运行您的过滤器函数,该函数将truefalse值返回给CouchDB;
  6. 如果结果是true文件将被复制;
  7. 转到第1页并循环播放所有文件;
  8. 对于非过滤复制,请使用此列表,丢弃第2-5页,并让p.6始终为true结果。这种开销会减慢整个复制过程。

    要显着提高过滤后的复制速度,您可以通过Erlang native server使用Erlang过滤器。它们在CouchDB中运行,不通过任何stdio接口,也没有应用JSON解码/编码开销。

    请注意,Erlang查询服务器不像JavaScript一样运行在沙盒内部,因此您需要真正信任使用它运行的代码。

    另一种选择是优化您的过滤功能,例如减少对象创建,方法调用,但实际上你不会为此赢得太多。