2

I'm trying to connect to couple of my Jenkins agents and run some commands on each of them. After researching, follow the answer from this link, this Jenkinsfile code works fine:

pipeline {
    agent none
    stages {
        stage('Check') {            
            matrix {
                agent {
                    label "${SLAVE}"
                }
   
                axes {
                    axis {
                        name 'SLAVE'
                        values "slv1", "slv2",
                        "slv3"
                    }
                }
                stages {
                    stage('do something') {
                        steps {
                            sh 'hostname'
                        }
                    }
                }
            }
        }
    }
}

But I want to check each of nodes is online or not before doing anything. I haven't had any luck with what I've tried. This is my latest trying:

Boolean finalResult = true

def checkStatus(String nodeName){
    Node cleanUpNode = Jenkins.instance.getNode(nodeName)
        Computer computer = cleanUpNode.toComputer()

        if (cleanUpNode == null) {
            println("ERROR: Node ${nodeName} doesn't exist")
            finalResult = false
            continue
        }

        if (computer.countBusy()) {
            println("WARNING: Ignore ${nodeName} as it is busy")
            continue
        }
        if (computer.isOffline())
        {
            println "Error! Node ${nodeName} is offline.";
            finalResult = false
            continue
        }
    return finalResult    
}

pipeline {
    agent none
    stages {
        stage('Check') {            
            matrix {
                agent {
                    label "${SLAVE}"
                }
                when {
                      expression { checkStatus(${SLAVE}) == true }
                }
                axes {
                    axis {
                        name 'SLAVE'
                        values "slv1", "slv2",
                        "slv3"
                    }
                }
                stages {
                    stage('do something') {
                        steps {
                            sh 'hostname'
                        }
                    }
                }
            }
        }
    }
}

My first idea is create an array to store all the nodes, then check it and assign variable into it through values in axis. But this idea is not supported

Can anyone help? Thanks in advance!

Ian W
  • 4,559
  • 2
  • 18
  • 37
himneh
  • 96
  • 6

1 Answers1

0

Focused on the checkStatus method, it has some general mistakes and won't work. What works in the Groovy Sandbox for me is the following. (your admin may need to approve some script signatures).

As I use Labels rather than the Node name, I've added the for loop. For the #nodesByLabel call you need to install the Pipeline Utility Jenkins plugin.

def checkStatus (String nodeLabel) {

    for (final String nodeName : nodesByLabel(nodeLabel)) {
        Node node = Jenkins.instance.getNode(nodeName)
    
        if (node == null) {
            println("ERROR: Node ${nodeName} doesn't exist")
            return false
        }
    
        Computer computer = node.toComputer()
 
        // TODO skip this; the node is always busy at this point
        if (computer.countBusy()) {
            println("WARNING: Ignore ${nodeName} as it is busy")
            return false
        }

        if (computer.isOffline()) {
           println "Error! Node ${nodeName} is offline."
           return false
        }
    }
    return true
}
jforge
  • 1
  • 3