Начиная с версии 1.3.0, вы можете открыть базу данных в режиме только для чтения, игнорируя блокировку:
final EnvironmentConfig config = new EnvironmentConfig().
setLogDataReaderWriterProvider("jetbrains.exodus.io.WatchingFileDataReaderWriterProvider").
setLogCacheShared(false).
setMemoryUsagePercentage(1);
final Environment env = Environments.newInstance(dir, config);
final PersistentEntityStore store = PersistentEntityStores.newInstance(env);
Мало того, что он игнорирует блокировку, но также автоматически выбирает новые данные, используя java.nio.file.WatchService
.
Один экземпляр Environment / EntityStore можно открыть как обычно (основной), а несколько экземпляров можно открыть, как указано выше (дополнительные). Ваш прокси-сервер должен правильно распределять трафик, чтобы вторичные экземпляры не получали запросы на запись. Очевидно, что ваше приложение должно решить возможную согласованность проблем, которые неизбежны при такой архитектуре.
Вторичные экземпляры могут быть открыты в любой JVM. Если вы открываете вторичные экземпляры в той же JVM, которая используется для открытия первичного экземпляра, следите за использованием памяти, поскольку вторичные экземпляры не используют общий кэш журнала. Основной экземпляр (если вы не используете setMemoryUsagePercentage
) может занимать 50% от максимальной кучи памяти. Хорошо, если общий процент использования памяти не превышает 50-55% (хотя это зависит от того, какой GC и какие настройки GC вы используете).
Если вы открываете вторичные экземпляры в отдельных JVM, пропустите настройки setLogCacheShared
и setMemoryUsagePercentage
в приведенном выше коде. Вам нужно только настроить просмотр DataReaderWriterProvider.
В версии 1.3.91 вы даже можете запускать JVM с дополнительными экземплярами на разных хостах. Каждый хост должен иметь копию базы данных в своей файловой системе, которую можно открыть следующим образом:
final EnvironmentConfig config = new EnvironmentConfig().
setLogDataReaderWriterProvider("jetbrains.exodus.io.WatchingFileDataReaderWriterProvider");
final Environment env = Environments.newInstance(dir, config);
final PersistentEntityStore store = PersistentEntityStores.newInstance(env);
Единственная дополнительная вещь, которую вы должны сделать со своей инфраструктурой, - это обеспечить периодическую синхронизацию изменений базы данных. Версия 1.3.91 протестирована и отлично работает с rsync . Синхронизация каждые 5-10 секунд в большинстве случаев была бы приемлемой, хотя высокие рабочие нагрузки при записи приводили бы к некоторым задержкам синхронизации.