Шаг 10: Queries -- чтение данных
Query не изменяет данные, а только читает и возвращает DTO. Это вторая сторона CQRS.
GetOrderQuery
В папке Orders/Queries/GetOrder:
using MediatR;
using OrderManagement.Application.Orders.DTOs;
namespace OrderManagement.Application.Orders.Queries.GetOrder;
public record GetOrderQuery(Guid OrderId) : IRequest<OrderDto>;
public class GetOrderQueryHandler
: IRequestHandler<GetOrderQuery, OrderDto>
{
private readonly IOrderRepository _orderRepository;
public GetOrderQueryHandler(IOrderRepository orderRepository)
=> _orderRepository = orderRepository;
public async Task<OrderDto> Handle(
GetOrderQuery query, CancellationToken ct)
{
var order = await _orderRepository
.GetByIdAsync(query.OrderId, ct)
?? throw new OrderNotFoundException(query.OrderId);
return new OrderDto(
order.Id, order.CustomerId,
order.Status.ToString(),
order.ShippingAddress.ToString(),
order.TotalAmount.Amount,
order.TotalAmount.Currency,
order.CreatedAt,
order.Items.Select(i => new OrderItemDto(
i.Id, i.ProductId, i.ProductName,
i.UnitPrice.Amount, i.Quantity,
i.TotalPrice.Amount)).ToList());
}
}
Маппинг Order -> OrderDto преобразует доменную сущность в объект для клиента. Status.ToString() конвертирует enum в строку "Confirmed". LINQ .Select() преобразует каждый OrderItem в OrderItemDto.
GetCustomerOrdersQuery
public record GetCustomerOrdersQuery(string CustomerId)
: IRequest<List<OrderDto>>;
public class GetCustomerOrdersQueryHandler
: IRequestHandler<GetCustomerOrdersQuery, List<OrderDto>>
{
private readonly IOrderRepository _orderRepository;
public GetCustomerOrdersQueryHandler(
IOrderRepository orderRepository)
=> _orderRepository = orderRepository;
public async Task<List<OrderDto>> Handle(
GetCustomerOrdersQuery query, CancellationToken ct)
{
var orders = await _orderRepository
.GetByCustomerIdAsync(query.CustomerId, ct);
return orders.Select(order => new OrderDto(
order.Id, order.CustomerId,
order.Status.ToString(),
order.ShippingAddress.ToString(),
order.TotalAmount.Amount,
order.TotalAmount.Currency,
order.CreatedAt,
order.Items.Select(i => new OrderItemDto(
i.Id, i.ProductId, i.ProductName,
i.UnitPrice.Amount, i.Quantity,
i.TotalPrice.Amount)).ToList()
)).ToList();
}
}