Форум программистов, компьютерный форум, киберфорум
Наши страницы
C#: Базы данных, ADO.NET
Войти
Регистрация
Восстановить пароль
 
Рейтинг 4.60/5: Рейтинг темы: голосов - 5, средняя оценка - 4.60
Bars4
68 / 8 / 1
Регистрация: 14.03.2013
Сообщений: 116
1

Пакетная передача обновлений (Insert) в базу данных посредством DataAdapter.Update

30.05.2017, 19:40. Просмотров 977. Ответов 17

Здравствуйте, господа
Кто-нибудь имел дело с пакетной передачей обновлений (а конкретно вставок) в базу данных посредством DataAdapter.Update с возвратом обновленных значений (актуализированных через @@IDENTITY) первичных ключей в исходные DataRow и с количество передаваемых за одно обращение к базе строк > 1 ?
Вцелом код решения у меня есть и успешно работает. А проблема возникла, именно когда я захотел увеличить размер передаваемого пакета с одной строки до, например, DataAdapter.UpdateBatchSize = 5
Если кто направит в правильном направлении за решением - буду очень благодарен
0
Лучшие ответы (1)
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
30.05.2017, 19:40
Ответы с готовыми решениями:

Как правильно сделать update с посредством dataadapter
Всем привет! Возник вопрос. Есть в бд табличка CountryId - int (ключ + индексируемый столбец)...

передача обновлений в базу данных
Подскажите - чем отличаются DataRowVersion.Original от DataRowVersion.Current ? В этом методе...

Обновление базы данных dataadapter.Update
знаю что таких тем было много но ни на одной из них я не нашел ответа на свой вопрос ...

Как вы делаете Update данных в БД (при использовании DataGridView, DataSet, DataAdapter)
Доброго дня, форумчане. Отдельный привет знакомым форумчанам. Решил поднять я старую наболевшую...

Запись данных в базу данных mdb с использованием DataAdapter и DataSet
Попробовал сделать Update для таблицы контактов: private void Form1_Load(object sender,...

17
hoolygan
356 / 283 / 76
Регистрация: 21.06.2016
Сообщений: 1,115
30.05.2017, 23:20 2
Лучший ответ Сообщение было отмечено Bars4 как решение

Решение

Вопрос на засыпку. А накуа?
Если, как Вы пишите, имеете дело с DataRow, то смело можете собирать их в таблицы, а таблицы в 1 датасет. Вот Вам и решение всех проблем. Датасет сериализуете в xml, а саму строку xml-ную передаете 1-им параметром в хранимку сиквелу. На стороне сиквела через xQuery десериализуете, и обновляете все свои таблички. Оттуда же, с процедуры можете вообще десяток селектов вызвать в коллбек шарпу. И не нужно выдумывать десяток велосипедов.
1
Bars4
68 / 8 / 1
Регистрация: 14.03.2013
Сообщений: 116
30.05.2017, 23:41  [ТС] 3
hoolygan, спасибо за профессиональный вариант.
Но коллбэк не проканает - я кодю из-под VB.NET
Да и с обновлением через хранимые процедуры еще не разобрался. Хотя признаю, что Ваш вариант самый верный.
Просто и само приложение и база сейчас на стадии разработки. И поэтому каждый раз переписывать процедуры обновления вслед за модификацией схемы данных таблицы тоже, на мой взгляд, не удобно.
Поэтому пока временно работаю через адаптер.
Что, по моему варианту обновления все плохо ?
0
hoolygan
356 / 283 / 76
Регистрация: 21.06.2016
Сообщений: 1,115
31.05.2017, 00:06 4
Bars4, а разве у vb.net нету тасков? а у тасков точно есть коллбеки (ну эт я их так по-привычке называю). Собственно говоря, можно же после отработки апдейта запускать селект. Да и адаптерный метод update всегда переопределить можно под себя, просто прописав в нем вызов хранимки.
А по поводу того, что переписывать.... ну тут не без этого. Расширяете/урезаете функционал - переделываете под себя
Но Вы не с того начали работу. Сначала делайте модель данных, а потом крутите БД. Может тогда проще вообще на EF делать? Ноэто так, к слову.
0
Bars4
68 / 8 / 1
Регистрация: 14.03.2013
Сообщений: 116
31.05.2017, 00:12  [ТС] 5
hoolygan, ты рушишь мой мир.
Я теперь не понимаю, что мне дальше делать...
Останавливать всю работу и садиться за буквари?
0
hoolygan
356 / 283 / 76
Регистрация: 21.06.2016
Сообщений: 1,115
31.05.2017, 00:22 6
Bars4, ну я бы все-таки сел с ручкой, бумажкой, и продумал модель данных, чтобы впоследствии не сильно переписывать ))
Смотря для чего это все делается. Если для еденичного случая с 1 формой, и 2мя контролами - то наверное пофиг. А если что-то серъезней - то без модели будет тяжело поддерживать проект. А это как бы самое главное, потому что доработок/хотелок всегда на 100500 процентов больше, чем первоначальных задумок.
1
Bars4
68 / 8 / 1
Регистрация: 14.03.2013
Сообщений: 116
31.05.2017, 00:35  [ТС] 7
hoolygan, Конечно, хотелось бы, чтобы проект получился жизнеспособным и развиваемым. Но по модели - даже не буду пытаться продумать и зафиксировать на бумаге (пытался, но потом понял, что многое решается по ходу реализации проекта) , ибо для этого надо иметь критический опыт и навыки проектирования БД.

Но если ты говоришь, что бурундук - птичка, значит бурундук - птичка...как бы не хотелось оттянуть это "до лучших времен" - придется пытаться переходить на процедурное обновление.
А тебе придется побыть дебаггером в этом нелегком деле...
0
Igr_ok
418 / 390 / 185
Регистрация: 04.08.2015
Сообщений: 1,072
31.05.2017, 09:11 8
Цитата Сообщение от Bars4 Посмотреть сообщение
Кто-нибудь имел дело с пакетной передачей обновлений (а конкретно вставок) в базу данных посредством DataAdapter.Update с возвратом обновленных значений (актуализированных через @@IDENTITY) первичных ключей в исходные DataRow и с количество передаваемых за одно обращение к базе строк > 1 ?
Всё это уже реализовано в DataAdapter. Если он у вас правильно "приготовлен"(создан с помощью мастера или класса SqlCommandBuilder), то в команде INSERT не только прописана вставка данных, но и возвращение ключевого значения.
0
Bars4
68 / 8 / 1
Регистрация: 14.03.2013
Сообщений: 116
31.05.2017, 11:44  [ТС] 9
Igr_ok, да, все команды вставки, обновления и удаления у меня уже заряжены в DataAdapter и адекватно работают.
Просто если объем обновлений за раз составляет несколько тысяч строк, тогда, из-за построчной передачи обновлений, наблюдается заторможенность обновления.
Вот поэтому я и хотел обернуть обновления в транзакции по несколько строк за раз, например по 100. Как это реализовать и какие параметры .UpdatedRowSource и .UpdateBatchSize адаптера выставлять не пойму
0
Igr_ok
418 / 390 / 185
Регистрация: 04.08.2015
Сообщений: 1,072
31.05.2017, 12:00 10
Bars4, для вставки большого кол-ва записей есть SqlBulkCopy: https://msdn.microsoft.com/ru-ru/lib...vs.110%29.aspx
1
Bars4
68 / 8 / 1
Регистрация: 14.03.2013
Сообщений: 116
31.05.2017, 14:22  [ТС] 11
Igr_ok, да, похоже на то
0
hoolygan
356 / 283 / 76
Регистрация: 21.06.2016
Сообщений: 1,115
31.05.2017, 15:10 12
Bars4, заторможенность обновления связана всегда в первую очередь с тем, что адаптер работает в синхронном режиме. Отпускайте его в асинхронность - и торможений не будет. Пока пользователь "раздуплится" - обновление уже произойдет.
А вот это SqlBulkCopy - хорошо только в 1-ом случае - если нужно строки гнать только в 1-ну таблицу. Когда же начинается логика работать внутри сиквела - начинают выдумывать десяток костылей, особенно, если есть связанные таблицы по Identity. Если просто нужно, например 1 таблицу скопировать в сиквел в 1-ну целевую таблицу - то пользуйтесь балком, если же нужно распихивать по десятку связанных таблиц (а чаще всего именно так и происходит в средне/больших проектах) - то никакой бал не поможет, даже больше - он вреден. Там либо EF, либо хранимки.
Объясню почему.
Напр, у вас проект, который Вы скомпилировали и раздали пользователям (5-20-50-1000 человек), а через неделю новая хотелка - "хочу когда поставлю галочку, чтобы у меня вот тут добавилось поле и сохранялись данные с вот этого комбобокса". И начинается.... пересборка проекта, изменение логики, и опять раскидывание на всех пользователей. Или же - изменение в хранимке, а пользователелям уже все работает, и они ничего не почуствовали. Вот как-то вот так вот.
1
Bars4
68 / 8 / 1
Регистрация: 14.03.2013
Сообщений: 116
31.05.2017, 17:08  [ТС] 13
hoolygan, да, обновления я передаю сложноструктурные, состоящие из каскада связаных подчиненных таблиц, в т.ч. самоподчиненных (отношение "слоновье ухо").
Но! В самой процедуре отправки обновления у меня все разложено по полочкам - последовательно потаблично в нисходящем по структуре порядке Select-ом выдергиваю строки .Added, .ModifiedOriginal и адаптером обновляю в базу с возвратом актуализированных ключей и других пересчитанных сервером данных через параметры.
С удаленными строками та же потеха, только в восходящем по структуре порядке.
А после возврата обновленных ключей - они каскадируются силами DataRelation.
Так вот в такой моей ситуации признается ли такое обновление однотабличным и нормально ли будет применять балк в этом случае (хоть и в качестве временной меры) ?.
А про хранимые процедуры я даже и не спорю - это правильная идеология и о ней пишут во всех букварях. И когда приложение уже поставлю на ноги обновляться буду только через хранимки. Но прямо сейчас переход на ХП потребует от меня времени на написание и отладку (если только найдется работоспособный пример двунаправленного обновления структурного DataSet через ХП, который можно освоить за день).
На сегодняшнем этапе разработке адаптер, по моему скромному мнению, при его правильном конфигурировании может показать неплохую производительность. Но только почему-то после обертывания .Update в транзакцию и установке .UpdateBatchSize > 1 возврат обновленных значений из БД через параметры перестает работать. И это как-то связано с .UpdatedRowSource.
0
hoolygan
356 / 283 / 76
Регистрация: 21.06.2016
Сообщений: 1,115
31.05.2017, 17:30 14
Bars4, бедный Ваш клиент если он сам мержит таблицы, создает отношения, раскладывает по полочкам
Пробуйте, я не скажу по поводу балка в таком случае, как он себя поведет - может быть Вы и расскажите об этом для последующих поколений.
0
Bars4
68 / 8 / 1
Регистрация: 14.03.2013
Сообщений: 116
31.05.2017, 20:51  [ТС] 15
hoolygan, я уловил Ваш сарказм
Ну я просто делаю так, как написано в литературе по ADO.NET.
Разве мог я предположить, что это все окажется курам насмех...
Какую книгу я должен взять в руки, где изложены приемы создания клиента в "правильном" стиле ?

Добавлено через 8 минут
З.ы. И кстати, как Вы поняли, я не мержу, а возвращаю значения через параметры - разве это не правильно ?
И что, можно обойтись без DataRelation для отображения Master-Detail гридов, один из которых еще и TreeGrid...
Правда, вы рушите мой мир. Возможно это пойдет мне же на благо...
0
hoolygan
356 / 283 / 76
Регистрация: 21.06.2016
Сообщений: 1,115
31.05.2017, 21:31 16
Bars4, совершенно, кстати, не сарказм был. Самый сейчас вот банальный пример из своей работы расскажу. Есть форма, в ней 8 вкладок, в каждой из них от 1 до 4-ех связанных таблиц. Все это договор, а в нем пару десятков контролов и таблиц. В некоторых таблицах колонки -это checkedComboBox, т.е. еще и связанные таблицы на каждую строку. Это предисловие. Ну соответственно все контролы забиндены в классы, т.е. есть общий класс договора, у него связи с остальными классами, в общем - просто модель данных. Когда договор идет на сохранение, то работа клиента - это просто сериализовать класс договора в xml-ку, примитивная работа на доли секунды. Все, дальше запускаю обыкновенную команду на сиквел, которой передаю название процедуры и xml-ку. А уже на стороне сиквела у меня хранимка на полторы тыс строчек, которая распарсивает, складывает, обновляет, удаляет, ну вы поняли. После того, как хранимка отработала - запускаю метод шарпа, который заново запращивает данные с сиквела. Ведь мало ли что при этом у меня там изменилось, может справочники добавились, может другие пользлватели что-то добавили.
Поэтому во всех книжках пишут не возвращать параметры при апдейте, а полностью перечитывать все.
Но это так, к слову было. Т.е. я не сарказничал, а рассказывал, как сделано у меня. Может тоже неправильно, я не буду доказывать, что так должно быть. Но точно скажу, что после обновления нужно запускать процесс считывания. Эра однопользовательских программ закончилась лет 30 назад, и нужно учитывать, что менять может не 1 пользователь
1
Igr_ok
418 / 390 / 185
Регистрация: 04.08.2015
Сообщений: 1,072
31.05.2017, 21:33 17
Bars4, скорость bulk copy достигается за счет отказа от логирования в SQL Server, так что это вам не поможет.
1
Bars4
68 / 8 / 1
Регистрация: 14.03.2013
Сообщений: 116
01.06.2017, 01:45  [ТС] 18
Igr_ok, спасибо, принял)

Добавлено через 16 минут
hoolygan, это я дуркую
Цитата Сообщение от Bars4 Посмотреть сообщение
я уловил Ваш сарказм

hoolygan, вот уже сутки перевариваю Вашу мысль по способу обновления и понимаю, что он - весьма хорош.
Я себе уже набросал план модификаций версий процедуры по повышению производительности передачи обновлений в БД.
Так одной из модификаций моей процедуры станет запуск передачи обновлений по одному процессу на каждую таблицу и на каждый тип обновлений.
А следующий вариант - уже будет Ваш.
И вот тут я бы уже набрался наглости просить какие-нибудь образцы кода клиента и процедуры , чтобы понимать с чего начинать (или в личку, если это комм. тайна).
0
01.06.2017, 01:45
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
01.06.2017, 01:45

проблема с DataAdapter.Update
вывожу при загрузке формы в datagrid табличку : Dim oCommand As New...

Не выполняется DataAdapter.Update
делаю так private void Form1_Load(object sender, EventArgs e) { ...

Волнует скорость DataSet и DataAdapter.Update
При использовании метода Update в базу данных вносятся изменения со всего DataSet'а или система...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
18
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2019, vBulletin Solutions, Inc.
Рейтинг@Mail.ru