Транзакция пакетного задания

#batch-processing

#пакетная обработка

Вопрос:

Допустим, в базе данных есть 100 записей для пакетного задания, когда выполняется пакетное задание, выберите эти 100 записей и затем начните обработку. Во время процесса, если ошибка возникает в 10-й записи, я должен откатить все 9 записей, которые уже были обработаны.

Как мы можем спроектировать этот сценарий??? Ваши предложения приветствуются.

Ответ №1:

Я полагаю, что вы спрашиваете, следует ли вам откатывать успешные записи, если ошибка возникает частично во время пакетной обработки.

Вы хотите, чтобы обновления вашей базы данных выполнялись в транзакциях таким образом, чтобы записи базы данных оставались согласованными и законными (в отношении базы данных и бизнес-правил) после фиксации или отката каждой транзакции.

Если каждый элемент в вашем списке из 100 записей может быть обработан и записан по отдельности, то я бы предложил использовать какой-либо флаг (это также может быть поле статуса), чтобы указать, была ли обработана каждая запись, затем просмотрите записи, чтобы обновить каждую из них. Если вы столкнулись с ошибкой, обратите внимание, что где-то (файл журнала, исключение, таблица ошибок… ваш вызов) и двигаться дальше. Когда вы закончите, вы зарегистрируете, какие записи были успешными, а какие неудачными. Затем вы должны иметь возможность вернуться и исправить все, что вызвало проблему (проблемы) в плохих записях, и повторно обработать пропущенные записи.

Если все 100 ваших записей должны завершиться успешно или завершиться неудачей вместе, вам нужно будет включить ваши обновления в транзакцию, чтобы все они завершились успешно или завершились неудачей как одно целое. Это будет работать для десятков записей или (возможно) сотен записей, но попытка масштабирования до тысяч записей в одной транзакции может создать проблемы с масштабируемостью (проблемы производительности и конкуренции), поэтому вам понадобится другое решение для подобного шаблона.

Комментарии:

1. Спасибо за ваш ответ, на самом деле я реализовал только этот способ. Я проверял у других экспертов, как они выполняют такую обработку, и каков наилучший способ сделать это…. Спасибо

Ответ №2:

Возможна различная степень детализации транзакции. Java (JTA) допускает несколько операций записи за один коммит.

  1. Открытая транзакция
  2. запись записи
  3. запись записи
  4. запись записи
  5. ошибка
  6. откат

Большинство баз данных также поддерживают транзакции, которые могут обрабатывать несколько строк или записи.

Это очень распространенное явление.

Комментарии:

1. хорошо ли откатывать все записи, которые были успешными? В вашем примере до точки № 4 все было нормально, и ошибка возникает в точке 5. теперь вы хотите откатить все успешные записи? Как вы думаете, если мы зафиксируем все успешные записи и пометим их выполнением каким-либо флагом, а затем пакетное задание сможет забрать остальные из них (пункт 5 и далее) в следующий раз. Мой вопрос в основном заключается в том, что было бы наилучшим подходом к разработке этого сценария??? Должны ли мы изменить размер пакета, а затем откатить только пакет сбоев или нам следует создать точку сохранения, а затем выполнить откат до точки сохранения???

Ответ №3:

Взгляните на ТОЧКИ СОХРАНЕНИЯ — они в основном разрешают транзакции внутри транзакции. Таким образом, вы можете выполнить довольно много работы, создать точку сохранения и выполнить еще больше работы, только откатившись к последней точке сохранения. Если что-то пойдет не так, вы можете просто откатить всю транзакцию назад.

Комментарии:

1. Изначально я пробовал точки сохранения через Java (у меня нет хранимой процедуры), но моя ситуация этого не позволяет, а также для этого требуется больше кода и логики, чем для сохранения в таблице базы данных со столбцом состояния… Также там была какая-то проблема с производительностью … спасибо за ваше предложение, Майк…