0

Implementando OData en .Net 6 #2

Hasta el momento tenemos lista nuestra base de datos, nuestro contexto con las entidades y nuestro controller configurado para con el soporte OData. Pero no termina acá, falta agregar los servicios necesarios en nuestro program.cs. 

Lo primero que debemos agregar es el siguiente método estático el cual configura y activa OData para nuestra entidad Product:

static IEdmModel GetEdmModel()
{
    ODataConventionModelBuilder builder = new();
    builder.EntitySet<Product>("Products");
    return builder.GetEdmModel();
}

Luego agregar a los servicios ODATA:

builder.Services
    .AddControllers()    
    .AddOData(opt => opt.AddRouteComponents("v1", GetEdmModel()).Filter().Select().Expand());

Te dejo el program.cs completo:

using Demo.OData.Models;
using Demo.OData.Services;
using Microsoft.AspNetCore.OData;
using Microsoft.EntityFrameworkCore;
using Microsoft.OData.Edm;
using Microsoft.OData.ModelBuilder;

static IEdmModel GetEdmModel()
{
    ODataConventionModelBuilder builder = new();
    builder.EntitySet<Product>("Products");
    return builder.GetEdmModel();
}

var builder = WebApplication.CreateBuilder(args);

builder.Services.AddDbContext<AdventureWorksContext>(
        options =>
            options.UseSqlServer(builder.Configuration.GetConnectionString("Default"))
    );

builder.Services
    .AddControllers()    
    .AddOData(opt => opt.AddRouteComponents("v1", GetEdmModel()).Filter().Select().Expand());

builder.Services.AddSwaggerGen(c =>
{
    c.SwaggerDoc("v1", new() { Title = "Demo.OData", Version = "v1" });
});

var app = builder.Build();

// Configure the HTTP request pipeline.
if (app.Environment.IsDevelopment())
{
    app.UseSwagger();
    app.UseSwaggerUI(c => c.SwaggerEndpoint("/swagger/v1/swagger.json", "Demo.OData v1"));
}

app.UseHttpsRedirection();

app.UseAuthorization();

app.MapControllers();

app.Run();

Bien, todo listo, ha llegado el momento de las pruebas. Ejecutaremos la com aplicación, si todo está correcto nos lanzará un navegador donde podremos visualizar los servicios que tenemos por medio de la interfaz de Swagger.

La imagen tiene un atributo ALT vacío; su nombre de archivo es aGCNMb79dkdut4ZpsWnNqgBRAf0AxMeHAG6Dj_zrcZ-zHH0GwHK1lnD7fptlHiJUBrgvLd1HZV0SsMy-61cKhgaO0AUXcOA5HEyXvlmXi66KRpuZAIFiUWjNs-GCmqSBIFadTwbCv657TTpBojRZ1-M

Vamos a probar los GET. Como comentamos antes, es posible pasarle parámetros. Pero primero vemos al Get que tiene como parámetro el Pagesize, nos de

https://localhost:7093/v1/Products
La imagen tiene un atributo ALT vacío; su nombre de archivo es Vc6uQi68SdIGDvZfLnBLHdCtTAPrtZYbIXxrtvfm3nJ63KYOHHp_owbIM3QcqURzI6NycB4k855E1_bwmF7egom3keGk5JZS9D1_ynq594kgvC3fRo5iQ6_6DDY9XEh2ajNO2Ncuxzy2UkScDl3SeJg

Ahora supongamos que solamente quiere traerme el nombre, muy simple, podemos usar el parámetro $select=name

https://localhost:7093/v1/Products?select=Name
La imagen tiene un atributo ALT vacío; su nombre de archivo es 8nRwDIFKVjLPIgrdM25gaYxDsuoAK6Rfi0LqZjKxLPavC78C0CNWk5-m91QSVpqxuoZi-9dKXgxvC1nJ0nNUVus-kBQdwIjsF88aPQ1ruuKKIx9FWpHQPKfPuzyq97Fpz4yVyfm_6_4rG5MN9svZfu4

Si deseamos traer por ejemplo, Name y Color, debemos usar $select=name, color. Lo siguiente será filtrar por el ProductId que es la Primary Key de la entidad.

https://localhost:7093/v1/Products/320?select=Name, Color

La imagen tiene un atributo ALT vacío; su nombre de archivo es hocaQJHajIZM1BrgD-r-DhOhsDYjbpMSAcT62JuuCsZvEF8bNIwzWkOoHEj-ZGQSldty94P1wRiKnHejJIQn3cqHSbb_nZ1LwR_iHdguWrRuiWcJehwpaA1LXIkulOdCyab_d3m1GnWq3VEswkYPJag

Probemos almacenar en la base de datos por medio del verbo POST. Algo que tenemos que tener presente, en nuestra base de datos de AdventureWorks, la tabla Products tiene relaciones. Así que si no le enviamos valores correctos de las relaciones fallará. En nuestra primera prueba enviaremos todos los datos de las foreign key.

La imagen tiene un atributo ALT vacío; su nombre de archivo es l2Wrey14BkLVNIuVX5tgasja7M7C9wEaprrFBGEAdx9LuruWsuA6rUYIvj-86zONkJyiRUhBhBe7La_4IUplg3S34o3Fr4pUEWxDY_Y-uR381nt0vzVF-z_nb5MIrw9yk3wYpNuXQA9z5EE4J5A5lKQ

Ahora supongamos que además de enviar estos valores, también queremos enviar Color porque es una columna de la entidad. Podemos hacerlo: 

La imagen tiene un atributo ALT vacío; su nombre de archivo es h1s-0wqYStPdrrZ6XwDTVqLy2mtY3Q8Nj_letuR4-DsxPAwf3PqWWgQYAUKu_OuCIytThDQz26gWQWGuMeOhWHbybmEdwvVIE6RmFKKj8M6syHRcErwypshIZXYamb_eZC7Q1Gya-549faR-KixoquU

Esto nos indica que no es necesario que enviemos todos los campos si no los necesitamos podemos enviar los que nos interesen.

Ahora el patch, como comentamos antes, el patch solo hará un cambio a un producto por medio de key, vamos cambiar el color de la entidad anterior de blue a green.

La imagen tiene un atributo ALT vacío; su nombre de archivo es KfR7I_NOpbuCtGnJ7tlvrjeYux87mOcF4zgUj4Keikr0CZoXX0ksEtWhfpp4QhKLL7X3l7GQI_9bU_NRX9Ehf3z4bGxB7w9W7LR63ehDDQboZbHI23k-Z5T40S2pbDEMDIO-sv8LI3dEx6MPR1zM6Hg

Solo nos queda el delete, veamos como se ve en postman:

La imagen tiene un atributo ALT vacío; su nombre de archivo es xpNwoirH-iPh3Goiz2osOuZi0HxocZSJqYkTMguzWWQzk7MmPLlkCfukG1wq7VHoTcHjLPuAUwcZDbule2kt57ULiM6t3VwtbMh9homYN8cN1-wjJN_ktOMfsgxCHJP3WxjBRzBr1l9nkTLOaZ1v8oc

Conclusiones

La implementación de OData es bastante sencilla, tal vez un poco laboriosa al principio, pero una vez lista tiene interesantes beneficios. El que me gustaría destacar es la reducción de DTO (Data Transfer Object) que van desde nuestros servidores de backend hasta nuestros frontend reduciendo el tráfico de red. Espero que les haya gustado. En futuros post veremos algunas funcionalidades más de OData.

Fernando Sonego

Deja una respuesta

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