Las pruebas unitarias de ASP.NET Web API 2

por Tom FitzMacken

Descargar el proyecto completado

En esta guía y aplicación se muestra cómo crear pruebas unitarias sencillas para la aplicación api web 2. En este tutorial se muestra cómo incluir un proyecto de prueba unitaria en la solución y escribir métodos de prueba que comprueban los valores devueltos desde un método de controlador.

En este tutorial se da por supuesto que está familiarizado con los conceptos básicos de ASP.NET API web. Para ver un tutorial introductorio, consulte Introducción a ASP.NET Web API 2.

Las pruebas unitarias de este tema se limitan intencionadamente a escenarios de datos simples. Para las pruebas unitarias de escenarios de datos más avanzados, consulte Mocking Entity Framework cuando se realizan pruebas unitarias de ASP.NET Web API 2 (Simulación de Entity Framework en pruebas unitarias de ASP.NET Web API 2).

Versiones de software usadas en el tutorial

En este tema

Este tema contiene las siguientes secciones:

Prerrequisitos

Visual Studio 2017 Community, Professional o Enterprise Edition

Descargar código

Descargue el proyecto completado. El proyecto descargable incluye código de pruebas unitarias para este tema y para el tema Simulación de Entity Framework al realizar pruebas unitarias en ASP.NET Web API.

Creación de una aplicación con un proyecto de prueba unitaria

Puede crear un proyecto de prueba unitaria al crear la aplicación o agregar un proyecto de prueba unitaria a una aplicación existente. En este tutorial se muestran ambos métodos para crear un proyecto de prueba unitaria. Para seguir este tutorial, puede usar cualquiera de los enfoques.

Adición de un proyecto de prueba unitaria al crear la aplicación

Cree una aplicación web ASP.NET denominada StoreApp.

crear proyecto

En las ventanas New ASP.NET Project (Nuevo proyecto de ASP.NET), seleccione la plantilla Empty (Vacía ) y agregue carpetas y referencias principales para Web API. Seleccione la opción Agregar pruebas unitarias . El proyecto de prueba unitaria se denomina automáticamente StoreApp.Tests. Puede conservar este nombre.

creación de un proyecto de prueba unitaria

Después de crear la aplicación, verá que contiene dos proyectos.

dos proyectos

Adición de un proyecto de prueba unitaria a una aplicación existente

Si no creó el proyecto de prueba unitaria al crear la aplicación, puede agregarlo en cualquier momento. Por ejemplo, supongamos que ya tiene una aplicación denominada StoreApp y quiere agregar pruebas unitarias. Para agregar un proyecto de prueba unitaria, haga clic con el botón derecho en la solución y seleccione Agregar y nuevo proyecto.

agregar un nuevo proyecto a la solución

Seleccione Probar en el panel izquierdo y seleccione Proyecto de prueba unitaria para el tipo de proyecto. Asigne al proyecto el nombre StoreApp.Tests.

agregar proyecto de prueba unitaria

Verás el proyecto de tests unitarios en tu solución.

En el proyecto de prueba unitaria, agregue una referencia de proyecto al proyecto original.

Configuración de la aplicación Web API 2

En el proyecto StoreApp, agregue un archivo de clase a la carpeta Models denominada Product.cs. Reemplace el contenido del archivo por el código siguiente.

using System;

namespace StoreApp.Models
{
    public class Product
    {
        public int Id { get; set; }
        public string Name { get; set; }
        public decimal Price { get; set; }
    }
}

Compile la solución.

Haga clic con el botón derecho en la carpeta Controladores y seleccione Agregar y Nuevo Elemento con Scaffold. Seleccione Controlador de WEB API 2- Vacío.

agregar nuevo controlador

Establezca el nombre del controlador en SimpleProductController y haga clic en Agregar.

especificar controlador

Reemplace el código existente por el código siguiente. Para simplificar este ejemplo, los datos se almacenan en una lista en lugar de en una base de datos. La lista definida en esta clase representa los datos de producción. Observe que el controlador incluye un constructor que toma como parámetro una lista de objetos Product. Este constructor permite pasar datos de prueba al hacer pruebas unitarias. El controlador también incluye dos métodos asincrónicos para ilustrar los métodos asincrónicos de pruebas unitarias. Estos métodos asincrónicos se implementaron llamando a Task.FromResult para minimizar el código extraño, pero normalmente los métodos incluirían operaciones que consumen muchos recursos.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using System.Web.Http;
using StoreApp.Models;

namespace StoreApp.Controllers
{
    public class SimpleProductController : ApiController
    {
        List<Product> products = new List<Product>();        
           
        public SimpleProductController() { }

        public SimpleProductController(List<Product> products)
        {
            this.products = products;
        }

        public IEnumerable<Product> GetAllProducts()
        {
            return products;
        }

        public async Task<IEnumerable<Product>> GetAllProductsAsync()
        {
            return await Task.FromResult(GetAllProducts());
        }

        public IHttpActionResult GetProduct(int id)
        {
            var product = products.FirstOrDefault((p) => p.Id == id);
            if (product == null)
            {
                return NotFound();
            }
            return Ok(product);
        }

        public async Task<IHttpActionResult> GetProductAsync(int id)
        {
            return await Task.FromResult(GetProduct(id));
        }
    }
}

El método GetProduct devuelve una instancia de la interfaz IHttpActionResult . IHttpActionResult es una de las nuevas características de Web API 2 y simplifica el desarrollo de pruebas unitarias. Las clases que implementan la interfaz IHttpActionResult se encuentran en el espacio de nombres System.Web.Http.Results . Estas clases representan posibles respuestas de una solicitud de acción y corresponden a códigos de estado HTTP.

Compile la solución.

Ya está listo para configurar el proyecto de prueba.

Instalación de paquetes NuGet en el proyecto de prueba

Cuando se usa la plantilla Empty para crear una aplicación, el proyecto de prueba unitaria (StoreApp.Tests) no incluye ningún paquete NuGet instalado. Otras plantillas, como la plantilla de API web, incluyen algunos paquetes NuGet en el proyecto de prueba unitaria. Para este tutorial, debe incluir el paquete Microsoft ASP.NET Web API 2 Core en el proyecto de prueba.

Haga clic con el botón derecho en el proyecto StoreApp.Tests y seleccione Administrar paquetes NuGet. Debes seleccionar el proyecto StoreApp.Tests para agregar los paquetes a ese proyecto.

administrar paquetes

Busque e instale el paquete microsoft ASP.NET Web API 2 Core.

instalación del paquete principal de api web

Cierre la ventana Administrar paquetes NuGet.

Creación de pruebas

De forma predeterminada, el proyecto de prueba incluye un archivo de prueba vacío denominado UnitTest1.cs. Este archivo muestra los atributos que se usan para crear métodos de prueba. Para las pruebas unitarias, puede usar este archivo o crear su propio archivo.

UnitTest1

En este tutorial, crearás tu propia clase de test. Puede eliminar el archivo UnitTest1.cs. Agregue una clase denominada TestSimpleProductController.cs y reemplace el código por el código siguiente.

using System;
using System.Collections.Generic;
using System.Threading.Tasks;
using System.Web.Http.Results;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using StoreApp.Controllers;
using StoreApp.Models;

namespace StoreApp.Tests
{
    [TestClass]
    public class TestSimpleProductController
    {
        [TestMethod]
        public void GetAllProducts_ShouldReturnAllProducts()
        {
            var testProducts = GetTestProducts();
            var controller = new SimpleProductController(testProducts);

            var result = controller.GetAllProducts() as List<Product>;
            Assert.AreEqual(testProducts.Count, result.Count);
        }

        [TestMethod]
        public async Task GetAllProductsAsync_ShouldReturnAllProducts()
        {
            var testProducts = GetTestProducts();
            var controller = new SimpleProductController(testProducts);

            var result = await controller.GetAllProductsAsync() as List<Product>;
            Assert.AreEqual(testProducts.Count, result.Count);
        }

        [TestMethod]
        public void GetProduct_ShouldReturnCorrectProduct()
        {
            var testProducts = GetTestProducts();
            var controller = new SimpleProductController(testProducts);

            var result = controller.GetProduct(4) as OkNegotiatedContentResult<Product>;
            Assert.IsNotNull(result);
            Assert.AreEqual(testProducts[3].Name, result.Content.Name);
        }

        [TestMethod]
        public async Task GetProductAsync_ShouldReturnCorrectProduct()
        {
            var testProducts = GetTestProducts();
            var controller = new SimpleProductController(testProducts);

            var result = await controller.GetProductAsync(4) as OkNegotiatedContentResult<Product>;
            Assert.IsNotNull(result);
            Assert.AreEqual(testProducts[3].Name, result.Content.Name);
        }

        [TestMethod]
        public void GetProduct_ShouldNotFindProduct()
        {
            var controller = new SimpleProductController(GetTestProducts());

            var result = controller.GetProduct(999);
            Assert.IsInstanceOfType(result, typeof(NotFoundResult));
        }

        private List<Product> GetTestProducts()
        {
            var testProducts = new List<Product>();
            testProducts.Add(new Product { Id = 1, Name = "Demo1", Price = 1 });
            testProducts.Add(new Product { Id = 2, Name = "Demo2", Price = 3.75M });
            testProducts.Add(new Product { Id = 3, Name = "Demo3", Price = 16.99M });
            testProducts.Add(new Product { Id = 4, Name = "Demo4", Price = 11.00M });

            return testProducts;
        }
    }
}

Ejecución de pruebas

Ya está listo para ejecutar las pruebas. Se probará todo el método marcado con el atributo TestMethod . En el elemento de menú Probar , ejecute las pruebas.

ejecutar pruebas

Abra la ventana Explorador de pruebas y observe los resultados de las pruebas.

resultados de pruebas

Resumen

Ha completado este tutorial. Los datos de este tutorial se simplificaron intencionadamente para centrarse en las condiciones de pruebas unitarias. Para las pruebas unitarias de escenarios de datos más avanzados, consulte Mocking Entity Framework cuando se realizan pruebas unitarias de ASP.NET Web API 2 (Simulación de Entity Framework en pruebas unitarias de ASP.NET Web API 2).