我有一个所有DomainClasses都在扩展的抽象类。 这个Abstracte类看起来像这样:
last_connect
我的DomainClass abstract class DomainBase {
Date created = new Date(), modified = new Date()
User createdBy, modifiedBy
int dataStatus = 30
}
也扩展了抽象类,并具有多个自引用关系:
User
UserSkill:
User principal
static hasMany = [employees: User, skills: UserSkill,...]
static mappedBy = [employees: 'none' ]
我得到了一个MappingException:
class UserSkill extends DomainBase {
String category
String name
static belongsTo = [User]
static hasMany = [users: User]
static mappedBy = [users: 'skills']
static mapping = {
table 'skill'
users column: 'skill_id', joinTable: 'user_skills'
}
}
如何正确地对类进行mapp?
答案 0 :(得分:1)
离开Grails一会儿......你有一个面向对象的设计问题。根据您的设计, DomainBase 位于层次结构的顶部。因为这个 DomainBase 不应该依赖于它的子类。原因如下:
根据Liskov substitution principle,如果B类从A类扩展,那么B类的实例应该可以在任何需要A类实例的地方使用。
例如,如果类 Duck 扩展了类 Bird ,我可以诚实地说鸭子 是 < EM>鸟。我的鼻子不会再长了。如果某个方法需要 Bird 并且我给它一个 Duck ,那么该方法将不会知道其中的差异。
在您的情况下,用户不能是 DomainClass ,因为 DomainClass 拥有用户。 Bird 可以有 Duck 吗?不。 Bird 不应该对 Duck 有任何了解。除了动物,你的阶级等级违反了这个原则。但这可以修复:)
只要您使用的是Groovy 2.3或Grater,Groovy trait就可以解决您的问题。
首先,在grails-app / src / main / groovy /中的某处创建一个特征。最好将它放在与域类相同的Groovy(Java)包中。
package xzy
trait Auditable {
Date created = new Date(), modified = new Date()
User createdBy, modifiedBy
int dataStatus = 30
}
然后,让您的域类实现特征。
package xyz
class User implements Auditable {
User principal
static hasMany = [employees: User, skills: UserSkill,...]
static mappedBy = [employees: 'none' ]
}
class UserSkill implements Auditable {
String category
String name
static belongsTo = [User]
static hasMany = [users: User]
static mappedBy = [users: 'skills']
static mapping = {
table 'skill'
users column: 'skill_id', joinTable: 'user_skills'
}
}
这是有效的,因为您的域类将神奇地获取特征(created,createBy和dataStatus)中定义的属性而无需继承。另外,如果方法需要 Audiable ,您可以将 User 或 UserSkill 传递给该方法,并且该方法不会知道其中的差异。
观看此内容:用户 和 UserSkills 可审核。有道理吗?