Однонаправленная репликация между двумя базами (постановка)
Рассмотрим вариант однонаправленной репликации между двумя базами A и B. Все изменения осуществляются на базе A. База B работает в режиме только для чтения. В дальнейшем, мы будем использовать термины "Удаленная база данных (УБД)" для базы А и "Центральная база данных (ЦБД)" для B.
Базы обмениваются между собой сообщениями. Канал связи между базами может быть непостоянным. Т.е. база A может посылать сообщения в тот момент, когда база B недоступна и наоборот. Порядок выполнения действий над объектами на базе A должен сохраняться при переносе на базу B. Транспорт передачи сообщений не гарантирует нам ни сохранности и целости конкретного сообщения, ни сохранения порядка при передаче нескольких сообщений.
Состояния объекта в УБД
Каждый объект в УБД находится в определенном состоянии. В таблице ниже перечислены возможные состояния, а также определены допустимые переходы из одного состояния в другое.
| Состояние | Описание | Блокировка | Переход |
|---|---|---|---|
| I | Каждый объект, который существовал до настройки схемы репликации (т.е. до создания УБД на основе изначально существовавшей ЦБД), имеет состояние I. В начальный момент времени такой объект присутствует как в УБД, так и в ЦБД. | Нет | L |
| L | Изменение объекта занесено в лог. Используется для информирования системы о необходимости отсылки сообщения "Передача объекта" на ЦБД. | Объект в состоянии L может быть изменен только в том случае, если после него в логе нет никаких других записей. Последовательные изменения (в смысле порядка записей в логе) одного и того же объекта допускаются. | S, B |
| B | Используется для остановки процесса передачи данных на ЦБД. При обработке объекта в состоянии B, процесс формирования сообщений останавливается с уведомлением пользователя о том, какая именно запись вызвала остановку. | Аналогично состоянию L. | L |
| S | Объект был отослан на ЦБД. | Аналогично состоянию L. | C, F |
| C | Изменение объекта успешно записано в ЦБД. | Нет | L |
| F | Изменение объекта не может быть записано в ЦБД. Необходимо срочное вмешательство системного администратораи ручная синхронизация данных УБД и ЦБД. | Объект остается в заблокированном состоянии. | L, С |
Состояния объекта в ЦБД
Поскольку данные передаются только в одном направлении, для объектов в ЦБД мы выделяем только три состояния.
| Состояние | Описание | Переход |
|---|---|---|
| I | Объект существовал до настройки схемы репликации. | R |
| R | Объект получен и записан в базу данных. | |
| F | Объект получен, но не может быть записан в базу данных. Необходимо срочное вмешательство системного администратора для ручного разрешения конфликта данных. | R |
Лог изменений
Фиксирование изменений состояния объекта осуществляется в логе, который заполняется триггерами и содержит:
- целочисленный порядковый номер изменения (начиная с единицы),
- идентификатор объекта,
- тип объекта,
- вид операции (создание, изменение, удаление),
- состояние объекта.
В дальнейшем, символом N мы будем обозначать номер изменения, а символом М -- максимальный номер изменения в логе. М принимается равным нулю, если лог пуст.
Состояние базы данных
Мы будем называть целое число S состоянием базы данных. Если S = М, значит все изменения переданы на ЦБД. Если S < M, -- необходимо осуществить передачу. Ситуация, когда S > M означает серьезный сбой в данных репликации, нарушение логической целостности.
В начальный момент времени:
S = M = 0
Базы данных А и B находятся в идентичном состоянии, если Sa = Sb и очередь сообщений пуста. Поскольку просто физическое отсутствие сообщений в очереди не означает того, что их там не было. То, говорить об идентичности баз мы можем только после того, как ЦБД послала "Запрос состояния УБД" и получила на него ответ.
Состояние УБД увеличивается на единицу каждый раз, когда подтверждается передача очередного объекта. Sa равно максимальному номеру записи в логе в состоянии C.
Состояние ЦБД увеличивается на единицу каждый раз, когда успешно принимается и записывается в базу очередной объект. Sb равно максимальному номеру записи в логе в состоянии R.
В начальный момент времени базы данных находятся в идентичном состоянии, т.е. выполняется:
Sa = Sb = Мa = Мb = 0
Связь в асинхронном режиме
В том случае, если при обмене данными между УБД и ЦБД нет постоянного канала связи, мы будем использовать следующие параметры:
Tr -- Допустимое время ожидания ответа на посланное сообщение. Ts -- Время простоя ЦБД с момента обработки последнего сообщения до отсылки запроса о состоянии УБД. Ti -- Период с которым УБД осуществляет проверку очереди сообщений и отсылку изменений на ЦБД.
Журнал репликации
Журнал используется системным администратором для выявления проблем или профилирования репликации. В журнал заносятся:
- Информативные сообщения
- Предупреждения
- Критические ошибки
Последовательность обмена сообщениями
Последовательность обмена сообщениями между исходной и конечной базами данных выглядит следующим образом:
База А
Проверяется очередь сообщений:
- Очередь сообщений пуста:
- Для записей в состоянии S, с момента отправки которых прошло времени больше чем Tr, на ЦБД отсылаем сообщение "Запрос подтверждения передачи объекта" с указанием идентификаторов объектов. Одновременно в журнале отражаем факт превышения времени ожидания ответа.
- Для каждой записи в состоянии L формируется и посылается отдельное сообщение "Передача объекта". После формирования и успешной отправки сообщения, запись в логе переводится в состояние S.
- Если в очереди присутствуют сообщения сортируем по порядковому номеру. Обрабатываем последовательно:
- "Подтверждение передачи объекта":
- Если номер из сообщения соответствует номеру первого объекта со статусом S (в порядке очередности записей в логе), то переводим объект в состояние C. Удаляем сообщение из очереди и продолжаем обрабатывать список.
- Если номер из сообщения меньше номера первого объекта со статусом S, то игнорируем такое сообщение. Удаляем сообщение из очереди и продолжаем обрабатывать список. Заносим в журнал информацию о получении такого подтверждения.
- Если номер из сообщения больше номера первого объекта со статусом S отсылаем на сервер сообщение "Запрос подтверждения передачи объекта". Сообщение из очереди не удаляем. Продолжаем обрабатывать список, пропуская все сообщения типа "Подтверждение передачи объекта". Помещаем информацию в журнал.
- "Запрос на передачу объекта".
- Если запрашиваемый объект находится в состоянии S, то передаем его на ЦБД. Удаляем сообщение из очереди и продолжаем обрабатывать список. Помещаем в журнал информацию о повторной передаче объекта.
- Если запрашиваемый объкт находится в состоянии L или C, или вообще отсутствует в списке, то игнорируем сообщение и удаляем его из очереди, а в журнал помещаем запись с информацией о ситуации.
- "Запрос состояния УБД".
- "Подтверждение передачи объекта":
База B
Проверяется наличие сообщений в очереди.
- Очередь пуста:
- Ранее было отправлено сообщение "Запрос состояния УБД":
- Если интервал времени на ответ не истек, то продолжаем ожидать.
- Интервал времени истек. Информируем системного администратора. Повторяем "Запрос состояния УБД".
- Если истек интервал проверки связи и состояния УБД, то отсылаем "Запрос состояния УБД".
- Ранее было отправлено сообщение "Запрос состояния УБД":
- Очередь не пуста:
- ...
- Если он соответствует ожидаемому, то происходит считывание и обработка сообщения.
- Если номер первого сообщения в очереди меньше ожидаемого, то просто игнорируем его (удаляем).
- Если номер первого сообщения в очереди больше ожидаемого, то посылаем запрос на пересылку сообщений с нужными номерами. Останавливаем дальнейшую обработку очереди. Ждем ответа от исходной базы.
- ...
Запрос состояния УБД
Когда база B хочет узнать текущее состояние синхронизации с базой А, она посылает специальное сообщение "Запрос состояния УБД" и фиксирует время его отправки. Получив данное сообщение, база А действует в соответствии со своим логом. Если он содержит записи, подлежащие отправке, то формируются и посылаются соответствующие сообщения. Непосредственного ответа на "Запрос состояния УБД" в этом случае не отсылается. Если лог не содержит записей для отправки, то формируется специальное сообщение "Состояние УБД", которым передается число Sa. После отсылки запроса База B периодически проверяет свою очередь сообщений. Если в течение заданного тайм-аута в очередь не поступило ни одного ответа от базы А, то системный администратор оповещается о возможном нарушении канала связи или неполадках на УБД. Если поступил ответ "Состояние УБД", то Sa сверяется с Sb. При их равенстве базы данных считаются идентичными (синхронизированными). Если Sa > Sb, то база B отсылает сообщение "Запрос на передачу объекта" с указанием номера Sb + 1. Состояние, когда Sa < Sb, свидетельствует о серьезной рассинхронизации двух баз данных и требует немедленного информирования системного администратора.
"Запрос состояния УБД" отсылается автоматически по истечении заданного интервала времени с момента обработки последнего сообщения от УБД или с момента отправки предыдущего запроса на состояние, на который не поступило ответа.
Структура сообщения
| Поле | Описание |
|---|---|
| Контрольная сумма | Хэш код MD5, который позволяет контролировать целостность полученного сообщения. Рассчитывается по всему потоку данных, включая и заголовок. |
| Идентификатор УБД | |
| Идентификатор ЦБД | |
| Номер записи в логе | |
| Данные |