我有两个具有双向一对一关联的域类:
域
class Nose {
String str1
static belongsTo = [face:Face]
}
class Face {
String str1
static hasOne = [nose: Nose]
}
控制器
class NoseController {
def create() {
nose.properties = params
nose.save(flush: true)
}
def delete() {
def nose = Nose.get(params.id as long)
nose.delete(flush: true)
}
}
class FaceController {
def create() {
def face = new Face()
def nose = Nose.get(params.id as long)
if(!nose){
face.nose = nose
face.properties = params
face.save(flush: true)
nose.face = face
nose.properties = params
nose.save(flush:true)
}else{
face.properties = params
face.save(flush: true)
}
}
def delete() {
def face = Face.get(params.id as long)
face.delete(flush: true)
}
}
创建 Nose 和 Face 对象后,我无法删除并更新。 当我想删除Face时,我得到例外:
org.springframework.dao.DataIntegrityViolationException:外键 试图删除teastrelation.Face的id为1的约束违规 org.grails.hbase.gorm.DeletePersistentMethod.invoke(DeletePersistentMethod.groovy:66) 在org.grails.hbase.gorm.PersistentMethod $ invoke.call(未知来源) 在org.grails.hbase.gorm.PersistentMethod $ invoke.call(未知来源)
要在FaceController中删除,我已更改删除操作:
def delete() {
def face = Face.get(params.id as long)
def nose = Nose.get(face.nose.id)
face.nose = null
nose.face = null
nose.save(flush:true)
face.save(flush:true)
face.delete(flush: true)
render params.id
}
并且只有在它之后我才能删除 Face 对象,但它会引发以下异常:
错误gorm.SavePersistentMethod - 无法在null上获取属性“class” object java.lang.NullPointerException:无法获取属性'class' null对象at org.codehaus.groovy.runtime.NullObject.getProperty(NullObject.java:56) 在 org.codehaus.groovy.runtime.InvokerHelper.getProperty(InvokerHelper.java:156) 在 org.codehaus.groovy.runtime.callsite.PojoMetaClassGetPropertySite.callGetProperty(PojoMetaClassGetPropertySite.java:41)
当我想更新Face对象时,我得到以下异常:
ERROR associations.ReferenceTable - 找不到引用表条目, row = [79,78,69,84,79,79,78,69,95,79,78,69,84,79,79,78, 69,95,68,79,77,65,73,78,50,95,0,0,0,0,0,0,0,1]
错误gorm.SavePersistentMethod - 无法在null上获取属性“class” object java.lang.NullPointerException:无法获取属性'class' null对象 at org.codehaus.groovy.runtime.NullObject.getProperty(NullObject.java:56) 在org.codehaus.groovy.runtime.InvokerHelper.getProperty(InvokerHelper.java:156) 在org.codehaus.groovy.runtime.callsite.PojoMetaClassGetPropertySite.callGetProperty(PojoMetaClassGetPropertySite.java:41)
我使用grails 1.3.2和hbase-0.2.4插件,我不能使用映射..
我做错了什么?
我已经花了很多时间来解决这个问题..如果有人可以的话,请帮忙。
答案 0 :(得分:1)
我创建了一个简单的应用程序来模拟您的问题。在我的例子中,我遵循了最佳实践,即编写服务来管理对象和一些测试。请注意,Domain1Controller上的create方法调用save(flush:true)
3次(d1两次,d2一次),这可能不是很好,可能是你的问题。
这就是我做的事情
域名1:
package com.example
class Owner {
String example;
static constraints = {
friend unique:true
}
static hasOne = [friend: Owned]
}
域名类2
package com.example
class Owned {
String name;
static constraints = {
}
static belongsTo = [owner: Owner]
}
管理这些域类的服务
package com.example
class OwnerService {
static transactional = true
def saveNewOwnerAndOwned(ownerField, ownedField){
def owner = new Owner(example: ownedField)
def owned = new Owned(name: ownedField)
owner.friend = owned
// since the relationship is bidirectional, need to set up
// the references both ways
owned.owner = owner
owner.save(flush: true)
return owner
}
def deleteOwner(id) {
def toDelete = Owner.get(id)
toDelete.delete(flush:true)
}
def deleteOwnedOfOwner(ownerId) {
def owner = Owner.get(ownerId)
def owned = owner.friend
// must break the relationship
owner.friend = null
owned.delete(flush: true);
}
}
测试以确保其正常工作
package com.example
class OwnerServiceIntegrationTests extends GroovyTestCase {
def ownerService
def sessionFactory
public void testSave(){
def owner = ownerService.saveNewOwnerAndOwned("im an owner", "im owned");
assertNotNull(owner)
assertNotNull(owner.id)
assertNotNull(owner.friend)
assertNotNull(owner.friend.id)
}
public void testDelete() {
def owner = ownerService.saveNewOwnerAndOwned("im an owner", "im owned");
def id = owner.id
def ownedId = owner.friend.id
ownerService.deleteOwner(id);
// since the integration tests hit an actual db
// clear the session so when i start testing im sure its accurate
def session = sessionFactory.getCurrentSession()
session.clear()
// make sure everything was deleted, i.e. not in db
assertNull(Owner.get(id))
assertNull(Owned.get(ownedId))
}
public void testDeleteOwned() {
def owner = ownerService.saveNewOwnerAndOwned("im an owner", "im owned");
def id = owner.id
ownerService.deleteOwnedOfOwner(id);
def session = sessionFactory.getCurrentSession()
session.clear()
owner = Owner.get(id)
// make sure owner still there but friend is not
assertNotNull(owner)
assertNull(owner.friend)
}
}