Primeros pasos con Moq ( parte II )

Después de unas semanas liadas con el cambio de residencia y la incorporación a Plain Concepts volvemos a la carga con los artículos referentes a Moq ( aquí está el primero de la serie ).

Empecemos por el principio, es decir, por el constructor de nuestro mock. Al hacer el new tenemos dos opciones a la hora de indicar el comportamiento de nuestro objeto imitador:

  • MockBehaviour.Loose: el mock devolverá siempre valores por defecto si no está definido el Returns y si se llama a una función del mock que no tenga un Setup, no lanzará ninguna excepción
  • MockBehaviour.Strict: si se llama a una función del mock que no tenga un Setup, se lanzará una excepción y el test fallará.

Yo recomiendo utilizar la segunda opción ( MockBehaviour.Strict ) ya que seremos mucho más conscientes de lo que está haciendo el test.

En el anterior artículo vimos el uso de la función Verify. Esta función tiene 9 sobrecargas, en las que básicamente se pueden configurar dos cosas:

  • El string de error en caso de no cumplirse la condición.
  • El número de veces que queremos verificar que se ha hecho la llamada a la función.

Esta segunda opción se hace mediante la utilización de los métodos estáticos de la estructura Times. Ejemplos de utilización podrían ser:

  • Times.Never(): queremos verificar que la función nunca se llama.
  • Times.Once(): queremos verificar que la función sólo se llama una vez.
  • Times.Exactly(3): queremos verificar que la función se llama tres veces.
  • Times.Between(1, 5, Range.Inclusive): queremos verificar que la función se llama entre 1 y 5 veces, ambas incluidas.

En el anterior artículo también vimos como verificar que se había establecido el valor de una propiedad. Obviamente también podemos verificar que el valor de una propiedad se haya recuperado. Podemos verlo en el siguiente ejemplo:

[TestMethod]
public void Verify_Timeout_was_get()
{
    var mockDao = new Mock<IDAO>();
    AssetManager assetManager = new AssetManager(mockDao.Object);
    mockDao.VerifyGet(dao => dao.Timeout);
}

Siguiendo con las propiedades, también les podemos hacer un setup. La versión más sencilla es tratarlas como una función, de manera que podemos especificar el valor que queremos que devuelvan cuando se les hace un get. Para hacer esto, actuamos como si de una función se tratara:

mockDao.Setup(dao => dao.Timeout).Returns(1500);

La segunda versión es un poco más compleja, no en el código que tenemos que teclear ( muy sencillo ) sino en las funcionalidades que nos da. Si utilizamos el siguiente código:

mockDao.SetupProperty(dao => dao.Timeout);

estamos indicando a Moq que empiece a trackear la propiedad Timeout, con lo que el mock será consciente de cuando estemos intentando establecer un valor a Timeout y se guardará tal valor para futuros usos. Esto nos permitirá poder escribir un código tal como este:

[TestMethod]
public void Track_timeout_property()
{
    var mockDao = new Mock<IDAO>();
    mockDao.SetupProperty(dao => dao.Timeout);
            
    IDAO idao = mockDao.Object;
    idao.Timeout = 400;
    Assert.AreEqual(400, idao.Timeout);
}

Y esto es todo por por hoy. En futuros artículos veremos más características de este framework.

A testear!!

 PD: Añado aquí el código de este artículo y del anterior de la série. [View:/cfs-file.ashx/__key/CommunityServer.Components.PostAttachments/00.00.19.03.06/Moq.zip]