Grails动态查找器,其中字段名称包含保留字

时间:2011-01-30 23:55:05

标签: grails groovy hql

所以我有一个grails域类:

class Message
{
    Inbox inbox
    Boolean hasBeenLogicallyDeletedByRecipient
    ...

    static belongsTo = [
        inbox:Inbox,
        ...
    ]

    static constraints = {
        hasBeenLogicallyDeletedByRecipient(nullable:false)
        ...
    }
}

我想使用动态查找器如下:

def messages = Message.findAllByInboxAndHasBeenLogicallyDeletedByRecipient(
                    inbox, false, [order:'desc',sort:'dateCreated'])

这可以很好地运行STS 2.6.0.M1中针对grails 1.2.1的单元测试用例; 启动Web应用程序后,由于 hasBeenLogicallyDeletedByRecipient 中的 By 而失败(我猜测它在构建查询时混淆了动态查找器解析)。

我可以使用在app中运行的条件构建器:

    def messages = Message.withCriteria {
        and {
            eq('inbox', inbox)
            eq('hasBeenLogicallyDeletedByRecipient', false)
        }
        order('dateCreated', 'desc')
    }

但是由于withCriteria没有被模拟,它不会立即在单元测试中工作,所以我可以将以下内容添加到单元测试中:

    Message.metaClass.static.withCriteria = { Closure c ->
        ...
    }

标准/单元测试是否嘲笑最佳/可接受的方法?我对这种嘲笑感到不自​​在,因为它避免了测试标准的关闭。

理想情况下,我宁愿使用动态查找器 - 是否有简洁的方法使其按原样工作? 如果无法绕过它,我想字段名称​​可以被更改(我有理由不想这样做,但这与问题无关)... < / p>

更新

当我尝试在应用程序中使用findAllByInboxAndHasBeenLogicallyDeletedByRecipient()时,这是堆栈跟踪 - 请注意它是如何获取最后一个并处理它与 findAll 作为财产。我在http://grails.org/OperatorNamesInDynamicMethods吃草了,但它没有提到关于 By 被禁止的任何内容。

org.codehaus.groovy.grails.exceptions.InvalidPropertyException: No property found for name [byInboxAndHasBeenLogicallyDeleted] for class [class xxx.Message]
    at xxx.messages.yyyController$_closure3.doCall(xxx.messages.yyyController:53)
    at xxx.messages.yyyController$_closure3.doCall(xxx.messages.yyyController)
    at java.lang.Thread.run(Thread.java:662)

1 个答案:

答案 0 :(得分:2)

测试数据库查询实际上是一个集成测试,而不是单元测试。您的测试是/ test / unit还是/ test / integration? - 我希望'withCriteria'在集成测试中完全正常运行,但不能在单元测试中使用。

来自grails docs(http://grails.org/doc/latest/),第9.1节:

  

单元测试是“单位”的测试   水平。换句话说,你正在测试   个别方法或代码块   不考虑周围   基础设施。在Grails你需要   要特别注意   单位和。之间的差异   集成测试,因为在单元中   测试 Grails不会注入任何一个   动态方法存在于   集成测试和运行时。