#entity-framework #rest #asp.net-web-api #lambda
#entity-framework #отдых #asp.net-web-api #лямбда
Вопрос:
Я выполняю лямбда-запросы к моделям (я делаю проекцию с другими классами — GameBankVM, GameCouponBankVM), и в конце я хотел бы выполнить цикл по результату запроса и обновить поле модели. Но я получаю объект или сложный тип ‘EPINMiddleWareAPI.Модели.GameBankVM’ не может быть создан в запросе LINQ to Entities.
Вот мой пример кода:
var gameBankResult = await (context.GameBanks.Where(g => g.productCode == initiate.productCode)
.Take(initiate.quantity)
.Select(g => new GameBankVM
{
quantity = g.quantity,
currency = g.currency,
initiationResultCode = g.initiationResultCode,
productCode = g.productCode,
productDescription = g.productDescription,
referenceId = g.referenceId,
responseDateTime = g.responseDateTime,
unitPrice = g.unitPrice,
totalPrice = g.totalPrice,
coupons = g.coupons.Select(c => new GameCouponBankVM
{
Pin = c.Pin,
Serial = c.Serial,
expiryDate = c.expiryDate
}).ToList()
})).ToListAsync();
if (gameBankResult.Count() != 0)
{
foreach (var item in gameBankResult)
{
item.referenceId = initiate.referenceId;
context.Entry(item).State = System.Data.Entity.EntityState.Modified;
}
await context.SaveChangesAsync();
return Ok(gameBankResult);
}
Как я могу обновить referenceId в моей модели / таблице GameBank?
Ответ №1:
В этом сценарии ваши данные не будут обновлены, потому что ваш запрос возвращает список GameBankVM, а не список GameBank, теперь, технически говоря, вы нарушаете SRP, вам следует либо обновить свои данные, либо запросить свои данные не одним и тем же методом, вы можете реорганизовать свой метод, напримерэто :
1. — Создайте частный метод для обновления данных, в этом случае вы запрашиваете напрямую GameBank, перебираете записи списка, вносите изменения и сохраняете их в базе данных, этот же метод может возвращать список GameBank, чтобы избежать повторного обхода базы данных.
2.- В контроллере после вызова вашего нового метода вы можете запустить запрос преобразования, чтобы преобразовать список GameBank в Список GameBankVM и вернуть его в представление.
Есть много других способов сделать это, я просто рекомендую это как менее эффективный способ заставить ваш контроллер работать. Но если вы хотите улучшить ситуацию, вы можете создать бизнес-уровень, на котором вы разрешаете все свои бизнес-правила, или вы можете использовать шаблоны, такие как CQS или CQRS.
Комментарии:
1. Спасибо за ваш ответ. На самом деле я использовал GameBankVM и GameCouponBankVM для проектирования запросов. Все, что я хочу сделать, это запросить базу данных и, если есть результаты, обновить их.
2. Точно, я понимаю, что вам это нужно для прогнозирования запросов, дело в том, что у вас не будет отслеживания в прогнозах запросов без объекта в проекции, посмотрите на это: docs.microsoft.com/en-us/ef/core/querying/tracking
3. Ваш запрос возвращает объекты виртуальной машины, которые не отслеживаются EF.
4. Под вашим руководством я выяснил, как выполнить запрос и обновление. Я сначала запрашиваю и обновляю объект, а затем делаю прогноз.