You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
I'd like to leverage the Upsert() capabilities of Mongo, and know when a document has changed on the Upsert when using GoLang maps. Specifically I want ChangeInfo.Updated to be 0 when the document has not changed.
Background
When it comes to JSON & BSON maps, there are differences in their respective specs:
JSON cares not about the ordering of keys in maps (keys are a "set" and ordering is not implied)
BSON strictly enforces ordering in maps (keys are still a "set" but ordering is implied)
Coupled with the fact that GoLang intentionally randomizes the order when walking over a map (ie: range <map>) means that 99% of my Upserts are coming back indicating that the document changed (when it really didn't). The only thing that changed was the randomized ordering of the keys by the lower level GoLang range function when walking maps.
This is the LOC that is the culprit (range'ing over the map):
If the addMap() function would fetch the map's keys, sort them, and then addElem() in that sorted order I'd be "set". The current code is taking GoLang's map random ordering (more akin to JSON), and encoding it as a strict ordering in BSON.
I've also tried using bson.D with no luck. Whenever Upsert()'ing with bson.D the order is preserved (not random in Mongo) -- however ChangeInfo.Updated is never 0 on identical / repeated calls.
What works:
golang struct's
What doesn't work:
bson.M (ie: map[string]interface{})
bson.D (ie: []DocElem)
I'm not able to model the docs via GoLang struct as this middleware component is agnostic to the model of the docs (more akin to a generic JSON processor), but it does need to know if/when the document has been modified on the Upsert().
What version of MongoDB are you using (mongod --version)?
Doesn't matter
What version of Go are you using (go version)?
Doesn't matter (greater than 1.0)
What operating system and processor architecture are you using (go env)?
Doesn't matter
What did you do?
Upsert a bson.M document (ie: map[string]interface{})
Repeated calls of the same map result in ChangeInfo.Updated not equal to 0, depending on the randomized order of golangs range <map> and BSON's internal strict ordering.
Can you reproduce the issue on the latest development branch?
Haven't tried, but a code review show the same range <map> problem (ie: randomized ordering of map keys).
The text was updated successfully, but these errors were encountered:
Actually, struct is broken too. In all cases, an Upsert (via any method) results in ChangeInfo.Updated not equal to 0 even though the document is not changed.
Since this driver is abandon-ware, we are moving to mongo-go-driver. That other driver does still have the range <map> problem, but at least there are ways to detect if documents have changed on upsert with it. L8r.
I'd like to leverage the
Upsert()
capabilities of Mongo, and know when a document has changed on the Upsert when using GoLang maps. Specifically I wantChangeInfo.Updated
to be0
when the document has not changed.Background
When it comes to JSON & BSON maps, there are differences in their respective specs:
Coupled with the fact that GoLang intentionally randomizes the order when walking over a map (ie:
range <map>
) means that 99% of my Upserts are coming back indicating that the document changed (when it really didn't). The only thing that changed was the randomized ordering of the keys by the lower level GoLangrange
function when walking maps.This is the LOC that is the culprit (range'ing over the map):
mgo/bson/encode.go
Line 205 in 113d396
If the
addMap()
function would fetch the map's keys, sort them, and thenaddElem()
in that sorted order I'd be "set". The current code is taking GoLang'smap
random ordering (more akin to JSON), and encoding it as a strict ordering in BSON.I've also tried using
bson.D
with no luck. WheneverUpsert()
'ing withbson.D
the order is preserved (not random in Mongo) -- howeverChangeInfo.Updated
is never0
on identical / repeated calls.What works:
struct
'sWhat doesn't work:
bson.M
(ie:map[string]interface{}
)bson.D
(ie:[]DocElem
)I'm not able to model the docs via GoLang
struct
as this middleware component is agnostic to the model of the docs (more akin to a generic JSON processor), but it does need to know if/when the document has been modified on theUpsert()
.What version of MongoDB are you using (
mongod --version
)?Doesn't matter
What version of Go are you using (
go version
)?Doesn't matter (greater than 1.0)
What operating system and processor architecture are you using (
go env
)?Doesn't matter
What did you do?
Upsert a
bson.M
document (ie:map[string]interface{}
)Repeated calls of the same map result in
ChangeInfo.Updated
not equal to0
, depending on the randomized order of golangsrange <map>
and BSON's internal strict ordering.Can you reproduce the issue on the latest
development
branch?Haven't tried, but a code review show the same
range <map>
problem (ie: randomized ordering of map keys).The text was updated successfully, but these errors were encountered: