Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
222 views
in Technique[技术] by (71.8m points)

javascript - How do I run a filter on a getNearest() query in RethinkDB?

I have a table with users and their locations saved as r.point datatypes & a geo index set on them. I am trying to run a .getNearest() query, which returns all the users closest to the given user (say, Mr. X). The results return all the users closest to Mr. X, but also include Mr. X. How do I filter all users except Mr. X?

What I've tried so far —

  1. In RethinkDB's Data Explorer (Plain ReQL commands)

    r.db('myDb').table('myTable').getNearest(r.point(-20, 39), {index: 'location'}).filter(function(user) {return user.id !== '2ff8902e-97f0-431a-a51c-900a57532967'}); // Assuming Mr.X's `id` is `2ff8902e-97f0-431a-a51c-900a57532967`
    

    This returns all users, including Mr. X. Attempt #2 was -

    r.db('myDb').table('myTable').getNearest(r.point(-20, 39), {index: 'location', maxDist:9000000}).filter(r.row('id').ne('2ff8902e-97f0-431a-a51c-900a57532967'));
    

    This returns nothing.

  2. In thinky, a Node.js ORM for RethinkDB.

    UserModel.getNearest(r.point(-20, 39), {index: 'location'}).filter(function(user) {return user.id !== '2ff8902e-97f0-431a-a51c-900a57532967'}).run();
    

    This returns all users, including Mr. X.

One solution I'm already aware of —

Using Thinky, I can do this.

const userId = '2ff8902e-97f0-431a-a51c-900a57532967';
const location = r.point(-20, 39);
const queryOptions = {index: 'location'};
UserModel.getNearest(location, queryOptions).run().then(function (users) {
  return users.filter(function(user) {
    return user.doc.id !== userId;
  });
});

I have a feeling I can make this faster; by making sure either the .filter() or another alternative function is run on the RethinkDB server than on my end. Is there room for improvement here? Or perhaps a nicer solution that I am overlooking?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

You actually do it correct and almost there. You just happen to use filter with wrong key.

r.db('myDb').table('myTable').getNearest(r.point(-20, 39), {index: 'location'})
    .filter(function(user) {
           return user('doc')('id').ne('2ff8902e-97f0-431a-a51c-900a57532967')
    })

The key thin is:

  1. getNearest returns an array of document. Each document has two fields: dist and doc(which is the document in table itself). Hence here we are using user('doc')('id') to get the key. https://rethinkdb.com/api/javascript/get_nearest/
  2. Inside filter function, we have to use ReQL command, in this case, the ne mean, not equal. https://www.rethinkdb.com/api/javascript/ne/

This is fast because we have the index on location. And filter function is executed on RethinkDB server.


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...