NoSQL Database by Christof Strauch - HTML preview

PLEASE NOTE: This is an HTML preview only and some elements such as links or page numbers may be incorrect.
Download the book in PDF, ePub, Kindle for a complete version.

Geospatial Indexes

To support location based queries like “find the closest n items to a specific location” MongoDB provides two-dimensional geospatial indexing (cf. [HMS+10]). The latitude and longitude values have to be saved in a document field that is either an object or an array with the first two elements representing coordinates, e.g.

{ loc : { 50, 30 } } // coordinates in an array field

{ loc : { x : 50, y : 30} } // coordinates in an object field

If an object field is used, the object’s fields do not have to have certain names and also do not have to appear in a certain order (though ordering has to be consistent among all documents).

An index on the geospatial coordinates is created using the special value 2d instead of an order:

db.< collection >. createIndex ( { <field > : "2d" } );

Without additional parameters for index creation, MongoDB suggests that latitude and longitude values shall be indexed and therefore aligns the index range to the interval ] img36.pngimg37.png180 ... 180[. If other values are indexed the index range should be given at index creation as follows:

db.< collection >. createIndex ( { <field > : "2d" } , { min : <min -value ,

             max : <max - value });

The range boundaries are exclusive which means that index values cannot take these values.

To query based on a geospatial index the query document can contain special criteria like $near and $maxDistance:

db.< collection >. find ( { <field > : [< coordinate >, <coordinate >]} ); // exact match

db.< collection >. find ( { <field > : { $near : [< coordinate >, <coordinate >] } } );

db.< collection >. find ( { <field > : { $near : [< coordinate >, <coordinate >],

                     $maxDistance : <value >} } );

In addition to limiting the distance in which matches shall be found it is also possible to define a shape (box or circle) covering a geospatial region as a selection criterion.

Besides the generic find operation MongoDB also provides a specialized way to query by geospatial criterions using the geoNear operation. The advantages of this operation are that it returns a distance value for each matching document and allows for diagnostics and troubleshooting. The geoNear operation has to be invoked using the db.runCommand syntax:

db. runCommand ({ geoNear : <collection >, near = [< coordinate >, <coordinate >], ...}) ;

As shown in the syntax example, no field name has to be provided to the geoNear operation as it auto- matically determines the geospatial index of the collection to query. match circular shapes) or adding the option spherical:true to the parameters of the geoNear operation. When using the aforementioned $near criterion MongoDB does its calculations based on an idealized model of a flat earth where an arcdegree of latitude and longitude is the same distance at each location. Since MongoDB 1.7 a spherical model of the earth is provided so that selections can use correct spherical distances by applying the $sphereNear criterion (instead of $near), the $centerSphere criterion (to When spherical distances are used, coordinates have to be given as decimal values in the order longitude, latitude using the radians measurement.

Geospatial indexing has some limitations in the MongoDB versions 1.6.5 (stable) and 1.7 (unstable as of December 2010). First, it is limited to indexing squares without wrapping at their outer boundaries. Second, only one geospatial index is allowed per collection. Third, MongoDB does not implement wrapping at the poles or at the -180img51.pngimg37.pngto 180img51.pngimg37.pngboundary. Lastly, geospatial indexes cannot be sharded.