Insert DBObject into MongoDB using Spring Data - mongodb

I tried to insert the following DBObject into MongoDB using Spring Data:
BasicDBObject document = new BasicDBObject();
document.put("country", "us");
document.put("city", "NY");
mongoTemplate.insert(document);
where mongoTemplate is my Spring template (org.springframework.data.mongodb.core.MongoTemplate).
When executing, I get:
Caused by: org.springframework.dao.InvalidDataAccessApiUsageException: No Persitent Entity information found for the class com.mongodb.BasicDBObject
at org.springframework.data.mongodb.core.MongoTemplate.determineCollectionName(MongoTemplate.java:1747)
at org.springframework.data.mongodb.core.MongoTemplate.determineEntityCollectionName(MongoTemplate.java:1732)
at org.springframework.data.mongodb.core.MongoTemplate.insert(MongoTemplate.java:658)
My JSON would be dynamic at the end. So any idea how to provide these entity information dynamically ?
Or is there another way to insert raw JSON into Mongodb through Spring Data ?

You are confusing spring-data with normal mongo persistence using the java driver.
If you want to persist data to mongoDB directly using the java driver then you would use the BasicDBObject like you have shown except that you would not use the mongoTemaplate class to persist but rather the MongoClient class. So it would look like this:
MongoClient mongoClient = new MongoClient( "localhost" , 27017 );
DB db = mongoClient.getDB( "mydb" );
BasicDBObject o = new BasicDBObject();
o.set......
coll.insert(o);
But if you are trying to persist a document using spring-data, then you need to create a java class to represent your document (eg: Person) and annotate this class with #Document(collection="person") and then use the mongoTemplate (which is a spring-data specific class to persist this entity. This is very similar to using JPA/hibernate.
So it would look something like this
#Document(collection="person")
public class Person {
private String fisrtName;
....
Relevant getters and setters
}
And then the persistence
Person p = new Person();
p.setFirstName("foo");
p.setLastName("bar");
....
mongoTemplate.save(p);

Another way to do this is to directly access the DBCollection object via the MongoTemplate:
DBObject company = new BasicDBObject();
...
DBCollection collection = mongoTemplate.getCollection("company");
collection.insert(company);

Another way to do it
Import statements
import com.mongodb.client.MongoCollection;
import org.bson.Document;
import org.springframework.data.mongodb.core.MongoTemplate;
Member Variables
#Autowired MongoTemplate mongoTemplate;
MongoCollection<Document> collection;
#PostConstruct
public void init(){
collection = mongoTemplate.getCollection("company");
}
And then, the method
public void insertRawData(){
Document company = new Document(new HashMap()); // If you have to insert a hashMap
// otherwise you can add one-by-one using company.put("foo","bar")
collection.insertOne(company);
}

Related

$or operator with multiple expressions and multiple fields in an expression using Spring Data Reactive MonogoDB

In MongoDB, I can use $or[{key1:'value11', key2:'value12'}, {key1:'value21', key2:'value22'}, {key1:'value31', key2:'value32'}, ...] to query several documents which matches at least one of the expressions in the $or operator. Then how the thing can be done using Spring Data Reactive MonogoDB?
In particular, I define a entity class as:
#Document
public class MyDocument
{
#Id
private String id;
private String field1;
private String field2;
}
And then, the repository interface for the entity:
public interface MyDocumentRepository extends ReactiveMongoRepository<MyDocument, String>
The question now is how to define a method in MyDocumentRepository to query the documents with field1 and field2:
There seems no proper keywords to create a query method (findAllBy(field1AndField2)In???)
If using JSON-based Query Methods, I really do know how to complete the Cloze test...
#Query("{$or:[(:fields)]}
Flux<MyDocument> findAllBy????(Flux<???> fields)
Spring Data MongoDB has support for ReactiveMongoTemplate. In a repository, you can use this as a connection to MongoDB which can be used with #Autowire.
In ReactiveMongoTemplate you can create Criteria with and and or operation like
Query query = new Query();
query.addCriteria(
new Criteria().andOperator(
Criteria.where("field1").exists(true),
Criteria.where("field1").ne(false)
)
);
and this can be passed to MongoDB with the before created instance of ReactiveMongoTemplate
Flux<Foo> result = reactiveMongoTemplate.find(query, Foo.class);
Documentation for use of configuration of ReactiveMongoTemplate if needed can be found here

How to update field type in a document using Java MongoDB Reactive driver?

I have a document in MongoDB collection:
{
"fOne": "strValue",
"fTwo": {
"nestedFArray": [
{
"dateF": "2010-01-02T13:00:01"
},
{
"dateF": "2010-01-02T13:00:01"
}
],
"nestedFObject": {
"anotherDateF": "2010-01-02T13:00:01"
}
}
}
fields fTwo.nestedFArray[0].dateF, fTwo.nestedFArray[1].dateF, fTwo.nestedFObject.anotherDateF stored as a string type; How to replace types of this field with DateTime type when I have a json paths for fields using java mongo reactive driver?
$.fTwo.nestedFArray[0].dateF
$.fTwo.nestedFArray[1].dateF
$.fTwo.nestedFObject.anotherDateF
The query is an aggregation which converts the string date values to Date values. The result list from the aggregation is iterated and the modified documents are updated in a for-loop. Note the code assumes a collection with multiple input documents.
The Java Code:
import org.bson.Document;
import org.bson.conversions.Bson;
import org.bson.types.ObjectId;
import com.mongodb.reactivestreams.client.MongoClient;
import com.mongodb.reactivestreams.client.MongoClients;
import com.mongodb.reactivestreams.client.MongoCollection;
import com.mongodb.reactivestreams.client.MongoDatabase;
import com.mongodb.client.model.UpdateOneModel;
import com.mongodb.client.model.WriteModel;
import com.mongodb.bulk.BulkWriteResult;
import java.util.*;
public class MongoReact {
public static void main(String[] args)
throws Throwable {
MongoClient mongoClient = MongoClients.create();
MongoDatabase db = mongoClient.getDatabase("testdb");
MongoCollection<Document> collection = db.getCollection("test");
List<Bson> pipeline =
Arrays.asList(
new Document("$project",
new Document("fTwo.nestedFObject.anotherDateF",
new Document("$dateFromString",
new Document("dateString", "$fTwo.nestedFObject.anotherDateF")
)
)
.append("fTwo.nestedFArray",
new Document("$map",
new Document("input", "$fTwo.nestedFArray")
.append("as", "e")
.append("in",
new Document("dateF",
new Document("$dateFromString",
new Document("dateString", "$$e.dateF")
)
)
)
)
)
)
);
SubscriberHelpers.ObservableSubscriber<Document> querySubscriber =
new SubscriberHelpers.ObservableSubscriber<Document>();
collection.aggregate(pipeline).subscribe(querySubscriber);
querySubscriber.await();
List<Document> resultDocs = querySubscriber.getReceived();
List<WriteModel<Document>> updates = new ArrayList<>();
for (Document doc : resultDocs) {
ObjectId id = (ObjectId) doc.get("_id");
Document f2Doc = (Document) doc.get("fTwo");
updates.add(new UpdateOneModel<Document>(
new Document("_id", id),
new Document("$set", new Document("fTwo", f2Doc))
));
}
SubscriberHelpers.PrintSubscriber<BulkWriteResult> updateSubscriber =
new SubscriberHelpers.PrintSubscriber<BulkWriteResult>("Bulk write results: %s");
collection.bulkWrite(updates).subscribe(updateSubscriber);
updateSubscriber.await();
mongoClient.close();
}
}
NOTES:
The SubscriberHelpers is a utility class used in the above code. I have used it as shown in the Quick Tour (with examples) section of the Reactive Streams Java Driver page.
The source code for the SubscriberHelpers.java can be found at: mongo-java-driver-reactivestreams/examples/tour/src/main/tour/. The usage of the code and examples source code is also there - you can compile and use it.
I have used MongoDB server 4.0, Java SE 8, MongoDB Reactive Streams driver 1.10.0 and mongodb-driver-async 3.9.0 to work with the above code.

How to fetch mongo db data and pass in jmeter request

I have one post call that response is like this.
{
"status":0,
"message":"Prescription Created",
"jsonResponse":{},
"cid":"C5975K",
"pid":"Rx5975K-175A",
"prescriptionSource":"GO_RX_CTO",
"imageStatus":[]
}
By taking this pid , I have to do the query for the one more record. For example:
db.order.find({"pid":"Rx5975K-175A"})
and the result of this query should pass in one more jmeter request.
I have used MongoDB Script (DEPRECATED) .. But this wont work as its deprecated ..
Tried with JSR223 Sampler, but its not working in new jmeter 3.2
import com.mongodb.*
import com.mongodb.BasicDBObject
MongoCredential coreCredential = MongoCredential.createCredential("${mongodb_user}", "${mongodb_database}", "${mongodb_password}".toCharArray());
MongoClient coreMongoClient = new MongoClient(new ServerAddress("${mongodb_server}", 13017), Arrays.asList(coreCredential));
DB coreDB = coreMongoClient.getDB("${mongodb_database}");
DBCollection coll = coreDB.getCollection("order");
coll.find();
You have to find your result based on "pid" and you are nowhere passing it. After finding you collection you need to create a query and searching using that query.
import com.mongodb.*
import com.mongodb.BasicDBObject
MongoCredential coreCredential = MongoCredential.createCredential("${mongodb_user}", "${mongodb_database}", "${mongodb_password}".toCharArray());
MongoClient coreMongoClient = new MongoClient(new ServerAddress("${mongodb_server}", 13017), Arrays.asList(coreCredential));
DB coreDB = coreMongoClient.getDB("${mongodb_database}");
DBCollection coll = coreDB.getCollection("order");
BasicDBObject query = new BasicDBObject();
query.put("pid", "Rx5975K-175A");
DBObject getData= coll.findOne(query);
and this will give you the desire result

getting a pojo from a mongo doc using morphia

Please can someone explain me this code using to create a pojo from a mongo doc? Is it necessary to create a class which contain database fields+getters and setters?
Morphia morphia=....;
MongoClient mongoClient = ............;
DB db = mongoClient.getDB( "contact" );
String contactId=.....;
//load the object from the collection
BasicDBObject idObj=new BasicDBObject ("_id", new ObjectId(contactId));
BasicDBObject obj=(BasicDBObject db.getCollection("personnal").findOne(idObj);
Contact contacy=morphia.fromDBObject(Contact.class,obj);
What value must be afect to contactId?
Why aren't you using Morphia's API if you have it available?
datastore.get(Contact.class, new ObjectId(contactId));

springdata MongoDB batch inserts with continueOnError option

MongoDB supports a continueOnError option so that batch insert continues even if there is a failure in a single document insertion.
Is there a way to achieve this using spring-data version 1.3.3.RELEASE. I am using the MongoOperations class and I don't see an API that allows me to do this.
Thanks!!
You should set this through the writeConcern options for MongoTemplate
mongoTemplate.setWriteConcern(
new WriteConcern(<Your options>).continueOnErrorForInsert(true));
Alternately there should be a constructor for for WriteConcern that does this as well.
More specifically as a usage, I set a Bean in a config class:
public #Bean
MongoTemplate mongoTemplate() throws Exception {
MongoTemplate mongoTemplate = new MongoTemplate(mongoDbFactory());
WriteConcern writeConcern = new WriteConcern(2);
writeConcern.continueOnErrorForInsert(true);
mongoTemplate.setWriteConcern(writeConcern);
return mongoTemplate;
}
And then later on, set up the operations:
MongoOperations mongoOperation = (MongoOperations) ctx.getBean("mongoTemplate");
Collection collection = new Collection() { ... }
mongoOperation.insert(collection,"collection"); // Uses the writeConcern options