Details
Description
With an empty data set, running an update operation against the server to perform a document replacement uses the _id in the query to initialize it:
local:PRIMARY> db.test.update({$and:[{_id: 1000}]}, {foo:10000}, {upsert:true})
WriteResult({ "nMatched" : 0, "nUpserted" : 1, "nModified" : 0, "_id" : 1000 })
local:PRIMARY> db.test.find()
{{
{ "_id" : 1000, "foo" : 10000 }}}
However doing the equivalent operation through the stitch library doesn't seem to take into account the query when initializing the upserted doc in the same manner. Here is a failing test case:
|
t.Run("upsert with a compound expression query should initialize upserted doc correctly with replacement", func(t *testing.T) {
|
matcher, err := stitchmongo.NewMatcher(bson.D{{"$and", []interface{}{
|
bson.D{{"_id", 1000}},
|
}}})
|
u.So(t, err, gc.ShouldBeNil)
|
defer matcher.Close()
|
updater, err := stitchmongo.NewUpdater(
|
bson.D{{"z", 3}},
|
matcher,
|
)
|
u.So(t, err, gc.ShouldBeNil)
|
defer updater.Close()
|
result, err := updater.ApplyUpsert()
|
u.So(t, err, gc.ShouldBeNil)
|
u.So(t, result.UpdatedDocument, gc.ShouldResemble, bson.D{{"_id", 1000}, {"z", 3}})
|
u.So(t, result.IsReplacement, gc.ShouldBeTrue)
|
})
|
|
|
|
Interestignly though the same operation does work equivalently to the server when the update uses $ modifiers instead. For example, the following test passes:
t.Run("upsert with a compound expression query should initialize upserted doc correctly with update modifiers", func(t *testing.T) {
|
matcher, err := stitchmongo.NewMatcher(bson.D{{"$and", []interface{}{
|
bson.D{{"_id", 1000}},
|
bson.D{{"x", 50}},
|
}}})
|
u.So(t, err, gc.ShouldBeNil)
|
defer matcher.Close()
|
updater, err := stitchmongo.NewUpdater(
|
bson.D{{"$set", bson.D{{"z", 3}}}},
|
matcher,
|
)
|
u.So(t, err, gc.ShouldBeNil)
|
defer updater.Close()
|
result, err := updater.ApplyUpsert()
|
u.So(t, err, gc.ShouldBeNil)
|
u.So(t, result.UpdatedDocument, gc.ShouldResemble, bson.D{{"_id", 1000}, {"x", 50}, {"z", 3}})
|
u.So(t, result.IsReplacement, gc.ShouldBeFalse)
|
})
|
|