Невозможно привести объект типа AsyncStateMachineBox System.Threading.Tasks.VoidTaskResult к типу System.Threading.Tasks.Task

Я новичок в веб-API ASP.NET и пытаюсь использовать внедрение зависимостей Entity Framework Core для данных POST в контроллер API с использованием шаблона MediatR. Но каждый раз, когда я запускаю свой код и он открывает пользовательский интерфейс Swagger, я получаю ответ с ошибкой 500, говорящий

Не удалось преобразовать объект типа «AsyncStateMachineBox1[System.Threading.Tasks.VoidTaskResult,S3E1.Repository.CartItemRepository+<Createitem>d__5]' to type 'System.Threading.Tasks.Task1[S3E1.Entities.CartItemEntity]».

Во-первых, я добавил внедрение зависимостей в Program.cs.

//Dependency Injection
builder.Services.AddDbContext<AppDataContext>(contextOptions => contextOptions.UseSqlServer(
    builder.Configuration.GetConnectionString("DefaultConnection")
    ));

//Connection
builder.Services.AddSingleton<DataConnectionContext>();

Это классы. AppDataContext.cs

public class AppDataContext : DbContext
    {
        
        public AppDataContext(DbContextOptions<AppDataContext> contextOptions) : base(contextOptions) { }

        public DbSet<CartItemEntity> CartItems { get; set; }
      
        public DbSet<OrderEntity> Orders { get; set; }

        public DbSet<UserEntity> Users{ get; set; }
        
    }

DataConnectionContext.cs

public class DataConnectionContext
    {
        private readonly IConfiguration _configuration;
        private readonly string _connectionString;

        public DataConnectionContext(IConfiguration configuration)
        {
            _configuration = configuration;
            _connectionString = _configuration.GetConnectionString("DefaultConnection");
        }

        public IDbConnection CreateConnection() => new SqlConnection(_connectionString);
    }

Далее создается репозиторий, содержащий интерфейс с методом create.

public interface ICartItemRepository
    {
        //public Task<IEnumerable<CartItemEntity>> GetCartItems();
        //public Task<CartItemEntity> GetCartItemEntity(Guid id);

        public Task Createitem(CartItemEntity itemEntity);
    }

Затем класс, который наследует интерфейс и вызывает конструкторы зависимостей

public class CartItemRepository : ICartItemRepository
    {

private readonly DataConnectionContext _connectionContext;
        private readonly AppDataContext _appDataContext;

        public CartItemRepository(DataConnectionContext connectionContext, AppDataContext appDataContext)
        {
            _connectionContext = connectionContext;
            _appDataContext = appDataContext;
        }

public async Task Createitem(CartItemEntity itemEntity)
        {
            _appDataContext.CartItems.Add(itemEntity);
            await _appDataContext.SaveChangesAsync();
            await _appDataContext.CartItems.ToListAsync();
        }
}

Далее идет команда для шаблона MediatR запроса POST.

public record AddCartItemCommand(CartItemEntity cartItem) : IRequest<CartItemEntity>;

и обработчик, который управляет и возвращает метод createitem

public class AddItemsHandler : IRequestHandler<AddCartItemCommand, CartItemEntity>
    {
        private readonly ICartItemRepository _cartItemRepository;

        public AddItemsHandler(ICartItemRepository cartItemRepository) => _cartItemRepository = cartItemRepository;

        public async Task<CartItemEntity> Handle(AddCartItemCommand request, CancellationToken cancellationToken)
        {
            return await (Task<CartItemEntity>) _cartItemRepository.Createitem(request.cartItem);
        }
    }

и, наконец, в контроллере

[Route("api/cart-items")]
    [ApiController]
    public class CartItemsController : ControllerBase
    {
        private ISender _sender;

        public CartItemsController(ISender sender) => _sender = sender;


[HttpPost]
        public async Task<CartItemEntity> Post(CartItemEntity cartItemEntity)
        {
            return await _sender.Send(new AddCartItemCommand(cartItemEntity));
        }
}

Я попытался изменить возвращаемый объект в обработчике, но каждый раз, когда я что-либо меняю, он всегда получает волнистую строку с ошибкой, поэтому я просто применил (Task) после ожидания. Это где я ошибся? Спасибо за любые ответы.

Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
0
0
482
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

Исключение понятно. Вы не можете бросить VoidTaskResult на Task<CartItemEntity>.

Решить проблему:

  1. В ICartItemRepository измените тип возвращаемого значения для Createitem на Task<CartItemEntity>.

  2. В CartItemRepository реализуйте метод Createitem из интерфейса ICartItemRepository. Верните вставленный itemEntity в метод.

  3. Поскольку вы реализовали Task<CartItemEntity> Createitem(CartItemEntity itemEntity) в интерфейсе ICartItemRepository, приведение к (Task<CartItemEntity>) больше не нужно, и его предлагается удалить.

public interface ICartItemRepository
{
    ...

    public Task<CartItemEntity> Createitem(CartItemEntity itemEntity);
}
public class CartItemRepository : ICartItemRepository
{
    ...

    public async Task<CartItemEntity> Createitem(CartItemEntity itemEntity)
    {
        _appDataContext.CartItems.Add(itemEntity);
        await _appDataContext.SaveChangesAsync();

        return itemEntity;
    }
}
public class AddItemsHandler : IRequestHandler<AddCartItemCommand, CartItemEntity>
{
    ...

    public async Task<CartItemEntity> Handle(AddCartItemCommand request, CancellationToken cancellationToken)
    {
         return await _cartItemRepository.Createitem(request.cartItem);
    }
}

Большое спасибо за это, недавно я только что изучил шаблоны MediatR, поэтому передача нескольких запросов и команд обработчикам сбивала с толку.

TroyUrtiz 11.11.2022 08:13

Другие вопросы по теме