You are viewing a plain text version of this content. The canonical link for it is here.
Posted to server-dev@james.apache.org by bt...@apache.org on 2022/10/28 03:53:31 UTC

[james-jspf] 03/03: [UPGRADES] Drop uk.nominet:dnsjnio

This is an automated email from the ASF dual-hosted git repository.

btellier pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/james-jspf.git

commit 3ea9bffa7b6344c4d85e801b5b703510f613b155
Author: Benoit Tellier <bt...@linagora.com>
AuthorDate: Thu Oct 27 17:05:09 2022 +0700

    [UPGRADES] Drop uk.nominet:dnsjnio
    
    DNSJava from 3.5 onward allows already asynchronous request execution,
    thus this external dependency, incompatible with DNSJava 3.5, can be dropped.
---
 assemble/pom.xml                                   |   4 -
 pom.xml                                            |   5 -
 resolver/pom.xml                                   |   4 -
 .../org/apache/james/jspf/core/DNSService.java     |   4 +
 .../jspf/executor/AsynchronousSPFExecutor.java     | 101 ++++++++++++++++
 .../james/jspf/impl/DNSJnioAsynchService.java      | 134 ---------------------
 .../james/jspf/impl/DNSServiceXBillImpl.java       |  32 ++++-
 .../main/java/org/apache/james/jspf/impl/SPF.java  |   4 +-
 .../org/apache/james/jspf/AbstractYamlTest.java    |  58 +++------
 .../org/apache/james/jspf/LoggingDNSService.java   |  52 +++++---
 .../james/jspf/MailZoneAsynchronousYamlTest.java   |   2 +-
 11 files changed, 192 insertions(+), 208 deletions(-)

diff --git a/assemble/pom.xml b/assemble/pom.xml
index 45caa92..55f736a 100644
--- a/assemble/pom.xml
+++ b/assemble/pom.xml
@@ -42,10 +42,6 @@
             <groupId>dnsjava</groupId>
             <artifactId>dnsjava</artifactId>
         </dependency>
-        <dependency>
-            <groupId>uk.nominet</groupId>
-            <artifactId>dnsjnio</artifactId>
-        </dependency>
         <dependency>
             <groupId>net.java.dev</groupId>
             <artifactId>jvyaml</artifactId>
diff --git a/pom.xml b/pom.xml
index 95799a9..c1770e2 100644
--- a/pom.xml
+++ b/pom.xml
@@ -87,11 +87,6 @@
                 <artifactId>dnsjava</artifactId>
                 <version>3.5.1</version>
             </dependency>
-            <dependency>
-                <groupId>uk.nominet</groupId>
-                <artifactId>dnsjnio</artifactId>
-                <version>1.0.3</version>
-            </dependency>
             <dependency>
                 <groupId>junit</groupId>
                 <artifactId>junit</artifactId>
diff --git a/resolver/pom.xml b/resolver/pom.xml
index 2138ecb..d78ec89 100644
--- a/resolver/pom.xml
+++ b/resolver/pom.xml
@@ -45,10 +45,6 @@
             <groupId>dnsjava</groupId>
             <artifactId>dnsjava</artifactId>
         </dependency>
-        <dependency>
-            <groupId>uk.nominet</groupId>
-            <artifactId>dnsjnio</artifactId>
-        </dependency>
         <dependency>
             <groupId>junit</groupId>
             <artifactId>junit</artifactId>
diff --git a/resolver/src/main/java/org/apache/james/jspf/core/DNSService.java b/resolver/src/main/java/org/apache/james/jspf/core/DNSService.java
index fb86a20..82935d7 100644
--- a/resolver/src/main/java/org/apache/james/jspf/core/DNSService.java
+++ b/resolver/src/main/java/org/apache/james/jspf/core/DNSService.java
@@ -22,6 +22,8 @@ package org.apache.james.jspf.core;
 import org.apache.james.jspf.core.exceptions.TimeoutException;
 
 import java.util.List;
+import java.util.concurrent.CompletableFuture;
+import java.util.concurrent.CompletionStage;
 
 /**
  * Interface which should be used to access all necassary DNS-Records
@@ -38,6 +40,8 @@ public interface DNSService {
      */
     public List<String> getRecords(DNSRequest request) throws TimeoutException;
 
+    CompletionStage<List<String>> getRecordsAsync(DNSRequest request);
+
     /**
      * Try to get all domain names for the running host
      * 
diff --git a/resolver/src/main/java/org/apache/james/jspf/executor/AsynchronousSPFExecutor.java b/resolver/src/main/java/org/apache/james/jspf/executor/AsynchronousSPFExecutor.java
new file mode 100644
index 0000000..ac8836d
--- /dev/null
+++ b/resolver/src/main/java/org/apache/james/jspf/executor/AsynchronousSPFExecutor.java
@@ -0,0 +1,101 @@
+/****************************************************************
+ * Licensed to the Apache Software Foundation (ASF) under one   *
+ * or more contributor license agreements.  See the NOTICE file *
+ * distributed with this work for additional information        *
+ * regarding copyright ownership.  The ASF licenses this file   *
+ * to you under the Apache License, Version 2.0 (the            *
+ * "License"); you may not use this file except in compliance   *
+ * with the License.  You may obtain a copy of the License at   *
+ *                                                              *
+ *   http://www.apache.org/licenses/LICENSE-2.0                 *
+ *                                                              *
+ * Unless required by applicable law or agreed to in writing,   *
+ * software distributed under the License is distributed on an  *
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY       *
+ * KIND, either express or implied.  See the License for the    *
+ * specific language governing permissions and limitations      *
+ * under the License.                                           *
+ ****************************************************************/
+
+package org.apache.james.jspf.executor;
+
+import org.apache.james.jspf.core.DNSLookupContinuation;
+import org.apache.james.jspf.core.DNSResponse;
+import org.apache.james.jspf.core.DNSService;
+import org.apache.james.jspf.core.SPFChecker;
+import org.apache.james.jspf.core.SPFCheckerExceptionCatcher;
+import org.apache.james.jspf.core.SPFSession;
+import org.apache.james.jspf.core.exceptions.NeutralException;
+import org.apache.james.jspf.core.exceptions.NoneException;
+import org.apache.james.jspf.core.exceptions.PermErrorException;
+import org.apache.james.jspf.core.exceptions.SPFResultException;
+import org.apache.james.jspf.core.exceptions.TempErrorException;
+import org.apache.james.jspf.core.exceptions.TimeoutException;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ * Synchronous implementation of SPFExecuter. All queries will get executed synchronously
+ */
+public class AsynchronousSPFExecutor implements SPFExecutor {
+    private static final Logger LOGGER = LoggerFactory.getLogger(AsynchronousSPFExecutor.class);
+
+    private DNSService dnsProbe;
+
+    public AsynchronousSPFExecutor(DNSService service) {
+        this.dnsProbe = service;
+    }
+
+    /**
+     * @see SPFExecutor#execute(SPFSession, FutureSPFResult)
+     */
+    public void execute(SPFSession session, FutureSPFResult result) {
+        SPFChecker checker;
+        while ((checker = session.popChecker()) != null) {
+            // only execute checkers we added (better recursivity)
+            LOGGER.debug("Executing checker: {}", checker);
+            final SPFChecker finalChecker = checker;
+            try {
+                final DNSLookupContinuation cont = checker.checkSPF(session);
+                // if the checker returns a continuation we return it
+                dnsProbe.getRecordsAsync(cont.getRequest())
+                    .thenAccept(results -> {
+                        try {
+                            cont.getListener().onDNSResponse(new DNSResponse(results), session);
+                        } catch (PermErrorException | NoneException | TempErrorException | NeutralException e) {
+                            handleError(session, finalChecker, e);
+                        }
+                    })
+                    .exceptionally(e -> {
+                        if (e instanceof TimeoutException) {
+                            try {
+                                cont.getListener().onDNSResponse(new DNSResponse((TimeoutException) e), session);
+                            } catch (PermErrorException | NoneException | TempErrorException | NeutralException ex2) {
+                                handleError(session, finalChecker, ex2);
+                            }
+                        }
+                        return null;
+                    });
+            } catch (Exception e) {
+                handleError(session, checker, e);
+            }
+        }
+        result.setSPFResult(session);
+    }
+
+    private void handleError(SPFSession session, SPFChecker checker, Exception e) {
+        while (e != null) {
+            while (checker == null || !(checker instanceof SPFCheckerExceptionCatcher)) {
+                checker = session.popChecker();
+            }
+            try {
+                ((SPFCheckerExceptionCatcher) checker).onException(e, session);
+                e = null;
+            } catch (SPFResultException ex) {
+                e = ex;
+            } finally {
+                checker = null;
+            }
+        }
+    }
+}
diff --git a/resolver/src/main/java/org/apache/james/jspf/impl/DNSJnioAsynchService.java b/resolver/src/main/java/org/apache/james/jspf/impl/DNSJnioAsynchService.java
deleted file mode 100644
index e2dc4e2..0000000
--- a/resolver/src/main/java/org/apache/james/jspf/impl/DNSJnioAsynchService.java
+++ /dev/null
@@ -1,134 +0,0 @@
-/****************************************************************
- * Licensed to the Apache Software Foundation (ASF) under one   *
- * or more contributor license agreements.  See the NOTICE file *
- * distributed with this work for additional information        *
- * regarding copyright ownership.  The ASF licenses this file   *
- * to you under the Apache License, Version 2.0 (the            *
- * "License"); you may not use this file except in compliance   *
- * with the License.  You may obtain a copy of the License at   *
- *                                                              *
- *   http://www.apache.org/licenses/LICENSE-2.0                 *
- *                                                              *
- * Unless required by applicable law or agreed to in writing,   *
- * software distributed under the License is distributed on an  *
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY       *
- * KIND, either express or implied.  See the License for the    *
- * specific language governing permissions and limitations      *
- * under the License.                                           *
- ****************************************************************/
-
-package org.apache.james.jspf.impl;
-
-import java.util.List;
-
-import org.apache.james.jspf.core.DNSRequest;
-import org.apache.james.jspf.core.exceptions.TimeoutException;
-import org.apache.james.jspf.executor.DNSAsynchLookupService;
-import org.apache.james.jspf.executor.IResponse;
-import org.apache.james.jspf.executor.IResponseQueue;
-import org.xbill.DNS.DClass;
-import org.xbill.DNS.Message;
-import org.xbill.DNS.Name;
-import org.xbill.DNS.Record;
-import org.xbill.DNS.Resolver;
-import org.xbill.DNS.TextParseException;
-import org.xbill.DNS.Type;
-
-import uk.nominet.dnsjnio.ExtendedNonblockingResolver;
-import uk.nominet.dnsjnio.LookupAsynch;
-
-public class DNSJnioAsynchService implements DNSAsynchLookupService {
-
-    private ExtendedNonblockingResolver resolver;
-
-    public DNSJnioAsynchService(ExtendedNonblockingResolver resolver) {
-        this.resolver = resolver;
-        LookupAsynch.setDefaultResolver(resolver);
-    }
-    
-    /**
-     * Set the timeout for the resolvers
-     * @param timeout
-     */
-    public synchronized void setTimeout(int timeout) {
-        Resolver[] res = resolver.getResolvers();
-        for (int i = 0; i < res.length; i++) {
-            res[i].setTimeout(timeout);
-        }
-    }
-    
-    /**
-     * @see org.apache.james.jspf.executor.DNSAsynchLookupService#getRecordsAsynch(org.apache.james.jspf.core.DNSRequest, int, org.apache.james.jspf.executor.IResponseQueue)
-     */
-    public void getRecordsAsynch(DNSRequest request, int id,
-            IResponseQueue responsePool) {
-        
-        Message message;
-        try {
-            message = makeQuery(request, id);
-            LookupAsynch la = new LookupAsynch(message.getQuestion().getName(), message.getQuestion().getType());
-            la.runAsynch(new Runnable() {
-
-                private IResponseQueue responsePool;
-                private Integer id;
-                private LookupAsynch lookup;
-
-                public void run() {
-                    responsePool.insertResponse(new IResponse() {
-
-                        public Exception getException() {
-                            if (lookup.getResult() == LookupAsynch.TRY_AGAIN) {
-                                return new TimeoutException(lookup.getErrorString());
-                            } else {
-                                return null;
-                            }
-                        }
-
-                        public Object getId() {
-                            return id;
-                        }
-
-                        public List<String> getValue() {
-                            return (DNSServiceXBillImpl.convertRecordsToList(lookup.getAnswers()));
-                        }
-                        
-                    });
-                }
-
-                public Runnable setResponsePool(LookupAsynch la, IResponseQueue responsePool,
-                        Integer integer) {
-                    this.lookup = la;
-                    this.responsePool = responsePool;
-                    this.id = integer;
-                    return this;
-                }
-                
-            }.setResponsePool(la, responsePool, new Integer(id)));
-            // this.resolver.sendAsync(message, new Integer(id), new ResponseQueueAdaptor(responsePool));
-        } catch (TextParseException e) {
-            // TODO Auto-generated catch block
-            e.printStackTrace();
-        }
-    }
-
-    private Message makeQuery(DNSRequest request, int id) throws TextParseException {
-        Name name = Name.fromString(request.getHostname(), Name.root);
-        
-        int type;
-        switch (request.getRecordType()) {
-            case DNSRequest.A: type = Type.A; break;
-            case DNSRequest.AAAA: type = Type.AAAA; break;
-            case DNSRequest.MX: type = Type.MX; break;
-            case DNSRequest.PTR: type = Type.PTR; break;
-            case DNSRequest.SPF: type = Type.SPF; break;
-            case DNSRequest.TXT: type = Type.TXT; break;
-            default: 
-                throw new UnsupportedOperationException("Unknown query type: "+request.getRecordType());
-        }
-        
-        Record question = Record.newRecord(name, type, DClass.ANY);
-        Message query = Message.newQuery(question);
-        query.getHeader().setID(id);
-        return query;
-    }
-}
diff --git a/resolver/src/main/java/org/apache/james/jspf/impl/DNSServiceXBillImpl.java b/resolver/src/main/java/org/apache/james/jspf/impl/DNSServiceXBillImpl.java
index 99c2690..7e15933 100644
--- a/resolver/src/main/java/org/apache/james/jspf/impl/DNSServiceXBillImpl.java
+++ b/resolver/src/main/java/org/apache/james/jspf/impl/DNSServiceXBillImpl.java
@@ -24,6 +24,8 @@ import java.net.UnknownHostException;
 import java.util.ArrayList;
 import java.util.Iterator;
 import java.util.List;
+import java.util.concurrent.CompletableFuture;
+import java.util.concurrent.CompletionStage;
 
 import org.apache.james.jspf.core.DNSRequest;
 import org.apache.james.jspf.core.DNSService;
@@ -35,6 +37,7 @@ import org.xbill.DNS.AAAARecord;
 import org.xbill.DNS.ARecord;
 import org.xbill.DNS.Lookup;
 import org.xbill.DNS.MXRecord;
+import org.xbill.DNS.Name;
 import org.xbill.DNS.PTRRecord;
 import org.xbill.DNS.Record;
 import org.xbill.DNS.Resolver;
@@ -42,6 +45,7 @@ import org.xbill.DNS.SPFRecord;
 import org.xbill.DNS.TXTRecord;
 import org.xbill.DNS.TextParseException;
 import org.xbill.DNS.Type;
+import org.xbill.DNS.lookup.LookupSession;
 
 /**
  * This class contains helper to get all neccassary DNS infos that are needed
@@ -167,7 +171,33 @@ public class DNSServiceXBillImpl implements DNSService {
             return null;
         }
     }
-    
+
+    @Override
+    public CompletionStage<List<String>> getRecordsAsync(DNSRequest request) {
+        String recordTypeDescription;
+        int dnsJavaType;
+        switch (request.getRecordType()) {
+            case DNSRequest.A: recordTypeDescription = "A"; dnsJavaType = Type.A; break;
+            case DNSRequest.AAAA: recordTypeDescription = "AAAA"; dnsJavaType = Type.AAAA; break;
+            case DNSRequest.MX: recordTypeDescription = "MX"; dnsJavaType = Type.MX; break;
+            case DNSRequest.PTR: recordTypeDescription = "PTR"; dnsJavaType = Type.PTR; break;
+            case DNSRequest.TXT: recordTypeDescription = "TXT"; dnsJavaType = Type.TXT; break;
+            case DNSRequest.SPF: recordTypeDescription= "SPF"; dnsJavaType = Type.SPF; break;
+            default: // TODO fail!
+                throw new IllegalArgumentException();
+        }
+        LOGGER.debug("Start {}-Record lookup for : {}", recordTypeDescription, request.getHostname());
+        final LookupSession lookupSession = LookupSession.defaultBuilder().build();
+
+        try {
+            return lookupSession.lookupAsync(Name.fromString(request.getHostname()), dnsJavaType)
+                .thenApply(result -> convertRecordsToList(result.getRecords().toArray(new Record[0])));
+        } catch (TextParseException e) {
+            LOGGER.debug("No {} Record found for host: {}", recordTypeDescription, request.getHostname());
+            throw new IllegalArgumentException();
+        }
+    }
+
     /**
      * Convert the given Record array to a List
      * 
diff --git a/resolver/src/main/java/org/apache/james/jspf/impl/SPF.java b/resolver/src/main/java/org/apache/james/jspf/impl/SPF.java
index 8f665ee..b9d8dfc 100644
--- a/resolver/src/main/java/org/apache/james/jspf/impl/SPF.java
+++ b/resolver/src/main/java/org/apache/james/jspf/impl/SPF.java
@@ -22,6 +22,7 @@ package org.apache.james.jspf.impl;
 
 import java.util.Iterator;
 import java.util.LinkedList;
+import java.util.concurrent.CompletableFuture;
 
 import org.apache.james.jspf.core.DNSLookupContinuation;
 import org.apache.james.jspf.core.DNSService;
@@ -41,6 +42,7 @@ import org.apache.james.jspf.core.exceptions.PermErrorException;
 import org.apache.james.jspf.core.exceptions.SPFErrorConstants;
 import org.apache.james.jspf.core.exceptions.SPFResultException;
 import org.apache.james.jspf.core.exceptions.TempErrorException;
+import org.apache.james.jspf.executor.AsynchronousSPFExecutor;
 import org.apache.james.jspf.executor.FutureSPFResult;
 import org.apache.james.jspf.executor.SPFExecutor;
 import org.apache.james.jspf.executor.SPFResult;
@@ -215,7 +217,7 @@ public class SPF implements SPFChecker {
         this.parser = new RFC4408SPF1Parser(new DefaultTermsFactory(wiringService));
         // We add this after the parser creation because services cannot be null
         wiringService.put(SPFCheckEnabled.class, this);
-        this.executor = new SynchronousSPFExecutor(dnsProbe);
+        this.executor = new AsynchronousSPFExecutor(dnsProbe);
     }
     
     
diff --git a/resolver/src/test/java/org/apache/james/jspf/AbstractYamlTest.java b/resolver/src/test/java/org/apache/james/jspf/AbstractYamlTest.java
index fa6af83..fa977f8 100644
--- a/resolver/src/test/java/org/apache/james/jspf/AbstractYamlTest.java
+++ b/resolver/src/test/java/org/apache/james/jspf/AbstractYamlTest.java
@@ -27,6 +27,10 @@ import java.util.Iterator;
 import java.util.List;
 import java.util.Locale;
 import java.util.Map;
+import java.util.concurrent.CompletableFuture;
+import java.util.concurrent.CompletionStage;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
 
 import org.apache.james.jspf.core.DNSRequest;
 import org.apache.james.jspf.core.DNSService;
@@ -40,7 +44,6 @@ import org.apache.james.jspf.executor.SPFExecutor;
 import org.apache.james.jspf.executor.SPFResult;
 import org.apache.james.jspf.executor.StagedMultipleSPFExecutor;
 import org.apache.james.jspf.executor.SynchronousSPFExecutor;
-import org.apache.james.jspf.impl.DNSJnioAsynchService;
 import org.apache.james.jspf.impl.DNSServiceAsynchSimulator;
 import org.apache.james.jspf.impl.DNSServiceXBillImpl;
 import org.apache.james.jspf.impl.DefaultTermsFactory;
@@ -51,7 +54,6 @@ import org.apache.james.jspf.tester.SPFYamlTestDescriptor;
 import org.apache.james.jspf.wiring.WiringService;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
-import org.xbill.DNS.Cache;
 import org.xbill.DNS.DClass;
 import org.xbill.DNS.Lookup;
 import org.xbill.DNS.Name;
@@ -61,12 +63,10 @@ import org.xbill.DNS.TextParseException;
 
 import junit.framework.AssertionFailedError;
 import junit.framework.TestCase;
-import uk.nominet.dnsjnio.ExtendedNonblockingResolver;
-import uk.nominet.dnsjnio.LookupAsynch;
-import uk.nominet.dnsjnio.NonblockingResolver;
 
 public abstract class AbstractYamlTest extends TestCase {
     private static final Logger LOGGER = LoggerFactory.getLogger(AbstractYamlTest.class);
+    private static final ExecutorService EXECUTOR_SERVICE = Executors.newCachedThreadPool();
 
     private static final int FAKE_SERVER_PORT = 31348;
     protected static final int TIMEOUT = 10;
@@ -78,7 +78,6 @@ public abstract class AbstractYamlTest extends TestCase {
     protected static final int SYNCHRONOUS_EXECUTOR = 1;
     protected static final int STAGED_EXECUTOR = 2;
     protected static final int STAGED_EXECUTOR_MULTITHREADED = 3;
-    protected static final int STAGED_EXECUTOR_DNSJNIO = 4;
     private int spfExecutorType = SYNCHRONOUS_EXECUTOR;
 
     SPFYamlTestDescriptor data;
@@ -161,40 +160,6 @@ public abstract class AbstractYamlTest extends TestCase {
             executor = new SynchronousSPFExecutor(dns);
         } else if (getSpfExecutorType() == STAGED_EXECUTOR || getSpfExecutorType() == STAGED_EXECUTOR_MULTITHREADED){
             executor = new StagedMultipleSPFExecutor(new DNSServiceAsynchSimulator(dns, getSpfExecutorType() == STAGED_EXECUTOR_MULTITHREADED));
-        } else if (getSpfExecutorType() == STAGED_EXECUTOR_DNSJNIO) {
-            
-            // reset cache between usages of the asynchronous lookuper
-            LookupAsynch.setDefaultCache(new Cache(), DClass.IN);
-            // reset cache between usages of the asynchronous lookuper
-            LookupAsynch.getDefaultCache(DClass.IN).clearCache();
-
-            try {
-                ExtendedNonblockingResolver resolver;
-                
-                if (getDnsServiceMockStyle() == FAKE_SERVER) {
-                    NonblockingResolver nonblockingResolver = new NonblockingResolver("127.0.0.1");
-                    resolver = ExtendedNonblockingResolver.newInstance(new NonblockingResolver[] {nonblockingResolver});
-                    nonblockingResolver.setPort(FAKE_SERVER_PORT);
-                    nonblockingResolver.setTCP(false);
-                } else if (getDnsServiceMockStyle() == REAL_SERVER) {
-                    resolver = ExtendedNonblockingResolver.newInstance();
-                    Resolver[] resolvers = resolver.getResolvers();
-                    for (int i = 0; i < resolvers.length; i++) {
-                        resolvers[i].setTCP(false);
-                    }
-                } else {
-                    throw new IllegalStateException("DnsServiceMockStyle "+getDnsServiceMockStyle()+" is not supported when STAGED_EXECUTOR_DNSJNIO executor style is used");
-                }
-                
-                DNSJnioAsynchService jnioAsynchService = new DNSJnioAsynchService(resolver);
-                jnioAsynchService.setTimeout(TIMEOUT);
-                executor = new StagedMultipleSPFExecutor(jnioAsynchService);
-
-            } catch (UnknownHostException e) {
-                // TODO Auto-generated catch block
-                e.printStackTrace();
-            }
-
         } else {
             throw new UnsupportedOperationException("Unknown executor type");
         }
@@ -465,6 +430,19 @@ public abstract class AbstractYamlTest extends TestCase {
             }
             return null;
         }
+
+        @Override
+        public CompletionStage<List<String>> getRecordsAsync(DNSRequest request) {
+            CompletableFuture<List<String>> completableFuture = new CompletableFuture<>();
+            EXECUTOR_SERVICE.execute(() -> {
+                try {
+                    completableFuture.complete(getRecords(request));
+                } catch (TimeoutException e) {
+                    completableFuture.completeExceptionally(e);
+                }
+            });
+            return completableFuture;
+        }
         
     }
 
diff --git a/resolver/src/test/java/org/apache/james/jspf/LoggingDNSService.java b/resolver/src/test/java/org/apache/james/jspf/LoggingDNSService.java
index f755c58..941175e 100644
--- a/resolver/src/test/java/org/apache/james/jspf/LoggingDNSService.java
+++ b/resolver/src/test/java/org/apache/james/jspf/LoggingDNSService.java
@@ -19,15 +19,15 @@
 
 package org.apache.james.jspf;
 
+import java.util.List;
+import java.util.concurrent.CompletionStage;
+
 import org.apache.james.jspf.core.DNSRequest;
 import org.apache.james.jspf.core.DNSService;
 import org.apache.james.jspf.core.exceptions.TimeoutException;
-import org.apache.james.jspf.executor.FutureSPFResult;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
-import java.util.List;
-
 public class LoggingDNSService implements DNSService {
     private static final Logger LOGGER = LoggerFactory.getLogger(LoggingDNSService.class);
 
@@ -93,21 +93,7 @@ public class LoggingDNSService implements DNSService {
     public List<String> getRecords(DNSRequest request) throws TimeoutException {
         try {
             List<String> result = dnsService.getRecords(request);
-            StringBuffer logBuff = new StringBuffer();
-            logBuff.append("getRecords(" + request.getHostname() + "," + request.getRecordType() + ") = ");
-            if (result != null) {
-                for (int i = 0; i < result.size(); i++) {
-                    logBuff.append(result.get(i));
-                    if (i == result.size() - 1) {
-                        logBuff.append("");
-                    } else {
-                        logBuff.append(",");
-                    }
-                }
-            } else {
-                logBuff.append("getRecords-ret: null");
-            }
-            LOGGER.debug(logBuff.toString());
+            debugLog(request, result);
             return result;
         } catch (TimeoutException e) {
             LOGGER.debug("getRecords({}) = TempErrorException[{}]",
@@ -116,4 +102,34 @@ public class LoggingDNSService implements DNSService {
         }
     }
 
+    private void debugLog(DNSRequest request, List<String> result) {
+        StringBuffer logBuff = new StringBuffer();
+        logBuff.append("getRecords(" + request.getHostname() + "," + request.getRecordType() + ") = ");
+        if (result != null) {
+            for (int i = 0; i < result.size(); i++) {
+                logBuff.append(result.get(i));
+                if (i == result.size() - 1) {
+                    logBuff.append("");
+                } else {
+                    logBuff.append(",");
+                }
+            }
+        } else {
+            logBuff.append("getRecords-ret: null");
+        }
+        LOGGER.debug(logBuff.toString());
+    }
+
+    @Override
+    public CompletionStage<List<String>> getRecordsAsync(DNSRequest request) {
+        return getRecordsAsync(request)
+            .thenApply(res -> {
+                debugLog(request, res);
+                return res;
+            })
+            .exceptionally(e -> {
+                LOGGER.debug("getRecords({}) = TempErrorException[{}]", request.getHostname(), e.getMessage());
+                return null;
+            });
+    }
 }
\ No newline at end of file
diff --git a/resolver/src/test/java/org/apache/james/jspf/MailZoneAsynchronousYamlTest.java b/resolver/src/test/java/org/apache/james/jspf/MailZoneAsynchronousYamlTest.java
index 21060a7..46d1889 100644
--- a/resolver/src/test/java/org/apache/james/jspf/MailZoneAsynchronousYamlTest.java
+++ b/resolver/src/test/java/org/apache/james/jspf/MailZoneAsynchronousYamlTest.java
@@ -70,7 +70,7 @@ public class MailZoneAsynchronousYamlTest extends MailZoneYamlTest {
     }
 
     protected int getSpfExecutorType() {
-        return STAGED_EXECUTOR_DNSJNIO;
+        return STAGED_EXECUTOR_MULTITHREADED;
     }
 
     static class MailZoneAsynchronousSuite extends TestSuite {


---------------------------------------------------------------------
To unsubscribe, e-mail: server-dev-unsubscribe@james.apache.org
For additional commands, e-mail: server-dev-help@james.apache.org