[SERVER-1640] $in operator for behaves unexpected on upserts Created: 19/Aug/10 Updated: 07/Mar/14 Resolved: 19/Aug/10 |
|
| Status: | Closed |
| Project: | Core Server |
| Component/s: | Write Ops |
| Affects Version/s: | 1.6.1 |
| Fix Version/s: | None |
| Type: | Bug | Priority: | Major - P3 |
| Reporter: | Torsten Curdt | Assignee: | Unassigned |
| Resolution: | Done | Votes: | 0 |
| Labels: | None | ||
| Remaining Estimate: | Not Specified | ||
| Time Spent: | Not Specified | ||
| Original Estimate: | Not Specified | ||
| Environment: |
any |
||
| Operating System: | ALL |
| Participants: |
| Description |
|
We would like to reduce the number of updates by using the $in operator going from buckets = [ '2010', '2010-08', '2010-08-01' ] , { '$inc' => { 'downloads' => 1 }}, :upsert => true) to buckets = [ '2010', '2010-08', '2010-08-01' ] }, { '$inc' => { 'downloads' => 1 }}, :upsert => true) Unfortunately we get very strange and inconsistent results. db.test.find() , { "$inc": { "d": 1 } }, true) db.test.update( {"b": 3}, { "$inc": { "d": 1 } }, true) db.test.update({"b": { "$in": [ 2, 3, 4 ] }}, { "$inc": { "d": 1 } }, true) We would expect also { "_id" : ObjectId("4c6d1e485153667a3fd349ba"), "b" : 4, "d" : 1 }to be there. Then we found there is 'multi' option to turn on in (from http://www.mongodb.org/display/DOCS/Updating ) "multi - if all documents matching criteria should be updated" But that still does not create a documents as expected. db.test.update({"b": { "$in": [ 2, 3, 4 ] }}, { "$inc": { "d": 1 } }, true, true) Now even more weird. Trying again it does create a document - but not the one expected: db.test.update({"b": { "$in": [ 55, 66 ] }}, { "$inc": { "d": 1 } }, true, true) What are we missing here? |
| Comments |
| Comment by Eliot Horowitz (Inactive) [ 19/Aug/10 ] |
|
In the last piece, it is supposed to do an upsert because the query doesn't match anything. |
| Comment by Eliot Horowitz (Inactive) [ 19/Aug/10 ] |
|
You can't combine a multi-update and an upsert. You can do a query with $in and figure out which objects need to inserted, and then do an multi-update on the others. But i think you're better of jusing doing multiple upserts in your code |
| Comment by Torsten Curdt [ 19/Aug/10 ] |
|
...and why is it creating { "_id" : ObjectId("4c6d1f1a5153667a3fd349ba"), "d" : 1 }then? according to you that should not happen either. |
| Comment by Torsten Curdt [ 19/Aug/10 ] |
|
Got at better way to combine the multiple updates in one then? |
| Comment by Eliot Horowitz (Inactive) [ 19/Aug/10 ] |
|
If you use upsert with multi, if any docs match, nothing will be created. Think about the case where you say update( { x : { $gt : 5 } } ) |