Java - напишите два файла атомарно - PullRequest
6 голосов
/ 22 марта 2012

Я столкнулся с проблемой, для которой у меня нет чистого решения.Я пишу Java-приложение, и приложение хранит определенные данные в ограниченном наборе файлов.Мы не используем какую-либо базу данных, просто файлы.Из-за некоторых действий, инициируемых пользователем, некоторые файлы должны быть изменены.Мне нужно, чтобы это была операция «все или ничего».То есть либо все файлы обновлены, либо ни один из них.К сожалению, если, например, 2 из 5 файлов изменены, а остальные 3 не вызваны каким-либо IOException.

Какова наилучшая стратегия для достижения этой цели?Является ли встраивание базы данных в память, такой как hsqldb, хорошей причиной для получения такого рода атомарности / транзакционного поведения?

Большое спасибо!

Ответы [ 5 ]

5 голосов
/ 22 марта 2012

Безопасный подход IMO:

  1. Резервное копирование
  2. Ведение списка обработанных файлов
  3. В случае исключения восстановите те, которые были обработаны с резервной копиейдо одного.

Зависит от того, насколько тяжелым он будет и ограничения по времени и тому подобное.

2 голосов
/ 22 марта 2012

Какова лучшая стратегия для достижения этой цели? Является ли встраивание базы данных в память, такой как hsqldb, хорошей причиной для получения такого рода атомарности / транзакционного поведения?

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


Файловые системы, как правило, не поддерживают транзакции с несколькими файлами.

Файловые системы, отличные от Windows, и NTFS, как правило, имеют свойство, позволяющее выполнять атомарную замену файлов, поэтому, если вы не можете использовать базу данных и

  • все файлы находятся в одном достаточно маленьком каталоге
  • , которым владеет ваше приложение и
  • , который хранится на одном физическом диске:

тогда вы можете сделать следующее:

  1. Скопируйте содержимое каталога, используя соответствующие жесткие ссылки.
  2. Изменить 5 файлов.
  3. Атомно поменять измененную копию каталога на оригинальную
1 голос
/ 22 марта 2012

Мой подход заключается в использовании блокировки в вашем Java-коде.Таким образом, только один процесс может записать какой-то файл одновременно.Я предполагаю, что ваше приложение является единственным, которое записывает файлы.Если даже при этом возникает проблема с записью для «отката» ваших файлов, вам нужно сохранить копию файлов, как указано выше.

1 голос
/ 22 марта 2012

Я успешно использовал библиотеку транзакций Apache Commons для атомарных операций с файлами.Это позволяет изменять файлы транзакционно и потенциально откатываться при сбоях.

Вот ссылка: http://commons.apache.org/transaction/

0 голосов
/ 22 марта 2012

Разве вы не можете заблокировать все файлы и записывать их только после того, как все файлы заблокированы?

...