【问题标题】:grails gorm null fieldsgrails gorm 空字段
【发布时间】:2014-09-03 12:59:08
【问题描述】:

我有两个域类:

class Person {

    String lastname
    String firstname
    String alias
    Date birthday
    String notes
    static belongsTo = [addressBook: AddressBook, mainAddress: Address]
    static hasMany = [tags: Tag, addresses: Address]

    static constraints = {
        mainAddress nullable: true
        addresses nullable: true
        alias nullable: true
        birthday: nullable: true
        tags nullable: true
        notes nullable: true
    }
}

class Address {

    AddressType addressType

    static belongsTo = [person: Person]
    String company
    String street
    String zipCode
    String city
    String eMail
    String phone
    String mobile
    String website

    static constraints = {
        person nullable: true
        company nullable: true
        website nullable: true
    }
}

它的目的是,每个人都有多个地址,并且可以将一个地址定义为主地址。

在我的控制器中,我做了一个

params.max = Math.min(max ?: 10, 100)
respond Person.list(params)

加载所有地址的所有人。我收到的人员对象包含一个地址列表,其中包含所有地址和主地址。但是用作主地址的地址在两个对象(列表中的一个和 mainAddress 对象)中都只有空(null)字段。当我不设置 mainAddress 时,地址列表中的地址对象带有正确设置的所有字段。数据库字段(到目前为止我使用的是 in-memory-db)似乎是正确的:

create table address (id bigint generated by default as identity, version bigint not null, address_type varchar(255) not null, city varchar(255) not null, company varchar(255), e_mail varchar(255) not null, mobile varchar(255) not null, person_id bigint, phone varchar(255) not null, street varchar(255) not null, website varchar(255), zip_code varchar(255) not null, primary key (id))
create table person (id bigint generated by default as identity, version bigint not null, address_book_id bigint not null, alias varchar(255), birthday timestamp not null, firstname varchar(255) not null, lastname varchar(255) not null, main_address_id bigint, notes varchar(255), primary key (id))

有人知道,为什么我的映射不起作用?

提前感谢您的帮助

罗兰

【问题讨论】:

  • 类人属于地址和地址属于人?你一定是在开玩笑
  • 您的意思可能是Person hasOne AddressAddress belongsTo Person

标签: grails grails-orm


【解决方案1】:

你的模型有很多问题,最严重的是person-mainAddress关系没有所有者,即双方belongsTo对方。如果可能,我会将您的模型简化为

class Person {
    // non-address properties omitted, because they're not relevant to this question
    static hasMany = [addresses: Address]

    Address getMainAddress() {
        Address.createCriteria().get {
            eq 'person', this
            eq 'isMain', true   
        }
    }

    static transients = ['mainAddress']

    static constraints = {

        addresses nullable: true, validator: { addresses ->

            // this prevents a person from having more than one main address
            addresses?.count { it.isMain } <= 1
        }
    }
}

class Address {
    // non-person properties omitted, because they're not relevant to this question     
    boolean isMain = false

    static belongsTo = [person: Person]

    static constraints = {
        // is it really OK for an address not to be associated with a person?
        person nullable: true
    }
}

我认为这符合您的要求,但这是一个更简单的模型,因为PersonAddress 之间只有一个(一对多)关系

【讨论】:

  • 感谢您的回答,我也试过了,效果很好。我更喜欢我发布的解决方案,因为使用 isMain 标志,每次我必须找出 mainAddress 时,我都必须单独遍历地址列表。
  • @Roland 不一定,我在Person 中添加了一个getMainAddress() 方法,它将检索主地址(如果存在)而不遍历所有地址
  • 提供 getter 提供了一个很好的解决方案,有利于我的解决方案不需要额外的连接表。它也更加灵活,因为您只在真正需要时才对 mainAddress 进行查询。非常感谢。
【解决方案2】:

我现在找到了解决方案:

class Person {

    Address mainAddress
    static hasMany = [addresses: Address]

    static constraints = {
        addresses nullable: true
        mainAddress nullable: true, unique: true
    }

    static mapping = {
        addresses joinTable: [name: 'person_address',key: 'person_id', column: 'address_id']
        mainAddress lazy: false
    }
}

class Address {
}

这样,地址映射到连接表 person_address 上,而 mainAddress 通过地址表中的 main_address_id 映射。 “mainAddress:lazy”映射是必需的,否则 mainAddress 的字段不会被填充。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2015-01-07
    • 2011-06-18
    • 1970-01-01
    • 2015-02-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多