Java MongoDB search for value in multiple fields - java

i have a java method
public List<Project> tagSearch(String searchCriteria){
Query query = new Query();
return mongoTemplate.find(query.addCriteria(Criteria.where("projectTag")
.regex(searchCriteria,"i")), Project.class, COLLECTION_NAME);
}
here it is searching the searchCriteria value in the field projectTag. I want to search for that value in multiple fields. for example another field projectName
appreciate your assistance.

Use orOperator
You can use as many criteria in orOperator. Then it will look like this :
Query query = new Query();
Criteria criteria1 = new Criteria().where("projectTag").regex(searchCriteria, "i");
Criteria criteria2 = new Criteria().where("projectName").regex(searchCriteria, "i");
query.addCriteria(new Criteria().orOperator(c1,c2));
return mongoTemplate.find(query, Project.class, COLLECTION_NAME);

You can use below code
final Criteria criteria = new Criteria();
criteria.orOperator(Criteria.where("projectTag").regex(searchCriteria, "i"),
Criteria.where("projectName").regex(searchCriteria, "i"));
final Query query = new Query(criteria);
final List<Project> projectEntities = mongoTemplate.find(query, Project.class);

Related

How to perform aggregation in mongodb using Java by setting query object instead of matchoperation?

Below is the code:
Criteria criteria=null;
criteria = new Criteria().andOperator(Criteria.where("OwnerId").is(ownerId), Criteria.where("Environment").is(env), Criteria.where("ServiceName").in(api));
MatchOperation matchOp= Aggregation.match(criteria);
ProjectionOperation projOp= Aggregation.project("SubServices").andInclude("ServerGroupName").andInclude("NodeName").andInclude("ServiceVersion")
.andExclude("_id");
Aggregation aggr = Aggregation.newAggregation(matchOp, projOp);
AggregationResults<Document> aggregate = mongoOperations.aggregate(aggr, "CNF_SERVICE",Document.class,"config",env);
The above code works fine. However, I need to make below changes in order to generate criteria dynamically:
Criteria criteria=new Criteria();
Query query= new Query();
if(ownerId!=null && ownerId>0) {
query.addCriteria(criteria.andOperator(Criteria.where("OwnerId").is(ownerId)));
}
if(env!=null) {
query.addCriteria(criteria.andOperator(Criteria.where("Environment").is(env)));
}
if(api!=null) {
query.addCriteria(criteria.andOperator(Criteria.where("ServiceName").in(api)));
}
MatchOperation matchOp= Aggregation.match("How to set the query here?");
ProjectionOperation projOp= Aggregation.project("SubServices").andInclude("ServerGroupName").andInclude("NodeName").andInclude("ServiceVersion")
.andExclude("_id");
Aggregation aggr = Aggregation.newAggregation(matchOp, projOp);
AggregationResults<Document> aggregate = mongoOperations.aggregate(aggr, "CNF_SERVICE",Document.class,"config",env);
I need to set the query to criteria and apply it to the match operation. How to achieve this?
Instead of Match Operation you can achieve like below code:
Hope, it will helpful
Criteria criteria=new Criteria();
Query query= new Query(); query.addCriteria(criteria.andOperator(Criteria.where("OwnerId").is(ownerId))); query.fields().include("SubServices"); query.fields().include("ServerGroupName"); query.fields().exclude("_id");
MongoTemplate.find(query, Map.Class, collectionName);

Dynamic JPA criteria builder

I am using Spring boot JPA to below execute below query
select DELTA_TYPE,OPERATION_ID,COUNT(*) from ACTIVE_DISCREPANCIES ad group by DELTA_TYPE,OPERATION_ID
DELTA_TYPE,OPERATION_ID, etc may come from external system, in repository class I tried to execute native query
#Query(value="select OPERATION_ID,DELTA_TYPE,count(*) from ACTIVE_DISCREPANCIES ad group by ?1",nativeQuery = true)
public List<Object[]> groupByQuery(#Param("reconType") String recGroupColumns);
where recGroupColumns="DELTA_TYPE,OPERATION_ID" but didnt work as #param will split ','
Second option for me was criteria query
public List<Object[]> getReconGroupList() {
String recGroupColumns = "OPERATION_ID,DELTA_TYPE";
String[] arrStr = recGroupColumns.split(",");
CriteriaBuilder criteriaBuilder = entityManager.getCriteriaBuilder();
CriteriaQuery<Object[]> query = criteriaBuilder.createQuery(Object[].class);
Root<ActiveDiscrepancies> adr = query.from(ActiveDiscrepancies.class);
query.groupBy(adr.get("operationId"), adr.get("deltaType"));
// query.groupBy(adr.get("deltaType"));
query.multiselect(adr.get("operationId"), adr.get("deltaType"), criteriaBuilder.count(adr));
TypedQuery<Object[]> typedQuery = entityManager.createQuery(query);
List<Object[]> resultList = typedQuery.getResultList();
return resultList;
}
Here how can I pass groupBy and multiselect dynamically?
Using projections we can solve this scenario, below is the code
Criteria criteria = getSession().createCriteria(ActiveDiscrepancies.class);
ProjectionList projectionList = Projections.projectionList();
for(String str : colList) {
projectionList.add(Projections.groupProperty(str));
}
projectionList.add(Projections.rowCount());
criteria.setProjection(projectionList);
List results = criteria.list();
getSession().close();

Want to create dynamic mongo query to accept the DTO fields

I am creating a REST service using springboot and MONGO as database.
I have a StudentDTO class with the following fields :
Class StudentDTO{
#Id
int s_no;
String name;
String dept;
int dept_no;
String course;
//getter and setters
}
I have some criteria on which i need to fetch the data. These criteria may vary. Below are some example :
1. Can fetch data on name, dept
2. Can fetch data on name, id
3. May want data on name, dept and course. etc
There is no fixed combination of criteria on which I can build my query.
One of the solution which is not appropriate i try to write is :
Query query = new Query();
Criteria criteria = new Criteria().andOperator(
Criteria.where("id").is(Integer.parseInt(dto.getId()),
Criteria.where("name").is(dto.getName()),
Criteria.where("dept").exists(true).is(dto.getDept()),
Criteria.where("dept_no").is(dto.getDept_no()),
Criteria.where("course").is(dto.getSource()));
query.addCriteria(criteria);
List<StudentDTO> recordsList = mongoTemplate.find(query, StudentDTO.class, "student_collection");
In the above solution there is no accommodation for the scenario is any of the field is missing.
To check weather attribute exist or not i tried using the below query :
Criteria.where("id").exist(true).is(Integer.parseInt(dto.getId());
but how i can add criteria over the DTO fields.
You can use below code. Use orOperator which accepts the array of criteria. Prepare the criteria values dynamically inside if statements and add the criteria array to or criteria.
Query query = new Query();
Criteria criteria = new Criteria();
List<Criteria> orCriterias = new ArrayList<>();
if( dto.getId() != null) {
orCriterias.add(Criteria.where("id").is(Integer.parseInt(dto.getId())));
}
... so on for other fields
criteria.orOperator(orCriterias.toArray(new Criteria[orCriterias.size()]));
query.addCriteria(criteria);
List<StudentDTO> recordsList = mongoTemplate.find(query, StudentDTO.class, "student_collection");

Mongo $or query inside $and using Java MongoOperations [duplicate]

Let´s see if somebody can help with this.
I want use Repository of Spring Data mongodb, and I want use Query annotation to filter the find by value A=10 or A=20
#Query("{A: 10, A:20}")
findById(int id);
Obiously "," try to make an AND, and I need an OR.
Any idea please?
Or if you are using a Criteria API
Criteria criteria = new Criteria();
criteria.orOperator(Criteria.where("A").is(10),Criteria.where("B").is(20));
Query query = new Query(criteria);
mongoOps.find(query, <Yourclass>.class, "collectionName");
I think this might work
#Query("{'$or':[ {'A':10}, {'B':20} ] }")
You can use Spring Data MongoDB like this:
Query query = new Query();
query.addCriteria(
Criteria.where("").orOperator(
Criteria.where("A").is(10),
Criteria.where("B").is(20)
)
);
mongoTemplate.find(query, YourClazz.class, "CollectionName");
In addition to helloJava answer, If you already have query with other criteria's you can add orOperation directly on query.addCriteria as below.
query.addCriteria(new Criteria().orOperator(Criteria.where("fieldA").is(value),
Criteria.where("fieldB").is(value2)));
You can use the $in operator in Spring Java:
Criteria criteria = Criteria.where("field").in(listOfOptions);
You can use the $in operator for that. I don't know Java Spring, but given your example, the Query part should look like:
#Query("{A: {$in: [10, 20]}}")
Use Spring's BasicQuery:
DBObject queryCondition = new BasicDBObject();
BasicDBList values = new BasicDBList();
values.add(new BasicDBObject("A", 10));
values.add(new BasicDBObject("B", 20));
queryCondition.put("$or", values);
Query query = new BasicQuery(queryCondition);
mongoTemplate.find(query, clazz);
Query query = new Query();
Criteria criteria = new Criteria();
criteria.orOperator(Criteria.where("category").is("your_Value_Category"),
Criteria.where("parentCategory").is("your_Value_ParentCategory"));
query.addCriteria(criteria);
mongoTemplate.find(query, YourPersistenceClass.class);
You can use Spring's Query structure:
Query query = new Query();
query.addCriteria(Criteria.where("id").is(10).orOperator(Criteria.where("id").is(20));
this.client.findOne(query, clazz);

Spring data mongo use OR in Query

Let´s see if somebody can help with this.
I want use Repository of Spring Data mongodb, and I want use Query annotation to filter the find by value A=10 or A=20
#Query("{A: 10, A:20}")
findById(int id);
Obiously "," try to make an AND, and I need an OR.
Any idea please?
Or if you are using a Criteria API
Criteria criteria = new Criteria();
criteria.orOperator(Criteria.where("A").is(10),Criteria.where("B").is(20));
Query query = new Query(criteria);
mongoOps.find(query, <Yourclass>.class, "collectionName");
I think this might work
#Query("{'$or':[ {'A':10}, {'B':20} ] }")
You can use Spring Data MongoDB like this:
Query query = new Query();
query.addCriteria(
Criteria.where("").orOperator(
Criteria.where("A").is(10),
Criteria.where("B").is(20)
)
);
mongoTemplate.find(query, YourClazz.class, "CollectionName");
In addition to helloJava answer, If you already have query with other criteria's you can add orOperation directly on query.addCriteria as below.
query.addCriteria(new Criteria().orOperator(Criteria.where("fieldA").is(value),
Criteria.where("fieldB").is(value2)));
You can use the $in operator in Spring Java:
Criteria criteria = Criteria.where("field").in(listOfOptions);
You can use the $in operator for that. I don't know Java Spring, but given your example, the Query part should look like:
#Query("{A: {$in: [10, 20]}}")
Use Spring's BasicQuery:
DBObject queryCondition = new BasicDBObject();
BasicDBList values = new BasicDBList();
values.add(new BasicDBObject("A", 10));
values.add(new BasicDBObject("B", 20));
queryCondition.put("$or", values);
Query query = new BasicQuery(queryCondition);
mongoTemplate.find(query, clazz);
Query query = new Query();
Criteria criteria = new Criteria();
criteria.orOperator(Criteria.where("category").is("your_Value_Category"),
Criteria.where("parentCategory").is("your_Value_ParentCategory"));
query.addCriteria(criteria);
mongoTemplate.find(query, YourPersistenceClass.class);
You can use Spring's Query structure:
Query query = new Query();
query.addCriteria(Criteria.where("id").is(10).orOperator(Criteria.where("id").is(20));
this.client.findOne(query, clazz);

Categories