¿Cómo enumerar todas las propiedades `env` dentro del trabajo de tubería de jenkins?


105

Dada una canalización de compilación de jenkins 2.1, jenkins inyecta una envvariable en node{}. Por ejemplo, BRANCH_NAMEse puede acceder con

node {
    echo ${env.BRANCH_NAME}
    ...

Quiero hacer eco de todas las env propiedades dentro de la tubería de jenkins.

... considerando que no conozco todas las propiedades de antemano.

Estoy buscando un código como

node {
    for(e in env){
        echo e + " is " + ${e}
    }
    ...

que se haría eco de algo como

 BRANCH_NAME is myBranch2
 CHANGE_ID is 44
 ...

env es un mapa. ¿Probaste la iteración normal? like - env.each {println it}
Jayan


3
Afaik env simplemente encapsula las variables de entorno. No creo que puedas recorrerlo. Pruebe 'sh env' en linux / 'bat set' en Windows.
Dominik Gebhart

1
@Renato @Jayan según mi comentario a continuación, env.each { name, value -> println "Name: $name -> Value $value" }imprime Name: org.jenkinsci.plugins.workflow.cps.EnvActionImpl@45c2d1ee -> Value null.
JamesThomasMoon1979

1
@ JamesThomasMoon1979 Eso es porque Pipeline rompe los cierres Groovy. Si lo corrige al estilo antiguo de Java (es decir, new ClassName() { ... }), debería funcionar. O lo ejecuta en un método etiquetado @NonCPS, luego los cierres también funcionarán dentro de eso.
Daniel C. Sobral

Respuestas:



80

Según la documentación de Jenkins para la canalización declarativa :

sh 'printenv'

Para la canalización con guiones de Jenkins :

echo sh(script: 'env|sort', returnStdout: true)

Lo anterior también clasifica sus variables env por conveniencia.


1
printenves solo un comando de shell que imprime el entorno, nada específico de Jenkins. Sin argumentos es equivalente a envsin argumentos. Estoy bastante seguro de sh 'printenv | sort'que funcionará en DCL o en una tubería con script.
simon.watts

Probado y sh 'printenv | sort'de hecho funciona para una tubería declarativa de Jenkins; fwiw sh 'env | sort'también funciona (Ambos probados en Jenkins ver. 2.46.1). Lo mencioné originalmente sh 'printenv'porque se mencionó en la documentación oficial de Jenkins.
Wimateeka

1
Si pierde el returnStdout: true, entonces no necesita el eco; Es solo imprimir lo que ya imprimió el script de shell.
Ed Randall

26

Los siguientes trabajos:

@NonCPS
def printParams() {
  env.getEnvironment().each { name, value -> println "Name: $name -> Value $value" }
}
printParams()

Tenga en cuenta que lo más probable es que falle en la primera ejecución y requiera que apruebe varios métodos maravillosos para ejecutar en jenkins sandbox. Esto se hace en "administrar jenkins / aprobación de script en proceso"

La lista que obtuve incluía:

  • BUILD_DISPLAY_NAME
  • BUILD_ID
  • BUILD_NUMBER
  • BUILD_TAG
  • BUILD_URL
  • CLASSPATH
  • HUDSON_HOME
  • HUDSON_SERVER_COOKIE
  • HUDSON_URL
  • JENKINS_HOME
  • JENKINS_SERVER_COOKIE
  • JENKINS_URL
  • JOB_BASE_NAME
  • NOMBRE DEL TRABAJO
  • JOB_URL

1
Esto no funciona:java.lang.UnsupportedOperationException: each on a CPS-transformed closure is not yet supported
octavian

5
¿Te aseguraste de incluir el @NonCPS?
Joe C.

1
Esta es la mejor respuesta porque funcionará fuera de un bloque de nodos . Muchas gracias por esto.
Gi0rgi0s

15

Puede lograr el resultado usando sh/ batstep y readFile:

node {
    sh 'env > env.txt'
    readFile('env.txt').split("\r?\n").each {
        println it
    }
}

Desafortunadamente, env.getEnvironment()devuelve un mapa muy limitado de variables de entorno.


1
sh 'env > env.txt'funciona bien e incluye variables de entorno creadas por el proceso de shell. env.getEnvironment()muestra solo las variables de entorno del conjunto de Jenkins, que son un subconjunto de las que se ven en la sh 'env'técnica. Además, necesita la aprobación de seguridad del script method org.jenkinsci.plugins.workflow.support.actions.EnvironmentAction getEnvironment. Lo env.each { name, value -> println "Name: $name -> Value $value" }recomendado por @Renato @Jayan solo imprime Name: org.jenkinsci.plugins.workflow.cps.EnvActionImpl@45c2d1ee -> Value null.
JamesThomasMoon1979

¡¡¡Agradable!!! Poder imprimir todas las variables env me ayudó a descubrir que Jenkins 2 establece una var JOB_BASE_NAME que contiene el nombre del trabajo sin la carpeta en la que reside.
Bill Agee

una versión que funcione en Windows también sería increíble :)
Bas Hamer

@Bas Hamer para una versión de Windows intente reemplazar "sh" por "bat"
Sebastien

2
Me da un error java.lang.UnsupportedOperationException: llamar al público estático java.lang.Object org.codehaus.groovy.runtime.DefaultGroovyMethods.each (java.lang.Object, groovy.lang.Closure) en un cierre transformado por CPS no es aún compatible (JENKINS-26481); encapsular en un método @NonCPS, o usar bucles de estilo Java
Ben Mathews

12

¿Por qué toda esta complicación?

sh 'env'

hace lo que necesita (bajo * nix)


Esto requiere un bloque de nodo para ejecutarse. Para mi caso de uso, necesito procesar qué entorno tendrá el nodo y luego activar un nodo en función de ciertos criterios.
Bill Warner

10

Aquí hay una secuencia de comandos rápida que puede agregar como un trabajo de canalización para enumerar todas las variables de entorno:

node {
    echo(env.getEnvironment().collect({environmentVariable ->  "${environmentVariable.key} = ${environmentVariable.value}"}).join("\n"))
    echo(System.getenv().collect({environmentVariable ->  "${environmentVariable.key} = ${environmentVariable.value}"}).join("\n"))
}

Esto enumerará las variables del sistema y de Jenkins.


9

Forma multiplataforma de enumerar todas las variables de entorno:

if (isUnix()) {
    sh env
}
else {
    bat set
}

7

Utilizo el complemento Blue Ocean y no me gustó que cada entrada de entorno tuviera su propio bloque. Quiero un bloque con todas las líneas.

Imprime mal:

sh 'echo `env`'

Imprime mal:

sh 'env > env.txt'
for (String i : readFile('env.txt').split("\r?\n")) {
    println i
}

Imprime bien:

sh 'env > env.txt'
sh 'cat env.txt'

Imprime bien: (como lo menciona @mjfroehlich)

echo sh(script: 'env', returnStdout: true)

3

Las respuestas anteriores ahora son anticuadas debido a la nueva sintaxis de canalización. A continuación se imprimen las variables de entorno.

script {
        sh 'env > env.txt'
        String[] envs = readFile('env.txt').split("\r?\n")

        for(String vars: envs){
            println(vars)
        }
    }

1
1. Necesita tenerlo en un bloque de script. 2. Están depreciando el ciclo del 'estilo maravilloso'.
Eddie

El forcon un cierre también causará problemas sin una @NonCPSanotación.
sorteo

2

Las soluciones Groovy puras que leen la envvariable global no imprimen todas las variables de entorno (por ejemplo, les faltan variables del environmentbloque, del withEnvcontexto y la mayoría de las variables específicas de la máquina del sistema operativo). Usando los pasos de shell es posible obtener un conjunto más completo, pero eso requiere un nodecontexto, que no siempre se desea.

Aquí hay una solución que utiliza el getContextpaso para recuperar e imprimir el conjunto completo de variables de entorno, incluidos los parámetros de canalización, para el contexto actual.

Advertencia: no funciona en la caja de arena Groovy. Sin embargo, puede usarlo desde una biblioteca compartida confiable.

def envAll = getContext( hudson.EnvVars )
echo envAll.collect{ k, v -> "$k = $v" }.join('\n')

1

si realmente desea recorrer la envlista, simplemente haga:

def envs = sh(returnStdout: true, script: 'env').split('\n')
envs.each { name  ->
    println "Name: $name"
}

0

otra forma de obtener exactamente el resultado mencionado en la pregunta:

envtext= "printenv".execute().text
envtext.split('\n').each
{   envvar=it.split("=")
    println envvar[0]+" is "+envvar[1]
}

Esto se puede ampliar fácilmente para crear un mapa con un subconjunto de variables env que coincidan con un criterio:

envdict=[:]
envtext= "printenv".execute().text
envtext.split('\n').each
{   envvar=it.split("=")
    if (envvar[0].startsWith("GERRIT_"))
        envdict.put(envvar[0],envvar[1])
}    
envdict.each{println it.key+" is "+it.value}

0

Supongo que necesitabas eso en forma de script, pero si alguien más solo quiere echar un vistazo a la GUI de Jenkins, esa lista se puede encontrar seleccionando la sección "Variables de entorno" en el menú contextual izquierdo de cada compilación Seleccionar proyecto = > Seleccionar compilación => Variables de entorno

ingrese la descripción de la imagen aquí


2
Esto no siempre está disponible.
shuckc

1
No creo que esté disponible para Jenkinsfiles en absoluto. La captura de pantalla parece una construcción de estilo libre.
Jakub Bochenski

0

Encontré que esta es la forma más fácil:

pipeline {
    agent {
        node {
            label 'master'
        }
    }   
    stages {
        stage('hello world') {
            steps {
                sh 'env'
            }
        }
    }
}

-1

Puede obtener todas las variables de su instancia de jenkins. Solo visita:

  • $ {jenkins_host} /env-vars.html
  • $ {jenkins_host} / pipeline-syntax / globals
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.