tutorial rhinoceros norma español caracteristicas .net unit-testing mocking rhino-mocks stubbing

.net - rhinoceros - ¿Los apéndices y simulacros de Rhino Mocks solo son buenos para interfaces?



ieee std 830 1998 (5)

¿Es correcto que los talones y simulacros de Rhino Mocks solo son buenos para interfaces, no para clases concretas? Pasé bastante tiempo tratando de hacer funcionar este pedazo de código. No esperaba que el pubSubClient aplastado llamara siempre al método Send de la clase. Ese método tiene algunas dependencias y lanza excepción.

[Test] public void Test01() { PubSubMessage psm = new PubSubMessage(); var pubSubClient = MockRepository.GenerateStub<PubSubClient>(); pubSubClient.Stub(x => x.Send(psm)).IgnoreArguments().Return(null); // actual PubSubClient Send method throws exception // the rest of the test is skipped... }

Sin embargo, cuando extraje la interfaz y ejecuto la misma prueba con IPubSubClient, parece que está funcionando como se esperaba.

¿Significa que tengo que extraer la interfaz para cada clase que quiero simular / apilar con Rhino? ¿O me falta algo, técnica o conceptualmente?

ACTUALIZACIÓN : OK, parece que descubrí qué parte faltaba: Rhino Mocks no puede interceptar llamadas a métodos no virtuales . Entonces, supongo que tengo interfaces o hago que todos los métodos de la clase concreta sean virtuales. Por favor corrígeme si hay otra opción.


Eso es esencialmente correcto, y generalmente es una buena práctica. Sin embargo, solo es realmente útil para un tipo específico de codificación.

No pienses en los objetos como cosas que un ''poder superior'' puede manipular. En su lugar, piensa en ellos como ''personas'' autónomas que pueden enviarse mensajes entre sí. Una interfaz representa los mensajes enviados por un solo objeto.

Luego, usa simulacros para verificar que se enviaron los mensajes correctos, no para proporcionar implementaciones falsas de dependencias.

Lo ideal es que no cree una interfaz que coincida exactamente con una clase existente; en cambio, la clase que consume la interfaz declara sus necesidades en forma de una interfaz.


La respuesta de Bryan de usar simulacros parciales es incorrecta. Para eso no son las mofas parciales.

La respuesta de Jon Erickson es correcta en su mayoría: Rhino Mocks y Moq no pueden interceptar llamadas no virtuales, ni pueden interceptar propiedades o métodos estáticos. Eso significa que no puedes fingir lo siguiente:

DateTime.Now; // static property, can''t fake static property someClass.SomeNonVirtualMethod(); // can''t fake non-virtual method sealedClass.Foo(); // can''t fake anything on sealed classes Utilities.SomeStaticMethod(); // can''t fake static methods someList.Any(); // can''t fake extension methods like Linq''s .Any()

TypeMock puede falsificar estos, como Jon mencionó.

Debe tenerse en cuenta que existe un marco de simulación adicional que puede interceptar todas las llamadas: el marco de Microsoft Moles . Funciona de la misma manera que lo hace TypeMock, usa la API del generador de perfiles .NET para interceptar llamadas.

Moles es gratis (por ahora). También es beta. Los lunares solo funcionan con las herramientas de Microsoft Pex . Y su API es claramente inferior a la elegante y refinada API de TypeMock.



No creo que haya otra forma de hacer esto que no sea hacer que cualquier método que quiera simular sea virtual. Creo que la forma en que se crean los simulacros de las clases concretas es mediante una subclasificación dinámica de la clase concreta que se está burlando y luego anular los métodos dados con el comportamiento que especifique en la prueba, por lo que esto requiere un método virtual para funcionar correctamente.


Tienes que hacer los métodos virtuales. Las simulaciones de Rhino (y la mayoría de los otros marcos de aislamiento) utilizan clases de proxy para crear los apéndices / simulacros.

Si usa el aislador TypeMock, puede simular cualquier cosa porque este marco de aislamiento utiliza la API del Analizador de .NET para crear sus ''stubs / mocks''