Unit testing Grails2.1单元测试命令对象mockForConstraintsTests不工作?
我对这个命令对象使用了手动编写的以及Grails生成的单元测试:Unit testing Grails2.1单元测试命令对象mockForConstraintsTests不工作?,unit-testing,grails,mocking,constraints,Unit Testing,Grails,Mocking,Constraints,我对这个命令对象使用了手动编写的以及Grails生成的单元测试: package myapp @grails.validation.Validateable class SearchCommand { String basisBuild String buildToSearch static constraints = { basisBuild(blank: false) } } 在手
package myapp
@grails.validation.Validateable
class SearchCommand {
String basisBuild
String buildToSearch
static constraints = {
basisBuild(blank: false)
}
}
在手写单元测试失败后,我使用了Grails:
create-unit-test myapp.SearchCommand
我填写了单元测试,并断言应该通过模拟约束的每个文档:
package myapp
import static org.junit.Assert.*
import grails.test.mixin.*
import grails.test.mixin.support.*
import org.junit.*
@TestMixin(GrailsUnitTestMixin)
class SearchCommandTests {
void setUp() {
mockForConstraintsTests(SearchCommand)
}
void tearDown() {
// Tear down logic here
}
void testSomething() {
SearchCommand commandUnderTest = new SearchCommand()
commandUnderTest.validate(basisBuild: "")
assertEquals "blank", commandUnderTest.errors['basisBuild']
}
}
为什么我会失败?
grails> test-app
| Running 9 unit tests... 9 of 9
| Failure: testSomething(com.siemens.soarian.sf.gap.SearchCommandTests)
| java.lang.AssertionError: expected:<blank> but was:<null>
at org.junit.Assert.fail(Assert.java:93)
grails>testapp
|正在运行9个单元测试。。。第9页,共9页
|失败:testSomething(com.siemens.soarian.sf.gap.SearchCommandTests)
|java.lang.AssertionError:应为:但为:
位于org.junit.Assert.fail(Assert.java:93)
编辑
如果现有版本中提到的补丁已经安装到位(感谢@codelark的帮助),那么适当地使用validate()
和mockForConstraintsTest
应该可以工作。为了从Web应用程序的角度(使用controller
)测试命令对象,以下信息将非常有用
使用控制器操作测试命令对象:-
命令
对象仅在用作控制器
中的一个操作
方法中的参数时才被视为该对象。请参阅(警告注释)。
在操作方法中使用SearchCommand
,您应该能够assertEquals
示例:
void testSomething() {
YourController controller = mockController(YourController) //Or instantiate
SearchCommand commandUnderTest = new SearchCommand ()
//Note the usage here. validate() does not take parameters
commandUnderTest.basisBuild = ''
commandUnderTest.validate()
//Call your action
controller.searchCommandAction(commandUnderTest)
assert response.text == 'Returned'
assertEquals "blank", commandUnderTest.errors['basisBuild']
}
控制器的操作:-
def searchCommandAction(SearchCommand sc){
render "Returned"
}
注意:
void testSomething() {
YourController controller = mockController(YourController) //Or instantiate
SearchCommand commandUnderTest = new SearchCommand ()
//Note the usage here. validate() does not take parameters
commandUnderTest.basisBuild = ''
commandUnderTest.validate()
//Call your action
controller.searchCommandAction(commandUnderTest)
assert response.text == 'Returned'
assertEquals "blank", commandUnderTest.errors['basisBuild']
}
没有grails bug的补丁,我们可以在@grails 2.1.4、2.2.0和2.2.1中看到下面的错误
当我只更正验证
并使用mockForConstraintTests
而不使用控制器
操作时,我会收到一个错误:
您使用的
验证方法不正确。您从未在类上设置该字段,因此该字段为空,而不是空。尝试按以下方式更改测试:
void testSomething() {
SearchCommand commandUnderTest = new SearchCommand()
commandUnderTest.basisBuild = ""
assertFalse commandUnderTest.validate()
assertEquals 'blank', commandUnderTest.errors['basisBuild']
}
Edit:在测试使用@Validatable
注释的命令类时,还有一个问题。错误评论中有一些变通方法。我相信我找到了grails支持的方法,可以在grails 2.0中对命令对象进行单元测试。您需要使用ControllerUnitTestMixin提供的mockCommandObject
归功于埃里克
我在回答中已经提到了validate()
方法更正。此外,在Grails2.x中,mockForConstraintsTests
必须被mockDomainObject
(来自ControllerUnitTestMixins
)替换或实例化(如我的回答所示)。按照您提出的修复方案,将在assertFalse commandUnderTest.validate()
中得到一个断言
失败。这是从grails 2.2.1中的一个工作示例中提取的。为什么说在2.x中必须替换mockForConstraintsTest
?它仍然在未弃用的测试API中,我正试图证明自己跟随您是错误的,但它在2.1.4、2.2.0和2.2.1中从未对我起作用。创建一个全新的项目,创建命令对象,创建测试,运行测试。开导我。:)包含在grails创建应用程序之后需要创建的两个文件。然后,grails测试app:unit
@dmahapatro我们的结果的差异似乎是由于一个未解决的grails bug造成的。显然,注释和模拟辅助对象之间存在交互问题。请注意,我在pastebin中的代码没有使用注释。我会用更多的细节更新我的答案。我希望我的编辑会有所帮助。我很想知道它的行为会有什么不同。:)