【问题标题】:test command object validation测试命令对象验证
【发布时间】:2011-03-31 16:58:25
【问题描述】:

我有以下命令对象:

class CategoryCommand {

    String name
    String seoName

    static constraints = {
        name(blank: false)
        seoName(blank: false)
    }
}

我正在尝试使用此测试用例测试约束验证:

class ValidationTests extends ControllerUnitTestCase {


    protected void setUp() {
        super.setUp()
        mockCommandObject(CategoryCommand)
    }

    void testValidation() {
        def command = new CategoryCommand()
        assertFalse command.validate()
    }
}

但是断言失败,因为命令对象通过了验证,即使违反了约束。

我的猜测是这也不起作用,因为mockCommandObject 添加了一个validate() 方法,但是该方法的实现总是返回true

是否有另一种方法可以测试命令类的验证。我需要 validate()errors 属性像运行应用程序时那样工作,以便正确测试它。我已经尝试将它作为集成测试和单元测试运行,但结果是一样的。

谢谢!

【问题讨论】:

  • 我编辑了我的答案,因为我忘记了我正在将 hasErrors 添加到我的命令对象的 metaClass 以便能够在单元测试中使用它。

标签: unit-testing validation grails groovy


【解决方案1】:

您应该在测试中使用mockCommandObject

mockCommandObject(CategoryCommand)

它允许您使用validate() 方法并轻松访问errors 属性。我为命令对象做了一堆单元测试,在我的情况下效果很好。

编辑

我注意到一些奇怪的行为,基本上不知道为什么。我有一个命令对象:

class ChangePasswordCommand {
  String oldPassword
  String newPassword
  String newPassword2

  static constraints = {
    oldPassword(blank: false)
    newPassword(blank: false, matches: ConfigurationHolder.config.application.password.regex)
    newPassword2(blank: false, validator: { val, obj ->
      if (val != obj.newPassword) {
        return 'registration.password.mismatch.error'
      }
    })
  }
}

我也有测试(和setUp()方法中的mockCommandObject(ChangePasswordCommand)):

    void testChangePasswordCommand_errors() {
            def cmd = new ChangePasswordCommand(oldPassword: '', newPassword: 'SomePass', newPassword2: 'SomeOtherPass')
            //def cmd = new ChangePasswordCommand()

            assertFalse cmd.validate()
            assertTrue cmd.hasErrors()
            assertEquals 3, cmd.errors.getErrorCount()
            assertEquals 'blank', cmd.errors.getFieldError('oldPassword').getCode()
            assertEquals 'matches.invalid', cmd.errors.getFieldError('newPassword').getCode()
            assertEquals 'registration.password.mismatch.error', cmd.errors.getFieldError('newPassword2').getCode()
}

当我运行测试时,它通过了。但是,当我注释第一行并取消注释第二行,以便将空命令对象投入测试时,cmd.validate() 断言测试失败。此外,当我评论cmd.validate() 断言时,它也无法断言cmd.hasErrors()。然后我删除了第一行中的 oldPassword 属性设置

def cmd = new ChangePasswordCommand(newPassword: 'SomePass', newPassword2: 'SomeOtherPass')

并且测试也失败了。所以看起来它因为null 属性值而刹车。我无法解释。

编辑 2

我是瞎子什么的。 mockCommandObject 添加 validate() 方法,但不添加 hasErrors() 方法。在我的测试中,setUp() 我也有:

ChangePasswordCommand.metaClass.hasErrors() { !delegate.validate() }

【讨论】:

  • mockForConstraintsTestsmockCommandObject 调用相同的 grails.test.MockUtils.addValidateMethod
  • 我将测试改为调用mockCommandObject,但结果是一样的。我已经更新了问题
  • 我编辑了我的答案,因为我对我的项目进行了一些测试。我注意到一些奇怪的行为,但无法解释原因。
  • 我不知道为什么我之前没有找到它,但是我将 hasErrors 方法添加到我的命令对象的 metaClass 以便能够在单元测试中使用它。适当编辑答案。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多