2011-06-03 17 views
13

Después de la ejecución de los dos casos de prueba siguientes, se imprime una ejecución COM en la consola. ¿Qué estoy haciendo mal?Excepciones COM a la salida con WPF

Si ejecuto cualquiera de las pruebas individualmente, o si ejecuto ambas pruebas juntas, la excepción se escribe en la consola exactamente una vez. Esto me hace sospechar que hay algún tipo de recurso por dominio de aplicación que no estoy limpiando.

He intentado las pruebas con NUnit y con MSTest, con el mismo comportamiento en ambos entornos. (En realidad, no estoy seguro de si se está ejecutando ambas pruebas en los resultados MSTest en una sola copia impresa o dos excepciones.)

Excepción:

System.Runtime.InteropServices.InvalidComObjectException: COM object that has been separated from its underlying RCW cannot be used. 
at System.Windows.Input.TextServicesContext.StopTransitoryExtension() 
at System.Windows.Input.TextServicesContext.Uninitialize(Boolean appDomainShutdown) 
at System.Windows.Input.TextServicesContext.TextServicesContextShutDownListener.OnShutDown(Object target) 
at MS.Internal.ShutDownListener.HandleShutDown(Object sender, EventArgs e) 

Código de ensayo:

using NUnit.Framework; 

namespace TaskdockSidebarTests.Client 
{ 
    [TestFixture, RequiresSTA] 
    public class ElementHostRCWError 
    { 
     [Test] 
     public void WinForms() 
     { 
      var form = new System.Windows.Forms.Form(); 
      var elementHost = new System.Windows.Forms.Integration.ElementHost(); 
      form.Controls.Add(elementHost); 

      // If the form is not shown, the exception is not printed. 
      form.Show(); 

      // These lines are optional. The exception is printed with or without 
      form.Close(); 
      form.Controls.Remove(elementHost); 
      elementHost.Dispose(); 
      form.Dispose(); 
     } 

     [Test] 
     public void WPF() 
     { 
      var window = new Window(); 

      // If the window is not shown, the exception is not printed. 
      window.Show(); 

      window.Close(); 
     } 
    } 
} 
+0

Tal http://social.msdn.microsoft.com/forums/en-US/vststest/thread/e53fdc45-23f3-4aee-aad9-f63769f2c638/ ayuda –

+0

Lamentablemente, no puedo usar MTA, como WPF requiere STA. Crear el formulario y el elemento host en SetUp tampoco parece ser el truco. Argh. –

+0

Si no me equivoco, esta excepción no hace que unittest falle, ¿o sí? He encontrado la misma excepción al realizar una prueba unitaria de mis controles WPF, elegí ignorarlo ...;) – Bubblewrap

Respuesta

18

Mirando mi propio código de nuevo, la siguiente línea podría ayudarme con la prueba de WPF, justo al final.

Dispatcher.CurrentDispatcher.InvokeShutdown(); 
+0

Sweeeeet! Eso lo hizo. ¡Gracias! Ahora solo necesito averiguar cómo adaptar esto a mi arquitectura de prueba. –

+0

Decepcionante, una vez que un despachador está vinculado a un hilo (es decir, Dispatcher.CurrentDispatcher), no se puede asociar ningún otro despachador con ese hilo. Y una vez que se ha cerrado el despachador, no se puede reiniciar. Entonces, aunque esto resuelve mi problema, lamentablemente no puedo simplemente hacer una llamada a InvokeShutdown() en el método TearDown de mi clase de prueba base. –

+0

Intente iniciar un nuevo hilo STA en cada prueba unitaria, realice la prueba en ese nuevo hilo y espere a que el hilo termine con Thread.Join(). – Bubblewrap

1

es probable que pueda 't unit test las clases Window y Form en absoluto. Ambas aplicaciones WinForms y WPF tienen una clase Application utilizada para iniciar la instalación de tuberías subyacente (bombas de mensajes y otras cosas). Apuesto a que es la clave para evitar esa excepción.

No está haciendo eso allí y es posible que no pueda hacerlo.

Todas las recomendaciones para pruebas unitarias que he leído alguna vez son que refactoriza para que las clases Form y Window no hagan nada que necesite una prueba unitaria (como el patrón M-V-VM en WPF). Podría tener algo que ver con no poder mostrar la IU.

Existen otras maneras de probar una IU. This answer analiza UI de prueba de unidad.

+3

En realidad, las pruebas funcionan bien, acabo teniendo mucha basura en mis archivos de registro. Con respecto a las pruebas de IU frente a las pruebas lógicas de negocios correctas, tengo la creencia de que cuanto más me acerque a probar lo que realmente trata el usuario, mejor dormiré por la noche. –

+0

+1 para Joel y Patrick, porque creo que ambos tienen razón. Si bien estoy de acuerdo con Joel en que el diseño debe ser así, no se puede argumentar que a veces solo tienes que automatizar algunos controles/ventanas solo porque algún código viejo/frágil/no lo necesita. – quetzalcoatl

Cuestiones relacionadas