Mongodb can't find object with too long _id

2019-09-17 05:33发布

问题:

I have a little bit strange situation.

I persist objects in collection "refs" explicitly setting _id. So I have objects with very big id's.

db.refs.find().sort({_id: -1});
// {_id: 9200000000165761625}
// ...

But when I try to find object with biggest id in mongo shell it returns nothing:

db.refs.find({_id: 9200000000165761625}); // nothing

But!

db.refs.find({_id: 9200000000165761625}).count(); // return 1

How could this happen?

回答1:

i could not reproduce your problem. i was able to successfully query on the _id value you specified.

ensure that when you are querying you are passing correct collection name



回答2:

JavaScript currently only has a single numeric type Number, which represents all values as 64-bit floating point values. The maximum safe integer representation in JavaScript's native Number type is 253-1 or 9007199254740991 (as returned by the constant Number.MAX_SAFE_INTEGER).

Any integer values beyond the safe range cannot be represented distinctly, so two or more mathematical values will map to the same JavaScript Number.

You can see this effect in the mongo shell with values adjacent to your provided _id (which is larger than the safe integer size):

> 9200000000165761624
9200000000165762000

> 9200000000165761625
9200000000165762000

> 9200000000165761626
9200000000165762000

However, these driver/client limitations are distinct from the underlying data types used in MongoDB's BSON format for documents. BSON has a 64-bit integer type which represents the full range of values: up to 263-1 for 64-bit integers.

Your example _id is within the 64-bit integer range so you should be able to insert or update this using a driver with support for 64-bit integers, but would not be able to safely query or manipulate long values in the mongo shell or other JavaScript environments. To avoid unexpected outcomes you may want to use a different data type for these long _id values.