【问题标题】:Why is grails.gorm.autoFlush set to true not working?为什么 grails.gorm.autoFlush 设置为 true 不起作用?
【发布时间】:2015-09-12 00:22:17
【问题描述】:

考虑以下代码:

class User {
    static constraints = {
        email email: true, unique: true
        token nullable: true
    }

    String email
    String password
    String token
}

@TestFor(User)
@TestMixin(DomainClassUnitTestMixin)
class UserSpec extends Specification {
    def "email should be unique"() {
        when: "twice same email"
        def user = new User(email: "test@test.com", password: "test")
        def user2 = new User(email: "test@test.com", password: "test")

        then: "saving should fail"
        user.save()
        !user2.save(failOnError: false)
    }
}

使用以下配置(部分),application.yml:

grails:
    gorm:
        failOnError: true
        autoFlush: true

user2.save(failOnError: false) 没有保存到数据库中,为什么没有返回 false

运行输出:grails test-app *UserSpec:

businesssoftware.UserSpec > 电子邮件应该是唯一的 FAILED org.spockframework.runtime.ConditionNotSatisfiedError at UserSpec.groovy:40

当我将 user.save() 替换为 user.save(flush: true) 时,它确实起作用了。

但是https://grails.github.io/grails-doc/latest/guide/conf.html 的文档第 4.1.3 节声称:

grails.gorm.autoFlush - 如果设置为 true,则导致合并、保存和删除方法刷新会话,而不需要使用 save(flush: true) 显式刷新。

作为参考,这是grails --version的输出:

| Grails 版本:3.0.2
| Groovy 版本:2.4.3
| JVM版本:1.8.0_40

这正是我正在做的,我在这里错过了什么?

【问题讨论】:

    标签: grails grails-orm grails-3.0


    【解决方案1】:

    我认为 autoFlush 文档具有误导性。

    grails.gorm.autoFlush - 如果设置为 true,则导致合并、保存和 删除方法来刷新会话,取代显式的需要 使用 save(flush: true) 刷新。

    看看GormInstanceApi的save()方法和doSave()。在 doSave() 结束时,您会看到只有在 flush 参数为 true 时才会刷新会话:

    if (params?.flush) {
        session.flush()
    }
    

    代码中没有任何内容表明 flush 参数可以来自任何其他地方,而不是传递给 save() 的内容。

    我找不到代码来证明这一点,但我认为 autoFlush 在 Hibernate 会话关闭时发挥作用,例如当控制器或服务方法存在/返回时。

    此外,用于 Spock 和 JUnit 的 GORM 实现不是真正的 GORM,因此它甚至可能不使用 autoFlush 配置。

    我要在这里冒险了。我没有尝试过,但您也许可以手动刷新会话。

    @TestFor(User)
    @TestMixin(DomainClassUnitTestMixin)
    class UserSpec extends Specification {
        def "email should be unique"() {
            when: "twice same email"
            def user = new User(email: "test@test.com", password: "test")
            def user2 = new User(email: "test@test.com", password: "test")
            simpleDatastore.currentSession.flush()
    
            then: "saving should fail"
            user.save()
            !user2.save(failOnError: false)
        }
    }
    

    simpleDataStore 来自DomainClassUnitTestMixin

    【讨论】:

      猜你喜欢
      • 2011-09-11
      • 2012-04-04
      • 1970-01-01
      • 1970-01-01
      • 2016-09-25
      • 2017-07-23
      • 2014-11-05
      • 2010-10-14
      • 2021-09-05
      相关资源
      最近更新 更多