Sono interessato a sapere come altre persone gestiscono il ripristino da una connessione errata utilizzando la libreria client java RabbitMQ ufficiale. Lo stiamo usando per connettere i nostri server applicativi al nostro cluster RabbitMQ e abbiamo implementato alcuni modi diversi per recuperare da un errore di connessione, ma nessuno di loro sembra giusto.Come gestite il ripristino da una connessione errata utilizzando la libreria client java RabbitMQ?
Immaginate questa applicazione pseudo:
public class OurClassThatStartsConsumers {
Connection conn;
public void start() {
ConnectionFactory factory = new ConnectionFactory();
factory.setUsername("someusername");
factory.setPassword("somepassword");
factory.setHost("somehost");
conn = factory.newConnection();
new Thread(new Consumer(conn.createChannel())).start();
}
}
class Consumer1 implements Runnable {
public Consumer1(Channel channel) {
this.channel = channel;
}
@Override
public void run() {
while (true) {
... consume incoming messages on the channel...
// How do we handle that the connection dies?
}
}
}
Nel mondo reale abbiamo diverse centinaia di consumatori. Quindi cosa succede se la connessione muore? Nell'esempio sopra Consumer1 non può recuperare, quando la connessione si chiude, si chiude anche il canale, uno stato dal quale non possiamo recuperare. Quindi, consente di guardare alcuni modi per risolvere questo:
Soluzione A)
Lasciate ogni consumatore hanno il loro collegamento e registrare gli eventi che si innescano quando la connessione muore e poi gestire la riconnessione.
Pro: Funziona
Contro:
- Dal momento che abbiamo un sacco di consumatori, che probabilmente non si vuole che molti connessioni.
- Potremmo eventualmente avere un sacco di codice duplicato per riconnessione al coniglio e gestire ricollegare
Soluzione B)
Avere ogni consumatore usa la stessa connessione e iscriviti alla sua eventi di errore di connessione.
Pro: meno connessioni rispetto nella Soluzione A
Contro: Poiché la connessione è chiusa dobbiamo riaprire/sostituirlo. La libreria client java non sembra fornire un modo per riaprire la connessione, quindi dovremmo sostituirla con una nuova connessione e quindi in qualche modo notificare a tutti gli utenti questa nuova connessione e dovranno ricreare i canali e i consumatori . Ancora una volta, molta logica che non voglio vedere nel consumatore finisce lì.
Soluzione C)
Wrap Connection
e Channel
classi è classi che gestiscono la logica ri-connessione, il consumatore ha solo bisogno di conoscere la classe WrappedChannel
. In caso di errore di connessione, il WrappedConnection
si occuperà di ristabilire la connessione e, una volta connesso, lo WrappedConnection
creerà automaticamente nuovi canali e registrerà i consumatori.
Pro: Funziona: questa è in realtà la soluzione che stiamo utilizzando oggi.
Contro: Sembra un trucco, penso che questo sia qualcosa che dovrebbe essere gestito in modo più elegante dalla libreria sottostante.
Forse c'è un modo migliore? La documentazione dell'API non parla molto del ripristino da una connessione difettosa.Qualsiasi input è apprezzato :)
Puoi dare un suggerimento su come esattamente codificarlo. Poiché sembra non esserci nessuna chiamata richiamata su cui possiamo recuperare tutti i canali, le code e le associazioni. Puoi dirmi esattamente come dovrei avvolgere la connessione ?? – jeevs
Dovrai racchiudere Connessione e Canale, non c'è modo di recuperare un canale dopo che è stato disconnesso, quindi dovrai crearne uno nuovo. –