variable restaurar modificar java_home entorno configurar java unit-testing testing junit environment-variables

restaurar - variables de entorno java windows 10



¿Cómo se prueba el código que depende de las variables de entorno utilizando JUnit? (9)

Tengo un fragmento de código Java que usa una variable de entorno y el comportamiento del código depende del valor de esta variable. Me gustaría probar este código con diferentes valores de la variable de entorno. ¿Cómo puedo hacer esto en JUnit?

He visto algunas formas de establecer variables de entorno en Java en general, pero estoy más interesado en el aspecto de pruebas unitarias, especialmente teniendo en cuenta que las pruebas no deberían interferir entre sí.


Bueno, puedes usar el método setup () para declarar los diferentes valores de tu env. variables en constantes. Luego use estas constantes en los métodos de prueba utilizados para probar los diferentes escenarios.


Creo que la forma más limpia de hacerlo es con Mockito.spy (). Es un poco más ligero que crear una clase separada para burlarse y pasar.

Mueva su variable de entorno a otro método:

@VisibleForTesting String getEnvironmentVariable(String envVar) { return System.getenv(envVar); }

Ahora en su prueba de unidad haga esto:

@Test public void test() { ClassToTest classToTest = new ClassToTest(); ClassToTest classToTestSpy = Mockito.spy(classToTest); Mockito.when(classToTestSpy.getEnvironmentVariable("key")).thenReturn("value"); // Now test the method that uses getEnvironmentVariable assertEquals("changedvalue", classToTestSpy.methodToTest()); }


Desacople el código de Java de la variable de entorno y proporcione un lector de variables más abstracto que realice con un código de referencia de EnvironmentVariable su código para las lecturas de prueba.

Luego, en su prueba, puede dar una implementación diferente del lector variable que proporciona los valores de prueba.

La inyección de dependencia puede ayudar en esto.


En una situación similar a esta, en la que tuve que escribir el caso de prueba que depende de la variable de entorno , intenté seguir:

  1. Fui a reglas del sistema según lo sugerido por Stefan Birkner . Su uso fue simple. Pero más temprano que tarde, encontré el comportamiento errático. En una ejecución, funciona, en la siguiente ejecución falla. Investigué y encontré que las Reglas del sistema funcionan bien con JUnit 4 o una versión superior. Pero en mi caso, estaba usando algunos frascos que dependían de JUnit 3 . Así que me salté las Reglas del sistema . Puedes encontrar más información aquí. La anotación @Rule no funciona al usar TestSuite en JUnit .
  2. Luego traté de crear una variable de entorno a través de la clase Process Builder proporcionada por Java . Aquí a través de Java Code podemos crear una variable de entorno, pero necesita conocer el proceso o el nombre del programa que yo no. También crea una variable de entorno para el proceso hijo, no para el proceso principal.

Perdí un día usando los dos enfoques anteriores, pero fue en vano. Entonces Maven vino a mi rescate. Podemos establecer Variables de entorno o Propiedades del sistema a través del archivo POM de Maven , que creo que es la mejor manera de realizar pruebas unitarias para proyectos basados ​​en Maven . Debajo está la entrada que hice en el archivo POM .

<build> <plugins> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-surefire-plugin</artifactId> <configuration> <systemPropertyVariables> <PropertyName1>PropertyValue1</PropertyName1> <PropertyName2>PropertyValue2</PropertyName2> </systemPropertyVariables> <environmentVariables> <EnvironmentVariable1>EnvironmentVariableValue1</EnvironmentVariable1> <EnvironmentVariable2>EnvironmentVariableValue2</EnvironmentVariable2> </environmentVariables> </configuration> </plugin> </plugins> </build>

Después de este cambio, volví a ejecutar Casos de prueba y, de repente, todo funcionó como esperaba. Para información del lector, exploré este enfoque en Maven 3.x , así que no tengo idea sobre Maven 2.x.


La solución habitual es crear una clase que gestione el acceso a esta variable ambiental, que luego puede simular en su clase de prueba.

public class Environment { public String getVariable() { return System.getenv(); // or whatever } } public class ServiceTest { private static class MockEnvironment { public String getVariable() { return "foobar"; } } @Test public void testService() { service.doSomething(new MockEnvironment()); } }

La clase bajo prueba obtiene la variable de entorno utilizando la clase Environment, no directamente desde System.getenv ().


Las Reglas del sistema de la biblioteca proporcionan una Regla JUnit para establecer variables de entorno.

public void EnvironmentVariablesTest { @Rule public final EnvironmentVariables environmentVariables = new EnvironmentVariables(); @Test public void setEnvironmentVariable() { environmentVariables.set("name", "value"); assertEquals("value", System.getenv("name")); } }

Descargo de responsabilidad: soy el autor de las Reglas del sistema.


No creo que esto haya sido mencionado todavía, pero también podrías usar Powermockito :

Dado:

package com.foo.service.impl; public class FooServiceImpl { public void doSomeFooStuff() { System.getenv("FOO_VAR_1"); System.getenv("FOO_VAR_2"); System.getenv("FOO_VAR_3"); // Do the other Foo stuff } }

Usted podría hacer lo siguiente:

package com.foo.service.impl; import static org.mockito.Mockito.when; import static org.powermock.api.mockito.PowerMockito.mockStatic; import static org.powermock.api.mockito.PowerMockito.verifyStatic; import org.junit.Beforea; import org.junit.Test; import org.junit.runner.RunWith; import org.mockito.InjectMocks; import org.mockito.MockitoAnnotations; import org.powermock.core.classloader.annotations.PrepareForTest; import org.powermock.modules.junit4.PowerMockRunner; @RunWith(PowerMockRunner.class) @PrepareForTest(FooServiceImpl.class) public class FooServiceImpTest { @InjectMocks private FooServiceImpl service; @Before public void setUp() { MockitoAnnotations.initMocks(this); mockStatic(System.class); // Powermock can mock static and private methods when(System.getenv("FOO_VAR_1")).thenReturn("test-foo-var-1"); when(System.getenv("FOO_VAR_2")).thenReturn("test-foo-var-2"); when(System.getenv("FOO_VAR_3")).thenReturn("test-foo-var-3"); } @Test public void testSomeFooStuff() { // Test service.doSomeFooStuff(); verifyStatic(); System.getenv("FOO_VAR_1"); verifyStatic(); System.getenv("FOO_VAR_2"); verifyStatic(); System.getenv("FOO_VAR_3"); } }


Si desea recuperar información sobre la variable de entorno en Java, puede llamar al método: System.getenv(); . Como las propiedades, este método devuelve un Mapa que contiene los nombres de las variables como claves y los valores de las variables como los valores del mapa. Aquí hay un ejemplo :

import java.util.Map; public class EnvMap { public static void main (String[] args) { Map<String, String> env = System.getenv(); for (String envName : env.keySet()) { System.out.format("%s=%s%n", envName, env.get(envName)); } } }

El método getEnv() también puede tomar un argumento. Por ejemplo :

String myvalue = System.getEnv("MY_VARIABLE");

Para las pruebas, haría algo como esto:

public class Environment { public static String getVariable(String variable) { return System.getenv(variable); } @Test public class EnvVariableTest { @Test testVariable1(){ String value = Environment.getVariable("MY_VARIABLE1"); doSometest(value); } @Test testVariable2(){ String value2 = Environment.getVariable("MY_VARIABLE2"); doSometest(value); } }


Esta respuesta a la pregunta ¿Cómo configuro las variables de entorno de Java? proporciona una forma de alterar el Mapa (no modificable) en System.getenv (). Por lo tanto, aunque REALMENTE no cambia el valor de la variable de entorno del sistema operativo, se puede usar para probar unidades, ya que cambia lo que System.getenv devolverá.