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

ggregory pushed a commit to branch 1.x
in repository https://gitbox.apache.org/repos/asf/commons-email.git


The following commit(s) were added to refs/heads/1.x by this push:
     new a05eccb4 MultiPartEmail attach methods now throw an IOException if the 
given file is a directory.
a05eccb4 is described below

commit a05eccb4ff0deee76a6017d46fa0f5aea3356afd
Author: Gary Gregory <[email protected]>
AuthorDate: Wed Feb 11 19:49:56 2026 -0500

    MultiPartEmail attach methods now throw an IOException if the given file
    is a directory.
    
    Fix tests on Java 25 and up
---
 pom.xml                                            | 18 +++++-----
 src/changes/changes.xml                            |  2 ++
 .../java/org/apache/commons/mail/EmailUtils.java   | 39 ++++++++++++++++++++++
 .../org/apache/commons/mail/MultiPartEmail.java    | 11 ++----
 .../apache/commons/mail/MultiPartEmailTest.java    |  8 +++++
 5 files changed, 61 insertions(+), 17 deletions(-)

diff --git a/pom.xml b/pom.xml
index 07481b8e..4c284f58 100644
--- a/pom.xml
+++ b/pom.xml
@@ -463,7 +463,6 @@
             </plugin>
         </plugins>
     </reporting>
-
     <profiles>
       <profile>
         <id>java17</id>
@@ -471,6 +470,9 @@
         <activation>
           <jdk>[17,)</jdk>
         </activation>
+        <properties>
+          <mockito-core.version>5.21.0</mockito-core.version>
+        </properties>
         <build>
           <plugins>
             <plugin>
@@ -495,14 +497,13 @@
       </profile>
       <profile>
         <id>java8</id>
-          <activation>
-              <jdk>[1.8,11)</jdk>
-          </activation>
-          <properties>
-            <mockito-core.version>4.11.0</mockito-core.version>
-          </properties>
+        <activation>
+          <jdk>[1.8,11)</jdk>
+        </activation>
+        <properties>
+          <mockito-core.version>4.11.0</mockito-core.version>
+        </properties>
       </profile>
-
         <profile>
             <id>rc</id>
             <distributionManagement>
@@ -515,5 +516,4 @@
             </distributionManagement>
         </profile>
     </profiles>
-
 </project>
diff --git a/src/changes/changes.xml b/src/changes/changes.xml
index a5f5c562..7e839578 100644
--- a/src/changes/changes.xml
+++ b/src/changes/changes.xml
@@ -27,6 +27,8 @@
       <!-- FIX -->
       <action type="fix" dev="ggregory" due-to="Gary Gregory">Fix minor PMD 
violations (Unnecessary qualifier).</action>     
       <action type="fix" dev="ggregory" due-to="Gary Gregory">Fix Apache RAT 
plugin console warnings.</action>
+      <action type="fix" dev="ggregory" due-to="Gary Gregory">Fix tests on 
Java 25 and up.</action>
+      <action type="fix" dev="ggregory" due-to="Gary Gregory, Henri Cook, 
Sebb">MultiPartEmail attach methods now throw an IOException if the given file 
is a directory.</action>
       <!-- ADD -->
       <!-- UPDATE -->
       <action type="update" dev="ggregory" due-to="Gary Gregory">Bump 
commons-parent from 65 to 96.</action>
diff --git a/src/main/java/org/apache/commons/mail/EmailUtils.java 
b/src/main/java/org/apache/commons/mail/EmailUtils.java
index c4130b0e..2efdcdc4 100644
--- a/src/main/java/org/apache/commons/mail/EmailUtils.java
+++ b/src/main/java/org/apache/commons/mail/EmailUtils.java
@@ -20,10 +20,13 @@ package org.apache.commons.mail;
 import java.io.File;
 import java.io.IOException;
 import java.nio.charset.StandardCharsets;
+import java.nio.file.Files;
+import java.nio.file.Path;
 import java.util.BitSet;
 import java.util.Collection;
 import java.util.Locale;
 import java.util.Map;
+import java.util.Objects;
 import java.util.Random;
 
 import javax.mail.MessagingException;
@@ -93,6 +96,42 @@ final class EmailUtils {
         SAFE_URL.set('@');
     }
 
+    /**
+     * Checks that the given file exists and is not a directory.
+     *
+     * @param file the file to check.
+     * @return the given file if it exists and is not a directory.
+     * @throws IOException if the given file does not exist or is a directory.
+     */
+    static File check(final File file) throws IOException {
+        Objects.requireNonNull(file, "file");
+        if (!file.exists()) {
+            throw new IOException("\"" + file + "\" does not exist");
+        }
+        if (file.isDirectory()) {
+            throw new IOException("\"" + file + "\" is a directory");
+        }
+        return file;
+    }
+
+    /**
+     * Checks that the given file exists and is not a directory.
+     *
+     * @param file the file to check.
+     * @return the given file if it exists and is not a directory.
+     * @throws IOException if the given file does not exist or is a directory.
+     */
+    static Path check(final Path file) throws IOException {
+        Objects.requireNonNull(file, "file");
+        if (!Files.exists(file)) {
+            throw new IOException("\"" + file + "\" does not exist");
+        }
+        if (Files.isDirectory(file)) {
+            throw new IOException("\"" + file + "\" is a directory");
+        }
+        return file;
+    }
+
     /**
      * Encodes an input string according to RFC 2392. Unsafe characters are 
escaped.
      *
diff --git a/src/main/java/org/apache/commons/mail/MultiPartEmail.java 
b/src/main/java/org/apache/commons/mail/MultiPartEmail.java
index 4310554c..c31eccb2 100644
--- a/src/main/java/org/apache/commons/mail/MultiPartEmail.java
+++ b/src/main/java/org/apache/commons/mail/MultiPartEmail.java
@@ -21,7 +21,6 @@ import java.io.IOException;
 import java.io.InputStream;
 import java.io.UnsupportedEncodingException;
 import java.net.URL;
-import java.nio.file.Files;
 import java.nio.file.OpenOption;
 import java.nio.file.Path;
 import java.util.Objects;
@@ -200,7 +199,7 @@ public class MultiPartEmail extends Email {
             String fileName = null;
             try {
                 fileName = attachment.getPath();
-                final File file = new File(fileName);
+                final File file = EmailUtils.check(new File(fileName));
                 if (!file.exists()) {
                     throw new IOException("\"" + fileName + "\" does not 
exist");
                 }
@@ -225,9 +224,7 @@ public class MultiPartEmail extends Email {
     public MultiPartEmail attach(final File file) throws EmailException {
         final String fileName = file.getAbsolutePath();
         try {
-            if (!file.exists()) {
-                throw new IOException("\"" + fileName + "\" does not exist");
-            }
+            EmailUtils.check(file);
             return attach(new FileDataSource(file), file.getName(), null, 
EmailAttachment.ATTACHMENT);
         } catch (final IOException e) {
             throw new EmailException("Cannot attach file \"" + fileName + 
"\"", e);
@@ -246,9 +243,7 @@ public class MultiPartEmail extends Email {
     public MultiPartEmail attach(final Path file, final OpenOption... options) 
throws EmailException {
         final Path fileName = file.toAbsolutePath();
         try {
-            if (!Files.exists(file)) {
-                throw new IOException("\"" + fileName + "\" does not exist");
-            }
+            EmailUtils.check(file);
             return attach(new PathDataSource(file, 
FileTypeMap.getDefaultFileTypeMap(), options), 
Objects.toString(file.getFileName(), null), null,
                     EmailAttachment.ATTACHMENT);
         } catch (final IOException e) {
diff --git a/src/test/java/org/apache/commons/mail/MultiPartEmailTest.java 
b/src/test/java/org/apache/commons/mail/MultiPartEmailTest.java
index 1753327c..b08b937c 100644
--- a/src/test/java/org/apache/commons/mail/MultiPartEmailTest.java
+++ b/src/test/java/org/apache/commons/mail/MultiPartEmailTest.java
@@ -133,6 +133,10 @@ public class MultiPartEmailTest extends AbstractEmailTest {
         final EmailAttachment attachment4 = new EmailAttachment();
         attachment4.setPath("");
         assertThrows(EmailException.class, () -> email.attach(attachment4));
+        attachment4.setPath("ThisFileDoesNotExist.txt");
+        assertThrows(EmailException.class, () -> email.attach(attachment4));
+        attachment4.setPath("target"); // a directory, not a file
+        assertThrows(EmailException.class, () -> email.attach(attachment4));
     }
 
     @Test
@@ -176,6 +180,10 @@ public class MultiPartEmailTest extends AbstractEmailTest {
         final EmailAttachment attachment4 = new EmailAttachment();
         attachment4.setPath("");
         assertThrows(EmailException.class, () -> email.attach(attachment4));
+        attachment4.setPath("ThisFileDoesNotExist.txt");
+        assertThrows(EmailException.class, () -> email.attach(attachment4));
+        attachment4.setPath("target"); // a directory, not a file
+        assertThrows(EmailException.class, () -> email.attach(attachment4));
     }
 
     /** TODO implement test for GetContainer */

Reply via email to