Моя настройка: asp. net mvc веб-приложение с присоединенной базой данных sql.
Приведено 3 примера таблиц, таких как:
Где мне нужно получить список всех счетов-фактур по данному контракту и общую сумму счетов-фактур (Сумма единиц проданных * Единица измерения) их проданных товаров.
Я попробовал ниже действие контроллера:
public IEnumerable<Invoice> Get(int contractId)
{
IEnumerable<Invoice> invoices = db.Invoices.Where(i => i.ContractId == invoiceId);
foreach (var invoice in invoices){
var items = db.Items.Where(t => t.InvoiceId == invoice.InvoiceId);
foreach (var item in items){
invoice.Total += item.UnitsSold * item.UnitPrice;
}
}
return invoices;
}
Но при var items = db.Items.Where(t => t.InvoiceId == invoice.InvoiceId);
Я получаю: Недопустимая операция Исключение: эта команда уже назначена открытому DataReader, который сначала должен быть закрыт . Я также попробовал IQueryable вместо IEnumerable, но все еще неисправен.
Любая помощь для получения этого права будет очень признательна.
Редактирование и решение:
Фактически приведенный выше пример является упрощенной версией моей проблемы, но данные посты помогли мне найти решение, подобное:
public IEnumerable<ContractInvoiceViewModel> Get(int contractId)
{
// here the total product sum for all invoices is built and stored in the respective invoice field
var invoices = db.Invoices.Where(i => i.ContractId == contractId).ToList();
foreach (var invoice in invoices)
{
var existingInvoice = db.Invoices.Find(invoice.InvoiceId);
var items = db.Items.Where(t => t.InvoiceId == invoice.InvoiceId).ToList();
decimal? tempSum = 0.00m;
foreach (var item in items)
{
tempSum += item.UnitPrice * item.UnitsSold;
}
existingInvoice.Total = tempSum;
db.Entry(existingInvoice).State = EntityState.Modified;
db.SaveChanges();
}
// here the viewmodels for the view are collected
IEnumerable<Invoice> invoicesForView = db.Invoices.Where(i => i.ContractId == contractId);
var contract = db.Contracts.Find(contractId);
var customer = db.Customers.Find(contract.CustomerId);
IList<ContractInvoiceViewModel> result = new List<ContractInvoiceViewModel>();
foreach (var invoiceItem in invoicesForView)
{
var model = new ContractInvoiceViewModel
{
InvoiceId = invoiceItem.InvoiceId,
ContractId = invoiceItem.ContractId,
ContractDate = contract.ContractDate,
InvoiceDate = invoiceItem.InvoiceDate,
Customer = customer.Name,
Info = contract.Info,
Total = invoiceItem.Total,
};
result.Add(model);
}
return result;
}
Я выбрал подход ToList (), потому что он работал. Подход со свойством навигации тоже работает, но там я также использовал ToList (), чтобы иметь возможность отправлять изменения базы данных для поля Invoice.Total внутри внешнего l oop.