RabbitMQ-berichten en asynchrone systemen · Les

Publisher confirms voor betrouwbaarheid

Implementeer publisher confirms om te garanderen dat berichten succesvol door de broker zijn ontvangen en verwerkt. Bouw betrouwbare producers die kunnen herstellen van netwerk- of brokerproblemen.

Les 2 van 411 stappen

Publisher confirms voor betrouwbaarheid is een gratis RabbitMQ-berichten en asynchrone systemen-les op CoddyKit. Dit is les 2 van 4. Je kunt 3 lessen uit dit leerpad gratis volledig lezen — daarna ontgrendelt CoddyKit PRO alle lessen, plus praktische oefeningen met een ingebouwde code-editor en een AI-tutor die 24/7 beschikbaar is. Deze les maakt deel uit van het leertraject RabbitMQ-berichten en asynchrone systemen. Je voortgang wordt gesynchroniseerd op het web en in de CoddyKit-app. De cursus RabbitMQ-berichten en asynchrone systemen bevat in totaal 4 lessen.

Waarom publisherbevestigingen?

Als je een bericht naar RabbitMQ verzendt, hoe weet je dan of het veilig bij de broker is aangekomen?

Standaard verzenden producers berichten zonder op een expliciete bevestiging van RabbitMQ te wachten. Dat is snel, maar het betekent dat berichten verloren kunnen gaan door netwerkproblemen of brokerstoringen vlak nadat ze zijn verzonden.

Publisherbevestigingen zijn een mechanisme waarmee producers bevestigingen (ACK's) van RabbitMQ kunnen ontvangen wanneer berichten succesvol door de broker zijn ontvangen en verwerkt.

De onzichtbare kloof bij het afleveren

Stel je voor dat je een belangrijke bestelling naar een verwerkingswachtrij verzendt. Zonder publisherbevestigingen verstuurt je applicatie het bericht simpelweg en gaat verder.

  • Wat gebeurt er als de netwerkverbinding het bericht onderweg laat vallen?
  • Wat gebeurt er als de RabbitMQ-server kort na ontvangst crasht, maar voordat je bericht persistent is gemaakt?

Zonder bevestiging zou je producer ervan uitgaan dat alles is gelukt, wat mogelijk tot gegevensverlies of inconsistente toestanden in je systeem leidt.

Hoe de bevestigingsmodus werkt

Om publisherbevestigingen te gebruiken, schakel je de 'bevestigingsmodus' in op een kanaal. Zodra deze modus is ingeschakeld, krijgt elk bericht dat via dat kanaal wordt gepubliceerd een unieke aflevertag.

  • ACK (positieve bevestiging): De broker stuurt een ACK terug naar de producer wanneer een bericht succesvol is ontvangen, naar de wachtrijen is gerouteerd en persistent is gemaakt (als het duurzaam is).
  • NACK (negatieve bevestiging): De broker stuurt een NACK als het bericht niet kon worden verwerkt (bijvoorbeeld omdat het niet kon worden gerouteerd of door een interne fout).

Deze feedbacklus sluit de 'afleveringskloof' tussen producer en broker.

De bevestigingsmodus inschakelen

Voordat je berichten publiceert, moet je RabbitMQ laten weten dat je publisherbevestigingen op je kanaal wilt gebruiken. Dit stel je één keer per kanaal in.

Voer dit voorbeeld uit om te zien hoe je de bevestigingsmodus inschakelt:

import com.rabbitmq.client.Channel;
import com.rabbitmq.client.Connection;
import com.rabbitmq.client.ConnectionFactory;

public class ConfirmSetup {
  public static void main(String[] args) throws Exception {
    ConnectionFactory factory = new ConnectionFactory();
    factory.setHost("localhost"); // Assumes RabbitMQ is running locally
    try (Connection connection = factory.newConnection();
         Channel channel = connection.createChannel()) {

      channel.confirmSelect(); // This line enables confirm mode
      System.out.println("Channel is now in confirm mode.");
      // Further publishing code would go here
    }
  }
}

Synchrone bevestigingen: `waitForConfirms`

Een manier om publisherbevestigingen te gebruiken is synchroon. Nadat de producer één of meer berichten heeft gepubliceerd, kan deze channel.waitForConfirms() of channel.waitForConfirmsOrDie() aanroepen.

  • Deze methode blokkeert de producer totdat voor alle berichten die sinds de vorige aanroep zijn gepubliceerd een ACK of NACK is ontvangen.
  • De implementatie is eenvoudig, maar de doorvoer kan aanzienlijk afnemen omdat de producer op elke batch berichten wacht.
  • Ideaal voor kleine aantallen kritieke berichten waarbij directe bevestiging van het grootste belang is.

Voorbeeld van code voor synchrone bevestigingen

In dit voorbeeld verzendt een producer één bericht en wacht daarna op de bevestiging. Als het bericht niet binnen 5 seconden wordt bevestigd, treedt er een time-out op.

import com.rabbitmq.client.Channel;
import com.rabbitmq.client.Connection;
import com.rabbitmq.client.ConnectionFactory;
import java.io.IOException;
import java.util.concurrent.TimeoutException;

public class SyncConfirmPublisher {
  private static final String QUEUE_NAME = "sync_confirm_queue";

  public static void main(String[] args) throws IOException, TimeoutException, InterruptedException {
    ConnectionFactory factory = new ConnectionFactory();
    factory.setHost("localhost");
    try (Connection connection = factory.newConnection();
         Channel channel = connection.createChannel()) {

      channel.queueDeclare(QUEUE_NAME, false, false, false, null);
      channel.confirmSelect(); // Enable confirm mode

      String message = "Hello, reliable world!";
      channel.basicPublish("", QUEUE_NAME, null, message.getBytes("UTF-8"));
      System.out.println(" [x] Sent '" + message + "'");

      // Wait for confirmation for up to 5 seconds
      if (channel.waitForConfirms(5000)) {
        System.out.println("Message confirmed by broker!");
      } else {
        System.out.println("Message not confirmed within timeout! It might be lost or delayed.");
      }
    }
  }
}

Asynchrone bevestigingen: listeners

Voor een hogere doorvoer kun je asynchrone publisherbevestigingen gebruiken. In plaats van te blokkeren, registreer je een ConfirmListener op het kanaal.

  • De listener heeft twee methoden: handleAck() voor succesvolle bevestigingen en handleNack() voor negatieve bevestigingen.
  • RabbitMQ levert ACK's en NACK's aan deze listener, zodat je producer berichten kan blijven publiceren zonder te wachten.
  • Voor deze aanpak is complexere logica nodig om onbevestigde berichten bij te houden, maar hij biedt betere prestaties bij het publiceren van grote aantallen berichten.

Voorbeeld van code voor asynchrone bevestigingen

Dit voorbeeld laat een asynchrone publisher zien. Er wordt een listener geregistreerd die ACK's en NACK's afhandelt zonder de hoofdthread te blokkeren.

Let op de Thread.sleep(), die het programma lang genoeg actief houdt om bevestigingen te ontvangen.

import com.rabbitmq.client.Channel;
import com.rabbitmq.client.ConfirmListener;
import com.rabbitmq.client.Connection;
import com.rabbitmq.client.ConnectionFactory;
import java.io.IOException;
import java.util.concurrent.ConcurrentNavigableMap;
import java.util.concurrent.ConcurrentSkipListMap;

public class AsyncConfirmPublisher {
  private static final String QUEUE_NAME = "async_confirm_queue";

  public static void main(String[] args) throws Exception {
    ConnectionFactory factory = new ConnectionFactory();
    factory.setHost("localhost");
    try (Connection connection = factory.newConnection();
         Channel channel = connection.createChannel()) {

      channel.queueDeclare(QUEUE_NAME, false, false, false, null);
      channel.confirmSelect(); // Enable confirm mode

      // Store unconfirmed messages by their delivery tag
      ConcurrentNavigableMap<Long, String> outstandingConfirms = new ConcurrentSkipListMap<>();

      channel.addConfirmListener(new ConfirmListener() {
        @Override
        public void handleAck(long deliveryTag, boolean multiple) throws IOException {
          if (multiple) {
            // Remove all messages up to this deliveryTag
            outstandingConfirms.headMap(deliveryTag + 1).clear();
          } else {
            outstandingConfirms.remove(deliveryTag);
          }
          System.out.println(" [x] Message with deliveryTag " + deliveryTag + " ACKed! Remaining: " + outstandingConfirms.size());
        }

        @Override
        public void handleNack(long deliveryTag, boolean multiple) throws IOException {
          String message = outstandingConfirms.get(deliveryTag);
          System.out.println(" [!] Message '" + message + "' (deliveryTag " + deliveryTag + ") NACKed! Re-sending or logging error.");
          // Handle NACK: re-publish, log, etc.
          if (multiple) {
             outstandingConfirms.headMap(deliveryTag + 1).clear();
          } else {
             outstandingConfirms.remove(deliveryTag);
          }
        }
      });

      String message = "Hello, async reliable world!";
      long nextPublishSeqNo = channel.getNextPublishSeqNo();
      outstandingConfirms.put(nextPublishSeqNo, message);
      channel.basicPublish("", QUEUE_NAME, null, message.getBytes("UTF-8"));
      System.out.println(" [x] Sent '" + message + "' (deliveryTag: " + nextPublishSeqNo + ")");

      // Keep main thread alive for a moment to receive confirms
      Thread.sleep(2000);
    }
  }
}

Synchroon of asynchroon: kies verstandig

De keuze tussen synchrone en asynchrone bevestigingen hangt af van de behoeften van je applicatie:

  • Synchroon (waitForConfirms):
    • Eenvoudiger te implementeren.
    • Lagere doorvoer omdat de verwerking wordt geblokkeerd.
    • Geschikt voor kleine aantallen zeer kritieke berichten waarbij directe bevestiging essentieel is.
  • Asynchroon (ConfirmListener):
    • Complexere implementatie (onbevestigde berichten moeten worden bijgehouden).
    • Hogere doorvoer omdat de verwerking niet wordt geblokkeerd.
    • Ideaal voor het publiceren van grote aantallen berichten waarbij prestaties belangrijk zijn.

Controle van bevestigingen

Je hebt geleerd over publisherbevestigingen. Laten we kijken of je deze vraag kunt beantwoorden.

Samenvatting: betrouwbaar publiceren

Gefeliciteerd! Je hebt geleerd hoe je je RabbitMQ-producers echt betrouwbaar maakt met publisherbevestigingen.

  • Publisherbevestigingen zorgen ervoor dat berichten die door een producer zijn verzonden, succesvol door de RabbitMQ-broker worden ontvangen en verwerkt.
  • Je schakelt de bevestigingsmodus op een kanaal in met channel.confirmSelect().
  • Synchrone bevestigingen (waitForConfirms()) zijn eenvoudig, maar blokkeren de verwerking en zijn geschikt voor kleine aantallen berichten.
  • Asynchrone bevestigingen (addConfirmListener()) bieden een hogere doorvoer voor situaties met grote aantallen berichten, maar vereisen dat berichten complexer worden bijgehouden.

Met publisherbevestigingen kun je robuuste systemen bouwen die berichtverlies beperken en de integriteit van kritieke gegevens waarborgen.

Gratis beginnen

Leer RabbitMQ-berichten en asynchrone systemen met een AI-tutor — gratis

Schrijf echte code en voer die uit in je browser, krijg direct hulp van een AI-tutor die 24/7 beschikbaar is en ga verder waar je gebleven bent op het web of in de app.

Cursussen
11
Lessen
44

Veelgestelde vragen

Is de les “Publisher confirms voor betrouwbaarheid” gratis?

Ja — je kunt hier op het web alle 3 lessen van het leerpad RabbitMQ-berichten en asynchrone systemen, waaronder “Publisher confirms voor betrouwbaarheid”, gratis volledig lezen. Daarna ontgrendelt CoddyKit PRO alle lessen, plus interactieve oefeningen met een ingebouwde code-editor en een AI-tutor die 24/7 beschikbaar is. De cursus RabbitMQ-berichten en asynchrone systemen bevat in totaal 4 lessen.

Wat leer ik in “Publisher confirms voor betrouwbaarheid”?

Implementeer publisher confirms om te garanderen dat berichten succesvol door de broker zijn ontvangen en verwerkt. Bouw betrouwbare producers die kunnen herstellen van netwerk- of brokerproblemen. Je oefent met RabbitMQ-berichten en asynchrone systemen door code rechtstreeks in de browser uit te voeren. Een AI-begeleider die 24/7 beschikbaar is beantwoordt je vragen terwijl je de les doorwerkt.

Heb ik ervaring nodig om met RabbitMQ-berichten en asynchrone systemen te beginnen?

Ervaring vooraf is niet nodig. RabbitMQ-berichten en asynchrone systemen op CoddyKit is opgebouwd voor beginners tot gevorderden, zodat je hier of bij het begin kunt starten en in je eigen tempo kunt leren. Dit is les 2 van 4.

Hoe lang duurt de les “Publisher confirms voor betrouwbaarheid”?

De meeste lessen van CoddyKit duren ongeveer 5–10 minuten. Elke les is kort en interactief, zodat je gestaag vooruitgaat en op het web en in de app precies verdergaat waar je was gebleven.

Kan ik code schrijven en uitvoeren in deze les over RabbitMQ-berichten en asynchrone systemen?

Ja. Elke les over RabbitMQ-berichten en asynchrone systemen bevat een ingebouwde code-editor, zodat je rechtstreeks in je browser echte code kunt schrijven en uitvoeren en direct feedback van AI krijgt — lokale installatie is niet nodig.

Alle lessen in deze cursus

  1. Persistente berichten en queues
  2. Publisher confirms voor betrouwbaarheid
  3. Consumer acknowledgements en opnieuw in de wachtrij plaatsen
  4. Transacties versus publisher confirms
← Terug naar RabbitMQ-berichten en asynchrone systemen