Cómo dar la propiedad del sistema a mi prueba a través de Gradle y -D

103

Tengo un programa Java que lee una propiedad del sistema

System.getProperty("cassandra.ip");

y tengo un archivo de compilación de Gradle con el que comienzo

gradle test -Pcassandra.ip=192.168.33.13

o

gradle test -Dcassandra.ip=192.168.33.13

sin embargo, System.getProperty siempre devolverá nulo .

La única forma que encontré fue agregar eso en mi archivo de compilación de Gradle a través de

test {
    systemProperty "cassandra.ip", "192.168.33.13"
}

¿Cómo lo hago a través de -D?

robkuz
fuente
1
¿Qué pasa cuando lo usas gradle -Dcassandra.ip=192.168.33.13? De todos modos, la tarea de prueba bifurca una o varias JVM nuevas. Por lo tanto, tendrá que pasar propiedades explícitamente. Sin embargo, nadie te obliga a codificar su valor en la compilación.
JB Nizet
También eche un vistazo a esta respuesta: stackoverflow.com/questions/23689054/…
IgalS

Respuestas:

124

El indicador -P es para las propiedades de Gradle y el indicador -D es para las propiedades de JVM. Debido a que la prueba puede estar bifurcada en una nueva JVM, el argumento -D pasado a gradle no se propagará a la prueba; parece que ese es el comportamiento que está viendo.

Puede usar systemProperty en su testbloque como lo ha hecho, pero basarlo en la propiedad gradle entrante pasándola con ella -P:

test {
    systemProperty "cassandra.ip", project.getProperty("cassandra.ip")
}

o alternativamente, si lo está pasando a través de -D

test {
    systemProperty "cassandra.ip", System.getProperty("cassandra.ip")
}
Jeff Storey
fuente
1
Esto no funciona para mí (probado con System.getProperties().stringPropertyNames().forEach(System.out::println);el código de Java, no aparece)
CLOVIS
Advertencia: se getPropertylanza MissingPropertyExceptionsi no se encuentra la propiedad. Use la respuesta de Eron en su lugar: stackoverflow.com/a/43112126/915441
Yngvar Kristiansen
1
Agregar valores predeterminados a gradle.propertiesevitará el MissingPropertyException.
Duncan Calvert
No puedo hacer que ninguno de estos métodos funcione. Haga lo que haga myProperty siempre es nulo. Esto también incluye todos los métodos que se mencionan a continuación. Me pregunto si esto tiene algo que ver con una versión más reciente, ya que todos los comentarios son de 2018. @CLOVIS, ¿encontraste una solución a esto?
Hester Lyons
@HesterLyons Solo quería saber si la compilación se estaba probando o se estaba ejecutando normalmente, así que usé la propiedad que gradle agrega al probar; puede ver el código aquí: github.com/CLOVIS-AI/wildfyre-java/blob/master/src/main/java/…
CLOVIS
27

Encontré este gran problema, excepto que no quiero volver a enumerar todas las propiedades dadas en la línea de comandos en el script de Gradle. Por lo tanto, envío todas las propiedades del sistema a mi prueba

task integrationTest(type: Test) {
    useTestNG()
    options {
        systemProperties(System.getProperties())
    }
}
MrSpock
fuente
Tenga cuidado al hacer esto. Podría romper fácilmente las comprobaciones actualizadas de Gradle cuando las propiedades del sistema cambian durante las invocaciones.
thokuest
9

Tuve un caso en el que necesitaba pasar varias propiedades del sistema a la JVM de prueba, pero no todas (no quería pasar las irrelevantes). Según las respuestas anteriores, y al usar subMappara filtrar las que necesitaba, esto funcionó para mí:

task integrationTest(type: Test) {
    // ... Do stuff here ...
    systemProperties System.getProperties().subMap(['PROP1', 'PROP2'])
}

En este ejemplo, sólo PROP1y PROP2será aprobada en, si es que existen en la JVM de Gradle.

avivr
fuente
5

Aquí hay una variante que pasa numerosas propiedades del proyecto a la JVM de prueba como propiedades del sistema. Prefiero las propiedades del proyecto a las propiedades del sistema para aumentar la flexibilidad.

task intTest(type: Test) {
    systemProperties project.properties.subMap(["foo", "bar"])
}

Que se puede pasar en la línea de comandos:

 $ gradle intTest -Pfoo=1 -Pbar=2

Y recuperado en tu prueba:

String foo = System.getProperty("foo");
Eron Wright
fuente
Al ejecutar System.getProperty("someprop")usando ese método subMap, obtuve en {someprop=foo}lugar de foo. Tuve que usar systemProperty "foo", project.properties.subMap(["foo"]).get("foo")en build.gradle
Yngvar Kristiansen
@YngvarKristiansen ¿dónde (cómo) estabas usando systemProperty "foo"? es decir, estoy pidiendo ver la línea completa de código donde se usó esto. Estoy intentando todo lo sugerido en esta pregunta y aún Gradle no pasa ningún argumento. ¡Esperando que esto se resuelva!
Hester Lyons
@HesterLyons Lo siento, no guardé mi código, así que ya no lo sé: \ Estoy de acuerdo en que parece fuera de lugar.
Yngvar Kristiansen
Gracias @YngvarKristiansen. Desde entonces, descubrí que mi problema estaba siendo causado por el complemento junit gradle que estaba incluido en mi gradle.build. Muy raro.
Hester Lyons
0

Así que hoy también me encontré con ese problema, y ​​lo que funcionó para mí fue lo siguiente:

ext.env='prod'
test {
  systemProperty 'env', System.properties['env'] ?: "${env}"
  println "# test environment: " + systemProperties['env']
  ...
}

Estoy llamando a mi tarea de prueba usando -Penv = dev y obtengo mi valor 'dev' en mi impresión, o 'prod' si no envío ningún valor, que es el comportamiento esperado para mí.

También se puede acceder al valor en el lado de Java, utilizando System.getProperty ("env") .

Mi conclusión al respecto es que el valor de entrada (parámetro) se almacena en realidad en System , lo que lo hace accesible a través de System.properties ['env'] o System.getProperty ("env") , mientras que la salida (propiedad del sistema) se almacena en una matriz systemProperties , haciéndola legible a través de systemProperties ['env'] .

Olivier B.
fuente