Любые функции записи В Python, которые имеют ту же безопасность, что и ACID в базах данных - PullRequest
4 голосов
/ 04 декабря 2010

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

Ответы [ 3 ]

5 голосов
/ 04 декабря 2010

В зависимости от того, что именно вы делаете со своими файлами и платформой, существует несколько вариантов:

  • Если вы последовательно сериализуете большой двоичный объект из памяти на диск для поддержания состояния(пример: dhcp арендует файл), если вы работаете в системе Posix, вы можете записать свои данные во временный файл и переименовать временный файл в вашу цель.На Posix-совместимых системах это гарантированно является атомарной операцией, не должно иметь значения, регистрируется ли файловая система или нет.Если вы работаете в системе Windows, есть встроенная функция с именем MoveFileTransacted , которую вы можете использовать через привязки.Но ключевая концепция здесь заключается в том, что временный файл защищает ваши данные, если система перезагружается, в худшем случае ваш файл содержит последнее хорошее обновление данных.Эта опция требует, чтобы вы записывали весь файл каждый раз, когда хотите записать изменение.В случае с файлом dhcp.leases это не сильно снижает производительность, большие файлы могут оказаться более громоздкими.

  • Если вы постоянно читаете и записываете биты данных, sqlite3 - это то, что нужно - он поддерживает атомарные коммиты для групп запросов и имеет собственный внутренний журнал.Здесь следует обратить внимание на то, что атомарные коммиты будут работать медленнее из-за накладных расходов на блокировку базы данных, ожидание сброса данных и т. Д.- если ваша файловая система смонтирована асинхронно, запись будет завершена, потому что write () вернется, но она еще не записана на диск.Переименование защищает вас в этом случае, sqlite3 также.

    Если ваша файловая система смонтирована асинхронно, возможно, можно записать данные и переместить их до записи данных.Поэтому, если вы работаете в системе Unix, может быть безопаснее смонтировать синхронизацию.Это на уровне " человек может умереть, если это не удастся " паранойя, хотя.Но если это встроенная система, и она умирает «Я могу потерять свою работу, если это не удастся », также является хорошим обоснованием для дополнительной защиты.

1 голос
/ 04 декабря 2010

Мне кажется, что ваша главная цель - обеспечить целостность записанных файлов в случае сбоя питания и сбоя системы.При этом необходимо учитывать несколько моментов:

  • Убедитесь, что ваши данные записываются на диск при закрытии файла.Даже если вы закроете его, некоторые данные могут находиться в кэше ОС в течение нескольких секунд, ожидая записи на диск.Вы можете принудительно записать на диск с помощью f.flush (), а затем os.fsync (f.fileno ()).
  • Не изменяйте существующие данные, пока не убедитесь, что обновленные данные находятся в безопасности надиск.Эта часть может быть довольно сложной (и зависит от ОС / файловой системы).
  • Использовать формат файла, который поможет вам проверить целостность данных (например, использовать контрольные суммы).

Другой альтернативой являетсяиспользовать sqlite3.

РЕДАКТИРОВАТЬ: Что касается моего второго пункта, я настоятельно рекомендую эту презентацию: http://www.flamingspork.com/talks/2007/06/eat_my_data.odp. Это также охватывает проблемы с «атомным переименованием».

1 голос
/ 04 декабря 2010

ZODB - это совместимое с ACID хранилище базы данных, написанное (главным образом) на python, поэтому в некотором смысле ответ - да. Но я могу представить, что это немного излишне:)

Либо ОС должна предоставить вам это, либо вам необходимо реализовать собственную совместимость с ACID. Например, определив «записи» в файле, который вы пишете, и при открытии / чтении проверьте, какие записи были записаны (это может означать, что вам нужно выбросить некоторые не полностью записанные данные). Например, ZODB реализует это, заканчивая запись, записывая размер самой записи; если вы можете прочитать этот размер и он соответствует, вы знаете, что запись была полностью записана.

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

...