Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

MongoDB & Spring Data - Searching for a user by firstname/lastname

I have the following collection:

User {
   firstname,
   lastname
}

I want to search for users by firstname and/or lastname (firstname/lastname/firstname+lastname).

What I have:

 Criteria criteria = new Criteria();
 criteria.orOperator(Criteria.where("firstname").regex(searchQuery),Criteria.where("lastname").regex(searchQuery));

The problem with the above is that I can either search by firstname OR lastname, but not both (e.g. ''John Smith'' is not possible while ''John'' or ''Smith'' is possible. This is happening because of the orOperator and I can not see any andOr or something similar.

So e.g. if I have "John Smith" inside my database, I can find him by querying either "John" , "Smith" , "John Smith" (just as in facebook for example)

Edit:

String queryx[] = searchQuery.split(" ");
for(String q : queryx) {
    criteria.orOperator(Criteria.where("firstname").regex(searchQuery),Criteria.where("lastname").regex(q));
}

Shows me the results, but it gives the following error inside my console:

  Due to limitations of the com.mongodb.BasicDBObject, you can't add a second '$or' expression specified as '$or : [ { "firstname" : { "$regex" : "john smith"}} , { "lastname" : { "$regex" : "smith"}}]'. Criteria already contains '$or : [ { "firstname" : { "$regex" : "john smith"}} , { "lastname" : { "$regex" : "john"}}]'.

Edit2:

String queryx[] = searchQuery.split(" ");
   ArrayList<Criteria> orOperators = new ArrayList<Criteria>();
for(String q : queryx) {
    Criteria criteria = new Criteria();
    criteria.orOperator(Criteria.where("firstname").regex(searchQuery),Criteria.where("lastname").regex(q));
    orOperators.add(criteria);
}

Criteria [] orArray = orOperators.toArray(new Criteria[orOperators.size()]);
Criteria c = Criteria.where("firstname").regex(searchQuery);
c.orOperator(orArray);

Query query = new Query(c).limit(limit);
return mongoOperations.find(query, User.class);

Edit 3:

String queryx[] = searchQuery.split(" ");
ArrayList<Criteria> cr = new ArrayList<Criteria>();
for (String q : queryx) {
    Criteria criteria = new Criteria();
    criteria.orOperator(Criteria.where("firstname").regex(q),
            Criteria.where("lastname").regex(q));
    cr.add(criteria);
}

Query query = new Query();
for (Criteria cri : cr) {
    query.addCriteria(cri); //this is the problem
}

return mongoOperations.find(query, User.class);

Error:

 Due to limitations of the com.mongodb.BasicDBObject, you can't add a second 'null' criteria. Query already contains '{ "$or" : [ { "firstname" : { "$regex" : "john smith"}} , { "lastname" : { "$regex" : "john"}}]}'.
like image 897
Moody Avatar asked Nov 18 '25 22:11

Moody


1 Answers

To search for firstname AND lastname you can easily do this:

String queryx[] = searchQuery.split(" ");
ArrayList<Criteria> cr = new ArrayList<Criteria>();
for (String q : queryx) {
    Criteria fCriteria = Criteria.where("firstname").regex(q);
    cr.add(fCriteria);
    Criteria lCriteria = Criteria.where("lastname").regex(q);
    cr.add(lCriteria);
}
Criteria c = cr.remove(0);
Criteria [] orArray = orOperators.toArray(new Criteria[orOperators.size()]);
c.orOperator(orArray);
query.addCriteria(c); //this is the problem
return mongoOperations.find(query, User.class);
like image 87
pinturic Avatar answered Nov 21 '25 14:11

pinturic



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!