3

我知道在 0.6 之前与流星一起打包的“迷你 mongo”在聚合方面有一些限制,但希望随着 0.6 的发布,故事会更容易一些。

我试图解决的是 mini-mongo 中缺乏“聚合”。

我有一个带有这样记录的 mongodb

db.account_records.findOne()
{
    "type" : "initial_balance",
    "amt" : 10,
    "account_id" : "95CPB9Be8NX3TGSpi",
    "_id" : "L9D7Agt4gW2Ht4NTA"
}

我想(在客户端)订阅如下查询..

db.events.aggregate( [ { $group: {_id:"$account_id", balance: { $sum: "$amt"}}}]);

..这给出了(当使用终端“mongo meteor”风格的“真实”mongodb运行时)..

{
    "result" : [
        {
            "_id" : "Dn5Eouw8K4RrP9SGw",
            "balance" : 169.99922000000308
        },
        {
            "_id" : "Bawopno2QGs8guMWy",
            "balance" : 1
        },
        {
            "_id" : "95CPB9Be8NX3TGSpi",
            "balance" : 5
        }
    ],
    "ok" : 1
}

在我看来,在客户端执行复杂的聚合子句是不可能的(或可取的),所以我可以看到我们拥有 mini-mongo 的原因。但我希望能够在新版本的流星中安装标准 npm 模块,创建一个可以从“真实”mongo 发布并在 mini-mongo 中订阅的查询可能会更容易一些?

--

PS我已经找到了,但是所有这些双下划线让我很紧张,我会尝试一些复杂的东西...... https://github.com/meteor/meteor/pull/644

4

2 回答 2

2

您可以在您的服务器上使用该聚合推送。在 Meteor 0.6.0 'engine' 版本之前,npm模块集成仍然非常非官方,因此下划线,最后它可以正式使用,所以下面应该可以工作(从 gi​​thub pull 修改为在 0.6.0 上工作:https://github. com/流星/流星/拉/644

服务器端js

var path = Npm.require('path');
var MongoDB = Npm.require('mongodb');
var Future = Npm.require('fibers/future');

var Animals = new Meteor.Collection("animals");

Meteor.startup(function () {
  Animals.aggregate = function(pipeline) {
    var self = this;

    var future = new Future;
    self.find()._mongo.db.createCollection(self._name, function (err, collection) {
      if (err) {
        future.throw(err);
        return;
      }
      collection.aggregate(pipeline, function(err, result) {
        if (err) {
          future.throw(err);
          return;
        }
        future.ret([true, result]);
      });
    });
    var result = future.wait();
    if (!result[0])
      throw result[1];

    return result[1];
  };

});

Meteor.methods({
  myAggregationMethod: function() {
    return Animals.aggregate([ {$project: {dog:1, age:1}}, {$sort:{age:1}} ]);
  }
});

在您的客户端 js上,当您要调用聚合时:

    Meteor.call('myAggregationMethod', function(err,result) {
      if (!err) {
          console.log(result)          
      } else {
        console.log(err);
      }
    });

添加 mongodb 包

1)在您的项目中创建一个名为 packages 的目录来存储您的包,并在另一个名为 mongodb 的目录中为 mongodb npm 包创建一个目录

2) 在 mongodb 中添加一个名为 contains 的package.js文件

Package.describe({
  summary: "Mongodb driver"
});

Npm.depends({'mongodb':"1.2.14"});

Package.on_use(function (api) {
  api.add_files('lib.js', 'server');
});

在同一个 mongodb 目录中添加另一个文件,名为lib.js

if(typeof(Npm) != "undefined") {
    MongoDB = Npm.require("mongodb");
}
else
{
    console.log("Please upgrade meteor to 0.6.0")
    MongoDB = __meteor_bootstrap__.require("mongodb");
}

最后删除线

var MongoDB = Npm.require("mongodb")来自您server.js,因为我们在全球范围内lib.js

于 2013-04-06T06:18:49.503 回答
1

要修复 Akshat 对 Meteor 0.9.0 的回答,请使用以下命令:

self.find()._mongo._withDb(function(db) {
  return db.createCollection(self._name, function(err, collection) {
    if (err) {
      console.log(err);
      future.throw(err);
      return;
    }
    return collection.aggregate(pipeline, function(err, result) {
      if (err) {
        future.throw(err);
        return;
      }
      return future["return"]([true, result]);
    });
  });
});

此外,无需包含MongoDB = Npm.require("mongodb")在标题中。

于 2014-09-03T21:20:50.967 回答