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 530227acacd5018a752f7aad887793309768cfa2
Author: Emerson Pinter <e...@pinter.dev>
AuthorDate: Fri Jan 24 15:53:53 2025 -0300

    Add more tests
---
 .../org/apache/james/jspf/SPFExecutorBaseTest.java | 193 +++++++++++++++++++++
 .../dnszones/SPFExecutorIntegrationTest-1.zone     |  12 ++
 2 files changed, 205 insertions(+)

diff --git 
a/resolver/src/test/java/org/apache/james/jspf/SPFExecutorBaseTest.java 
b/resolver/src/test/java/org/apache/james/jspf/SPFExecutorBaseTest.java
index ae1c296..acdc376 100644
--- a/resolver/src/test/java/org/apache/james/jspf/SPFExecutorBaseTest.java
+++ b/resolver/src/test/java/org/apache/james/jspf/SPFExecutorBaseTest.java
@@ -1,22 +1,33 @@
 package org.apache.james.jspf;
 
 import org.apache.james.jspf.core.DNSService;
+import org.apache.james.jspf.core.exceptions.SPFErrorConstants;
 import org.apache.james.jspf.executor.SPFResult;
+import org.apache.james.jspf.helpers.FakeResolver;
 import org.apache.james.jspf.impl.DNSServiceXBillImpl;
 import org.apache.james.jspf.impl.SPF;
 import org.junit.Before;
 import org.junit.Test;
 import org.xbill.DNS.DClass;
 import org.xbill.DNS.Lookup;
+import org.xbill.DNS.Name;
 import org.xbill.DNS.Resolver;
+import org.xbill.DNS.SPFRecord;
 import org.xbill.DNS.SimpleResolver;
+import org.xbill.DNS.TXTRecord;
+import org.xbill.DNS.TextParseException;
 
+import java.io.IOException;
 import java.net.UnknownHostException;
+import java.nio.file.Paths;
 import java.util.concurrent.ThreadLocalRandom;
+import java.util.stream.Collectors;
+import java.util.stream.IntStream;
 
 import static org.junit.Assert.assertEquals;
 
 public abstract class SPFExecutorBaseTest {
+    protected final String zonesDir = "src/test/resources/dnszones";
 
     protected abstract SPF createSPF();
 
@@ -27,6 +38,10 @@ public abstract class SPFExecutorBaseTest {
         Lookup.getDefaultCache(DClass.IN).clearCache();
     }
 
+    public String getZonePath(String zoneFile) {
+        return Paths.get(zonesDir, zoneFile).toAbsolutePath().toString();
+    }
+
     @Test
     public void test() {
         SPF spf = createSPF();
@@ -68,4 +83,182 @@ public abstract class SPFExecutorBaseTest {
         assertEquals("Received-SPF: temperror (spfCheck: Error in retrieving 
data from DNS) client-ip=207.54.72.202; 
envelope-from=do_not_re...@reyifglerifwukfvbdjhrkbvebvekvfulervkerkeruerbeb.de; 
helo=reyifglerifwukfvbdjhrkbvebvekvfulervkerkeruerbeb.de;",
                 result.getHeader());
     }
+
+    @Test
+    public void shouldReturnPassIfJustOneTxtSpf1Record() throws IOException {
+        String testDomain = "spfexecutor.fake";
+        String hostname = "shouldReturnPassIfJustOneTxtSpf1Record." + 
testDomain;
+        String ip = "192.0.2.127";
+
+        //setup resolver
+        FakeResolver fakeResolver = new FakeResolver();
+        fakeResolver.fromZoneFile(testDomain, 
getZonePath("SPFExecutorIntegrationTest-1.zone"));
+        fakeResolver.addRecords(FakeResolver.genNRandomTXTRecords(hostname + 
".", 300));
+
+        SPF spf = createCustomSPF(new DNSServiceXBillImpl(fakeResolver));
+        SPFResult result = spf.checkSPF(ip, "a_user@" + hostname, hostname);
+        assertEquals(String.format(
+                        "Received-SPF: %3$s (spfCheck: domain of %2$s 
designates %1$s as permitted sender) client-ip=%1$s; envelope-from=a_user@%2$s; 
helo=%2$s;",
+                        ip, hostname, SPFErrorConstants.PASS_CONV),
+                result.getHeader());
+        assertEquals(SPFErrorConstants.PASS_CONV, result.getResult());
+    }
+
+    @Test
+    public void shouldReturnErrorIfMoreThanOneTxtSpf1Record() throws 
IOException {
+        String testDomain = "spfexecutor.fake";
+        String hostname = "shouldReturnErrorIfMoreThanOneTxtSpf1Record." + 
testDomain;
+        String ip = "192.0.2.127";
+
+        //setup resolver
+        FakeResolver fakeResolver = new FakeResolver();
+        fakeResolver.fromZoneFile(testDomain, 
getZonePath("SPFExecutorIntegrationTest-1.zone"));
+
+        SPF spf = createCustomSPF(new DNSServiceXBillImpl(fakeResolver));
+        SPFResult result = spf.checkSPF(ip, "a_user@" + hostname, hostname);
+        assertEquals(String.format(
+                        "Received-SPF: %3$s (spfCheck: Error in processing SPF 
Record) client-ip=%1$s; envelope-from=a_user@%2$s; helo=%2$s;",
+                        ip, hostname, SPFErrorConstants.PERM_ERROR_CONV),
+                result.getHeader());
+        assertEquals(SPFErrorConstants.PERM_ERROR_CONV, result.getResult());
+    }
+
+    @Test
+    public void shouldReturnErrorIfMoreThanOneSpfRecord() throws IOException {
+        String testDomain = "spfexecutor.fake";
+        String hostname = "shouldReturnErrorIfMoreThanOneSpfRecord." + 
testDomain;
+        String ip = "192.0.2.127";
+
+        //setup resolver
+        FakeResolver fakeResolver = new FakeResolver();
+        fakeResolver.setRecords(FakeResolver.genNRandomTXTRecords(hostname + 
".", 300));
+        fakeResolver.addRecord(new SPFRecord(
+                Name.fromString(hostname + "."), DClass.IN, 30L, 
String.format("v=spf1 ip4:%s ip4:1.1.1.1 -all", ip)));
+        fakeResolver.addRecord(new SPFRecord(
+                Name.fromString(hostname + "."), DClass.IN, 30L, 
String.format("v=spf1 ip4:%s -all", ip)));
+
+        SPF spf = createCustomSPF(new DNSServiceXBillImpl(fakeResolver));
+        SPFResult result = spf.checkSPF(ip, "a_user@" + hostname, hostname);
+        assertEquals(String.format(
+                        "Received-SPF: %3$s (spfCheck: Error in processing SPF 
Record) client-ip=%1$s; envelope-from=a_user@%2$s; helo=%2$s;",
+                        ip, hostname, SPFErrorConstants.PERM_ERROR_CONV),
+                result.getHeader());
+        assertEquals(SPFErrorConstants.PERM_ERROR_CONV, result.getResult());
+    }
+
+    /*
+     * Test the limit described in RFC7208 section "4.6.4.  DNS Lookup Limits"
+     */
+    @Test
+    public void shouldReturnErrorIfDepthMoreThan10() throws IOException {
+        String testDomain = "spfexecutor.fake";
+        String hostname = "shouldReturnErrorIfDepthMoreThan10." + testDomain;
+        String ip = "192.0.2.127";
+
+        //setup resolver
+        FakeResolver fakeResolver = new FakeResolver();
+        fakeResolver.addRecord(new TXTRecord(Name.fromString(hostname + "."),
+                DClass.IN, 30L, String.format("v=spf1 ip4:4.3.2.1 
include:depth0.%s -all", hostname)));
+
+        fakeResolver.addRecords(IntStream.range(0, 10).mapToObj(
+                i -> {
+                    try {
+                        String txt = String.format("v=spf1 ip4:4.3.2.2 
include:depth%s.%s -all", i + 1, hostname);
+                        return new TXTRecord(
+                                Name.fromString(String.format("depth%s.%s.", 
i, hostname), Name.fromString(testDomain)),
+                                DClass.IN, 30L, txt);
+                    } catch (TextParseException e) {
+                        throw new RuntimeException(e);
+                    }
+                }).collect(Collectors.toList()));
+
+
+        SPF spf = createCustomSPF(new DNSServiceXBillImpl(fakeResolver));
+        SPFResult result = spf.checkSPF(ip, "a_user@" + hostname, hostname);
+        assertEquals(String.format(
+                        "Received-SPF: %3$s (spfCheck: Error in processing SPF 
Record) client-ip=%1$s; envelope-from=a_user@%2$s; helo=%2$s;",
+                        ip, hostname, SPFErrorConstants.PERM_ERROR_CONV),
+                result.getHeader());
+        assertEquals(SPFErrorConstants.PERM_ERROR_CONV, result.getResult());
+    }
+
+    /*
+     * Test the limit described in RFC7208 section "4.6.4.  DNS Lookup Limits"
+     */
+    @Test
+    public void shouldReturnPassIfDepth10orLess() throws IOException {
+        String testDomain = "spfexecutor.fake";
+        String hostname = "shouldReturnPassIfDepth10OrLess." + testDomain;
+        String ip = "192.0.2.127";
+
+        //setup resolver
+        FakeResolver fakeResolver = new FakeResolver();
+        fakeResolver.addRecord(new TXTRecord(Name.fromString(hostname + "."),
+                DClass.IN, 30L, String.format("v=spf1 ip4:4.3.2.1 
include:depth0.%s -all", hostname)));
+
+        int count = 10;
+        fakeResolver.addRecords(IntStream.range(0, count).mapToObj(
+                i -> {
+                    try {
+                        String txt;
+                        if (i == count - 1) {
+                            txt = String.format("v=spf1 ip4:4.3.2.2 ip4:%s 
-all", ip);
+                        } else {
+                            txt = String.format("v=spf1 ip4:4.3.2.2 
include:depth%s.%s -all", i + 1, hostname);
+                        }
+                        return new TXTRecord(
+                                Name.fromString(String.format("depth%s.%s.", 
i, hostname), Name.fromString(testDomain)),
+                                DClass.IN, 30L, txt);
+                    } catch (TextParseException e) {
+                        throw new RuntimeException(e);
+                    }
+                }).collect(Collectors.toList()));
+
+
+        SPF spf = createCustomSPF(new DNSServiceXBillImpl(fakeResolver));
+        SPFResult result = spf.checkSPF(ip, "a_user@" + hostname, hostname);
+        assertEquals(String.format(
+                        "Received-SPF: %3$s (spfCheck: domain of %2$s 
designates %1$s as permitted sender) client-ip=%1$s; envelope-from=a_user@%2$s; 
helo=%2$s;",
+                        ip, hostname, SPFErrorConstants.PASS_CONV),
+                result.getHeader());
+        assertEquals(SPFErrorConstants.PASS_CONV, result.getResult());
+    }
+
+    @Test
+    public void shouldReturnPermErrorIfIncludeDomainNotFound() throws 
IOException {
+        String testDomain = "spfexecutor.fake";
+        String hostname = "shouldReturnPermErrorIfIncludeDomainNotFound." + 
testDomain;
+        String ip = "192.0.2.127";
+
+        //setup resolver
+        FakeResolver fakeResolver = new FakeResolver();
+        fakeResolver.fromZoneFile(testDomain, 
getZonePath("SPFExecutorIntegrationTest-1.zone"));
+
+        SPF spf = createCustomSPF(new DNSServiceXBillImpl(fakeResolver));
+        SPFResult result = spf.checkSPF(ip, "a_user@" + hostname, hostname);
+        assertEquals(String.format(
+                        "Received-SPF: %3$s (spfCheck: Error in processing SPF 
Record) client-ip=%1$s; envelope-from=a_user@%2$s; helo=%2$s;",
+                        ip, hostname, SPFErrorConstants.PERM_ERROR_CONV),
+                result.getHeader());
+        assertEquals(SPFErrorConstants.PERM_ERROR_CONV, result.getResult());
+    }
+
+    @Test
+    public void shouldHandleMultipleStrings() throws IOException {
+        String testDomain = "spfexecutor.fake";
+        String hostname = "shouldReturnPassIfMultipleStrings." + testDomain;
+        String ip = "192.0.2.127";
+
+        //setup resolver
+        FakeResolver fakeResolver = new FakeResolver();
+        fakeResolver.fromZoneFile(testDomain, 
getZonePath("SPFExecutorIntegrationTest-1.zone"));
+
+        SPF spf = createCustomSPF(new DNSServiceXBillImpl(fakeResolver));
+        SPFResult result = spf.checkSPF(ip, "a_user@" + hostname, hostname);
+        assertEquals(String.format(
+                        "Received-SPF: %3$s (spfCheck: domain of %2$s 
designates %1$s as permitted sender) client-ip=%1$s; envelope-from=a_user@%2$s; 
helo=%2$s;",
+                        ip, hostname, SPFErrorConstants.PASS_CONV),
+                result.getHeader());
+        assertEquals(SPFErrorConstants.PASS_CONV, result.getResult());
+    }
 }
diff --git 
a/resolver/src/test/resources/dnszones/SPFExecutorIntegrationTest-1.zone 
b/resolver/src/test/resources/dnszones/SPFExecutorIntegrationTest-1.zone
new file mode 100644
index 0000000..8898bee
--- /dev/null
+++ b/resolver/src/test/resources/dnszones/SPFExecutorIntegrationTest-1.zone
@@ -0,0 +1,12 @@
+$TTL 30
+@   30    IN    SOA    ns1.fakeresolver.apache. 
hostmaster.fakeresolver.apache. 1 30 30 30 30
+@   30    IN    NS     ns1
+
+shouldReturnErrorIfMoreThanOneTxtSpf1Record         IN    TXT   "v=spf1 
ip4:192.0.2.162 -all"
+shouldReturnErrorIfMoreThanOneTxtSpf1Record         IN    TXT   "v=spf1 
ip4:192.0.2.127 ip4:1.1.1.1 -all"
+
+shouldReturnPassIfJustOneTxtSpf1Record              IN    TXT   "v=spf1 
include:_spf.google.com include:spf.protection.outlook.com ip4:2.3.4.5 
ip4:192.0.2.127 -all"
+
+shouldReturnPermErrorIfIncludeDomainNotFound        IN    TXT   "v=spf1 
ip4:4.3.2.1 include:unknownDomain.fake -all"
+
+shouldReturnPassIfMultipleStrings                 IN    TXT   "v=spf1 mx a 
ip4:192.0.2.127 ip4:4.3.2.1 ip4:4.3.2.1 ip4:4.3.2.1 ip4:4.3.2.1 ip4:4.3.2.1 
ip4:4.3.2.1 ip4:4.3.2.1 ip4:4.3.2.1 ip4:4.3.2.1 ip4:4.3.2.1 ip4:4.3.2.1 
ip4:4.3.2.1 ip4:4.3.2.1 ip4:4.3.2.1 ip4:4.3.2.1 ip4:4.3.2.1 ip4:4.3.2.1 
ip4:4.3.2.1" " ip4:4.3.2.1 -all"


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

Reply via email to