¿Puede un proyecto de prueba unitaria cargar el archivo app.config de la aplicación de destino?

150

Estoy probando una aplicación .NET (.exe) que usa un archivo app.config para cargar las propiedades de configuración. La aplicación de prueba unitaria en sí no tiene un archivo app.config.

Cuando intento probar un método unitario que utiliza cualquiera de las propiedades de configuración, devuelven nulo . Supongo que esto se debe a que la aplicación de prueba unitaria no se cargará en la aplicación de destino app.config.

¿Hay alguna manera de anular esto o tengo que escribir un script para copiar el contenido del app.config de destino en un app.config local?

Esta publicación hace esta pregunta, pero el autor realmente la está mirando desde un ángulo diferente al mío.

EDITAR: Debo mencionar que estoy usando VS08 Team System para mis pruebas unitarias.

Jordan Parmer
fuente

Respuestas:

59

La forma más sencilla de hacer esto es agregar el .configarchivo en la sección de implementación en su prueba unitaria.

Para hacerlo, abra el .testrunconfigarchivo desde sus Elementos de solución. En la sección Implementación, agregue los .configarchivos de salida del directorio de compilación de su proyecto (presumiblemente bin\Debug).

Todo lo que aparece en la sección de implementación se copiará en la carpeta de trabajo del proyecto de prueba antes de que se ejecuten las pruebas, por lo que su código dependiente de la configuración se ejecutará correctamente.

Editar: Olvidé agregar, esto no funcionará en todas las situaciones, por lo que es posible que deba incluir un script de inicio que cambie el nombre de la salida .configpara que coincida con el nombre de la prueba de la unidad.

Jeromy Irvine
fuente
9
Es mucho más fácil simplemente agregar una aplicación.config fiel al proyecto de prueba; entonces no necesita jugar con .testrunconfig en absoluto.
Rowland Shaw el
13
@Rowland si hace eso, debe mantener dos copias de app.config. Prefiero pasar 10 segundos, una vez, usando la herramienta .testrunconfig que tener que recordar actualizar la app.config en ambos lugares.
Jeromy Irvine
66
¿No puedes agregar una referencia que no se copia? (Agregar elemento existente ...)
EFraim
66
El comentario de EFraim debe ser la respuesta aceptada, esto es mucho más simple que cualquier otra cosa.
reggaeguitar
28
Para la solución de EFraim: asegúrese de utilizar "Agregar como enlace" desde el botón de comando. De lo contrario, aún obtendrá una copia. Además, aunque la pregunta es específicamente para una aplicación .Net, esto no funcionará para una aplicación web ya que la configuración de una aplicación web tiene un nombre incorrecto (Web.Config, no App.Config)
Rob Von Nesselrode
103

En Visual Studio 2008 agregué el app.configarchivo al proyecto de prueba como un elemento existente y seleccioné la copia como enlace para asegurarme de que no esté duplicado. De esa manera solo tengo una copia en mi solución. ¡Con varios proyectos de prueba resulta muy útil!

Agregar elemento existente

Agregar como enlace

bbodenmiller
fuente
77
¡Respuesta perfecta, simple y objetiva! +1
Custodio
2
Esta es la mejor solución y debe marcarse como la respuesta.
niaher
44
Para agregar un elemento existente "como un enlace" debe: "En el cuadro de diálogo Agregar elemento existente, busque y seleccione el elemento del proyecto que desea vincular", luego: "En la lista desplegable del botón Abrir, seleccione Agregar como enlace. "
uriel
Esto funciono muy bien para mi. Estoy tratando de pensar en una situación en la que no funcionaría ... Y ahora he pensado lo suficiente. ¡Gracias!
Dudeman3000
53

Ya sea que esté usando Team System Test o NUnit , la mejor práctica es crear una Biblioteca de clases separada para sus pruebas. Simplemente agregando un App.config a su proyecto de prueba se copiará automáticamente a su carpeta bin cuando compile .

Si su código depende de pruebas de configuración específicas, la primera prueba que escribiría valida que el archivo de configuración está disponible ( para que sepa que no estoy loco ):

<configuration>
   <appSettings>
       <add key="TestValue" value="true" />
   </appSettings>
</configuration>

Y la prueba:

[TestFixture]
public class GeneralFixture
{
     [Test]
     public void VerifyAppDomainHasConfigurationSettings()
     {
          string value = ConfigurationManager.AppSettings["TestValue"];
          Assert.IsFalse(String.IsNullOrEmpty(value), "No App.Config found.");
     }
}

Idealmente, debería escribir código de manera que sus objetos de configuración pasen a sus clases. Esto no solo lo separa del problema del archivo de configuración, sino que también le permite escribir pruebas para diferentes escenarios de configuración.

public class MyObject
{
     public void Configure(MyConfigurationObject config)
     {
          _enabled = config.Enabled;
     }

     public string Foo()
     {
         if (_enabled)
         {
             return "foo!";
         }
         return String.Empty;
     }

     private bool _enabled;
}

[TestFixture]
public class MyObjectTestFixture
{
     [Test]
     public void CanInitializeWithProperConfig()
     {
         MyConfigurationObject config = new MyConfigurationObject();
         config.Enabled = true;

         MyObject myObj = new MyObject();
         myObj.Configure(config);

         Assert.AreEqual("foo!", myObj.Foo());
     }
}
bryanbcook
fuente
2
Estoy de acuerdo con el espíritu de pasar la dependencia de configuración aquí, esto parece haber sido respondido por Mark Seemann, ¡nada menos! por aquí: Fallas en las pruebas unitarias debido a la falta del archivo .config
Shaun
Falta una "línea: valor de cadena = ConfigurationManager.AppSettings [" TestValue]; Traté de arreglarlo, pero habría tenido que encontrar otros 5 caracteres para arreglarlo para obtener stackoverflow que me permitiera hacer una edición.
Jane
22

Si tiene una solución que contiene, por ejemplo, Aplicación web y Proyecto de prueba, probablemente desee que Test Project utilice web.config de la Aplicación web.

Una forma de resolverlo es copiar web.config para probar el proyecto y renombrarlo como app.config.

Otra solución mejor es modificar la cadena de compilación y hacer que haga una copia automática de web.config para probar el directorio de salida de proyectos. Para hacerlo, haga clic con el botón derecho en Probar aplicación y seleccione propiedades. Ahora debería ver las propiedades del proyecto. Haga clic en "Crear eventos" y luego haga clic en el botón "Editar post-compilación ..." Escriba la siguiente línea hasta allí:

copy "$(SolutionDir)\WebApplication1\web.config" "$(ProjectDir)$(OutDir)$(TargetFileName).config"

Y haga clic en Aceptar. (Tenga en cuenta que lo más probable es que necesite cambiar WebApplication1 a medida que proyecta el nombre que desea probar). Si tiene una ruta incorrecta a web.config, la copia falla y lo notará durante la compilación incorrecta.

Editar:

Para copiar del proyecto actual al proyecto de prueba:

copy "$(ProjectDir)bin\WebProject.dll.config" "$(SolutionDir)WebProject.Tests\bin\Debug\App.Config"
Antti
fuente
Muy buena solución. Esto me ayudó a evitar copiar y duplicar .configarchivos. ¡Gracias por compartir! :)
Leniel Maccaferri
Muy buena solución! Muchas gracias.
Vin Shahrdar
Buena solución, pero qué sucede cuando los principales web.configsolo tienen referencias a .configarchivos externos dentro del mismo proyecto. Como la ruta solo puede apuntar a carpetas dentro del mismo directorio (lo cual es cierto normalmente), al ejecutar pruebas, no podrá manejar esos archivos externos. ¿Alguna idea de cómo solucionarlo?
Sugafree
Esto funcionó para mí: copie "$ (SolutionDir) \ MainProject \ Web.config" "$ (ProjectDir) app.config"
Andrew
8

Esto es un poco viejo pero encontré una mejor solución para esto. Intenté la respuesta elegida aquí, pero parece que .testrunconfig ya está obsoleto.

1. Para pruebas unitarias, la configuración es una interfaz (IConfig)

para las pruebas unitarias, la configuración realmente no debería ser parte de lo que está probando, así que cree una simulación que pueda inyectar. En este ejemplo, estaba usando Moq.

Mock<IConfig> _configMock;
_configMock.Setup(config => config.ConfigKey).Returns("ConfigValue");
var SUT = new SUT(_configMock.Object);

2. Para la prueba de integración, agregue dinámicamente la configuración que necesita

Configuration config = ConfigurationManager.OpenExeConfiguration(ConfigurationUserLevel.None);
if(config.AppSettings.Settings[configName] != null)
{
    config.AppSettings.Settings.Remove(configName);
}
config.AppSettings.Settings.Add(configName, configValue);
config.Save(ConfigurationSaveMode.Modified, true);
ConfigurationManager.RefreshSection("appSettings");
MichaelChan
fuente
5

Esto es muy facil.

  • Haga clic derecho en su proyecto de prueba
  • Agregar -> elemento existente
  • Puedes ver una pequeña flecha justo al lado del botón Agregar
  • Seleccione el archivo de configuración, haga clic en "Agregar como enlace"
Hari Das
fuente
4

Si está utilizando NUnit, eche un vistazo a esta publicación . Básicamente, necesitará tener su app.config en el mismo directorio que su archivo .nunit.

Cory Foy
fuente
Estoy usando VS08 Team System para mis pruebas unitarias, pero gracias por el consejo de NUnit.
Jordan Parmer
2

Si su aplicación está utilizando una configuración como Asp.net ConnectionString, debe agregar el atributo HostType a su método, de lo contrario no se cargarán incluso si tiene un archivo App.Config.

[TestMethod]
[HostType("ASP.NET")] // will load the ConnectionString from the App.Config file
public void Test() {

}
Zyo
fuente
0

Uso NUnit y en el directorio de mi proyecto tengo una copia de mi aplicación. Configure que cambio alguna configuración (ejemplo, redirijo a una base de datos de prueba ...). Necesita tenerlo en el mismo directorio del proyecto probado y estará bien.

Patrick Desjardins
fuente
0

No pude obtener ninguna de estas sugerencias para trabajar con nUnit 2.5.10, así que terminé usando la funcionalidad Proyecto -> Editar de nUnit para especificar el archivo de configuración para el destino (como otros han dicho que necesita estar en la misma carpeta que el. nunit archivo en sí). El lado positivo de esto es que puedo darle al archivo de configuración un nombre Test.config que lo hace mucho más claro qué es y por qué es)

Jane
fuente
0

Sus pruebas unitarias se consideran como un entorno que ejecuta su código para probarlo. Al igual que cualquier entorno normal, usted tiene, por ejemplo, puesta en escena / producción. Es posible que también deba agregar un .configarchivo para su proyecto de prueba. Una solución alternativa es crear una biblioteca de clases y convertirla en Proyecto de prueba agregando los paquetes NuGet necesarios, como NUnit y NUnit Adapter. funciona perfectamente bien con Visual Studio Test Runner y Resharper y tiene su app.configarchivo en su proyecto de prueba. ingrese la descripción de la imagen aquí

ingrese la descripción de la imagen aquí

ingrese la descripción de la imagen aquí

ingrese la descripción de la imagen aquí

Y finalmente depuré mi prueba y valor de App.config:

ingrese la descripción de la imagen aquí

Ben
fuente