grails GORM派生属性

时间:2015-01-11 04:54:35

标签: hibernate grails gorm

我的grails域对象中有一个字段,我想成为其他表的派生字段。我的域名如下所示

class VotingTally{

   int votesSource1
   int votesSource2
   int totalVotes

}

static mapping = {
    totalVotes formula: (votesSource1.numOfVotes+ votesSource2.numOfVotes)
}

我得到的错误是

No such property: votesSource1 for class: org.grails.datastore.mapping.config.groovy.MappingConfigurationBuilder

2 个答案:

答案 0 :(得分:1)

首先,formula应该是一个带有SQL表达式的字符串(你有Groovy表达式)。像:

static mapping = {
    totalVotes formula: 'numOfVotes1 + numOfVotes2'
}

但是在你的情况下,你想要计算连接表中的值,而这是不可能的。你无法从这里添加JOIN

似乎只有一种方法 - 从代码中加载它:

static transients = ['totalVotes']

int getTotalVotes() {
    VotesSource.get(votesSource1).numOfVotes + VotesSource.get(votesSource2).numOfVotes 
}

答案 1 :(得分:0)

正如Andrew von Dollen所提到的,你仍然可以通过使用子选择来使用公式,但它并不总是最佳选择。此外,您的域名需要有一种方式来关联两个投票来源(通常是一对多或多对多关系)。它相当于:

static mapping = { totalVotes formula: '((select count(*) from vote_source_1 vs1 where vs1.source_id = id) + (select count(*) from vote_source_2 vs2 where vs2.source_id = id))' }

请注意,上述内容可能不会对您有所帮助。它取决于您的特定数据库引擎和您的域模型,它通过一些共享ID来链接投票来源。

优点:

  • 您可以像对待任何其他属性一样对属性值进行排序和查询
  • 避免创建非规范化数据库
  • 将处理成本放入数据库中(也可能是一个...)

缺点:

    如果使用非标准SQL,
  • 可以引入数据库引擎类型依赖。
  • 不会在新实例或脏实例上给出准确的值,因为该属性在保存实例(并且可能已刷新)之前不会生效或更新