Легкое восстановление после сбоя для Python - PullRequest
0 голосов
/ 31 октября 2009

Каков наилучший способ облегчить восстановление после сбоя для моей программы?

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

  1. Вы можете предположить, что ключи и значения в словаре легко конвертируются в строки, т.е. используя модуль str или .
  2. Я хочу, чтобы это было полностью кроссплатформенным, по крайней мере, таким же кроссплатформенным, как Python *
  3. Я не хочу просто записывать каждое значение в файл и загружать его в мою программу, может произойти сбой во время записи файла
  4. ОБНОВЛЕНИЕ : Это облегченный модуль, поэтому о СУБД не может быть и речи.
  5. ОБНОВЛЕНИЕ : Алекс прав в том, что мне на самом деле не нужно для защиты от сбоев во время записи, но есть обстоятельства, когда я хотел бы иметь возможность вручную прекратить это в восстанавливаемом состоянии.
  6. ОБНОВЛЕНИЕ Добавлено сильно ограниченное решение с использованием стандартного ввода ниже

Ответы [ 5 ]

2 голосов
/ 31 октября 2009

Нет хорошего способа защиты от "сбоя вашей программы при записи контрольной точки в файл", но почему вы должны так беспокоиться о , что ?! Что еще делает ваша программа в тот момент, кроме того, что «сохраняет контрольную точку в файл», что может привести к ее аварийному завершению?!

Трудно превзойти pickle (или cPickle) за переносимость сериализации в Python, но это просто "превращение ваших ключей и значений в строки". Для сохранения пар ключ-значение (один раз в виде строки) несколько безопаснее, чем просто добавление в файл ( не извлечение файлов, если ваши сбои намного, гораздо чаще, чем обычно, как вы предлагаете tjey) есть).

Если ваша среда невероятно подвержена сбоям по какой-либо причине ( очень дешевый HW? -), просто убедитесь, что вы закрываете файл (и fflush, если ОС также подвержена сбоям ;-), затем снова откройте его для добавления. Таким образом, наихудшее, что может случиться, - это то, что самое последнее добавление будет неполным (из-за сбоя в середине событий) - тогда вы просто поймаете исключение, вызванное снятием этой неполной записи, и вернете только то, что не было сохранено (потому что они не были завершены из-за сбоя, ИЛИ потому что они были завершены, но не полностью сохранены из-за сбоя, в конце концов получается то же самое).

Если у вас есть возможность установить контрольную точку для механизма базы данных (вместо того, чтобы просто делать это с файлами), подумайте об этом серьезно! Механизм БД будет вести журналы транзакций и обеспечивать свойства ACID, что значительно облегчит программирование на стороне приложения, ЕСЛИ вы можете на это рассчитывать! -)

1 голос
/ 31 октября 2009

Pickle / cPickle имеют проблемы.

Я использую модуль JSON для сериализации объектов. Мне это нравится, потому что он не только работает на любой ОС, но и на других языках программирования; многие другие языки и платформы имеют легкодоступную поддержку десериализации JSON, что позволяет легко использовать одни и те же объекты в разных программах.

1 голос
/ 31 октября 2009

Одной из возможностей может быть создание нескольких файлов меньшего размера ... каждый из которых представляет подмножество состояния, которое вы пытаетесь сохранить, и каждый из них имеет контрольную сумму или тег, указывающий, что он завершен как последняя строка / дата в файл (непосредственно перед закрытием файла).

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

Не зная больше о характере данных, с которыми вы работаете, невозможно быть более конкретным.

Конечно, вы можете использовать файлы или систему СУБД. Любая достойная СУБД (PostgreSQL, MySQL, если вы используете надлежащие серверные части) может дать вам гарантии ACID и поддержку транзакций. Поэтому данные, которые вы читаете, должны всегда соответствовать ограничениям, которые вы вводите в свою схему, и / или транзакциям (BEGIN, COMMIT, ROLLBACK), которые вы обработали.

Возможное преимущество размещения вашей сериализованной даты в СУБД состоит в том, что вы можете разместить СУБД в отдельной системе (которая вряд ли будет страдать от той же нестабильности, что и ваш тестовый хост в одно и то же время).

1 голос
/ 31 октября 2009

Модуль pickle поддерживает сериализацию объектов в файл (и загрузку из файла):

http://docs.python.org/library/pickle.html

0 голосов
/ 31 октября 2009

Решение с жесткими ограничениями

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

Downsides:

  • Это достаточно сложно
  • Добавляет дополнительный поток
  • Это мешает мне использовать стандартный ввод для чего-либо еще
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...