Домой Edit me on GitHub

2019-06-19

Каналы передачи данных | Сетевое программирование | Базы данных | Основы Веб-программирования

ZODB

См.также

ZODB - объектно-ориентированная база данных для Python-объектов.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
import persistent

class Account(persistent.Persistent):

  def __init__(self):
      self.balance = 0.0

  def deposit(self, amount):
      self.balance += amount

  def cash(self, amount):
      assert amount < self.balance
      self.balance -= amount

ZODB используется в Zope, Plone, Zenoss, ERP5 и некоторых других системах. Например, ZODB и ZEO (без Zope) используются в системе Indico — программном обеспечении для организации симпозиумов, конференций, лекций и т. п., разработанном и используемом ЦЕРНом. Примером отечественного проекта с использованием этой базы данных является ранняя версия программы электронного документооборота «NauDoc» от компании Naumen.

На данный момент реализована полностью на Python [1]. Но в зависимостях используется BTrees, который реализован с использованием языка C.

Конкурентный доступ

Изначально является базой данных доступной только для одного процесса. Но данное ограничение обходится с помощью ZEO (Zope Enterprise Objects). Данная технология подменяет стандартное файловое хранилище ZODB на клиент-серверное. «Клиент» не записывает данные на диск, а передаёт их для этого на «сервер», который уже и реализует логику записи. Клиентов может быть несколько, благодаря чему и достигается возможность одновременной работы с одним хранилищем.

Существует ещё один способ конкурентного доступа к данным в ZODB: реализация хранилища в реляционных базах данных [2]. При таком способе множественный доступ реализуется самой РСУБД стандартными для неё методами через управление подключениями.

Особенности

ZODB является иерархической базой данных. Корневой элемент создаётся при старте базы данных. Структура представляет собой словарь сериализованных (pickle) объектов языка Python. Для записи объекта в хранилище достаточно, чтобы он мог быть сериализован методом стандартной библиотеки Python’а.

Для оптимизации хранения древовидных структур применяется встроенный модуль OOBTree реализованный на языке C. Но для его эффективной работы необходимо ручное поддержание структуры дерева.

Полностью поддерживается механизм транзакций и ACID [3]. Также присутствует поддержка точек сохранения. Это когда в кэш сохраняется часть большой транзакции для освобождения ресурсов. Присутствует сохранение истории изменений и их отмена.

Для хранения Blob-данных (таких как изображения, например) используется специальный тип хранилища. В нём отсутствует реализация механизмов версионирования данных. За счёт чего эти данные не оказывают критического влияния на быстродействие системы хранения.

Для востребованных данных существует кэширование в памяти. Он динамически изменяется в зависимости от нужды в объектах: неиспользуемые объекты автоматически удаляются.

Для объектов в базе применяется версионирование, что может значительным образом увеличить размер хранилища. Для сокращения объёма хранилища и удаления неиспользуемых версий объектов используется метод packing. Его рекомендуется применять по расписанию, т.к. удалённые объекты также остаются в хранилище. Это аналог команды VACUUM из PostgreSQL.

Заключение

В заключение хочется сказать, что аналоги ZODB присутствуют во многих языках программирования. Например, в Ruby это PStore, в Java - ObjectDB.

Также необходимо упомянуть главные недостатки ZODB:

  • Отсутствие встроенных механизмов сложных индексов. В ZODB нет таких мощных механизмов создания индексов как в реляционных СУБД. Она использует перебор словаря для нахождения нужных значений. Что накладывает серьёзные ограничения на реализацию поиска по сложным критериям.
  • Отсутствие удобного доступа к данным из приложений реализованных не на Python. В случае реализации какого-либо сложного проекта на базе ZODB, придётся реализовывать API для доступа к данным, хранящимся в ней, для тех программ, которые выполнены не на Python. Что не всегда возможно.

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

Примером такого проекта может являться задача учёта структуры сети интернет-провайдера.

Практика

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

Настройка окружения

Установим необходимые зависимости для проекта.

pip install zodb

Реализация задачи

Для начала создадим классы для реализации задачи без сохранения.

[1]https://github.com/zopefoundation/ZODB
[2]https://github.com/zodb/relstorage
[3]Atomicity Consistency Isolation Durability
Previous: SQLite Next: Redis