Я пытаюсь выяснить, подходит ли Disruptor для моего приложения: достаточно сложный генератор нагрузки, используемый для тестирования высокопроизводительных баз данных в течение длительных периодов времени. Паттерн Disruptor привлекателен, потому что:
- Высокая пропускная способность
- Низкая задержка
- Нет мусора / предсказуемое длительное поведение
Упрощенная версия топологии приложения выглядит следующим образом:
C1a C1b P1 ----> C1c C1d \ C1e \ \ \ \ \ \ \ Cx / P2 --> C2a --> C2b /
=== P1 ===
Системный компонент, питаемый P1
, имеет 1 производителя, питающего множество параллельных потребителей (в настоящее время Executor
). Каждое событие должно быть обработано ровно один раз одним из этих потребителей. Ограничение порядка таково: если A создается раньше B, то A начнет выполняться раньше B, однако B может завершиться раньше.
После обработки событие передается на заключительный этап Cx
. Думайте о Cx
как о преобразователе/регистраторе: он должен обрабатывать события последовательно, поскольку структуры данных, с которыми он работает, не являются потокобезопасными.
Вопрос 1. Как лучше всего использовать Disruptor для обработки C1a-C1e
?
Я склоняюсь к использованию WorkerPool
.
=== P2 ===
Системный компонент, питаемый P2
, представляет собой простую цепочку рабочих процессов: событие создается P2
, C2a
выполняет над ним некоторые вычисления, C2b
выполняет над ним дальнейшие вычисления, наконец, оно пересылается Cx
.
Вопрос 2. Возможно ли иметь 1 Disruptor с 2 производителями, где каждый производитель передает разные подграфы зависимостей?
Вопрос 3. Если ответ на вопрос 2 отрицательный, возможно ли разделить потребителя Cx
между двумя разными разрушителями, и если да, то как?
Вопрос 4. Если ответ на вопрос 2 и вопрос 3 отрицательный, есть ли способ заставить эту топологию работать с Disruptor?
Заранее спасибо!
-- Для справки-
Это не решение, но связано. Для всех, кто заинтересован, в этом блоге объясняется, как создать полусложный рабочий процесс, например, такой:
C1a --> C1b C2a --> C2b P1 --> C3a --> C3b --> Cx C4a --> C4b C5a --> C5b