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-project.git


The following commit(s) were added to refs/heads/master by this push:
     new 1819fddf13 ENHACEMENTS: ManageSieve capabilities (#2916)
1819fddf13 is described below

commit 1819fddf13c88476a0766ccc91c81d66d14da682
Author: Benoit TELLIER <[email protected]>
AuthorDate: Tue Feb 17 18:38:57 2026 +0100

    ENHACEMENTS: ManageSieve capabilities (#2916)
    
    * [ENHANCEMENT] ManageSieve: do not advertize STARTTLS over unencrypted 
channels
    * [ENHANCEMENT] ManageSieve: Send capabilities after STARTTLS negociation 
and Auth
    * [ENHANCEMENT] Use Apache James and real version in Capability 
IMPLEMENTATION
---
 .../org/apache/james/managesieve/scripts/capability.test      |  6 +++---
 .../java/org/apache/james/managesieve/core/CoreProcessor.java |  6 ++++--
 .../mailets/managesieve/ManageSieveMailetTestCase.java        |  4 ++--
 .../netty/ManageSieveChannelUpstreamHandler.java              | 11 +++++++++++
 .../org/apache/james/managesieveserver/AuthenticateTest.java  |  4 +++-
 5 files changed, 23 insertions(+), 8 deletions(-)

diff --git 
a/mpt/impl/managesieve/core/src/main/resources/org/apache/james/managesieve/scripts/capability.test
 
b/mpt/impl/managesieve/core/src/main/resources/org/apache/james/managesieve/scripts/capability.test
index 5ae0e4344a..ae8c08f533 100644
--- 
a/mpt/impl/managesieve/core/src/main/resources/org/apache/james/managesieve/scripts/capability.test
+++ 
b/mpt/impl/managesieve/core/src/main/resources/org/apache/james/managesieve/scripts/capability.test
@@ -22,7 +22,7 @@ SUB {
 S: "SASL" "PLAIN"
 S: "SIEVE" ".*"
 S: "STARTTLS"
-S: "IMPLEMENTATION" "Apache ManageSieve v1.0"
+S: "IMPLEMENTATION" "Apache James ManageSieve"
 S: "VERSION" "1.0"
 }
 S: OK
@@ -32,7 +32,7 @@ SUB {
 S: "SASL" "PLAIN"
 S: "SIEVE" ".*"
 S: "STARTTLS"
-S: "IMPLEMENTATION" "Apache ManageSieve v1.0"
+S: "IMPLEMENTATION" "Apache James ManageSieve"
 S: "VERSION" "1.0"
 }
 S: OK
@@ -48,7 +48,7 @@ S: "OWNER" "user"
 S: "SASL" "PLAIN"
 S: "SIEVE" ".*"
 S: "STARTTLS"
-S: "IMPLEMENTATION" "Apache ManageSieve v1.0"
+S: "IMPLEMENTATION" "Apache James ManageSieve"
 S: "VERSION" "1.0"
 }
 S: OK
diff --git 
a/protocols/managesieve/src/main/java/org/apache/james/managesieve/core/CoreProcessor.java
 
b/protocols/managesieve/src/main/java/org/apache/james/managesieve/core/CoreProcessor.java
index 0e44c9c33d..0224dac400 100644
--- 
a/protocols/managesieve/src/main/java/org/apache/james/managesieve/core/CoreProcessor.java
+++ 
b/protocols/managesieve/src/main/java/org/apache/james/managesieve/core/CoreProcessor.java
@@ -64,7 +64,7 @@ public class CoreProcessor implements CoreCommands {
         String execute() throws ManageSieveException, 
SieveRepositoryException, IOException;
     }
 
-    public static final String IMPLEMENTATION_DESCRIPTION = "Apache 
ManageSieve v1.0";
+    public static final String IMPLEMENTATION_DESCRIPTION = "Apache James 
ManageSieve";
     public static final String MANAGE_SIEVE_VERSION = "1.0";
 
     private final SieveRepository sieveRepository;
@@ -96,6 +96,9 @@ public class CoreProcessor implements CoreCommands {
 
     private Map<Capabilities, String> computeCapabilityMap(Session session) {
         Map<Capabilities, String> capabilities = 
Maps.newHashMap(capabilitiesBase);
+        if (!session.isSslEnabled()) {
+            capabilities.put(Capabilities.STARTTLS, null);
+        }
         if (session.isAuthenticated()) {
             capabilities.put(Capabilities.OWNER, session.getUser().asString());
         }
@@ -345,7 +348,6 @@ public class CoreProcessor implements CoreCommands {
         Map<Capabilities, String> capabilitiesBase = new HashMap<>();
         capabilitiesBase.put(Capabilities.IMPLEMENTATION, 
IMPLEMENTATION_DESCRIPTION);
         capabilitiesBase.put(Capabilities.VERSION, MANAGE_SIEVE_VERSION);
-        capabilitiesBase.put(Capabilities.STARTTLS, null);
         if (!extensions.isEmpty()) {
             capabilitiesBase.put(Capabilities.SIEVE, extensions);
         }
diff --git 
a/server/mailet/mailets/src/test/java/org/apache/james/transport/mailets/managesieve/ManageSieveMailetTestCase.java
 
b/server/mailet/mailets/src/test/java/org/apache/james/transport/mailets/managesieve/ManageSieveMailetTestCase.java
index 6180a60af2..bb5a80d3ae 100644
--- 
a/server/mailet/mailets/src/test/java/org/apache/james/transport/mailets/managesieve/ManageSieveMailetTestCase.java
+++ 
b/server/mailet/mailets/src/test/java/org/apache/james/transport/mailets/managesieve/ManageSieveMailetTestCase.java
@@ -93,7 +93,7 @@ class ManageSieveMailetTestCase {
         initializeMailet();
         mailet.service(mail);
         ensureResponseContains("Re: CAPABILITY", "\"SIEVE\" \"a b c\"",
-            "\"IMPLEMENTATION\" \"Apache ManageSieve v1.0\"",
+            "\"IMPLEMENTATION\" \"Apache James ManageSieve\"",
             "\"VERSION\" \"1.0\"",
             "\"STARTTLS\"",
             "\"SASL\" \"PLAIN\"",
@@ -109,7 +109,7 @@ class ManageSieveMailetTestCase {
         mail.setAttribute(new Attribute(Mail.SMTP_AUTH_USER, 
AttributeValue.of("test")));
         mailet.service(mail);
         ensureResponseContains("Re: CAPABILITY", "\"SIEVE\" \"a b c\"",
-            "\"IMPLEMENTATION\" \"Apache ManageSieve v1.0\"",
+            "\"IMPLEMENTATION\" \"Apache James ManageSieve\"",
             "\"OWNER\" \"test@localhost\"",
             "\"VERSION\" \"1.0\"",
             "\"STARTTLS\"",
diff --git 
a/server/protocols/protocols-managesieve/src/main/java/org/apache/james/managesieveserver/netty/ManageSieveChannelUpstreamHandler.java
 
b/server/protocols/protocols-managesieve/src/main/java/org/apache/james/managesieveserver/netty/ManageSieveChannelUpstreamHandler.java
index 134d1b375c..a790d96de8 100644
--- 
a/server/protocols/protocols-managesieve/src/main/java/org/apache/james/managesieveserver/netty/ManageSieveChannelUpstreamHandler.java
+++ 
b/server/protocols/protocols-managesieve/src/main/java/org/apache/james/managesieveserver/netty/ManageSieveChannelUpstreamHandler.java
@@ -84,6 +84,7 @@ public class ManageSieveChannelUpstreamHandler extends 
ChannelInboundHandlerAdap
             }
 
             Session manageSieveSession = 
ctx.channel().attr(NettyConstants.SESSION_ATTRIBUTE_KEY).get();
+            Session.State statePriorExecution = manageSieveSession.getState();
             String responseString = 
manageSieveProcessor.handleRequest(manageSieveSession, request);
             attachment.resetCumulation();
             attachment.write(responseString);
@@ -92,6 +93,16 @@ public class ManageSieveChannelUpstreamHandler extends 
ChannelInboundHandlerAdap
                 manageSieveSession.setSslEnabled(true);
                 manageSieveSession.setState(Session.State.UNAUTHENTICATED);
                 attachment.stopDetectingCommandInjection();
+
+                // RFC-5804 section 1.7 returning capabilities is mandated 
after STARTTLS
+                String capabilities = 
manageSieveProcessor.handleRequest(manageSieveSession, "CAPABILITY");
+                attachment.write(capabilities);
+            }
+            if (manageSieveSession.getState() == Session.State.AUTHENTICATED &&
+                statePriorExecution != Session.State.AUTHENTICATED) {
+                // RFC-5804 section 1.7 returning capabilities is mandated 
after AUTH
+                String capabilities = 
manageSieveProcessor.handleRequest(manageSieveSession, "CAPABILITY");
+                attachment.write(capabilities);
             }
         } catch (NotEnoughDataException ex) {
             // Do nothing will keep the cumulation
diff --git 
a/server/protocols/protocols-managesieve/src/test/java/org/apache/james/managesieveserver/AuthenticateTest.java
 
b/server/protocols/protocols-managesieve/src/test/java/org/apache/james/managesieveserver/AuthenticateTest.java
index 63f9b86ec0..7c069ca104 100644
--- 
a/server/protocols/protocols-managesieve/src/test/java/org/apache/james/managesieveserver/AuthenticateTest.java
+++ 
b/server/protocols/protocols-managesieve/src/test/java/org/apache/james/managesieveserver/AuthenticateTest.java
@@ -29,7 +29,7 @@ import org.junit.jupiter.api.BeforeEach;
 import org.junit.jupiter.api.Disabled;
 import org.junit.jupiter.api.Test;
 
-public class AuthenticateTest {
+class AuthenticateTest {
     private ManageSieveClient client;
     private final ManageSieveServerTestSystem testSystem;
 
@@ -159,6 +159,7 @@ public class AuthenticateTest {
         this.client.sendCommand(command);
         ManageSieveClient.ServerResponse firstAuthenticationResponse = 
this.client.readResponse();
         
Assertions.assertThat(firstAuthenticationResponse.responseType()).isEqualTo(ManageSieveClient.ResponseType.OK);
+        this.client.readResponse(); // Read capabilities
 
         this.client.sendCommand(command);
         ManageSieveClient.ServerResponse secondAuthenticationResponse = 
this.client.readResponse();
@@ -234,5 +235,6 @@ public class AuthenticateTest {
         this.client.sendCommand("AUTHENTICATE \"PLAIN\" \"" + 
Base64.getEncoder().encodeToString(initialClientResponse.getBytes(StandardCharsets.UTF_8))
 + "\"");
         ManageSieveClient.ServerResponse authenticationResponse = 
this.client.readResponse();
         
Assertions.assertThat(authenticationResponse.responseType()).isEqualTo(ManageSieveClient.ResponseType.OK);
+        this.client.readResponse(); // Read capabilities
     }
 }


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to