2009-10-17 2 views
0

У меня есть требование, чтобы одно сообщение JMS, отправленное клиентом, должно быть надежно (точно один раз) передано двум системам. Эти 2 системы не HA-включены, так что лучшее предложение, что я придумал это:Как «скопировать» сообщение JMS в 2 адресата?

  1. создания одной очереди, где клиентские сообщения в

  2. создать два «промежуточные» очередей

  3. использует пользовательский «DuplicatorMDB», который будет считывать сообщения из очереди клиентов и отправлять их в две очереди в рамках одной и той же транзакции.

 
client->JMSDQ->DuplicatorMDB->Q1->MDB->System1 
          \->Q2->MDB->System2 

Есть ли существующие функциональные возможности, как это? Каким будет правильный способ сбалансировать систему, чтобы она оставалась стабильной, если одна или обе бэкэнд-системы опущены?

Сервер приложений WebLogic 10.

Я не могу использовать темы для этого, потому что в кластере тем вызовет слишком много дублирования сообщений. Если у нас есть 2 экземпляра, то с тем он будет идти, как это:

 
client->Topic-->[email protected]>System1 
      | \->[email protected]>System2 
      \---->[email protected]>System1 
      \--->[email protected]>System2 

Таким образом, каждое сообщение будет доставлено дважды System1 и дважды System2 и если там будет 8 серверов в кластере, каждое сообщение будет доставлен 8 раз. Это то, что я действительно хотел бы избежать ...

Наконец-то я получил некоторое время, чтобы проверить его, и вот что я наблюдал: 2 узла в кластере. 2 сервера JMS: jms1 на узле1, jms2 на узле2. Распределенная тема dt. MDB с надежной подпиской и jms-client-id = durableSubscriber. Начал работу системы: 0 сообщений, mdb @ node1 встает, mdb @ node2 пытается периодически подключаться, но это невозможно, потому что «Client id, durableSubscriber, используется». Как и ожидалось.

Отправлено в 100 сообщениях: jms1 @ dt messages current = 0, messages total = 100, consumer current = 1 Я могу видеть, что node1 обработал 100 сообщений.
jms2 @ dt messages current = 100, общая сумма сообщений = 100, потребители current = 1 В этом разделе ожидаются сообщения «duplicate».

Отправлено в других 100 сообщениях, 100 обработанных на узле1, 200 ожидающих узла2.

Перезагруженный узел1, mdb @ node2 подключен к dt и начал обработку «ожидающих» сообщений. На узел2 обработано 200 сообщений.

После того, как узел1 поднят, mdb @ node1 не может подключиться к dt, а подключен mdb @ node2.

jms1 @ дт сообщений тока = 0, сообщений Всего = 0, потребители тока = 0
jms2 @ дт сообщений тока = 0, сообщения всего = 200, потребители тока = 1

Отправить в более 100 сообщений, Я вижу, что все 100 сообщений обрабатываются на узле2 и отбрасываются на node1.

jms1 @ дт сообщений тока = 0, сообщения всего = 100, потребители тока = 0
jms2 @ дт сообщения ток = 0, Всего сообщений = 300, потребители тока = 1

Теперь я перезагружать node2, MDB @ node1 подключается к dt. После перезагрузки mdb @ node2 подключается к dt и mdb @ node1 отключается от dt.

jms1 @ дт сообщений тока = 0, сообщения всего = 100, потребители тока = 1
jms2 @ дт сообщений тока = 0, сообщений Всего = 0, текущие потребители = 1

Я посылаю в 100 сообщениях все они обрабатываются на node2 и находится в теме на node1:

jms1 @ дт сообщений тока = 100, сообщения всего = 200, потребители ток = 1
jms2 @ дт сообщений тока = 0, сообщения всего = 0, потребители ток = 1

Затем я отключил de2 и я вижу 100 «ожидающих сообщений», обрабатываемых на узле1 после того, как mdb @ node1 снова подключится к теме.

Таким образом, результат: Я отправил 400 сообщений, 700 были обработаны MDB, из которых 300 были дублирующими.

Похоже, что пересоединение MDB работает хорошо, как ожидалось, но сообщения могут быть дублированы, если узел, на котором размещен «активный» MDB, отключается.

Это может быть ошибка или особенность реализации JMS weblogic.

+1

Я что-то упустил? Почему бы не использовать тему? – SingleShot

+0

Любая обратная связь по прочным подпискам? –

ответ

1

Я не использовал Weblogic, но большинство решений JMS имеют концепцию очередей и тем. Вам нужна тема JMS. Подписчики регистрируются, и тема гарантирует, что сообщение доставляется каждому подписчику один раз.

Configuration details.

Update: Если вы работаете с проблемами в кластерной среде, я хотел бы убедиться, что все настроено правильно (здесь является руководством для JMS Topic Clustering). Это определенно звучит странно, что Weblogic терпит неудачу так жалко при кластеризации. Если это не сработает, вы можете посмотреть стороннюю очередь сообщений, такую ​​как RabbitMQ, которые поддерживают JMS и, безусловно, не будут иметь этой проблемы.

+0

Существует проблема с темами в кластере, которые создадут слишком много копий сообщений - см. Обновление к сообщению ... –

0

Это поведение, которое должна выполнить ESB-реализация. С точки зрения обработки накладных расходов не было бы большой разницы, но может быть полезно разделить проблемы между «сантехникой» и кодом приложения.

Как это происходит, в реализации WebSphere JMS есть поддержка для установки посредников, которые отвечают таким требованиям. Я не знаю, есть ли у WebLogic что-то подобное, или же связанные с ними продукты ESB являются для вас вариантом, но я бы рекомендовал изучить эти возможности. У вас в настоящее время есть простое требование, и ваш код, безусловно, достаточен, однако довольно легко представить себе, как несколько незначительных дополнительных требований (можно ли просто преобразовать это поле из доллара в фунты до того, как мы перейдем к этому месту назначения, не могли ли мы отправлять сообщения с этот контент к этому месту назначения ...) и вот! вы обнаружите, что пишете собственный ESB.

+0

Нет необходимости в ESB IMO, это то, для чего нужны темы. –

+0

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

0

[...] Таким образом, каждое сообщение будет доставлено дважды в System1 и дважды в System2, и если в кластере будет 8 серверов, каждое сообщение будет доставлено 8 раз. Именно этого я и хотел бы избежать ...

Это право для недолгосрочных подписок, но не для долговечных. Для обеспечения долговечности все MDB имеют одинаковый идентификатор соединения и идентификатор подписки (на основе имени MDB по умолчанию), поэтому только один MDB сможет подключать и получать сообщения одновременно. Первый MDB, которому нужно попробовать, удастся подключиться, другие обнаружат конфликт и потерпят неудачу, но продолжайте повторять попытку. Таким образом, использование прочной подписки на тему должно делать трюк.

+0

Я предполагаю, что вы имеете в виду прочную подписку, потому что это свойство получателя, а не тема. Если MDB имеет прочную подписку (и для этого требуется указать ClientID), то он может быть развернут только на одном узле кластера. При развертывании WLS во второй узел происходит сбой, поскольку клиент уже имеет тот же идентификатор клиента. –

+0

Из документов WLS10: «Идентификатор подписки должен быть уникальным в своей теме, поэтому MDB с надежной подпиской на тему не может запускаться на нескольких экземплярах сервера в кластере». http://download.oracle.com/docs/cd/E12839_01/web.1111/e13719/message_beans.htm#i1161176 –

+0

Да, это то, что я имел в виду, я был недостаточно ясен. Что касается документации, я не уверен, что вы хотите показать. Почему вы не ввели весь абзац: «Идентификатор подписки должен быть уникальным в своей теме, поэтому MDB с надежной подпиской на тему не может выполняться на нескольких экземплярах сервера в кластере. После того, как первый экземпляр MDB запускается на сервере экземпляр в кластере, дополнительный экземпляр EJB может успешно развертываться на другом кластерном сервере, но когда MDB запускается, обнаруживается конфликт, и этот экземпляр MDB не может полностью подключиться к JMS ». –