Стратегии для Java ORM с ненадежной сетью и низкой пропускной способностью - PullRequest
7 голосов
/ 01 мая 2011

Я смотрю на Hibernate для системы, которая должна работать в ненадежной сети. Существует единственная центральная база данных, к которой нам нужен доступ для чтения и записи, но она доступна через довольно неоднородную сеть Wi-Fi. Кроме того, могут быть потери питания, которые не завершают работу приложения без ошибок, поэтому любое решение должно иметь постоянный кэш, который может выдержать циклы питания. Наконец, это встроенная система с очень скромной памятью и дисковым пространством, поэтому, например, полная репликация базы данных не является осуществимой стратегией.

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

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

В поисках опыта или возможных альтернатив.

Ответы [ 6 ]

3 голосов
/ 09 мая 2011

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

У вас уже есть решение в головес Hibernate кеш уровня 2.Но вы не сказали, каковы реальные требования.У вас нереальная сеть.Это нормально, у вас нереальный источник питания.Тоже норм.Теперь какой уровень сервиса вы хотите достичь?Что приемлемо или нет?

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

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

Это уже много предположений.Хорошо, но что произойдет, если один жесткий диск выйдет из строя после сбоя питания?Вы знаете, что жесткий диск не любит сбой питания и может быть поврежден при сбое питания или даже может быть поврежден?

Итак, вы установили RAID и добавили источник бесперебойного питания.Это мило.Вы обнаружите событие сбоя питания от ОС.Завершите текущую транзакцию и корректно завершите работу.RAID защищает вас от сбоя диска.

Хорошо, но что произойдет, если весь компьютер перестанет работать?Что происходит в случае пожара?Или повреждение водой?Все диски будут управляться, данные не будут восстановлены, а то, что не синхронизировано с центральной базой данных, будет потеряно.Это приемлемо или нет?

Даже при включенном вайфай, блок питания работает отлично ... Какова надежность центральной базы данных в любом случае?У вас есть регулярные резервные копии?Или кластерное решение?Вы уверены, что ваша центральная база данных надежна в любом случае?

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

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

Это функциональная проблема.Что делать, если несколько модификаций происходит в автономном режиме и вам нужно объединить?Что приемлемо?Что не является.Это может быть то, что при повторном подключении применяются самые последние изменения, более старые изменения отбрасываются.Или же обнаруживаются конфликты и пользователю предлагается разобраться с ними.Вы можете попытаться применить изменения в очереди и применить их все ...

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

2 голосов
/ 01 мая 2011

Как насчет постановки в очередь операций с БД в долговременной / постоянной очереди сообщений, и позволить некоторому промежуточному программному обеспечению для обмена сообщениями решить проблему сети?

В зависимости от того, как вы это делаете, могут возникать проблемы с согласованностью (ну, я думаю, «аномалия» - правильное слово), но если у вас ненадежная сеть и вы все еще хотите достойную производительность, тогда можно согласиться на расслабленную согласованностьпуть

Я бы не хотел использовать EhCache и т. Д. Они не были предназначены для этого, и, следовательно, вам, возможно, придется «растянуть» каркас.С другой стороны, очереди сообщений имеют решения, разработанные для таких сценариев.

2 голосов
/ 01 мая 2011

Вы не можете ожидать успеха в сети, подобной той, что существует между hibernate и базой данных.

Я рекомендую вам определить набор атомарных операций высокого уровня, а затем определить набор (например)отдых для них.Или, если хотите, вы можете использовать мыло и посмотреть опции WS- * для надежного обмена сообщениями, чтобы позаботиться о повторных попытках и всех других беспорядочных деталях.ссылка будет работать лучше, чем SQL, или что-то еще большое при репликации.

1 голос
/ 11 мая 2011

Hibernate (и кэш второго уровня) действительно не предназначены для этого.Я предполагаю, что вам лучше всего использовать небольшую встроенную СУБД Java (например, H2 или HSQLDB) в качестве локальной временной очереди (в наиболее долговременном доступном режиме), а затем выполнять синхронизацию с фоновым потоком.Затем вы можете предоставить пользовательский интерфейс синхронизирующего счетчика, подключенный к этому фоновому потоку, чтобы обеспечить некоторую степень обратной связи для пользователя.

Кстати, Hibernate немного сложен для встраивания во встроенную среду.Возможно, вы захотите рассмотреть myBatis вместо этого.

1 голос
/ 01 мая 2011

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

Возможно, вы можете хранить сжатый журнал транзакций.

0 голосов
/ 15 мая 2011

Репликатор Daffodil (http://enterprise.replicator.daffodilsw.com/index.html) позволяет выполнять репликацию между источниками JDBC. Он поддерживает двунаправленные обновления, слияние и разрешение конфликтов, а также частичные реплики.

Это можно использовать для синхронизации основной базы данных с локальной (частичной)Вы можете использовать hibernate для связи с локальной базой данных реплик и сделать все остальное вне этого процесса.

...