I have shared library that calls pipeline step method(withCredentials).I am trying to test withCredentials method is being called correctly with sh scripts on calling myMethodToTest but facing error while iterating in withCredentials closure:
Method To Test
class myClass implements Serializable{
def steps
public myClass(steps) {this.steps = steps}
public void myMethodToTest(script, credentialsId, dataObject) {
dataObject.myKeyValue.each {
steps.withCredentials([[
$class: ‘UsernamePasswordMultiBinding’, credentialsId: "${credentialsId}",
usernameVariable: 'USR', passwordVariable: 'PWD']]) {
steps.sh("git push --set-upstream origin ${it.branch}")
}
}
}
}
Mocking
class Steps {
def withCredentials(List args, Closure closure) {}
}
class Script {
public Map env = [:]
}
Test case
def "testMyMethod"(){
given:
def steps = Spy(Steps)
def script = Mock(Script)
def myClassObj = new myClass(steps)
def myDataObject = [
'myKeyValue' : [['branch' :'mock' ]]
]
when:
def result = myClassObj.myMethodToTest(script, credId, myDataObject)
then:
1 * steps.withCredentials([[
$class: 'UsernamePasswordMultiBinding',
credentialsId: "mycredId",
usernameVariable: 'USR',
passwordVariable: 'PWD'
]])
1 * steps.sh(shString)
where:
credId | shString
"mycredId" | "git push --set-upstream origin mock"
Error (it variable becomes null in closure)
java.lang.NullPointerException: Cannot get property 'branch' on null object
You have a case of two nested closures
dataObject.myKeyValue.each { // <- first closure it references the map
steps.withCredentials([[
$class: ‘UsernamePasswordMultiBinding’, credentialsId: "${credentialsId}",
usernameVariable: 'USR', passwordVariable: 'PWD']]) { // <- second closure it is null as no parameter is passed to this closure
steps.sh("git push --set-upstream origin ${it.branch}")
}
}
To fix it you should name the first parameter
dataObject.myKeyValue.each { conf ->
steps.withCredentials([[
$class: ‘UsernamePasswordMultiBinding’, credentialsId: "${credentialsId}",
usernameVariable: 'USR', passwordVariable: 'PWD']]) {
steps.sh("git push --set-upstream origin ${conf.branch}")
}
}