38 lines
1.6 KiB
C#
38 lines
1.6 KiB
C#
using MediatR;
|
|
using Microsoft.EntityFrameworkCore;
|
|
using SequenceAuth.Example.Domain;
|
|
using SequenceAuth.Example.Infrastructure;
|
|
|
|
namespace SequenceAuth.Example.Features.Todos;
|
|
|
|
public enum ChangeTodoStatusOutcome { Success, NotFound, Unauthorized }
|
|
|
|
public record ChangeTodoStatusResult(ChangeTodoStatusOutcome Outcome, TodoItem? Item);
|
|
|
|
public record ChangeTodoStatusCommand(Guid TodoId, Guid UserId, TodoStatus NewStatus) : IRequest<ChangeTodoStatusResult>;
|
|
|
|
public class ChangeTodoStatusCommandHandler(AppDbContext dbContext) : IRequestHandler<ChangeTodoStatusCommand, ChangeTodoStatusResult>
|
|
{
|
|
public async Task<ChangeTodoStatusResult> Handle(ChangeTodoStatusCommand request, CancellationToken cancellationToken)
|
|
{
|
|
var todo = await dbContext.Todos.FirstOrDefaultAsync(t => t.Id == request.TodoId, cancellationToken);
|
|
|
|
return todo switch
|
|
{
|
|
null => new ChangeTodoStatusResult(ChangeTodoStatusOutcome.NotFound, null),
|
|
{ UserId: var userId } when userId != request.UserId => new ChangeTodoStatusResult(ChangeTodoStatusOutcome.Unauthorized, null),
|
|
_ => await UpdateStatusAsync(todo, request.NewStatus, cancellationToken)
|
|
};
|
|
}
|
|
|
|
private async Task<ChangeTodoStatusResult> UpdateStatusAsync(TodoItem todo, TodoStatus newStatus, CancellationToken cancellationToken)
|
|
{
|
|
var updatedTodo = todo with { Status = newStatus };
|
|
|
|
dbContext.Entry(todo).CurrentValues.SetValues(updatedTodo);
|
|
await dbContext.SaveChangesAsync(cancellationToken);
|
|
|
|
return new ChangeTodoStatusResult(ChangeTodoStatusOutcome.Success, updatedTodo);
|
|
}
|
|
}
|