Shr*_*uti 4 groovy mocking jenkins spock jenkins-pipeline
我有一个调用管道步骤方法(withCredentials)的共享库。我正在尝试测试 withCredentails 方法是否在调用 myMethodToTest 时使用 sh 脚本正确调用,但面临错误:
\n\n class myClass implements Serializable{\n def steps\n public myClass(steps) {this.steps = steps}\n\n public void myMethodToTest(script, String credentialsId) {\n steps.withCredentials([[$class: \xe2\x80\x98UsernamePasswordMultiBinding\xe2\x80\x99, credentialsId: "${credentialsId}", usernameVariable: \xe2\x80\x98USR\xe2\x80\x99, passwordVariable: \xe2\x80\x98PWD\xe2\x80\x99]]) {\n steps.sh """\n export USR=${script.USR}\n export PWD=${script.PWD}\n $mvn -X clean deploy\n """\n }\n }\n}\nRun Code Online (Sandbox Code Playgroud)\n\n//模拟
\n\nclass Steps {\n def withCredentials(List args, Closure closure) {}\n}\n\nclass Script {\n public Map env = [:]\n}\nRun Code Online (Sandbox Code Playgroud)\n\n//测试用例
\n\ndef "testMyMethod"(){\n given:\n def steps = Mock(Steps)\n def script = Mock(Script)\n def myClassObj = new myClass(steps)\n script.env[\'USR\'] = "test-user"\n\n when:\n def result = myClassObj.myMethodToTest(script, credId)\n\n then:\n 1 * steps.withCredentials([[$class: \'UsernamePasswordMultiBinding\', credentialsId: "mycredId", usernameVariable: \'USR\', passwordVariable: \'PWD\']]) \n 1 * steps.sh(shString)\n\n where:\n credId | shString\n "mycredId" | "export USR=\'test-user\'"\nRun Code Online (Sandbox Code Playgroud)\n\n//错误
\n\nToo few invocations for:\n\n1 * steps.withCredentials([[$class: \'UsernamePasswordMultiBinding\', credentialsId: "mycredId", usernameVariable: \xe2\x80\x98USR\xe2\x80\x99, passwordVariable: \xe2\x80\x98PWD\xe2\x80\x99]]) (0 invocations)\n\nUnmatched invocations (ordered by similarity):\n\n1 * steps.withCredentials([[\'$class\':\'UsernamePasswordMultiBinding\', \'credentialsId\':mycredId, \'usernameVariable\xe2\x80\x99:\xe2\x80\x99USR\xe2\x80\x99, \'passwordVariable\':\'PWD\xe2\x80\x99]]\nRun Code Online (Sandbox Code Playgroud)\n
您的代码中存在大量微妙和不那么微妙的错误,包括测试类和应用程序类。因此,让我提供一个新的MCVE,其中我修复了所有内容并评论了测试中的一些关键部分:
package de.scrum_master.stackoverflow.q59442086
class Script {
public Map env = [:]
}
Run Code Online (Sandbox Code Playgroud)
package de.scrum_master.stackoverflow.q59442086
class Steps {
def withCredentials(List args, Closure closure) {
println "withCredentials: $args, " + closure
closure()
}
def sh(String script) {
println "sh: $script"
}
}
Run Code Online (Sandbox Code Playgroud)
package de.scrum_master.stackoverflow.q59442086
class MyClass implements Serializable {
Steps steps
String mvn = "/my/path/mvn"
MyClass(steps) {
this.steps = steps
}
void myMethodToTest(script, String credentialsId) {
steps.withCredentials(
[
[
class: "UsernamePasswordMultiBinding",
credentialsId: "$credentialsId",
usernameVariable: "USR",
passwordVariable: "PWD"]
]
) {
steps.sh """
export USR=${script.env["USR"]}
export PWD=${script.env["PWD"]}
$mvn -X clean deploy
""".stripIndent()
}
}
}
Run Code Online (Sandbox Code Playgroud)
package de.scrum_master.stackoverflow.q59442086
import spock.lang.Specification
class MyClassTest extends Specification {
def "testMyMethod"() {
given:
// Cannot use mock here because mock would have 'env' set to null. Furthermore,
// we want to test the side effect of 'steps.sh()' being called from within the
// closure, which also would not work with a mock. Thus, we need a spy.
def steps = Spy(Steps)
def myClass = new MyClass(steps)
def script = new Script()
script.env['USR'] = "test-user"
when:
myClass.myMethodToTest(script, credId)
then:
1 * steps.withCredentials(
[
[
class: 'UsernamePasswordMultiBinding',
credentialsId: credId,
usernameVariable: 'USR',
passwordVariable: 'PWD'
]
],
_ // Don't forget the closure parameter!
)
// Here we need to test for a substring via argument constraint
1 * steps.sh({ it.contains(shString) })
where:
credId | shString
"mycredId" | "export USR=test-user"
}
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1658 次 |
| 最近记录: |