作者热门文章
- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
我正在尝试找到一种将动态字段添加到 grails 域类的方法。我确实根据 Burt 的文章找到了动态域类插件,但这对我们的需求来说太过分了。
假设我们有一个域类 person:
class Person extends DynamicExtendableDomainObject {
String firstName
String lastName
static constraints = {
firstName(nullable: false, blank: false, maxSize: 50)
lastName(nullable: false, blank: false)
}
}
DynamicExtendableDomainObject
类,Person 类继承自该类。这会为每个继承自此的 Domain 类添加一个自定义字段,以将动态属性存储为
JSON
在其中(有点像 Perl 中的 KiokuDB 存储它们)。
saveinterceptor
来实现。 , 将这些属性序列化为 JSON 并将它们存储在特殊字段中。
最佳答案
您可以尝试在运行时将属性添加到类型为 DynamicExtendableDomainObject
的 DomainClass通过在 metaClass 中扩展 getProperty()、setProperty()、setProperties(),然后使用 beforeUpdate()、beforeInsert() 和 afterLoad() 来 Hook 到 Persistence。
例如在 Bootstrap(或服务)中:
def yourDynamicFieldDefinitionService
for(GrailsClass c in grailsApplication.getDomainClasses()){
if(DynamicExtendableDomainObject.isAssignableFrom(c.clazz)){
Set extendedFields = yourDynamicFieldDefinitionService.getFieldsFor(c.clazz)
//getProperty()
c.clazz.metaClass.getProperty = { String propertyName ->
def result
if(extendedFields.contains(propertyName)){
result = delegate.getExtendedField(propertyName)
} else {
def metaProperty = c.clazz.metaClass.getMetaProperty(propertyName)
if(metaProperty) result = metaProperty.getProperty(delegate)
}
result
}
//setProperty()
c.clazz.metaClass.setProperty = { propertyName , propertyValue ->
if(extendedFields.contains(propertyName)){
delegate.setExtendedField(propertyName, propertyValue)
delegate.blobVersionNumber += 1
} else {
def metaProperty = c.clazz.metaClass.getMetaProperty(propertyName)
if(metaProperty) metaProperty.setProperty(delegate, propertyValue)
}
}
//setProperties()
def origSetProperties = c.clazz.metaClass.getMetaMethod('setProperties',List)
c.clazz.metaClass.setProperties = { def properties ->
for(String fieldName in extendedFields){
if(properties."${fieldName}"){
delegate."${fieldName}" = properties."${fieldName}"
}
}
origSetProperties.invoke(delegate,properties)
}
}
}
abstract DynamicExtendableDomainObject {
String yourBlobField
Long blobVersionNumber //field to signal hibernate that the instance is 'dirty'
Object getExtendedField(String fieldName){
...
}
void setExtendedField(String fieldName, Object value){
...
}
def afterLoad(){
//fill your transient storage to support getExtendedField + setExtendedField
}
def beforeUpdate(){
//serialize your transient storage to yourBlobField
}
def beforeInsert(){
//serialize your transient storage to yourBlobField
}
}
关于grails - 在 Grails 中向域对象添加动态字段,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15067352/
我是一名优秀的程序员,十分优秀!