Подтвердить что ты не робот

Решения Java для распределенных транзакций и/или данных, разделяемых в кластере

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

  • Какие технологии (технологии разработки программного обеспечения или конкретные технологии) вы предложили бы подходить к этой проблеме?
  • Какие методы вы используете для создания слоя персистентности для масштабирования для многих читателей/писателей Масштабировать транзакции приложений и масштабировать доступ к общим данным (лучший подход заключается в устранении общих данных, какие методы вы можете применять для устранения общих данных).
  • Различные подходы, по-видимому, необходимы в зависимости от того, читаются или записываются ваши транзакции, но мне кажется, что если вы можете оптимизировать "тяжелое приложение записи", которое также было бы эффективным для "чтения"

"Лучшее" решение позволит вам написать приложение Java для одного node и, надеюсь, "скрыть" большинство сведений о доступе/блокировке общих данных.

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

  • Явные блокировки (который чрезвычайно подвержен ошибкам и медленнее координирует работу нескольких узлов в распределенной системе)
  • Программная транзакционная память (STM) AKA optimistic concurrency, где транзакция откатывается во время фиксации, если обнаруживает, что общее состояние изменилось (и транзакция позже может быть повторена). Какой подход лучше масштабируется и каковы компромиссы в распределенной системе?

Я изучал масштабирующие решения (и в целом приложения, которые служат примером масштабирования), например:

  • Terracotta - обеспечивает "прозрачное" масштабирование путем расширения модели памяти Java для включения распределенной общей памяти с использованием механизма блокировки Java concurrency синхронизированный, ReentrantReadWriteLocks).
  • Google App Engine Java - Позволяет писать приложения на Java (или python), которые будут распространяться среди "облачных" серверов, где вы распространяете сервер обрабатывает транзакцию, и вы используете BigTable для хранения ваших постоянных данных (не знаете, как ваши транзакции, которые получают доступ к общим данным или обрабатывают блокировки, могут эффективно масштабироваться).
  • Darkstar MMO Server - Darkstar - это сервер MMO с открытым исходным кодом с открытым исходным кодом (массово многопользовательский онлайн), который они масштабируют транзакции в поточном транзакционном режиме, позволяя транзакция только для определенной суммы и фиксации, и если потребуется, она будет откатываться (вроде как транзакционная память программного обеспечения). Они проводят исследования поддержки настройки сервера node для масштабирования.
  • Оптимистическая блокировка Hibernate - если вы используете Hibernate, вы можете использовать их оптимистичную поддержку concurrency для поддержки транзакционная память программного обеспечения поведение типа
  • Apache CouchDB, как предполагается, "масштабируется" для многих библиотек чтения/записи в естественной конфигурации сетки. (есть ли хороший пример того, как вы управляете блокировкой данных или обеспечиваете изоляцию транзакций?):
  • JCache - Масштабирование "чтения" тяжелых приложений путем кэширования результатов по общим запросам, которые вы можете использовать в Google appengine для доступа к memcached и кэш-памяти другие часто читаемые данные.

Terracotta представляется наиболее полным решением в том, что вы можете "легко" изменить существующее серверное приложение для поддержки масштабирования (после определения объектов @Root и методов AutoLockRead/Write). Проблема состоит в том, чтобы действительно получить максимальную отдачу от распределенного приложения, оптимизация для распределенных систем на самом деле не такая мысль, которую вы, должно быть, должны ее проектировать, зная, что доступ к объектам потенциально может быть заблокирован сетевым вводом-выводом.

Для правильного масштабирования кажется, что он всегда сводится к разделению данных и транзакций балансировки нагрузки таким образом, что данный "исполнительный блок" (cpu core → thread → распределенное приложение node → мастер базы данных node)

Похоже, что для того, чтобы правильно распределить приложения, кластерирование должно быть в состоянии разделить ваши транзакции с точки зрения чтения/записи данных. Какие решения люди придумывают для распространения своих данных приложений (Oracle, Google BigTable, MySQL, Data warehousing) и вообще как вы управляете данными секционирования (многие мастера записи, со многими другими считываемыми DB и т.д.).

Что касается масштабирования уровня сохранения данных, то какой тип конфигурации масштабируется наилучшим образом с точки зрения разделения ваших данных на многие читатели/многие авторы (как правило, я разделял свои данные на основе данного пользователя (или любого другого основного объекта, обычно является вашим "корневым" объектом объекта), принадлежащим одной основной БД)

4b9b3361

Ответ 1

Мысль, что я нашел отличную платформу Java Clustering/Distributed, хотел снова открыть ее -

Оформить заказ http://www.hazelcast.com

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

Ответ 2

Спасибо за красивое подведение итогов всех возможностей в одном месте.

Однако здесь отсутствует один метод. Это MapReduce-Hadoop. Если можно поставить проблему в парадигму MapReduce, это, пожалуй, наиболее широко доступное решение. Я также задаюсь вопросом, можно ли расширить шаблон Actor Framework (JetLang, Kilim и т.д.) На кластер.

Ответ 4

Не забудьте Erlang Mnesia.

Mnesia предоставляет вам такие вещи, как транзакции, с которыми вы привыкли в обычной БД, но обеспечивает операции в реальном времени и отказоустойчивость. Кроме того, вы можете переконфигурировать вещи без простоя. Недостатком является то, что он является резидентной базой данных, поэтому вам нужно фрагментировать действительно большие таблицы. Самый большой размер стола - 4 ГБ.

Ответ 5

В то время как Oracle Coherence и многие другие предлагаемые решения хороши для обмена данными, вы указали только блокировку и STM как способы управления мутацией состояния в распределенной среде; те, как правило, довольно плохие способы масштабирования государственного управления. На другом сайте я недавно опубликовал следующее о том, как реализовать (например) счетчики последовательности:

Если вы смотрите на счетчик, то использование чего-то вроде Coherence EntryProcessor легко достигнет поведения "один раз и только один раз" и HA для любого количества монотонно увеличивающихся последовательностей; здесь вся реализация:

public class SequenceCounterProcessor
        extends AbstractProcessor
    {
    public Object process(InvocableMap.Entry entry)
        {
        long l = entry.isPresent() ? (Long) entry.getValue() + 1 : 0;
        entry.setValue(l);
        return l;
        }
    }

Угу. Это. Автоматическая и бесшовная НА, динамическая масштабируемая эластичность, однократное и однократное поведение и т.д. Сделано.

EntryProcessor - это тип распределенного закрытия, который мы ввели в 2005 году.

В стороне, в Java 8 (еще не выпуске), проект Lambda вводит официальную поддержку закрытия в языке и стандартных библиотеках.

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

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

Несколько оптимизаций к вышеперечисленному включают добавление интерфейсов ExternalizableLite и PortableObject для оптимизации сериализации и избежание сериализации коробочного длинного путем перехода непосредственно к форме "готовность к сети" данных:

public Object process(InvocableMap.Entry entry)
    {
    try
        {
        BinaryEntry binentry = (BinaryEntry) entry;
        long l = entry.isPresent() ? binentry.getBinaryValue()
                .getBufferInput().readLong() + 1 : 0L;
        BinaryWriteBuffer buf = new BinaryWriteBuffer(8);
        buf.getBufferOutput().writeLong(l);
        binentry.updateBinaryValue(buf.toBinary());
        return l;
        }
    catch (IOException e)
        {
        throw new RuntimeException(e);
        }
    }

И так как он без гражданства, почему бы не получить одноэкранный экземпляр, готовый к работе?

public static final SequenceCounterProcessor INSTANCE =
        new SequenceCounterProcessor();

Использование его в любом месте сети так же просто, как одна строка кода:

long l = (Long) sequences.invoke(x, SequenceCounterProcessor.INSTANCE);

Где "x" - любой объект или имя, которое идентифицирует конкретный счетчик последовательностей, который вы хотите использовать. Для получения дополнительной информации см. Базу знаний Coherence по адресу: http://coherence.oracle.com/

Oracle Coherence - это распределенная система. Всякий раз, когда вы начинаете когерентность node, он соединяется с другими узлами когерентности, которые уже запущены, и динамически формирует эластичный кластер. Этот кластер хранит данные в многораздельном, высокодоступном (HA) и транзакционно последовательном режиме и выполняет операции (например, те, что я показал выше), которые работают с этими данными "один раз и только один раз".

Кроме того, в дополнение к возможности вызова любой из этих логических схем или доступа к любой из этих данных прозрачно из любой Coherence node, вы также можете вызывать любую из этих логических схем или получать доступ к любой из этих данных прозрачно из любого процесса на сети (при условии аутентификации и авторизации, конечно). Таким образом, этот код будет работать из любого кластера Coherence node или любого клиента (Java/C/С++/С#/.NET):

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

Ответ 6

Возможно, эти slides будут полезны. По нашему опыту я бы рекомендовал Oracle (Tangosol) Coherence и GigaSpaces как самую мощную инфраструктуру распространения данных и обработки там. В зависимости от точной природы проблемы может светиться один из них. Терракота также вполне применима для некоторых проблем.