Как вставить в БД из файла CVS с помощью оператора Loop - PullRequest
0 голосов
/ 30 сентября 2019

У меня проблемы с моим кодом. Я вставляю в свою базу данных, используя загруженный файл с разделителями-запятыми (CSV), который имеет 5 строк. первая строка успешно вставлена ​​в БД, но во втором цикле для вставки второй строки я сталкиваюсь с ошибкой:

Невозможно вставить явное значение для столбца идентификаторов в таблице 'bdoToDbs', когда для IDENTITY_INSERT установлено значение OFF.

Вот мои Loop коды

            while (i < users.Count)
            {
                ViewBag.CompanyCode = users[i].CompanyCode;
                ViewBag.ProductCode = users[i].ProductCode;
                ViewBag.TransactionDate = users[i].TransactionDate;
                ViewBag.TransactionTime = users[i].TransactionTime;
                ViewBag.OriginatingBranch = users[i].OriginatingBranch;
                ViewBag.CustomerNumber = users[i].CustomerNumber;
                ViewBag.TransactionOrigin = users[i].TransactionOrigin;
                ViewBag.TypeOfPayment = users[i].TypeOfPayment;
                ViewBag.CheckNumber = users[i].CheckNumber;
                ViewBag.TransactionAmount = users[i].TransactionAmount;
                ViewBag.CustomerName = users[i].CustomerName;

                bdoToDb.CompanyCode = ViewBag.CompanyCode;
                bdoToDb.ProductCode = ViewBag.ProductCode;
                bdoToDb.TransactionDate = ViewBag.TransactionDate;
                bdoToDb.TransactionTime = ViewBag.TransactionTime;
                bdoToDb.OriginatingBranch = ViewBag.OriginatingBranch;
                bdoToDb.CustomerNumber = ViewBag.CustomerNumber;
                bdoToDb.TransactionOrigin = ViewBag.TransactionOrigin;
                bdoToDb.TypeOfPayment = ViewBag.TypeOfPayment;
                bdoToDb.CheckNumber = ViewBag.CheckNumber;
                bdoToDb.TransactionAmount = ViewBag.TransactionAmount;
                bdoToDb.CustomerName = ViewBag.CustomerName;
                bdoToDb.UserName = ViewBag.DisplayName;
                bdoToDb.UserIP = HttpContext.Connection.RemoteIpAddress.ToString();
                bdoToDb.UserDate = DateTime.Now.ToString("MM/dd/yyyy");
                i++;
                _context.Add(bdoToDb);
                await _context.SaveChangesAsync();
            });
            return RedirectToAction(nameof(Index));
        }

1 Ответ

0 голосов
/ 30 сентября 2019

Одним из прекрасных свойств ядра EF является то, что оно отслеживает изменения, а затем вы можете зафиксировать все эти изменения одновременно с сохранением. Если вы переместите

       await _context.SaveChangesAsync();

за пределы цикла while (отредактировано: И создайте новый объект на каждой итерации в соответствии с проницательным комментарием ниже), это сработает. В случае таблиц вставки идентификаторов вы не устанавливаете идентификатор объекта, но, таким образом, вы можете узнать, чем в итоге будет этот идентификатор, после вызова сохранения изменений он обновит поле идентификатора вашего объекта. Поэтому после первого сохранения поле идентификатора устанавливается равным следующему идентификатору, затем вы обновляете все свойства объекта и затем используете .Add, чтобы он попытался вставить его, но идентификатор уже установлен и помечен как измененный. Вы также можете обойти это, создавая новый экземпляр объекта каждый раз, или, возможно, EF найдет способ очистить этот идентификатор и пометить его как неизмененный ... но я бы порекомендовал перенести сохранение в конец, так как оно, вероятно, будет болееэффективный. Если это для очень больших объемов данных, возможно, сохраняйте их каждый раз, когда вы пропускаете 1000 записей или около того, но если данные не огромны, об этом не стоит беспокоиться.

К последующему запросу что-то вроде этого:(вам действительно нужны отдельные экземпляры объектов, потому что EF хранит их в памяти)

            ViewBag.TransactionAmount = users[i].TransactionAmount;
            ViewBag.CustomerName = users[i].CustomerName;

            // added constructor
            bdoToDb = new BdoToDb(); // <- don't know name of your class

            bdoToDb.CompanyCode = ViewBag.CompanyCode;
            bdoToDb.ProductCode = ViewBag.ProductCode;
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...