I am trying to create this query from Java for MongoDB.
Do you know how can I construct it in java?
db.node.find({
connectedWithIds: { $in: [
ObjectId('56bca32fe74a987ad8724da1')
] }
})
I tried to use this:
ObjectId arr[] = {new ObjectId("5409ae2e2cdc31c5aa0ce0a5")};
BasicDBObject inQuery = new BasicDBObject("$in", arr);
BasicDBObject query = new BasicDBObject("connectedWithIds", inQuery);
but the results is below:
{ "connectedWithIds" : { "$in" : [ { "$oid" : "5409ae2e2cdc31c5aa0ce0a5"}]}}
and occurs this error:
error: {
"$err" : "Can't canonicalize query: BadValue cannot nest $ under $in",
"code" : 17287
}
I could overcome this error with the code below:
ArrayList<ObjectId> vals = new ArrayList<ObjectId>();
vals.add(objectId);
BasicDBObject inQuery = new BasicDBObject("$in", vals);
BasicDBObject query = new BasicDBObject("connectedWithIds", inQuery);
List<BasicDBObject> users = (List<BasicDBObject>) customQueryManager.executeQuery("node", query);
Related
I want to parse a java string to mongo DBObject or BasicDBObject as below.
List<DBObject> query = new ArrayList<DBObject>();
String allQry = "{ \"$match\" : { \"CUSTOMERID\" : { \"$gt\" : 10}}}, { \"$project\" : { \"CUSTOMERNAME\" : 1 , \"COUNTRY\" : 1 , \"CUSTOMERID\" : 1}},{ \"$sort\" : { \"COUNTRY\" : 1}}";
BasicDBObject dbobj = BasicDBObject.parse(allQry);
query.add(dbobj);
System.out.println("qqqquery : "+query);
Cursor aggCur = collection.aggregate(query, aggOpt);
After run above example codes, it outputs qqqquery : [{ "$match" : { "CUSTOMERID" : { "$gt" : 10}}}]. There are $match , $project and $sort in allQry. Why do not it includes $project and $sort in this query? It only includes $match, who can help to check this reason? Thanks.
Following this tutorial:
http://pingax.com/trick-convert-mongo-shell-query-equivalent-java-objects/
you could add all parts of your query like this:
MongoClient mongo = new MongoClient();
DB db = mongo.getDB("pingax");
DBCollection coll = db.getCollection("aggregationExample");
/*
MONGO SHELL : db.aggregationExample.aggregate(
{$match : {type : "local"}} ,
{$project : { department : 1 , amount : 1 }}
);
*/
DBObject match = new BasicDBObject("$match", new BasicDBObject("type", "local"));
DBObject project = new BasicDBObject("$project", new BasicDBObject("department", 1).append("amount", 1));
AggregationOutput output = coll.aggregate(match,project,group,sort);
Related:
How to find documents matching multiple criteria
Executing Mongo like Query (JSON)through Java
when i use this query on mongo shell
db.matchgrup.aggregate([{$match:{ "longitude" : {"$gte":73.8172198689148,"$lte":73.8200133489148}, "latitude" :{"$gte":19.98591316489416,"$lte":19.98870664489416} }},{ "$group": {"_id":null, "band_4" : { "$avg" : "$band_4"},"band_8":{"$avg":"$band_8"} } }])
it return
{ "_id" : null, "band_4" : 1578.8266666666666, "band_8" : 2649.0155555555557 }
but when i used mongo java driver for same query
searchQuery1 =new BasicDBObject("longitude", new BasicDBObject("$gte", X.doubleValue()).append("$lte", px1.doubleValue()));
criteria.add(searchQuery1);
searchQuery2=new BasicDBObject("latitude", new BasicDBObject("$gte", py2.doubleValue()).append("$lte", Y.doubleValue() ));
criteria.add(searchQuery2);
query2=new BasicDBObject("$and",criteria);
group1 = new BasicDBObject();
group1.put("_id", null);
group1.put("band_4", new BasicDBObject("$avg", "$band_4"));
group1.put("band_8", new BasicDBObject("$avg", "$band_8"));
output = coll.aggregate(
new BasicDBObject("$match",query2),
new BasicDBObject("$group",group1));
for (DBObject doc : output.results()) {
band4=(Double)doc.get("band_4");
band8=(Double)doc.get("band_8");
}
and it doesn't retuen any value and doesnt goes inside of for loop of doc
can anybody help me out what m doing wrong
I have a collection containing contacts and each contact document has a firstName and lastName attribute.
Now I want to query the database by using Java and the MongoDb Java driver in version 3.2.
I try to find a contact with a concatenated firstName + lastName. My query looks like the following for the MongoDb shell:
db.getCollection('contacts').aggregate(
{
$project:{
fullName:{
$concat: [ "$firstName", " ", "$lastName" ]
}
}
},
{
$match:{
fullName:"John Doe"
}
}
);
Now I tried to get my head around the MongoDb Java driver to get the same accomplished in Java:
AggregateIterable<Document> documents = contactUserCollection.aggregate(Arrays.asList(project(computed("fullName", "$firstName $lastName")), match(eq("fullName", firstLastName))));
But this isn't working.
Does someone have an idea how I could accomplish this?
Thank you
You could try the following:
/*
MONGO SHELL :
var pipeline = [
{
"$project": {
"otherfieldsA": 1,
"otherfieldsB": 1,
"otherfieldsC": 1,
"fullName": {
"$concat": [ "$fistName", " ", "$lastName" ]
}
}
}
{
"$match": { "fullName": "John Doe" }
}
];
db.contacts.aggregate(pipeline);
*/
public class JavaAggregation {
public static void main(String args[]) throws UnknownHostException {
MongoClient mongo = new MongoClient();
DB db = mongo.getDB("test");
DBCollection coll = db.getCollection("contacts");
// create the pipeline operations, build the $project operations
BasicDBList concatenate = new BasicDBList();
concatenate.add("$firstName");
concatenate.add(" ");
concatenate.add("$lastName");
DBObject fullName = new BasicDBObject("$concat", concatenate);
DBObject fields = new BasicDBObject("otherfieldsA", 1);
fields.put("otherfieldsB", 1);
fields.put("otherfieldsC", 1);
fields.put("fullName", fullName);
DBObject project = new BasicDBObject("$project", fields);
// create the $match operator
DBObject match = new BasicDBObject("$match",
new BasicDBObject("fullName", "John Doe")
);
AggregationOutput documents = coll.aggregate(match, project, group, sort);
for (DBObject result : documents.results()) {
System.out.println(result);
}
}
}
I am having hard time converting the below nested mongodb query with $and and $or to java/groovy
db.personSync.find({
$and:[
{$or:[
{ "name" : { "$regex" : "(?i)^test1" , "$options" : "i"}},
{ "name" : { "$regex" : "(?i)^dev" , "$options" : "i"}}
]},
{ "email" : { "$regex" : "(?i)^test" , "$options" : "i"}}
]}
);
]}
);
I was able to write code for $or part as below
def mongoCritera = new ArrayList<BasicDBObject>();
mongoCritera.add('name', java.util.regex.Pattern.compile('(?i)^test1`'))
mongoCritera.add('name', java.util.regex.Pattern.compile('(?i)^dev`'))
def query = new BasicDBObject("\$or", mongoCritera);
collection.find(query);
But I couldn't accommodate $and logic, can someone please help me with this?
def andCritera = new ArrayList<BasicDBObject>();
def orCritera1= new ArrayList<BasicDBObject>();
orCritera1.add('name', java.util.regex.Pattern.compile('(?i)^test1`'))
orCritera1.add('name', java.util.regex.Pattern.compile('(?i)^dev`'))
def orQuery1 = new BasicDBObject("\$or", orCritera1);
andCritera.add(orQuery1)
def orCritera2= new ArrayList<BasicDBObject>();
orCritera1.add('email', java.util.regex.Pattern.compile('(?i)^test`'))
def orQuery2 = new BasicDBObject("\$or", orCritera2);
andCritera.add(orQuery2)
def query = new BasicDBObject("\$and", andCritera);
def cursor = collection.find(query)
while (cursor.hasNext()) {
println 'person '+ cursor.next();
}
As per my understanding you wants to write a query fetch
name should be start from (test1 or dev) case insensitive and email start with test (also case insensitive) ? if yes try this
db.personSync.find({$and:[{name:{"$regex":"^[test|dev]","$options":"i"}},{email:{"$regex":"^test1","$options":"i"}}]})
public static void main(String[] args) {
MongoClient c = new MongoClient();
MongoDatabase db = c.getDatabase("test");
MongoCollection<Document> collection = db.getCollection("so3");
ArrayList<Document> andCritera = new ArrayList<Document>();
ArrayList<Document> orCritera1= new ArrayList<Document>();
orCritera1.add(new Document("name", java.util.regex.Pattern.compile("(?i)^[test1|dev]")));
Document orQuery1 = new Document("$or", orCritera1);
andCritera.add(orQuery1);
andCritera.add(new Document("email", java.util.regex.Pattern.compile("(?i)^test")));
Document query = new Document("$and", andCritera);
ArrayList<Document> docList = new ArrayList<Document>();
collection.find(query).into(docList);
for(Document doc:docList){
System.out.println(doc);
}
}
I validated this is working fine :)
In the following query , I'm doing addition to a field (This field having ISO date as value) then extracting hour from that field, then group by on hour
db.campaigns.aggregate([
{$group : { _id: {$hour:{$add:['$time', 19800000]}}}}
])
Sample record of the collection
db.campaigns.findOne()
{
"_id" : ObjectId("53c7afdab92be74745af9068"),
"time" : ISODate("2013-03-08T12:25:24.973Z"),
"type" : "annoying",
"PINGS" : 143
}
The above one is working fine in Mongo shell,
I'm trying write this query in Java
Here is my partial Java code
DBObject group2Fields = new BasicDBObject();
group2Fields.put("hour", new BasicDBObject("$hour", new BasicDBObject("$add",new BasicDBObject("time",19800000))));
DBObject group2 = new BasicDBObject("_id", group2Fields);
DBObject secondGroup = new BasicDBObject("$group", group2);
I'm getting "errmsg" : "exception: field inclusion is not allowed inside of $expressions"
try this:
DBObject group2Fields = new BasicDBObject();
BasicDBList addObjects = new BasicDBList();
addObjects.add("$time");
addObjects.add(19800000);
group2Fields.put("$hour", new BasicDBObject("$add", addObjects));
DBObject group2 = new BasicDBObject("_id", group2Fields);
DBObject secondGroup = new BasicDBObject("$group", group2);
Nesting calls in your code generally helps you to "visualise" the structure that you want:
BasicDBList addArgs = new BasicDBList();
addArgs.add("$time");
addArgs.add(19800000);
DBObject group = new BasicDBObject("$group",
new BasicDBObject("_id",
new BasicDBObject("$hour",
new BasicDBObject("$add", addArgs)
)
)
);
Which of course produces a group variable that serializes like so:
{ "$group" : { "_id" : { "$hour" : { "$add" : [ "$time" , 19800000]}}}}