Domain List fields in Grails 2.4.4 - grails

I'm upgrading a 2.3 app to 2.4.4 and I have several domains that use List fields similar to the following and I'm receiving an error as described here.
class Game {
List score
static hasMany = [ score: Integer ]
}
I'm assuming use of the above is the actual cause of the problem but I can't be sure because the error message doesn't point to a domain.
Is this type of list definition not good grails practice?
I get the error:
2014-10-31 16:26:32 ERROR [context.GrailsContextLoaderListener] Error initializing the pplication: Error creating bean with name 'transactionManagerPostProcessor':
....
Error creating bean with name 'sessionFactory': Invocation of init method failed; nested exception is org.hibernate.MappingException: Association references unmapped class: java.util.List
UPDATE
I found the domain and the problem associated with the error. Here's the problem domain and associated List. If I remove the List, the problem is corrected.
class Team {
List teamTourney
static hasMany = [ teamTourney: TeamTourney ]
}

For anyone that might receive this error in the future you can add
log4j = {
debug 'org.codehaus.groovy.grails.orm.hibernate.cfg'
}
to the config and it will tell you what class and property is causing the problem.

Is this type of list definition not good grails practice?
The code that you show there should be fine. See the project at https://github.com/jeffbrown/integerlist.

The problem was a List referencing an undefined field. Among the domains in my project was a type-o in the field name associated with a List. It would be nice if the error message pointed at the location of the error, a point also in this post.
Thanks, Scott.

Related

Laravel Nova: Query params empty for /nova-api/installations/relate-authorization in hasMany relationship

I have defined a HasMany relationsship in my Nova resource. Nova fires two requests when trying to load the children in the parent detail view:
1. GET /nova-api/childResources?viaResource=parentResources&viaResourceId=4711&viaRelationship=childResources&relationshipType=hasMany
-> This correctly returns the related records.
2. GET /nova-api/childResources/relate-authorization?viaResource=parentResources&viaResourceId=4711&viaRelationship=childResources&relationshipType=hasMany
-> This fails with a HTTP 500 returning Class name must be a valid object or a string.
Digging deeper into the underlying NovaRequest, I found out that all query params are gone inside the request. This is why viaResource cannot be used to instantiate a class and to above error occurs.
I have no idea, what could cause this.
Turned out, the problem originated from an incomplete nginx configuration. I wasn’t passing the query string to PHP.

Puzzling validation error after upgrading from Grails 2.2.5 to 4.0.11

A method which was working for a long time in Grails 2.2.5 has broken after moving to 4.0.11 with a validation error on saving, and the error is a puzzle to me. I have a domain class 'Decline' which has one of its properties 'user', which is of domain class user. As part of the save process I assign the currently logged in user to this property:
Decline decline = new Decline()
decline.policy = policy
decline.declineTime = new Date()
decline.field = field
decline.cause = reason
decline.user = User.getUser()
decline.save(flush:true)
This was working fine in 2.2.5 but now I get the following validation error:
Field error in object 'myapp.pei.Decline' on field 'user.userType': rejected value [DIRECT_CLIENT]; codes [myapp.User.userType.nullable.error.myapp.pei.Decline.user.userType,myapp.User.userType.nullable.error.user.userType,myapp.User.userType.nullable.error.userType,myapp.User.userType.nullable.error.myapp.UserType,myapp.User.userType.nullable.error,user.userType.nullable.error.myapp.pei.Decline.user.userType,user.userType.nullable.error.user.userType,user.userType.nullable.error.userType,user.userType.nullable.error.myapp.UserType,user.userType.nullable.error,myapp.User.userType.nullable.myapp.pei.Decline.user.userType,myapp.User.userType.nullable.user.userType,myapp.User.userType.nullable.userType,myapp.User.userType.nullable.myapp.UserType,myapp.User.userType.nullable,user.userType.nullable.myapp.pei.Decline.user.userType,user.userType.nullable.user.userType,user.userType.nullable.userType,user.userType.nullable.myapp.UserType,user.userType.nullable,nullable.myapp.pei.Decline.user.userType,nullable.user.userType,nullable.userType,nullable.myapp.UserType,nullable]; arguments [userType,class myapp.User]; default message [Property [{0}] of class [{1}] cannot be null]
There are two things which are puzzling about this. Firstly, and more importantly, this appears to be an error saving the User object. But why is it even trying to save the User object? I have assigned an existing User object which it should be using. Secondly, the specific error is 'rejected value [DIRECT_CLIENT]' for field 'user.userType', but the error message is that this field cannot be null. So it's rejecting a value but telling me it cannot be null! The value, incidentally, is of a UserType enum defined thus:
public enum UserType {
ADMIN_USER,ADMIN_OWNER_USER,SUPER_USER,BROKER,DIRECT_CLIENT
}
I wonder what change from version 2.2.5 to 4 (or maybe 3) could have caused this?
It seems there was some change in behaviour of deepValidate between Grails 2.x and 4.x which is causing this, although I don't see why validation of the associated User object should be failing when it can actually be saved OK separately. But what got me past this issue was to set the following in the mapping block for Decline:
user cascadeValidate: 'none'
This ensures that when the Decline object is saved it does not attempt to validate the User as well.

Grails Saving Object With Composite Key Throws Error

So, my team has been having multiple issues while upgrading our existing app from Grails 1.3.7 to 2.1.0. The latest headache occurs when trying to save a domain class object that has a composite key based on two other domain objects.
We are hanging Grails on a legacy database which we cannot readily change, so all of the domain classes have custom mappings to hook up with it. Below is a quick, slimmed down version of the domain classes in question.
Class Product {
Short prodKey
String name
static hasMany = [groupProduct: GroupProduct]
//Also includes mapping to legacy db and simple constraints
}
Class Group {
Short groupKey
String name
static hasMany =[ groupProduct: GroupProduct]
//This domain class has several other mappings and variables, but they are not relevant
}
Class GroupProduct {
Group group
Product product
Character indicator
static belongsTo = [Product,Group]
static mapping = {
id composite: ["group", "product"]
group lazy:false, column:"GROUP_KEY", joinTable:"GROUP"
product lazy:false, column:"PROD_KEY", joinTable:"PRODUCT"
version false
}
//Only constraint is indicator is Y or N
}
In the app a user is able to select multiple products for a group to turn on or off via a checkbox list. The parameters contain the groupKey and a list of all checked products. The controller gets an instance of the specified group and then a list of all Products. The products are matched against the list in the parameters, every time a match is found a GroupProduct object is made with the indicator set to 'Y', otherwise a GroupProduct object is made with the indicator set to 'N'.
Class GroupProductController{
//allowedMethods and other actions...
def update = {
def groupInstance = Group.get(params.GroupId)
def groupProducts= []
def products= Products.list()
products.each{
def indicator = ...//code to get value of check box for this Product. Returns either Y or N, works as expected
def groupProduct= new GroupProduct(group:groupInstance ,
product:it,
indicator: indicator)
groupProducts.add(groupProduct)
}
groupInstance.discard()
groupProducts.each{
it.save(failOnError: true, flush:true)//This line throws a DB2 SQL error. SQLCODE=-407
}
}
}
Resulting error is:
org.hibernate.util.JDBCExceptionReporter|DB2 SQL Error: SQLCODE=-407, SQLSTATE=23502, SQLERRMC= , DRIVER=3.50.152
org.codehaus.groovy.grails.orm.hibernate.events.PatchedDefaultFlushEventListener|Could not synchronize database state with session
org.hibernate.exception.ConstraintViolationException: could not update: [GroupProduct#component[group,product]{product=Product#1, group=Group#938926168}]
at com.controllers.ProductGroupController$_closure2_closure8.doCall(ProductGroupController.groovy:86)
at com.nationwide.nas.beam.controllers.ProductGroupController$_closure2.doCall(ProductGroupController.groovy:79)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:615)
at java.lang.Thread.run(Thread.java:722)
Caused by: com.ibm.db2.jcc.b.lm: DB2 SQL Error: SQLCODE=-407, SQLSTATE=23502, SQLERRMC= , DRIVER=3.50.152
at com.ibm.db2.jcc.b.wc.a(wc.java:575)
at com.ibm.db2.jcc.b.wc.a(wc.java:57)
at com.ibm.db2.jcc.b.wc.a(wc.java:126)
at com.ibm.db2.jcc.b.tk.b(tk.java:1593)
at com.ibm.db2.jcc.b.tk.c(tk.java:1576)
at com.ibm.db2.jcc.t4.db.k(db.java:353)
at com.ibm.db2.jcc.t4.db.a(db.java:59)
at com.ibm.db2.jcc.t4.t.a(t.java:50)
at com.ibm.db2.jcc.t4.tb.b(tb.java:200)
at com.ibm.db2.jcc.b.uk.Gb(uk.java:2355)
at com.ibm.db2.jcc.b.uk.e(uk.java:3129)
at com.ibm.db2.jcc.b.uk.zb(uk.java:568)
at com.ibm.db2.jcc.b.uk.executeUpdate(uk.java:551)
at org.apache.commons.dbcp.DelegatingPreparedStatement.executeUpdate(DelegatingPreparedStatement.java:105)
... 5 more
The error occurs when trying to save the GroupProduct objects. According to IBM the error code -407 is caused by AN UPDATE, INSERT, OR SET VALUE IS NULL, BUT THE OBJECT COLUMN column-name CANNOT CONTAIN NULL VALUES. However, none of the variables for the GroupProducts are actually null. The Group and Product instances are pulled straight from the database, which means they have already been validated and shouldn't have any constraint violations, and I can see that the indicator field is being set correctly.
There is also no problem when running this code under the original 1.3.7 version of the project. If anyone could shed some light on this I'd be very grateful. Thanks
After much debugging and hunting through code, I managed to find the issue. All of our domain classes extend an abstract base domain, which has a createdTimestamp and updatedTimestamp field. Before doing an insert we set both fields, and before doing an update we update the updatedTimestamp.
The issue was that when we were saving, the new object had a null createdTimestamp field, which was throwing the error. Added in code to check if the GroupProduct object we were making already existed, and if so set the new objects createdTimestamp field to the existing object's before saving. Now everything works as expected.
Its strange that Grails 1.3.7 did not have any issues with this code, though. Only thing I can figure is that it automatically associated the new objects with existing ones in the DB. Probably the strangest behavior change I've found during the upgrade process. Hope this helps anyone running into a similar issue.

org.springframework.dao.InvalidDataAccessApiUsageException when using grails dynamic finder

Using Grails i'm trying a dynamic finder like this one
Policy.findAllByResourceAndUser(resource,user)
But When i call this, grails raise this exception
Caused by: org.springframework.dao.InvalidDataAccessApiUsageException: object references
an unsaved transient instance - save the transient instance before flushing: gmedia.User;
nested exception is org.hibernate.TransientObjectException: object references an unsaved
transient instance - save the transient instance before flushing: gmedia.User
Do we need to save the parameter of the finder?
Where i'm wrong?
http://www.grails.org/DomainClass+Dynamic+Methods#findAllBy*
Policy.findAllByResourceAndUser(resource,user)
capital "B" in "By" is the first thing I see wrong? Is that a type on the question?
def res = new Resource(name:"resource name").save()
def user = new User(name:"My Name").save()
def policy = new Policy( user:user, resource:res, right: "right string").save()
println Policy.findAllByResourceAndUser(res,user)
not elegant, but you get the idea, there must be a problem in the way you are saving your objects
your user object will "never" get saved with that code... you have to specify values for all of you properties or define your constraints appropriately. I think you should review the documentation for Domain Objects in Grails because it appears there are fundamental problems in your approach see http://www.grails.org/GORM+-+Creating+a+domain+class
#Aaron Saunders
these are two domain class
class Resource{
static contraints={}
}
class User extends Resource{
String name
String password
String email
Date creationDate
Date lastModicationDate
}
class Policy{
Resource resource
User user
String right
static mapping={
user cascade:'all-delete-orpahn'
resource cascade:'all-delete-orpahn'
}
Maybe it a consequence of the inheritance between User and Resource
i faced the same issue today..i found the solution...there is a foreign key relation which is getting set as NULL.....so when it tries to save null it throws this exception..so make sure all the values are not null...else u may need to change the cascade definition in ur mapping xml..

Grails "not-null property references a null or transient value" exception on web flow

I'm getting "org.springframework.dao.DataIntegrityViolationException: not-null property references a null or transient value: A.b" exception on web flow in grails 1.1.2.
there is
class B {
...
static belongsTo = [a:A]
...
}
and
class A {
...
static hasMany = [b:B]
...
}
Does anyone know what is wrong?
Thanks
Tom
Solved.
There was a different problem. I wasn't persisting anything. There appeared some inconsistences between serialized data in the flow and persisted data in the database. So a select query caused this exception.
This is really going to depend most on what your parameters are and how you're handling creation or maintenance of the GORM objects, not your actual object graph.
Agree with #John. One of the common solutions is, you should be saving the object as
a.addToB(b)
a.save()
Hope it helps.
This problem is related to the ORM (I guess you are using hibernate below). The problem will be solved if you configure the cascade property of the mapped attributes.
I don't know how to configure it in grails, but this doc of hibernate should help you to understand where the problem is: http://docs.jboss.org/hibernate/stable/entitymanager/reference/en/html/objectstate.html#objectstate-transitive

Resources