Entendiendo los Web API con .Net Core y Entity framework
Un sencillo pero potente API que te mostrará cómo funciona esta tecnología y cómo se programa en un entorno real

En este post vamos a aprender a hacer un backend, mediante un API, primero te recomiendo que leas este post acerca de qué es un API para que tengas un mejor alcance 😉 luego este otro post te ayudará a conocer mejor de que va esto de .Net Core y luego empecemos.

El proyecto que desarrollaremos juntos no es un sistema completo evidentemente, pero sí es lo suficiente como para que puedas defenderte allá afuera y más aún si estas iniciando o tienes conocimientos pero sin entender bien el porqué de las cosas, hay tanta información esparcida allá afuera que es difícil a veces consolidar todo, es por eso que me tomé un tiempo de consultar fuentes y reunir recursos y los pude consolidar aquí.

Como lo he mencionado en anteriores posts, si estamos empezando en algo o tenemos un conocimiento regular apliquemos Pareto, para qué complicarnos la vida tratando de querer aprender todo de porrazo? Concentrémonos en ese 20% de conocimiento que utilizaremos el 80% del tiempo, eso es lo que se pretende abarcar en esta entrada, en este Web API abarcaremos cómo se hacen los métodos GET, POST, PUT y DELETE para la entidad autores, haciendo uso de buenas prácticas y configuraciones adecuadas bajo el enfoque de Entity framework Code first, es decir EF se encargará de crear la base de datos, aquí el programador sólo se preocupa de hacer su código y EF traducirá eso a un esquema de base de datos. Let's do it.

Creación y entorno del proyecto en VS

Este proyecto será desarrollado en Visual Studio 2019 y al crear el proyecto debemos tener en cuenta las siguientes características:

  • .NET 5
  • No authentication
  • HTTPS Configured
  • Open API support enabled

Al crear el proyecto notaremos como Visual Studio nos crea por defecto un controlador llamado WeatherForecast, si ese es el caso, bórralo.

Instalar desde Nuget las siguientes dependencias:

  • Microsoft.EntityFrameworkCore.SqlServer
  • Microsoft.EntityFrameworkCore.Tools

Primer controlador y entidad

Un controlador no es más que una clase pero que hereda de:

ControllerBase

Y tiene los siguientes decoradores:

[ApiController]

[Route("api/autores")]

Así que creamos una clase en la carpeta Controllers llamada AutoresController (aproveché para poner una ruta en el decorador Route).

Creamos una carpeta llamada Entidades, aquí crearás las clases para cada entidad, cada entidad corresponderá con una tabla en la base de datos, salvo aquellas que explícitamente indiques que no. Crea tu primera entidad así:

public class Autor
{
    public int Id { get; set; }
    public string Nombre { get; set; }
}

Entonces hasta ahora nuestro proyecto va quedando así:

Nuestro primer método: GET

En el controlador AutorController codear el primer método en este caso GET:

    [ApiController]
    [Route("api/autores")]
    public class AutoresController : ControllerBase
    {
        [HttpGet]
        public ActionResult<List<Autor>> Get()
        {
			//Por ahora una lista estática hasta que creemos la bd
            return new List<Autor>()
            {
                new Autor { Id = 1, Nombre = "Gerson" },
                new Autor { Id = 2, Nombre = "Luis" },
                new Autor { Id = 3, Nombre = "Antonio" }
            };
        }
    }

Como ves en el comentario, por ahora nuestro método get sólo devolverá una lista estática para poder probarlo rápidamente, más adelante actualizaremos este método.

La clase ApplicationDbContext

Esta clase nos servirá para configurar las tablas que queramos que se creen en la base de datos, ya que estamos usando el enfoque Code First.

		public class ApplicationDbContext : DbContext //hacemos que herede de DbContext y generamos constructor con options
    {
        public ApplicationDbContext(DbContextOptions options) : base(options)
        {

        }
        public DbSet<Autor> Autor { get; set; } //el nombre de esta propiedad será el que tenga la tabla generada en la BD
    }

Configurando la cadena de conexión

Esto se hace desde el proveedor de configuración

appsettings.Development.json

Esto es mejor que hardcodear en nuestras clases, y agregamos lo siguiente:

{
  "Logging": {
    "LogLevel": {
      "Default": "Information",
      "Microsoft": "Warning",
      "Microsoft.Hosting.Lifetime": "Information"
    }
  },
  "connectionStrings": {
    "defaultConnection": "Data Source = .;Initial Catalog=Biblioteca;Integrated Security=true"
  }
}

Configurar la clase Startup

Agregamos las siguientes líneas al método ConfigureServices de la clase Startup:

public void ConfigureServices(IServiceCollection services)
        {

            services.AddControllers();

            //Configurando la conexión a la BD y el contexto de datos
            services.AddDbContext<ApplicationDbContext>(options =>
                options.UseSqlServer(Configuration.GetConnectionString("defaultConnection")));

            services.AddSwaggerGen(c =>
            {
                c.SwaggerDoc("v1", new OpenApiInfo { Title = "WebAPIBiblioteca", Version = "v1" });
            });
        }

Creamos la primera migración

Una migración es como una serie es configuraciones guardadas, como una especia de fotografía en un momento dado, que toma toda la configuración de nuestro código para posteriormente plasmarla en nuestra base de datos.

Las migaciones se administran desde la consola de del Package manager, para abrirla vamos al menú Tools > Nuget Package Manager > Package Manager Console y ejecutamos el comando:

Add-migration Inicial

Lo que esto hace es crear una migración, en este caso como es la primera, crea la carpeta Migrations con las definiciones que tendrán las tablas en la base de datos, confirmémoslo:

Antes
Después

Ahora enviamos todo eso a la base de datos con el comando:

update-database

Método POST

En el controlador de Autores, codeamos el método post

Para poder hacer uso del ApplicationDbContext definido antes, necesitamos usar la inyección de dependencias.

private readonly ApplicationDbContext context;

public AutoresController(ApplicationDbContext context) //constructor
{
    this.context = context;
}

Procedemos con el método en sí aplicando programación asíncrona:

        [HttpPost]
        public async Task<ActionResult> Post(Autor autor)
        {
            context.Add(autor);
            await context.SaveChangesAsync();
            return Ok();
        }

Y actualizamos de paso el método get que antes tenía una lista estática

        [HttpGet]
        public async Task<ActionResult<List<Autor>>> Get()
        {            
            return await context.Autor.ToListAsync();            
        }

Probamos con Postman o Swagger, debería funcionar y también revisamos en la base de datos ✔

Funciona yeah crack!

Método PUT

De forma similar al post y haciendo uso de la programación asíncrona y buenas prácticas tenemos:

		[HttpPut("{id:int}")]//especificamos un parámetro de ruta
        public async Task<ActionResult> Put(Autor autor, int id)
        {
            if (autor.Id != id)
                return BadRequest("El id del autor no coincide con el id de la URL");

            var existe = await context.Autor.AnyAsync(x => x.Id == id);
            if (!existe)
                return NotFound();

            context.Update(autor);            
            await context.SaveChangesAsync();
            return Ok();            
        }

Método DELETE

Finalmente el método para eliminar:

		[HttpDelete("{id:int}")]
        public async Task<ActionResult> Delete(int id)
        {
            var existe = await context.Autor.AnyAsync(x => x.Id == id);
            if (!existe)
                return NotFound();

            context.Remove(new Autor() { Id = id });
            await context.SaveChangesAsync();

            return Ok();
        }

Te lo mereces por haber llegado hasta aquí crack

Finalmente...

En esta entrada hemos desarrollado un API para una entidad, aplicando buenas prácticas como programación asíncrona, inyección de dependencias, validaciones básicas, el uso de ActionResult entre otros, sin embargo hace falta algunas cosas más, que serán desarrolladas en un próximo post, de momento practica y practica crack! hazlo tu mismo.

Ya sabes, si este contenido te aportó conocimiento compártela crack, eso ayuda bastante, hasta la vista baby 💪😉

2 comentarios en «Entendiendo los Web API con .Net Core y Entity framework»

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *