2014-09-23 5 views
0

Мне нужно изменить существующий геопространственный запрос, чтобы он включал расстояние в результатах поиска. (И документ, и существующий запрос используют устаревшие пары координат.) Исходный запрос использует $ near. Читая документацию MongoDB, похоже, что geoNear должен возвращать расстояние, как показано в нескольких примерах.MongoDB: geoNear не возвращается расстояние

В то время как я был в состоянии изменить запрос на использование geoNear, расстояния не включены в результатах поиска. Вот пример нового запроса:

{ 
    geoNear: 'users', 
    near: [ '0', '0' ], 
    maxDistance: '90', 
    query: { userName: { '$regex': '^test' } } 
} 

Одна вещь, которая мне не ясно, как Монго связывает расположение к указанному в запросе на местоположение документа. В моем случае у документа пользователя есть поле с именем lastKnownPosition. Как Монго даже знает, как запросить эту область?

Вот пример результатов поиска:

{ 
    "__v" : 0 , 
    "_id" : { "$oid" : "5413824f8b4d6f7505120a53"} , 
    "lastKnownPosition" : { "lon" : 0 , "lat" : 0} ", 
    "userName" : "test123" 
} 
+0

Какие результаты вы получаете назад или это даст вам ошибку? –

+0

Я возвращаю список пользователей. Я обновляю сообщение с результатами. – attila226

+0

Есть ли шанс получить образец из нескольких документов из вашей коллекции? –

ответ

0

Я не могу вспомнить ни одного случая, когда не будет возвращен на расстояние. Таким образом, вы должны делать что-то другое, как это представлено в данном примере:

var async = require('async'), 
    mongoose = require('mongoose'), 
    Schema = mongoose.Schema; 

mongoose.connect('mongodb://localhost/test'); 

var geoSchema = new Schema({ 
    "lastKnownPosition": { 
    "lon": Number, 
    "lat": Number 
    }, 
    "userName": String 
}); 

geoSchema.index({ "lastKnownPosition": "2d" }); 

var Geo = mongoose.model("Geo", geoSchema, "testgeo"); 

mongoose.connection.on("open", function(err,conn) { 

    async.series(
    [ 

     function(callback) { 
     Geo.remove({},function(err) { 
      callback(); 
     }); 
     }, 

     function(callback) { 
     Geo.create(
      { 
      "lastKnownPosition": { "lon": 0, "lat": 0 }, 
      "userName": "test123" 
      }, 
      function(err,doc) { 
      if (err) throw err; 
      callback(); 
      } 
     ); 
     }, 

     // Mongoose method 
     function(callback) { 
     Geo.geoNear(
      [0,0], 
      { 
      maxDistance: 90, 
      query: { 'userName': { '$regex': '^test' } } 
      }, 
      function(err,docs) { 
      if (err) throw err; 
      console.log(docs); 
      callback(); 
     }); 
     }, 

     // Native method 
     function(callback) { 
     Geo.db.db.executeDbCommand(
      { 
      "geoNear": "testgeo", 
      "near": [ 0, 0 ], 
      "maxDistance": 90, 
      "query": { 'userName': /^test/ }, 
      },function(err,result) { 
      if (err) throw err; 
      console.log(result.documents[0].results[0]); 
      callback(); 
      } 
     ); 
     }, 

     // aggregate method 
     function(callback) { 
     Geo.aggregate(
      [ 
      { "$geoNear": { 
       "near": [0,0], 
       "distanceField": "distance", 
       "maxDistance": 90, 
       "query": { "userName": { "$regex": "^test" } } 
      }} 
      ], 
      function(err,result) { 
      if (err) throw err; 
      console.log(result); 
      callback(); 
      } 
     ); 
     } 
    ], 
    function(err) { 
     mongoose.disconnect(); 
    } 
); 

}); 

который производит вывод вроде следующего:

[ { dis: 0, 
    obj: 
    { userName: 'test123', 
     __v: 0, 
     _id: 54225696ce2837e4495cd188, 
     lastKnownPosition: { lon: 0, lat: 0 } } } ] 
{ dis: 0, 
    obj: 
    { _id: 54225696ce2837e4495cd188, 
    userName: 'test123', 
    lastKnownPosition: { lon: 0, lat: 0 }, 
    __v: 0 } } 
[ { _id: 54225696ce2837e4495cd188, 
    userName: 'test123', 
    lastKnownPosition: { lon: 0, lat: 0 }, 
    __v: 0, 
    distance: 0 } ] 

Все есть поле «расстояние», который по умолчанию для " dis "и отдельно к документу с помощью команды "geoNear" либо в вызове, либо указывается и включается в документ из оператора $geoNear.

Следуйте любым из этих шаблонов, и вы получите желаемые результаты.

+0

Я добавил индекс через Mongoose, как показано в примере, и когда я просматриваю документ в uMongo, отображается новый индекс. Однако по какой-то причине я все еще не получаю дистанцию ​​в результатах. Какую еще информацию я могу предоставить, что было бы полезно? – attila226

+0

@ attila226 Заполните пример полностью, для чего предназначен листинг. Дело в чем-то в вашем коде отличается от этого, и поэтому все не работает. Запрос не будет работать вообще, если индекс отсутствует, так что это не часть. –

0

Вы можете создать только один индекс 2d каждой коллекции, так Монго непосредственно знает, какое поле для запроса против.

http://docs.mongodb.org/v2.2/core/geospatial-indexes/#create-a-geospatial-index

+0

Индекс там не был, поэтому я добавил его. Тем не менее, расстояние все еще не возникает в результатах. – attila226

Смежные вопросы