-
Improvement
-
Resolution: Postponed
-
Minor
-
None
I found it difficult to retrieve the Computer that is executing, or that is selected for execution within a CPS script, without accessing the env global object. The reason I wanted to retrieve it without accessing env is because I need to know this information while actually rebuilding the environment. Doing it accessing env in this situation, which also must be NonCPS is doable but tricky (I do it here), and possibly less efficient. If a reliable method can be written, I recommend to offer an alternative method to retrieve this information, similarly as I do it below in the method getCurrentComputerSafe(), for which I can't guarantee the correctness because I'm not familiar with Jenkins internals:
import org.jenkinsci.plugins.workflow.cps.CpsThread; echo "Computer name: ${getCurrentComputerSafe().displayName}" // Prints: Built-In Node pipeline { agent any stages { stage('Stage1') { agent { label 'MyNode' } steps { script { echo "Computer name: ${getCurrentComputerSafe().displayName}" // Prints: MyNode } } } } } @NonCPS static private Computer getCurrentComputerSafe() { // Try get executing computer first def current = Computer.currentComputer(); if (current != null) return current; // Reverse iterate steps to find a delegate computer that // will execute def threads = CpsThread.current().group.threads.toArray(); for (int i = threads.length - 1; i >= 0; i--) { def thread = threads[i]; if (thread.step == null) continue; def filePath = thread.step.context.get(hudson.FilePath); if (filePath == null) continue; return filePath.toComputer(); } // As a last measure, return the master computer def computers = Jenkins.instance.computers; for (int i = 0; i < threads.length; i++) { def computer = computers[i]; if (computer instanceof Jenkins.MasterComputer) return computer; } throw new Exception('Unexpected no master computer found'); }
- links to