MissingPropertyException 在 spock 测试 where 块中抛出
MissingPropertyException thrown in spock test where block
我一直在使用 spock 对我的 java 项目进行单元测试,但 运行 遇到了问题。我有一个实用程序方法可以从 http 请求获取参数,或者如果 http 请求为 null 则为空字符串,并且我正在尝试使用 spock 对其进行测试。我的测试如下所示:
package foo.bar.test
import foo.bah.HttpRequestPropertyLoader
import spock.lang.Unroll
import javax.servlet.http.HttpServletRequest
import spock.lang.Specification
class HttpRequestPropertyLoaderTest extends Specification {
HttpRequestPropertyLoader subjectUnderTest
def result
def setup() {
subjectUnderTest = new HttpRequestPropertyLoader()
}
@Unroll("When my http request is #nullOrNot then when I get parameter from it the response=#response" )
def "Test load data from request"() {
given:
HttpServletRequest mockHttpRequest = Mock()
mockHttpRequest.getAttribute("foo") >> "bar"
when:
result = subjectUnderTest.loadStringFromHttpRequest(httpRequest, "foo")
then:
result == response
where:
httpRequest | response | nullOrNot
null | "" | "null"
mockHttpRequest | "bar" | "not null"
}
}
然而,当我运行这个测试时,我得到以下错误:
groovy.lang.MissingPropertyException: No such property: mockHttpRequest for class: foo.bar.test.HttpRequestPropertyLoaderTest at foo.bar.test.HttpRequestPropertyLoaderTest.Test load data from request(HttpRequestPropertyLoaderTest.groovy)
经过一些研究,我了解到 where
块在 given
块之前 运行,因此出现错误,但我只是想知道是否有解决方法?
我知道要使用测试外部的变量,我需要用 @Shared
注释来注释变量,这对我来说似乎是不好的做法。每个测试都应该 运行 与其他测试完全分开,所以不要真的想要一个在测试之间保持其状态的对象。
是否可以设置从 where 块以任何其他方式返回的 Mock 对象?
根据 tim_yates 查看 https://code.google.com/p/spock/issues/detail?id=15#c4 的建议,我发现了一个相当优雅的解决方案,不涉及使用 @Shared
注释。测试定义现在看起来像这样:
package foo.bar.test
import foo.bah.HttpRequestPropertyLoader
import spock.lang.Unroll
import javax.servlet.http.HttpServletRequest
import spock.lang.Specification
class HttpRequestPropertyLoaderTest extends Specification {
HttpRequestPropertyLoader subjectUnderTest
def result
def setup() {
subjectUnderTest = new HttpRequestPropertyLoader()
}
@Unroll("When my http request is #nullOrNot then when I get parameter from it the response=#response" )
def "Test load data from request"() {
when:
result = subjectUnderTest.loadStringFromHttpRequest(httpRequest, "foo")
then:
result == response
where:
httpRequest << {
HttpServletRequest mockHttpRequest = Mock()
mockHttpRequest.getAttribute("foo") >> "bar"
[null, mockHttpRequest]
}()
response << ["", "bar"]
nullOrNot << ["null", "not null"]
}
}
我一直在使用 spock 对我的 java 项目进行单元测试,但 运行 遇到了问题。我有一个实用程序方法可以从 http 请求获取参数,或者如果 http 请求为 null 则为空字符串,并且我正在尝试使用 spock 对其进行测试。我的测试如下所示:
package foo.bar.test
import foo.bah.HttpRequestPropertyLoader
import spock.lang.Unroll
import javax.servlet.http.HttpServletRequest
import spock.lang.Specification
class HttpRequestPropertyLoaderTest extends Specification {
HttpRequestPropertyLoader subjectUnderTest
def result
def setup() {
subjectUnderTest = new HttpRequestPropertyLoader()
}
@Unroll("When my http request is #nullOrNot then when I get parameter from it the response=#response" )
def "Test load data from request"() {
given:
HttpServletRequest mockHttpRequest = Mock()
mockHttpRequest.getAttribute("foo") >> "bar"
when:
result = subjectUnderTest.loadStringFromHttpRequest(httpRequest, "foo")
then:
result == response
where:
httpRequest | response | nullOrNot
null | "" | "null"
mockHttpRequest | "bar" | "not null"
}
}
然而,当我运行这个测试时,我得到以下错误:
groovy.lang.MissingPropertyException: No such property: mockHttpRequest for class: foo.bar.test.HttpRequestPropertyLoaderTest at foo.bar.test.HttpRequestPropertyLoaderTest.Test load data from request(HttpRequestPropertyLoaderTest.groovy)
经过一些研究,我了解到 where
块在 given
块之前 运行,因此出现错误,但我只是想知道是否有解决方法?
我知道要使用测试外部的变量,我需要用 @Shared
注释来注释变量,这对我来说似乎是不好的做法。每个测试都应该 运行 与其他测试完全分开,所以不要真的想要一个在测试之间保持其状态的对象。
是否可以设置从 where 块以任何其他方式返回的 Mock 对象?
根据 tim_yates 查看 https://code.google.com/p/spock/issues/detail?id=15#c4 的建议,我发现了一个相当优雅的解决方案,不涉及使用 @Shared
注释。测试定义现在看起来像这样:
package foo.bar.test
import foo.bah.HttpRequestPropertyLoader
import spock.lang.Unroll
import javax.servlet.http.HttpServletRequest
import spock.lang.Specification
class HttpRequestPropertyLoaderTest extends Specification {
HttpRequestPropertyLoader subjectUnderTest
def result
def setup() {
subjectUnderTest = new HttpRequestPropertyLoader()
}
@Unroll("When my http request is #nullOrNot then when I get parameter from it the response=#response" )
def "Test load data from request"() {
when:
result = subjectUnderTest.loadStringFromHttpRequest(httpRequest, "foo")
then:
result == response
where:
httpRequest << {
HttpServletRequest mockHttpRequest = Mock()
mockHttpRequest.getAttribute("foo") >> "bar"
[null, mockHttpRequest]
}()
response << ["", "bar"]
nullOrNot << ["null", "not null"]
}
}