From e5b2cac11209b16cae11cf02c9092451f491a557 Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Wed, 31 Aug 2022 15:14:32 -1000 Subject: [PATCH] Param binding refactor (#27) --- .../samples/arg-lists/Models/Todo.cs | 9 ++ .../samples/arg-lists/Models/TodoDb.cs | 18 +++ .../samples/arg-lists/Models/TodoItemDTO.cs | 12 ++ .../minimal-apis/samples/arg-lists/Program.cs | 106 +++++++++++------- 4 files changed, 107 insertions(+), 38 deletions(-) create mode 100644 fundamentals/minimal-apis/samples/arg-lists/Models/Todo.cs create mode 100644 fundamentals/minimal-apis/samples/arg-lists/Models/TodoDb.cs create mode 100644 fundamentals/minimal-apis/samples/arg-lists/Models/TodoItemDTO.cs diff --git a/fundamentals/minimal-apis/samples/arg-lists/Models/Todo.cs b/fundamentals/minimal-apis/samples/arg-lists/Models/Todo.cs new file mode 100644 index 0000000..de34db0 --- /dev/null +++ b/fundamentals/minimal-apis/samples/arg-lists/Models/Todo.cs @@ -0,0 +1,9 @@ +namespace TodoApi.Models; + +public class Todo +{ + public int Id { get; set; } + public string? Name { get; set; } + public bool IsComplete { get; set; } + public string? Secret { get; set; } +} diff --git a/fundamentals/minimal-apis/samples/arg-lists/Models/TodoDb.cs b/fundamentals/minimal-apis/samples/arg-lists/Models/TodoDb.cs new file mode 100644 index 0000000..09ef3b7 --- /dev/null +++ b/fundamentals/minimal-apis/samples/arg-lists/Models/TodoDb.cs @@ -0,0 +1,18 @@ +using Microsoft.EntityFrameworkCore; + +namespace TodoApi.Models; + +class TodoDb : DbContext +{ + public TodoDb(DbContextOptions options) + : base(options) { } + + public DbSet Todos => Set(); +} + + +record TodoItemRequest(int Id, TodoDb Db); + +record CreateTodoItemRequest(TodoItemDTO Dto, TodoDb Db); + +record EditTodoItemRequest(int Id, TodoItemDTO Dto, TodoDb Db); diff --git a/fundamentals/minimal-apis/samples/arg-lists/Models/TodoItemDTO.cs b/fundamentals/minimal-apis/samples/arg-lists/Models/TodoItemDTO.cs new file mode 100644 index 0000000..81800d3 --- /dev/null +++ b/fundamentals/minimal-apis/samples/arg-lists/Models/TodoItemDTO.cs @@ -0,0 +1,12 @@ +namespace TodoApi.Models; + +public class TodoItemDTO +{ + public int Id { get; set; } + public string? Name { get; set; } + public bool IsComplete { get; set; } + + public TodoItemDTO() { } + public TodoItemDTO(Todo todoItem) => + (Id, Name, IsComplete) = (todoItem.Id, todoItem.Name, todoItem.IsComplete); +} diff --git a/fundamentals/minimal-apis/samples/arg-lists/Program.cs b/fundamentals/minimal-apis/samples/arg-lists/Program.cs index 8ca013a..c0204bb 100644 --- a/fundamentals/minimal-apis/samples/arg-lists/Program.cs +++ b/fundamentals/minimal-apis/samples/arg-lists/Program.cs @@ -1,4 +1,6 @@ +// using Microsoft.EntityFrameworkCore; +using TodoApi.Models; var builder = WebApplication.CreateBuilder(args); builder.Services.AddDatabaseDeveloperPageExceptionFilter(); @@ -8,12 +10,17 @@ var app = builder.Build(); app.MapGet("/todoitems", async (TodoDb db) => await db.Todos.Select(x => new TodoItemDTO(x)).ToListAsync()); -app.MapGet("/todoitems/{id}", async ([AsParameters] TodoItemRequest request) => - await request.Db.Todos.FindAsync(request.Id) +// +app.MapGet("/todoitems/{id}", async (int Id, TodoDb Db) => + await Db.Todos.FindAsync(Id) is Todo todo ? Results.Ok(new TodoItemDTO(todo)) : Results.NotFound()); +// +// Remaining code removed for brevity. +// +// app.MapPost("/todoitems", async ([AsParameters] CreateTodoItemRequest request) => { var todoItem = new Todo @@ -27,8 +34,63 @@ app.MapPost("/todoitems", async ([AsParameters] CreateTodoItemRequest request) = return Results.Created($"/todoitems/{todoItem.Id}", new TodoItemDTO(todoItem)); }); +// -app.MapPut("/todoitems/{id}", async ([AsParameters] EditTodoItemRequest request) => +// +app.MapPut("/todoitems/{id}", async (int Id, TodoItemDTO Dto, TodoDb Db) => +{ + var todo = await Db.Todos.FindAsync(Id); + + if (todo is null) return Results.NotFound(); + + todo.Name = Dto.Name; + todo.IsComplete = Dto.IsComplete; + + await Db.SaveChangesAsync(); + + return Results.NoContent(); +}); +// + +// +app.MapDelete("/todoitems/{id}", async (int Id, TodoDb Db) => +{ + if (await Db.Todos.FindAsync(Id) is Todo todo) + { + Db.Todos.Remove(todo); + await Db.SaveChangesAsync(); + return Results.Ok(new TodoItemDTO(todo)); + } + + return Results.NotFound(); +}); +// + +// --- [AsParameters] go here ---------------------- +// +app.MapGet("/ap/todoitems/{id}", async ([AsParameters] TodoItemRequest request) => + await request.Db.Todos.FindAsync(request.Id) + is Todo todo + ? Results.Ok(new TodoItemDTO(todo)) + : Results.NotFound()); +// + +// +app.MapPost("/ap/todoitems", async ([AsParameters] CreateTodoItemRequest request) => +{ + var todoItem = new Todo + { + IsComplete = request.Dto.IsComplete, + Name = request.Dto.Name + }; + + request.Db.Todos.Add(todoItem); + await request.Db.SaveChangesAsync(); + + return Results.Created($"/todoitems/{todoItem.Id}", new TodoItemDTO(todoItem)); +}); +// +app.MapPut("/ap/todoitems/{id}", async ([AsParameters] EditTodoItemRequest request) => { var todo = await request.Db.Todos.FindAsync(request.Id); @@ -41,8 +103,10 @@ app.MapPut("/todoitems/{id}", async ([AsParameters] EditTodoItemRequest request) return Results.NoContent(); }); +// -app.MapDelete("/todoitems/{id}", async ([AsParameters] TodoItemRequest request) => +// +app.MapDelete("/ap/todoitems/{id}", async ([AsParameters] TodoItemRequest request) => { if (await request.Db.Todos.FindAsync(request.Id) is Todo todo) { @@ -55,37 +119,3 @@ app.MapDelete("/todoitems/{id}", async ([AsParameters] TodoItemRequest request) }); app.Run(); - -public class Todo -{ - public int Id { get; set; } - public string? Name { get; set; } - public bool IsComplete { get; set; } - public string? Secret { get; set; } -} - -public class TodoItemDTO -{ - public int Id { get; set; } - public string? Name { get; set; } - public bool IsComplete { get; set; } - - public TodoItemDTO() { } - public TodoItemDTO(Todo todoItem) => - (Id, Name, IsComplete) = (todoItem.Id, todoItem.Name, todoItem.IsComplete); -} - - -class TodoDb : DbContext -{ - public TodoDb(DbContextOptions options) - : base(options) { } - - public DbSet Todos => Set(); -} - -record TodoItemRequest(int Id, TodoDb Db); - -record CreateTodoItemRequest(TodoItemDTO Dto, TodoDb Db); - -record EditTodoItemRequest(int Id, TodoItemDTO Dto, TodoDb Db);