JAMES-4030 Carry over Bouncer exceptions
This results on a nack of the underlying mailqueue, thus not loosing the email
diff --git a/server/mailet/mailets/src/main/java/org/apache/james/transport/mailets/remote/delivery/Bouncer.java b/server/mailet/mailets/src/main/java/org/apache/james/transport/mailets/remote/delivery/Bouncer.java
index 7ba6556..a50bc4d 100644
--- a/server/mailet/mailets/src/main/java/org/apache/james/transport/mailets/remote/delivery/Bouncer.java
+++ b/server/mailet/mailets/src/main/java/org/apache/james/transport/mailets/remote/delivery/Bouncer.java
@@ -35,9 +35,12 @@
import org.apache.mailet.AttributeValue;
import org.apache.mailet.Mail;
import org.apache.mailet.MailetContext;
+import org.apache.mailet.ProcessingState;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
+import com.github.fge.lambdas.Throwing;
+
public class Bouncer {
private static final Logger LOGGER = LoggerFactory.getLogger(Bouncer.class);
@@ -53,18 +56,14 @@
this.mailetContext = mailetContext;
}
- public void bounce(Mail mail, Exception ex) {
+ public void bounce(Mail mail, Exception ex) throws MessagingException {
configuration.getBounceProcessor().ifPresentOrElse(
- bounceProcessor -> {
+ Throwing.<ProcessingState>consumer(bounceProcessor -> {
computeErrorCode(ex).ifPresent(mail::setAttribute);
mail.setAttribute(new Attribute(DELIVERY_ERROR, AttributeValue.of(getErrorMsg(ex))));
- try {
- mailetContext.sendMail(mail, bounceProcessor.getValue());
- } catch (MessagingException e) {
- LOGGER.warn("Exception re-inserting failed mail: ", e);
- }
- },
- () -> bounceWithMailetContext(mail, ex));
+ mailetContext.sendMail(mail, bounceProcessor.getValue());
+ }).sneakyThrow(),
+ Throwing.runnable(() -> bounceWithMailetContext(mail, ex)).sneakyThrow());
}
private Optional<Attribute> computeErrorCode(Exception ex) {
@@ -76,18 +75,12 @@
.map(code -> new Attribute(DELIVERY_ERROR_CODE, AttributeValue.of(code)));
}
- private void bounceWithMailetContext(Mail mail, Exception ex) {
+ private void bounceWithMailetContext(Mail mail, Exception ex) throws MessagingException {
if (!mail.hasSender()) {
LOGGER.debug("Null Sender: no bounce will be generated for {}", mail.getName());
} else {
LOGGER.debug("Sending failure message {}", mail.getName());
- try {
- mailetContext.bounce(mail, explanationText(mail, ex));
- } catch (MessagingException me) {
- LOGGER.warn("Encountered unexpected messaging exception while bouncing message", me);
- } catch (Exception e) {
- LOGGER.warn("Encountered unexpected exception while bouncing message", e);
- }
+ mailetContext.bounce(mail, explanationText(mail, ex));
}
}
diff --git a/server/mailet/mailets/src/main/java/org/apache/james/transport/mailets/remote/delivery/DeliveryRunnable.java b/server/mailet/mailets/src/main/java/org/apache/james/transport/mailets/remote/delivery/DeliveryRunnable.java
index 2576b03..9ae75a0 100644
--- a/server/mailet/mailets/src/main/java/org/apache/james/transport/mailets/remote/delivery/DeliveryRunnable.java
+++ b/server/mailet/mailets/src/main/java/org/apache/james/transport/mailets/remote/delivery/DeliveryRunnable.java
@@ -206,7 +206,7 @@
}
}
- private void handlePermanentFailure(Mail mail, ExecutionResult executionResult) {
+ private void handlePermanentFailure(Mail mail, ExecutionResult executionResult) throws MessagingException {
mail.setAttribute(new Attribute(IS_DELIVERY_PERMANENT_ERROR, AttributeValue.of(true)));
bouncer.bounce(mail, executionResult.getException().orElse(null));
}
diff --git a/server/mailet/mailets/src/main/java/org/apache/james/transport/mailets/remote/delivery/MailDelivrer.java b/server/mailet/mailets/src/main/java/org/apache/james/transport/mailets/remote/delivery/MailDelivrer.java
index c086d39..3d1f8b2 100644
--- a/server/mailet/mailets/src/main/java/org/apache/james/transport/mailets/remote/delivery/MailDelivrer.java
+++ b/server/mailet/mailets/src/main/java/org/apache/james/transport/mailets/remote/delivery/MailDelivrer.java
@@ -218,7 +218,12 @@
if (!validUnsentAddresses.isEmpty()) {
if (!invalidAddresses.isEmpty()) {
mail.setRecipients(invalidAddresses);
- bouncer.bounce(mail, sfe);
+ try {
+ bouncer.bounce(mail, sfe);
+ } catch (MessagingException e) {
+ LOGGER.warn("Failed bouncing permanently failed recipients, returning full temporarily failure instead", e);
+ return logAndReturn(mail, ExecutionResult.temporaryFailure(sfe));
+ }
}
mail.setRecipients(validUnsentAddresses);
if (enhancedMessagingException.hasReturnCode()) {