I can't figure out what I'm doing wrong here. I'm using pymongo and have the following map/reduce code (all attributes of the document are directly accessible - i.e. no embedded parts relevant here:
(in file getTableMap.js):
function() {
var tablePoints1 = 0;
var tablePoints2 = 0;
if (this.pointsTeam1 == this.pointsTeam2) {
tablePoints1 = 1;
tablePoints2 = 1;
}
else {
if (this.pointsTeam1 > this.pointsTeam2) {
tablePoints1 = 3;
}
else {
tablePoints2 = 3;
}
}
emit(this.idTeam1, [tablePoints1, this.pointsTeam1, this.pointsTeam2]);
emit(this.idTeam2, [tablePoints2, this.pointsTeam2, this.pointsTeam1]);
}
The python code which calls the map_reduce looks like this:
def getTableOnMatchday(self):
m = Code(open('getTableMap.js','r').read())
r = Code("""function(k,values) {
var foo = 'foo';
return(foo);
}""")
result = bl_1.map_reduce(m, r, "myresult")
for doc in result.find():
print doc
For the Python code I adapted the simple example straight from the docs: http://api.mongodb.org/python/current/examples/map_reduce.html Map Reduce example from pymongo 2.0.1 docum开发者_JAVA技巧entation
The Python traceback I get when I run the code is:
>>> api.getTableOnMatchday()
Traceback (most recent call last):
pymongo.errors.OperationFailure: command SON([('mapreduce', u'bl1_2011'),
...
...
...
) failed: db assertion failure
That didn't exactly tell me very much so I turned the mongod logging on to verbose and found this in the logs:
Thu Sep 15 21:04:02 [conn7] User Assertion: 13606:'out' has to be a string
or an object
From looking at the Python code that actually generates the map_reduce call, the third parameter ('out', according to the pymongo 2.0.1 docs) is 'myresult', which certainly is a string.
What is pymongo complaining about here? The Javascript is syntactically correct (I think). I know the reduce currently does nothing, but this should not prevent the compiling of the command serverside - or maybe it does?
I think I've found the answer, through more trial and error and through reading the documentation for the PHP driver:
result = bl_1.map_reduce(m, r, out="foo")
You actually have to specify out=string as third parameter.
The example in the documentation leads astray here as it says to do:
result = bl_1.map_reduce(m, r, "foo")
MapReduce output options: pre-v1.8: If you do not specify a value for out, then the results will be placed into a temporary collection whose name will be given in command's output (see below). Otherwise, you can specify the name of a collection for the out option and the results will be placed there.
v1.8+: the output options have changed. Map-reduce no longer generates temporary collections (thus, keepTemp has been removed).
more information can be found here
精彩评论