Grails 3.1 - Can't find codec for domain class - mongodb

I am not able to convert domain class into Basic DB object.
Below is my code:
def update_val
class_object.class.withNewSession { MongoCodecSession m ->
update_val = m.pendingUpdates.find {
it.key.name == d.class.getName()
}.value[0]nativeEntry.regions[0]."${instance.getDbKey()}"[0]
}
On below findOneAndUpdate function, I am getting error: "Can't find a codec for class class.domain". updateVal is returning as Domain Class object.
ClassName.class.findOneAndUpdate(new BasicDBObject(findVal), new BasicDBObject(updateval))
I am converting it from Grails 3.0 to Grails 3.1, here nativeEntry is returning as a domain class while in previous version, nativeEntry is returning as BasicDBObject.
Any solution?
I am using Grails 3.1 with gorm 5.0 and mongodb 3.4

I have resolved it. Add below solution to Application.yml
grails:
mongodb:
engine: mapping
It will convert MongoCodecSession to the previous MongoSession.
As in codecs, objects are no longer converted first to MongoDB Document objects and then to Groovy objects, instead the driver reads Groovy objects directly from the JSON stream at the driver level, which is far more efficient than the previous MongoSession.

Related

How to get ROUTE_PATTERN from request in play 2.6 scala

I've extracted ROUTE_PATTERN in play 2.5 with:
request.tags.get("ROUTE_PATTERN")
now I updated play 2.6 and this code doesn't work anymore. I read play documentation here:
What’s new in Play 2.6
I tried:
object Attrs {
val RoutePattern: TypedKey[String] = TypedKey("ROUTE_PATTERN")
}
request.attrs.get(Attrs.RoutePattern)
It always returns None. How I can get the RoutePattern of request in play 2.6?
From the 2.6 migration guide:
If you used any of the Router.Tags.* tags, you should change your code to use the new Router.Attrs.HandlerDef (Scala)....
This new attribute contains a HandlerDef object with all the information that is currently in the tags. The current tags all correspond to a field in the HandlerDef object....
The field in HandlerDef that corresponds to the old ROUTE_PATTERN tag is path:
import play.api.routing.{ HandlerDef, Router }
import play.api.mvc.RequestHeader
val handler = request.attrs(Router.Attrs.HandlerDef)
val routePattern = handler.path

Meteor Angular2 and external changed of Mongodb

I play around with a simple Meteor Angular 2 app which only read from database. I have another app which change the database. But when the database is changed, I got error on Meteor app.
Exception in queued task: EXCEPTION: Error in client/match.html:0:19
ORIGINAL EXCEPTION: TypeError: Cannot read property 'league' of undefined
ORIGINAL STACKTRACE:
TypeError: Cannot read property 'league' of undefined
at DebugAppView._View_MatchComponent0.detectChangesInternal (MatchComponent.template.js:101:59)
at DebugAppView.AppView.detectChanges (http://localhost:3001/packages/modules.js?hash=5bea6cc36ccb7076b2a2834b250a3c141ff0cd78:57326:14)
at DebugAppView.detectChanges (http://localhost:3001/packages/modules.js?hash=5bea6cc36ccb7076b2a2834b250a3c141ff0cd78:57415:44)
at DebugAppView.AppView.detectViewChildrenChanges (http://localhost:3001/packages/modules.js?hash=5bea6cc36ccb7076b2a2834b250a3c141ff0cd78:57346:34)
at DebugAppView._View_MatchesComponent1.detectChangesInternal (MatchesComponent.template.js:106:8)
at DebugAppView.AppView.detectChanges (http://localhost:3001/packages/modules.js?hash=5bea6cc36ccb7076b2a2834b250a3c141ff0cd78:57326:14)
at DebugAppView.detectChanges (http://localhost:3001/packages/modules.js?hash=5bea6cc36ccb7076b2a2834b250a3c141ff0cd78:57415:44)
at DebugAppView.AppView.detectContentChildrenChanges (http://localhost:3001/packages/modules.js?hash=5bea6cc36ccb7076b2a2834b250a3c141ff0cd78:57341:37)
at DebugAppView._View_MatchesComponent0.detectChangesInternal (MatchesComponent.template.js:65:8)
at DebugAppView.AppView.detectChanges (http://localhost:3001/packages/modules.js?hash=5bea6cc36ccb7076b2a2834b250a3c141ff0cd78:57326:14)
ERROR CONTEXT:
[object Object]
I'm using autopublish which collection:
import {Mongo} from 'meteor/mongo';
export let MatchCollection = new Mongo.Collection('matches');
And angular component:
export class MatchesComponent
{
matches;
constructor() {
this.matches = MatchCollection.find();
}
}
Note: Meteor Blaze version works well. And I'm new to Meteor Angular2.
Thanks for all help.
I guess you are using *ngFor.
You can use this more stable way
this.matches = MatchCollection.find().fetch();
MatchCollection.find(); returns Mongo.Cursor<any>;
MatchCollection.find().fetch(); returns Array<any>
Weird, the bug should be already fixed...
It looks like the external change removed a property names league within the document, which your angular2 view uses somewhere.
Have a look at the document via meteor mongo to see how the document looks like in the storage before and after it has been modified by the external process.

Elasticsearch scala elastic4s settings from property file

is there a way how to pass settings to elastic4s from property file? The following way works but it is not flexible in munltienvironment:
val settings = ImmutableSettings.settingsBuilder().put("cluster.name","elasticsearch").build()
val client = ElasticClient.remote(settings, "154.86.209.242" -> 9300, "153.89.219.241" -> 9300)
I tried java configuration file elasticsearch.yaml as mantioned in java doc but that doesn't work.
Any suggestion here?
You can do this using the same method you would for the Java client. The ImmutableSettings is a Java Client class not something that is specific to elastic4s.
To load your properties file from the classpath, eg if you have something in src/main/resources/com/package/settings.props
ImmutableSettings.settingsBuilder().loadFromClasspath("/com/package/mysettings.yaml")
Or if you want to load from an input stream:
ImmutableSettings.settingsBuilder().loadFromStream(myinputstream)
There are other methods too, just check out the ImmutableSettings.settingsBuilder object.

Apply default mapping to mock Mongo domains in Grails unit test

I've started using the new mocking support in grails-datastore-gorm-mongodb. My app defaults domain mappings to use references when persisting relationships to mongodb. I need to find a way to get the mocked mongo to do the same thing. How do I apply the same default mapping in a unit test?
In Config.groovy, it looks like this:
// configure mongo to use dbrefs:
grails.mongo.default.mapping = {
'*'(reference: true)
}
Here's a sample of code that I currently use:
import spock.lang.*
import grails.test.mixin.mongodb.MongoDbTestMixin
import com.github.fakemongo.Fongo
#Mixin([MongoDbTestMixin])
class MySpec extends Specification {
def setup() {
mongoDomain(new Fongo("test").mongo, [ MyDomain ])
new MyDomain(name: 'domain').save(validate: false, flush: true)
}
}
How do I apply that config to this test code?
I'm using Grails 2.3.9 and mongodb 3.0.1 plugin.
Looks like MongoDbTestMixin offers a few flavors of the mongoDomain method:
mongoDomain(Mongo mongo, Collection<Class> persistentClasses) - Sets up a GORM for MongoDB domain for the given Mongo instance and domain classes
mongoDomain(Map config, Collection<Class> persistentClasses) - Sets up a GORM for MongoDB domain for the given configuration and domain classes
The 2nd option allows to pass a configuration map which allows to configure mongo to use dbrefs (otherwise an empty configuration is used, see MongoDbDataStoreSpringInitializer ). However this method does not allow you to pass the Fongo instance.
You can try to:
Ask the Grails team to add a method which combines both options (pull request?)
Extend MongoDbTestMixin or create your own mixin

Partial Update on MongoDB Error

I'm trying to have a partial update on one of my documents in MongoDB, using C# driver. I've followed the following posts:
How do you update multiple field using Update.Set in MongoDB using official c# driver?
Partial mongodb upsert using the c# driver?
I get the following error when trying to do the update: "Only classes can be mapped currently", in the AutoMapper CreateClassMap class, the type received is System.Collections.Generic.IEnumerable`1[[MongoDB.Bson.BsonElement, MongoDB.Bson]], where it cannot be an interface.
The code I'm using is:
public void UpdateObjectByFields<T>(int id, Dictionary<string, object> modifiedFields)
where T : class
{
var collection = m_MongoDatabase.GetCollection<T>();
var builder = new UpdateBuilder();
foreach (var modifiedField in modifiedFields)
{
builder.Set(modifiedField.Key, modifiedField.Value.ToString());
}
collection.Update(Query.EQ("_id", id), builder);
}
where the T type is a valid collection in the Mongo.
What am I doing wrong?
Thanks,
Nir
Got this to work, apparently I was using some old dlls for the C# driver.
Fixed it by using the dlls from here:
https://github.com/mongodb/mongo-csharp-driver/downloads
Thanks,
Nir.