2012-12-18 14 views
5

Attualmente sto aggiungendo il supporto JMS a un framework simile a un'applicazione-server. Il JMS sarà implementato da HornetQ (broker stand-alone, jar hornetq sul classpath dei server) ma non c'è né JBoss né spring né qualsiasi altra cosa che possa fornire MDB.Procedura consigliata per l'elaborazione di messaggi multi-threading sulle code JMS

Il passaggio successivo consiste nell'aggiungere un listener di messaggi a una coda xa che consenta l'elaborazione parallela dei messaggi in arrivo. Alcuni messaggi potrebbero avviare attività a esecuzione prolungata, quindi l'idea di base è generare i thread di lavoro dal metodo onMessage.

Nel mio lungo viaggio attraverso Internet mi sono imbattuto in this discussion, dove uno dei partecipanti ha menzionato, che non lo farebbe ma userebbe una coda interna extra per l'attività: il listener di messaggi (a thread singolo) quindi semplicemente afferrerebbe il messaggi dalla coda in entrata e creare nuovi messaggi per una coda interna, dove all'altra estremità di quella coda interna alcuni thread di lavoro combattono per i messaggi in arrivo. I messaggi in entrata quindi verrebbero riconosciuti una volta che sono stati "copiati" nella coda interna (che per me è ok).

Purtroppo non dicono perché sarebbe meglio di non deporre le uova thread di lavoro dal metodo onMessage - forse, perché l'ascoltatore sarebbe bloccare se tutte le discussioni dalla piscina sono occupati. Così sto cercando pro ei contro per le decisioni disegni:

  • Avvio thread di lavoro dal metodo onMessage del messaggio ascoltatore
  • Usa una coda interna a "inviare messaggi al thread di lavoro"

risposta

3

Limiti di transazione a parte, se avere o meno thread (o processi) di lettura da una coda si riduce semplicemente a se l'ordine dei messaggi è importante o meno. Ovviamente se l'ordine è importante, allora un singolo thread mantiene naturalmente quell'ordine, mentre più thread non forniranno tale garanzia.

Ciò che si trova normalmente è che l'ordine è importante ma attraverso un sottoinsieme di tutti i messaggi. In questo scenario, se un singolo thread non è performante, è necessario rimuovere quei messaggi dalla coda e re-accodati nel minor tempo possibile perché per conservare l'ordine sarà necessario utilizzare una lettura a thread singolo dall'iniziale coda - da qui l'uso di una o più code interne. Il problema che ne deriva è che la transazione verrà chiusa prima che i messaggi vengano elaborati completamente e quindi è necessario un qualche tipo di memoria temporanea per garantire che i messaggi non vengano rilasciati se il processo dovesse cadere prima che l'elaborazione fosse avvenuta.

Se, come suggerisce la tua domanda, non sei troppo preoccupato di lasciar cadere i messaggi, allora il java.util.concurrent.BlockingQueue suona come quello che ti serve per le code interne con un singolo thread che gestisce ciascuna.