Использование DVCS для контрольного журнала СУБД - PullRequest
2 голосов
/ 17 июня 2011

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

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

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

Строки данных будут сериализованы в json, каждый «файл»может быть рядом.В качестве альтернативы, вся таблица может храниться в «файле», где каждая строка находится на номере строки, равном ее первичному ключу (при условии, что таблицы не слишком большие, я ожидаю, что у всех будет менее 4000 строк).Это может означать, что наборы изменений могут генерироваться автоматически, не обращаясь к остальной части таблицы "file".

(Но я сомневаюсь в этом, потому что я думаю, что нам нужен SHA-1 хэш всего файла. Возможно, файлы могут быть разбиты на предсказуемое количество строк, например, 0 < primary key < 1000 в файле 1, 1000 < primary key < 2000 в файле 2 и т. Д., Сохраняя их малыми)

Кто-нибудь знаком с внутренностями DVCS 'или структурами данных в целом, кто мог бы прокомментировать такой подход? Как это можно сделать, и нужно ли вообще это делать?

Я полагаю, что в такой системе есть два аспекта: 1) отображение данных SQL в систему DVCS и 2) сохранение данных DVCS в хранилище данных ключ / значение (не в файлах) для эффективности.

(NB бит сериализации json покрыт моим ORM)

Ответы [ 3 ]

2 голосов
/ 18 июня 2011

Я немного разбирался в этом, и вот несколько комментариев, которыми можно поделиться.

Хотя я думал, что использование Mercurial от Python упростит задачу, но у DVCS есть множество функций, которые не нужны (особенно ветвление, слияние). Я думаю, что было бы проще просто украсть некоторые дизайнерские решения и внедрить базовую систему для моих нужд. Итак, вот что я придумала.

Blobs

Система создает json-представление записи, подлежащей архивированию, и генерирует ее хэш SHA-1 («идентификатор узла», если хотите). Этот хеш представляет состояние этой записи в данный момент времени и является таким же, как «blob» git.

1012 * Изменения *

Изменения сгруппированы в наборы изменений. Набор изменений принимает к сведению некоторые метаданные (временную метку, коммиттер и т. Д.) И ссылки на любые родительские наборы изменений и текущее «дерево».

Деревья

Вместо того, чтобы использовать подход Mercurial «Manifest», я выбрал «древовидную» структуру git. Дерево - это просто список BLOB-объектов (экземпляров модели) или других деревьев. На верхнем уровне каждая таблица базы данных получает свое собственное дерево. Следующим уровнем могут быть все записи. Если записей много (часто они есть), их можно разбить на поддеревья.

Это означает, что если вы измените только одну запись, вы можете оставить нетронутыми деревья в покое. Это также позволяет каждой записи иметь свой собственный BLOB-объект, что значительно упрощает управление.

Хранение

Мне нравится идея Revlog Mercurial, потому что она позволяет минимизировать хранение данных (сохраняя только наборы изменений) и в то же время обеспечивать быстрый поиск (все наборы находятся в одной структуре данных). Это делается для каждой записи.

Я думаю, что такая система, как MongoDB, была бы лучшей для хранения данных (это должно быть ключ-значение, и я думаю, что Redis слишком сосредоточен на хранении всего в памяти, что не важно для архива). Он будет хранить наборы изменений, деревья и журналы. Несколько дополнительных клавиш для текущего заголовка и т. Д., И система завершена.

Поскольку мы используем деревья, нам, вероятно, не нужно явно связывать внешние ключи с точным «блобом», на который он ссылается. Достаточно просто использовать первичный ключ. Я надеюсь!

Вариант использования: 1. Архивирование изменений

Как только изменение сделано, текущее состояние записи сериализуется в json, и для ее состояния генерируется хеш. Это сделано для всех других связанных изменений и упаковано в набор изменений. После завершения соответствующие журналы обновляются, новые деревья и поддеревья генерируются с новыми хешами объектов («blob»), а набор изменений «фиксируется» с метаинформацией.

Вариант использования 2. Восстановление старого состояния

После нахождения соответствующего набора изменений (поиск MongoDB?), Дерево затем перебирается, пока мы не найдем искомый идентификатор BLOB-объекта. Мы переходим в журнал изменений и получаем состояние записи или генерируем ее, используя доступные снимки и наборы изменений. Затем пользователь должен будет решить, нужно ли извлекать внешние ключи, но сделать это будет легко (используя тот же набор изменений, с которым мы начали).

Резюме

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

0 голосов
/ 17 июня 2011

Взгляните на cqrs и источники событий Грега Янга. У меня также есть пост в блоге о работе в мета-событиях, которые точно определяют изменения схемы в реке бизнес-событий.

http://adventuresinagile.blogspot.com/2009/09/rewind-button-for-your-application.html

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

0 голосов
/ 17 июня 2011

Если база данных не требует интенсивной записи (как вы говорите), почему бы просто не реализовать реальные таблицы базы данных таким образом, чтобы достичь вашей цели?Например, добавьте столбец «версия».Затем никогда не обновляйте и не удаляйте строки, за исключением этого специального столбца, для которого можно задать значение NULL, означающее «текущий», 1, означающее «самый старый из известных», и подниматься оттуда.Если вы хотите обновить строку, установите ее версию на следующую более высокую и вставьте новую без версии.Затем при запросе просто выберите строки с пустой версией.

...