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 2020/06/21 09:16:32 UTC

[james-project] 09/12: JAMES-3167 Reactify MailboxMapper

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

commit 5ccf47c38a651653a79283f9f83b491d72b852e9
Author: Benoit Tellier <bt...@linagora.com>
AuthorDate: Wed Jun 3 14:08:55 2020 +0700

    JAMES-3167 Reactify MailboxMapper
---
 .../org/apache/james/mailbox/MailboxManager.java   |   4 +-
 .../org/apache/james/mailbox/RightManager.java     |   4 +-
 .../apache/james/mailbox/MailboxManagerTest.java   |  40 ++-
 .../james/mailbox/backup/DefaultMailboxBackup.java |   2 +-
 .../mailbox/cassandra/mail/CassandraACLMapper.java |  14 +-
 .../cassandra/mail/CassandraMailboxMapper.java     |  62 ++---
 .../cassandra/mail/CassandraMessageIdMapper.java   |  27 +-
 .../mail/task/MailboxMergingTaskRunner.java        |  27 +-
 .../CassandraMailboxManagerConsistencyTest.java    |  50 ++--
 .../cassandra/mail/CassandraACLMapperTest.java     |  27 +-
 .../CassandraMailboxMapperConcurrencyTest.java     |   6 +-
 .../cassandra/mail/CassandraMailboxMapperTest.java | 180 ++++++------
 .../mail/migration/MailboxPathV2MigrationTest.java |  11 +-
 ...asticSearchListeningMessageSearchIndexTest.java |   2 +-
 .../james/mailbox/jpa/mail/JPAMailboxMapper.java   | 159 +++++------
 .../jpa/mail/TransactionalMailboxMapper.java       |  27 +-
 .../mailbox/maildir/mail/MaildirMailboxMapper.java | 306 +++++++++++----------
 .../DomainUserMaildirMailboxManagerTest.java       |   5 +
 .../InMemoryMailboxSessionMapperFactory.java       |   2 +-
 .../inmemory/mail/InMemoryMailboxMapper.java       | 100 +++----
 .../inmemory/mail/InMemoryMessageIdMapper.java     |   9 +-
 .../james/vault/DeletedMessageVaultHook.java       |  27 +-
 .../mailbox/spamassassin/SpamAssassinListener.java |   4 +-
 .../spamassassin/SpamAssassinListenerTest.java     |  12 +-
 .../store/StoreMailboxAnnotationManager.java       |   5 +-
 .../james/mailbox/store/StoreMailboxManager.java   | 251 +++++++----------
 .../james/mailbox/store/StoreMessageIdManager.java |  68 ++---
 .../james/mailbox/store/StoreRightManager.java     |  75 +++--
 .../mailbox/store/SystemMailboxesProviderImpl.java |   2 +-
 .../james/mailbox/store/mail/MailboxMapper.java    |  52 +---
 .../store/quota/DefaultUserQuotaRootResolver.java  |   2 +-
 .../store/search/ListeningMessageSearchIndex.java  |   6 +-
 .../store/search/SimpleMessageSearchIndex.java     |   3 +-
 .../james/mailbox/store/transaction/Mapper.java    |   2 +-
 .../store/transaction/TransactionalMapper.java     |  20 +-
 .../mailbox/store/MessageIdManagerTestSystem.java  |   6 +-
 .../store/StoreMailboxManagerAnnotationTest.java   |  28 +-
 .../mailbox/store/StoreMailboxManagerTest.java     |  12 +-
 .../james/mailbox/store/StoreRightManagerTest.java |  12 +-
 .../store/SystemMailboxesProviderImplTest.java     |   4 +
 .../store/mail/model/MailboxMapperACLTest.java     | 137 ++++-----
 .../store/mail/model/MailboxMapperTest.java        |  79 +++---
 .../store/mail/model/MessageIdMapperTest.java      |   2 +-
 .../store/mail/model/MessageMapperTest.java        |   2 +-
 .../mailbox/store/mail/model/MessageMoveTest.java  |   4 +-
 .../quota/DefaultUserQuotaRootResolverTest.java    |   4 +-
 .../mailbox/tools/indexer/ReIndexerImpl.java       |   3 +-
 .../mailbox/tools/indexer/ReIndexerPerformer.java  |  10 +-
 .../apache/james/imap/processor/ListProcessor.java |  12 +-
 .../org/apache/james/modules/MailboxProbeImpl.java |  12 +-
 .../adapter/mailbox/MailboxManagerManagement.java  |   4 +-
 .../adapter/mailbox/MailboxManagementTest.java     |  46 ++--
 .../james/transport/mailets/RandomStoring.java     |   2 +-
 .../jmap/draft/methods/GetMailboxesMethod.java     |   2 +-
 .../jmap/draft/methods/GetMailboxesMethodTest.java |   2 +-
 .../james/jmap/draft/model/MailboxFactoryTest.java |   2 +-
 .../event/PropagateLookupRightListenerTest.java    |  28 +-
 .../james/jmap/method/MailboxGetMethod.scala       |   2 +-
 .../jmap/MessageFastViewProjectionCorrector.java   |  23 +-
 .../webadmin/service/UserMailboxesService.java     |   2 +-
 .../webadmin/routes/UserMailboxesRoutesTest.java   |  29 +-
 61 files changed, 992 insertions(+), 1070 deletions(-)

diff --git a/mailbox/api/src/main/java/org/apache/james/mailbox/MailboxManager.java b/mailbox/api/src/main/java/org/apache/james/mailbox/MailboxManager.java
index d5ac9d7..ee859af 100644
--- a/mailbox/api/src/main/java/org/apache/james/mailbox/MailboxManager.java
+++ b/mailbox/api/src/main/java/org/apache/james/mailbox/MailboxManager.java
@@ -243,9 +243,7 @@ public interface MailboxManager extends RequestAware, RightManager, MailboxAnnot
      * @param session
      *            the context for this call, not null
      */
-    List<MailboxMetaData> search(MailboxQuery expression, MailboxSession session) throws MailboxException;
-
-    Flux<MailboxMetaData> searchReactive(MailboxQuery expression, MailboxSession session);
+    Flux<MailboxMetaData> search(MailboxQuery expression, MailboxSession session);
 
     /**
      * Searches for messages matching the given query.
diff --git a/mailbox/api/src/main/java/org/apache/james/mailbox/RightManager.java b/mailbox/api/src/main/java/org/apache/james/mailbox/RightManager.java
index 3fd6d8a..e66934a 100644
--- a/mailbox/api/src/main/java/org/apache/james/mailbox/RightManager.java
+++ b/mailbox/api/src/main/java/org/apache/james/mailbox/RightManager.java
@@ -109,9 +109,7 @@ public interface RightManager {
      *         {@code session.getUser()} is null.
      * @throws MailboxException in case of unknown mailbox or unsupported right
      */
-    Rfc4314Rights myRights(MailboxId mailboxId, MailboxSession session) throws MailboxException;
-
-    Publisher<Rfc4314Rights> myRightsReactive(MailboxId mailboxId, MailboxSession session);
+    Publisher<Rfc4314Rights> myRights(MailboxId mailboxId, MailboxSession session);
 
     /**
      * Update the Mailbox ACL of the designated mailbox. We can either ADD REPLACE or REMOVE entries.
diff --git a/mailbox/api/src/test/java/org/apache/james/mailbox/MailboxManagerTest.java b/mailbox/api/src/test/java/org/apache/james/mailbox/MailboxManagerTest.java
index 2eaa904..603483b 100644
--- a/mailbox/api/src/test/java/org/apache/james/mailbox/MailboxManagerTest.java
+++ b/mailbox/api/src/test/java/org/apache/james/mailbox/MailboxManagerTest.java
@@ -1003,7 +1003,9 @@ public abstract class MailboxManagerTest<T extends MailboxManager> {
                 MailboxQuery.privateMailboxesBuilder(session)
                     .matchesAllMailboxNames()
                     .build(),
-                session);
+                session)
+                .collectList()
+                .block();
             assertThat(metaDatas).hasSize(1);
             assertThat(metaDatas.get(0).getPath()).isEqualTo(MailboxPath.inbox(session));
         }
@@ -1025,7 +1027,9 @@ public abstract class MailboxManagerTest<T extends MailboxManager> {
                 MailboxQuery.privateMailboxesBuilder(session)
                     .matchesAllMailboxNames()
                     .build(),
-                session);
+                session)
+                .collectList()
+                .block();
             assertThat(metaDatas)
                 .hasSize(1)
                 .first()
@@ -1046,7 +1050,9 @@ public abstract class MailboxManagerTest<T extends MailboxManager> {
                 MailboxQuery.privateMailboxesBuilder(session)
                     .matchesAllMailboxNames()
                     .build(),
-                session);
+                session)
+                .collectList()
+                .block();
             assertThat(metaDatas).hasSize(1);
             assertThat(metaDatas.get(0).getPath()).isEqualTo(MailboxPath.inbox(session));
         }
@@ -1068,7 +1074,7 @@ public abstract class MailboxManagerTest<T extends MailboxManager> {
                 .matchesAllMailboxNames()
                 .build();
 
-            assertThat(mailboxManager.search(mailboxQuery, session1))
+            assertThat(mailboxManager.search(mailboxQuery, session1).toStream())
                 .extracting(MailboxMetaData::getPath)
                 .hasSize(1)
                 .containsOnly(inbox1);
@@ -1092,7 +1098,7 @@ public abstract class MailboxManagerTest<T extends MailboxManager> {
                 .matchesAllMailboxNames()
                 .build();
 
-            assertThat(mailboxManager.search(mailboxQuery, session2))
+            assertThat(mailboxManager.search(mailboxQuery, session2).toStream())
                 .extracting(MailboxMetaData::getPath)
                 .containsOnly(inbox1);
         }
@@ -1117,7 +1123,7 @@ public abstract class MailboxManagerTest<T extends MailboxManager> {
                 .matchesAllMailboxNames()
                 .build();
 
-            assertThat(mailboxManager.search(mailboxQuery, session2))
+            assertThat(mailboxManager.search(mailboxQuery, session2).toStream())
                 .extracting(MailboxMetaData::getPath)
                 .containsOnly(inbox1, inbox2);
         }
@@ -1143,7 +1149,7 @@ public abstract class MailboxManagerTest<T extends MailboxManager> {
                 .matchesAllMailboxNames()
                 .build();
 
-            assertThat(mailboxManager.search(mailboxQuery, session2))
+            assertThat(mailboxManager.search(mailboxQuery, session2).toStream())
                 .extracting(MailboxMetaData::getPath)
                 .containsOnly(inbox1);
         }
@@ -1176,7 +1182,7 @@ public abstract class MailboxManagerTest<T extends MailboxManager> {
                 .matchesAllMailboxNames()
                 .build();
 
-            assertThat(mailboxManager.search(mailboxQuery, session2))
+            assertThat(mailboxManager.search(mailboxQuery, session2).toStream())
                 .extracting(MailboxMetaData::getPath)
                 .containsOnly(mailboxPath1);
         }
@@ -1413,7 +1419,7 @@ public abstract class MailboxManagerTest<T extends MailboxManager> {
                 .matchesAllMailboxNames()
                 .build();
 
-            assertThat(mailboxManager.search(mailboxQuery, session2))
+            assertThat(mailboxManager.search(mailboxQuery, session2).toStream())
                 .isEmpty();
         }
     }
@@ -1562,6 +1568,22 @@ public abstract class MailboxManagerTest<T extends MailboxManager> {
         }
 
         @Test
+        protected void renameMailboxShouldChangeTheMailboxPathOfTheChildMailbox() throws Exception {
+            MailboxSession session = mailboxManager.createSystemSession(USER_1);
+
+            MailboxPath mailboxPath1 = MailboxPath.forUser(USER_1, "mbx1");
+            MailboxPath mailboxPath2 = MailboxPath.forUser(USER_1, "mbx2");
+            mailboxManager.createMailbox(mailboxPath1, session);
+            MailboxPath mailboxPath1Child = MailboxPath.forUser(USER_1, "mbx1.child");
+            Optional<MailboxId> mailboxChildId = mailboxManager.createMailbox(mailboxPath1Child, session);
+
+            mailboxManager.renameMailbox(mailboxPath1, mailboxPath2, session);
+
+            assertThat(mailboxManager.getMailbox(mailboxChildId.get(), session).getMailboxPath())
+                    .isEqualTo(MailboxPath.forUser(USER_1, "mbx2.child"));
+        }
+
+        @Test
         protected void renameMailboxByIdShouldChangeTheMailboxPathOfAMailbox() throws Exception {
             MailboxSession session = mailboxManager.createSystemSession(USER_1);
 
diff --git a/mailbox/backup/src/main/java/org/apache/james/mailbox/backup/DefaultMailboxBackup.java b/mailbox/backup/src/main/java/org/apache/james/mailbox/backup/DefaultMailboxBackup.java
index 62dc067..9f19a89 100644
--- a/mailbox/backup/src/main/java/org/apache/james/mailbox/backup/DefaultMailboxBackup.java
+++ b/mailbox/backup/src/main/java/org/apache/james/mailbox/backup/DefaultMailboxBackup.java
@@ -146,7 +146,7 @@ public class DefaultMailboxBackup implements MailboxBackup {
             .user(session.getUser())
             .build();
         Stream<MailboxPath> paths = mailboxManager.search(queryUser, session)
-            .stream()
+            .toStream()
             .map(MailboxMetaData::getPath);
         List<MailAccountContent> mailboxes = paths
             .flatMap(path -> getMailboxWithAnnotationsFromPath(session, path))
diff --git a/mailbox/cassandra/src/main/java/org/apache/james/mailbox/cassandra/mail/CassandraACLMapper.java b/mailbox/cassandra/src/main/java/org/apache/james/mailbox/cassandra/mail/CassandraACLMapper.java
index b04814c..0ff9efa 100644
--- a/mailbox/cassandra/src/main/java/org/apache/james/mailbox/cassandra/mail/CassandraACLMapper.java
+++ b/mailbox/cassandra/src/main/java/org/apache/james/mailbox/cassandra/mail/CassandraACLMapper.java
@@ -120,21 +120,19 @@ public class CassandraACLMapper {
         return deserializeACL(cassandraId, serializedACL);
     }
 
-    public ACLDiff updateACL(CassandraId cassandraId, MailboxACL.ACLCommand command) throws MailboxException {
-        MailboxACL replacement = MailboxACL.EMPTY.apply(command);
-        return updateAcl(cassandraId, aclWithVersion -> aclWithVersion.apply(command), replacement)
+    public Mono<ACLDiff> updateACL(CassandraId cassandraId, MailboxACL.ACLCommand command) {
+        return Mono.fromCallable(() -> MailboxACL.EMPTY.apply(command))
+        .flatMap(replacement -> updateAcl(cassandraId, aclWithVersion -> aclWithVersion.apply(command), replacement))
             .flatMap(aclDiff -> userMailboxRightsDAO.update(cassandraId, aclDiff)
             .thenReturn(aclDiff))
-            .blockOptional()
-            .orElseThrow(() -> new MailboxException("Unable to update ACL"));
+            .switchIfEmpty(Mono.error(new MailboxException("Unable to update ACL")));
     }
 
-    public ACLDiff setACL(CassandraId cassandraId, MailboxACL mailboxACL) throws MailboxException {
+    public Mono<ACLDiff> setACL(CassandraId cassandraId, MailboxACL mailboxACL) {
         return updateAcl(cassandraId, acl -> new ACLWithVersion(acl.version, mailboxACL), mailboxACL)
             .flatMap(aclDiff -> userMailboxRightsDAO.update(cassandraId, aclDiff)
             .thenReturn(aclDiff))
-            .blockOptional()
-            .orElseThrow(() -> new MailboxException("Unable to update ACL"));
+            .switchIfEmpty(Mono.defer(() -> Mono.error(new MailboxException("Unable to update ACL"))));
     }
 
     private Mono<ACLDiff> updateAcl(CassandraId cassandraId, Function<ACLWithVersion, ACLWithVersion> aclTransformation, MailboxACL replacement) {
diff --git a/mailbox/cassandra/src/main/java/org/apache/james/mailbox/cassandra/mail/CassandraMailboxMapper.java b/mailbox/cassandra/src/main/java/org/apache/james/mailbox/cassandra/mail/CassandraMailboxMapper.java
index e84978f..0e13275 100644
--- a/mailbox/cassandra/src/main/java/org/apache/james/mailbox/cassandra/mail/CassandraMailboxMapper.java
+++ b/mailbox/cassandra/src/main/java/org/apache/james/mailbox/cassandra/mail/CassandraMailboxMapper.java
@@ -40,6 +40,7 @@ import org.apache.james.mailbox.model.MailboxPath;
 import org.apache.james.mailbox.model.UidValidity;
 import org.apache.james.mailbox.model.search.MailboxQuery;
 import org.apache.james.mailbox.store.mail.MailboxMapper;
+import org.apache.james.util.FunctionalUtils;
 import org.apache.james.util.ReactorUtils;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
@@ -85,12 +86,11 @@ public class CassandraMailboxMapper implements MailboxMapper {
     }
 
     @Override
-    public void delete(Mailbox mailbox) {
+    public Mono<Void> delete(Mailbox mailbox) {
         CassandraId mailboxId = (CassandraId) mailbox.getMailboxId();
-        deletePath(mailbox)
+        return deletePath(mailbox)
             .thenEmpty(mailboxDAO.delete(mailboxId)
-                .retryWhen(Retry.backoff(MAX_RETRY, MIN_RETRY_BACKOFF).maxBackoff(MAX_RETRY_BACKOFF)))
-            .block();
+                .retryWhen(Retry.backoff(MAX_RETRY, MIN_RETRY_BACKOFF).maxBackoff(MAX_RETRY_BACKOFF)));
     }
 
     private Flux<Void> deletePath(Mailbox mailbox) {
@@ -144,17 +144,10 @@ public class CassandraMailboxMapper implements MailboxMapper {
     }
 
     @Override
-    public Mailbox findMailboxById(MailboxId id) throws MailboxException {
+    public Mono<Mailbox> findMailboxById(MailboxId id) {
         CassandraId mailboxId = (CassandraId) id;
         return retrieveMailbox(mailboxId)
-            .blockOptional()
-            .orElseThrow(() -> new MailboxNotFoundException(id));
-    }
-
-    @Override
-    public Mono<Mailbox> findMailboxByIdReactive(MailboxId id) {
-        CassandraId mailboxId = (CassandraId) id;
-        return retrieveMailbox(mailboxId);
+            .switchIfEmpty(Mono.error(() -> new MailboxNotFoundException(id)));
     }
 
     private Mono<Mailbox> retrieveMailbox(CassandraId mailboxId) {
@@ -203,40 +196,26 @@ public class CassandraMailboxMapper implements MailboxMapper {
     }
 
     @Override
-    public Mailbox create(MailboxPath mailboxPath, UidValidity uidValidity) throws MailboxException {
+    public Mono<Mailbox> create(MailboxPath mailboxPath, UidValidity uidValidity) {
         CassandraId cassandraId = CassandraId.timeBased();
         Mailbox mailbox = new Mailbox(mailboxPath, uidValidity, cassandraId);
 
-        if (!tryCreate(mailbox, cassandraId).block()) {
-            throw new MailboxExistsException(mailbox.generateAssociatedPath().asString());
-        }
-        return mailbox;
-    }
-
-    private Mono<Boolean> tryCreate(Mailbox cassandraMailbox, CassandraId cassandraId) {
-        return mailboxPathV2DAO.save(cassandraMailbox.generateAssociatedPath(), cassandraId)
+        return mailboxPathV2DAO.save(mailbox.generateAssociatedPath(), cassandraId)
             .filter(isCreated -> isCreated)
-            .flatMap(mailboxHasCreated -> persistMailboxEntity(cassandraMailbox)
-                .thenReturn(true))
-            .defaultIfEmpty(false);
+            .flatMap(mailboxHasCreated -> persistMailboxEntity(mailbox)
+                .thenReturn(mailbox))
+            .switchIfEmpty(Mono.error(() -> new MailboxExistsException(mailbox.generateAssociatedPath().asString())));
     }
 
     @Override
-    public MailboxId rename(Mailbox mailbox) throws MailboxException {
+    public Mono<MailboxId> rename(Mailbox mailbox) {
         Preconditions.checkNotNull(mailbox.getMailboxId(), "A mailbox we want to rename should have a defined mailboxId");
 
         CassandraId cassandraId = (CassandraId) mailbox.getMailboxId();
-        try {
-            if (!tryRename(mailbox, cassandraId).block()) {
-                throw new MailboxExistsException(mailbox.generateAssociatedPath().asString());
-            }
-        } catch (RuntimeException e) {
-            if (e.getCause() instanceof MailboxNotFoundException) {
-                throw (MailboxNotFoundException)e.getCause();
-            }
-            throw e;
-        }
-        return cassandraId;
+        return tryRename(mailbox, cassandraId)
+            .filter(FunctionalUtils.identityPredicate())
+            .switchIfEmpty(Mono.error(() -> new MailboxExistsException(mailbox.generateAssociatedPath().asString())))
+            .thenReturn(cassandraId);
     }
 
     private Mono<Boolean> tryRename(Mailbox cassandraMailbox, CassandraId cassandraId) {
@@ -261,13 +240,12 @@ public class CassandraMailboxMapper implements MailboxMapper {
     }
 
     @Override
-    public boolean hasChildren(Mailbox mailbox, char delimiter) {
+    public Mono<Boolean> hasChildren(Mailbox mailbox, char delimiter) {
         return Flux.merge(
                 mailboxPathDAO.listUserMailboxes(mailbox.getNamespace(), mailbox.getUser()),
                 mailboxPathV2DAO.listUserMailboxes(mailbox.getNamespace(), mailbox.getUser()))
             .filter(idAndPath -> isPathChildOfMailbox(idAndPath, mailbox, delimiter))
-            .hasElements()
-            .block();
+            .hasElements();
     }
 
     private boolean isPathChildOfMailbox(CassandraIdAndPath idAndPath, Mailbox mailbox, char delimiter) {
@@ -286,13 +264,13 @@ public class CassandraMailboxMapper implements MailboxMapper {
     }
 
     @Override
-    public ACLDiff updateACL(Mailbox mailbox, MailboxACL.ACLCommand mailboxACLCommand) throws MailboxException {
+    public Mono<ACLDiff> updateACL(Mailbox mailbox, MailboxACL.ACLCommand mailboxACLCommand) {
         CassandraId cassandraId = (CassandraId) mailbox.getMailboxId();
         return cassandraACLMapper.updateACL(cassandraId, mailboxACLCommand);
     }
 
     @Override
-    public ACLDiff setACL(Mailbox mailbox, MailboxACL mailboxACL) throws MailboxException {
+    public Mono<ACLDiff> setACL(Mailbox mailbox, MailboxACL mailboxACL) {
         CassandraId cassandraId = (CassandraId) mailbox.getMailboxId();
         return cassandraACLMapper.setACL(cassandraId, mailboxACL);
     }
diff --git a/mailbox/cassandra/src/main/java/org/apache/james/mailbox/cassandra/mail/CassandraMessageIdMapper.java b/mailbox/cassandra/src/main/java/org/apache/james/mailbox/cassandra/mail/CassandraMessageIdMapper.java
index f98090a..2777ec4 100644
--- a/mailbox/cassandra/src/main/java/org/apache/james/mailbox/cassandra/mail/CassandraMessageIdMapper.java
+++ b/mailbox/cassandra/src/main/java/org/apache/james/mailbox/cassandra/mail/CassandraMessageIdMapper.java
@@ -39,6 +39,7 @@ import org.apache.james.mailbox.model.MailboxId;
 import org.apache.james.mailbox.model.MessageId;
 import org.apache.james.mailbox.model.UpdatedFlags;
 import org.apache.james.mailbox.store.FlagsUpdateCalculator;
+import org.apache.james.mailbox.store.MailboxReactorUtils;
 import org.apache.james.mailbox.store.mail.MailboxMapper;
 import org.apache.james.mailbox.store.mail.MessageIdMapper;
 import org.apache.james.mailbox.store.mail.MessageMapper.FetchType;
@@ -48,7 +49,6 @@ import org.apache.james.util.FunctionalUtils;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
-import com.github.fge.lambdas.runnable.ThrowingRunnable;
 import com.github.steveash.guavate.Guavate;
 import com.google.common.collect.Multimap;
 
@@ -133,31 +133,18 @@ public class CassandraMessageIdMapper implements MessageIdMapper {
     @Override
     public void save(MailboxMessage mailboxMessage) throws MailboxException {
         CassandraId mailboxId = (CassandraId) mailboxMessage.getMailboxId();
-        unbox(() -> mailboxMapper.findMailboxByIdReactive(mailboxId)
-            .switchIfEmpty(Mono.error(new MailboxNotFoundException(mailboxId)))
+        MailboxReactorUtils.block(mailboxMapper.findMailboxById(mailboxId)
+            .switchIfEmpty(Mono.error(() -> new MailboxNotFoundException(mailboxId)))
             .then(messageDAO.save(mailboxMessage))
-            .thenEmpty(saveMessageMetadata(mailboxMessage, mailboxId))
-            .block());
+            .thenEmpty(saveMessageMetadata(mailboxMessage, mailboxId)));
     }
 
     @Override
     public void copyInMailbox(MailboxMessage mailboxMessage) throws MailboxException {
         CassandraId mailboxId = (CassandraId) mailboxMessage.getMailboxId();
-        unbox(() -> mailboxMapper.findMailboxByIdReactive(mailboxId)
-            .switchIfEmpty(Mono.error(new MailboxNotFoundException(mailboxId)))
-            .then(saveMessageMetadata(mailboxMessage, mailboxId))
-            .block());
-    }
-
-    private void unbox(ThrowingRunnable runnable) throws MailboxNotFoundException {
-        try {
-            runnable.run();
-        } catch (RuntimeException e) {
-            if (e.getCause() instanceof MailboxNotFoundException) {
-                throw (MailboxNotFoundException) e.getCause();
-            }
-            throw e;
-        }
+        MailboxReactorUtils.block(mailboxMapper.findMailboxById(mailboxId)
+            .switchIfEmpty(Mono.error(() -> new MailboxNotFoundException(mailboxId)))
+            .then(saveMessageMetadata(mailboxMessage, mailboxId)));
     }
 
     private Mono<Void> saveMessageMetadata(MailboxMessage mailboxMessage, CassandraId mailboxId) {
diff --git a/mailbox/cassandra/src/main/java/org/apache/james/mailbox/cassandra/mail/task/MailboxMergingTaskRunner.java b/mailbox/cassandra/src/main/java/org/apache/james/mailbox/cassandra/mail/task/MailboxMergingTaskRunner.java
index 2de3caf..bf9888d 100644
--- a/mailbox/cassandra/src/main/java/org/apache/james/mailbox/cassandra/mail/task/MailboxMergingTaskRunner.java
+++ b/mailbox/cassandra/src/main/java/org/apache/james/mailbox/cassandra/mail/task/MailboxMergingTaskRunner.java
@@ -41,6 +41,8 @@ import org.apache.james.util.streams.Limit;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
+import reactor.core.publisher.Mono;
+
 public class MailboxMergingTaskRunner {
     private static final Logger LOGGER = LoggerFactory.getLogger(MailboxMergingTaskRunner.class);
 
@@ -64,7 +66,7 @@ public class MailboxMergingTaskRunner {
     public Task.Result run(CassandraId oldMailboxId, CassandraId newMailboxId, MailboxMergingTask.Context context) {
         return moveMessages(oldMailboxId, newMailboxId, mailboxSession, context)
             .onComplete(
-                () -> mergeRights(oldMailboxId, newMailboxId),
+                () -> mergeRights(oldMailboxId, newMailboxId).block(),
                 () -> mailboxDAO.delete(oldMailboxId).block());
     }
 
@@ -88,20 +90,13 @@ public class MailboxMergingTaskRunner {
         }
     }
 
-    private void mergeRights(CassandraId oldMailboxId, CassandraId newMailboxId) {
-        try {
-            MailboxACL oldAcl = cassandraACLMapper.getACL(oldMailboxId)
-                .defaultIfEmpty(MailboxACL.EMPTY)
-                .block();
-            MailboxACL newAcl = cassandraACLMapper.getACL(newMailboxId)
-                .defaultIfEmpty(MailboxACL.EMPTY)
-                .block();
-            MailboxACL finalAcl = newAcl.union(oldAcl);
-
-            cassandraACLMapper.setACL(newMailboxId, finalAcl);
-            rightsDAO.update(oldMailboxId, ACLDiff.computeDiff(oldAcl, MailboxACL.EMPTY)).block();
-        } catch (MailboxException e) {
-            throw new RuntimeException(e);
-        }
+    private Mono<Void> mergeRights(CassandraId oldMailboxId, CassandraId newMailboxId) {
+            Mono<MailboxACL> oldAclMono = cassandraACLMapper.getACL(oldMailboxId)
+                    .defaultIfEmpty(MailboxACL.EMPTY);
+            Mono<MailboxACL> newAclMono = cassandraACLMapper.getACL(newMailboxId)
+                    .defaultIfEmpty(MailboxACL.EMPTY);
+        return Mono.zip(oldAclMono, newAclMono)
+            .flatMap(acls -> cassandraACLMapper.setACL(newMailboxId, acls.getT1())
+                .then(rightsDAO.update(oldMailboxId, ACLDiff.computeDiff(acls.getT2(), MailboxACL.EMPTY))));
     }
 }
diff --git a/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/CassandraMailboxManagerConsistencyTest.java b/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/CassandraMailboxManagerConsistencyTest.java
index ccd5249..345a5e7 100644
--- a/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/CassandraMailboxManagerConsistencyTest.java
+++ b/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/CassandraMailboxManagerConsistencyTest.java
@@ -90,7 +90,7 @@ class CassandraMailboxManagerConsistencyTest {
             cassandra.getConf().registerScenario(NOTHING);
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                     .isEmpty();
                 softly.assertThat(testee.list(mailboxSession))
                     .isEmpty();
@@ -108,7 +108,7 @@ class CassandraMailboxManagerConsistencyTest {
             cassandra.getConf().registerScenario(NOTHING);
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                     .isEmpty();
                 softly.assertThat(testee.list(mailboxSession))
                     .isEmpty();
@@ -142,7 +142,7 @@ class CassandraMailboxManagerConsistencyTest {
                 .get();
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                     .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                         softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxId);
                         softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPath);
@@ -185,7 +185,7 @@ class CassandraMailboxManagerConsistencyTest {
                 .get();
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                     .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                         softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxId);
                         softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPath);
@@ -213,7 +213,7 @@ class CassandraMailboxManagerConsistencyTest {
             cassandra.getConf().registerScenario(NOTHING);
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                     .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                         softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxId);
                         softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPath);
@@ -237,7 +237,7 @@ class CassandraMailboxManagerConsistencyTest {
             cassandra.getConf().registerScenario(NOTHING);
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                     .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                         softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxId);
                         softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPath);
@@ -265,7 +265,7 @@ class CassandraMailboxManagerConsistencyTest {
                 .get();
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                     .hasSize(2)
                     .anySatisfy(mailboxMetaData -> {
                         softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxId);
@@ -297,7 +297,7 @@ class CassandraMailboxManagerConsistencyTest {
                 .get();
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                     .hasSize(2)
                     .anySatisfy(mailboxMetaData -> {
                         softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxId);
@@ -349,7 +349,7 @@ class CassandraMailboxManagerConsistencyTest {
                 .get();
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                     .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                         softly.assertThat(mailboxMetaData.getId()).isEqualTo(newMailboxId);
                         softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPathRenamed);
@@ -380,7 +380,7 @@ class CassandraMailboxManagerConsistencyTest {
                 cassandra.getConf().registerScenario(NOTHING);
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                         .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                             softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxId);
                             softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPath);
@@ -405,7 +405,7 @@ class CassandraMailboxManagerConsistencyTest {
                 cassandra.getConf().registerScenario(NOTHING);
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                         .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                             softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxId);
                             softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPath);
@@ -429,7 +429,7 @@ class CassandraMailboxManagerConsistencyTest {
                 cassandra.getConf().registerScenario(NOTHING);
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                         .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                             softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxId);
                             softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPath);
@@ -453,7 +453,7 @@ class CassandraMailboxManagerConsistencyTest {
                 cassandra.getConf().registerScenario(NOTHING);
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                         .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                             softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxId);
                             softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPath);
@@ -483,7 +483,7 @@ class CassandraMailboxManagerConsistencyTest {
                     .get();
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                         .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                             softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxId);
                             softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPath);
@@ -510,7 +510,7 @@ class CassandraMailboxManagerConsistencyTest {
                     .get();
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                         .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                             softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxNewId);
                             softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPath);
@@ -537,7 +537,7 @@ class CassandraMailboxManagerConsistencyTest {
                     .get();
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                         .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                             softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxNewId);
                             softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPath);
@@ -565,7 +565,7 @@ class CassandraMailboxManagerConsistencyTest {
                     .get();
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                         .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                             softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxNewId);
                             softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPath);
@@ -595,7 +595,7 @@ class CassandraMailboxManagerConsistencyTest {
                 doQuietly(() -> testee.deleteMailbox(inboxPath, mailboxSession));
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                         .isEmpty();
                     softly.assertThat(testee.list(mailboxSession))
                         .isEmpty();
@@ -618,7 +618,7 @@ class CassandraMailboxManagerConsistencyTest {
                 doQuietly(() -> testee.deleteMailbox(inboxId, mailboxSession));
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                         .isEmpty();
                     softly.assertThat(testee.list(mailboxSession))
                         .isEmpty();
@@ -640,7 +640,7 @@ class CassandraMailboxManagerConsistencyTest {
                 doQuietly(() -> testee.deleteMailbox(inboxPath, mailboxSession));
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                         .isEmpty();
                     softly.assertThat(testee.list(mailboxSession))
                         .isEmpty();
@@ -663,7 +663,7 @@ class CassandraMailboxManagerConsistencyTest {
                 doQuietly(() -> testee.deleteMailbox(inboxId, mailboxSession));
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                         .isEmpty();
                     softly.assertThat(testee.list(mailboxSession))
                         .isEmpty();
@@ -691,7 +691,7 @@ class CassandraMailboxManagerConsistencyTest {
                     .get();
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                         .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                             softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxId);
                             softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPath);
@@ -719,7 +719,7 @@ class CassandraMailboxManagerConsistencyTest {
                     .get();
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                         .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                             softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxNewId);
                             softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPath);
@@ -746,7 +746,7 @@ class CassandraMailboxManagerConsistencyTest {
                     .get();
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                         .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                             softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxNewId);
                             softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPath);
@@ -774,7 +774,7 @@ class CassandraMailboxManagerConsistencyTest {
                     .get();
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession))
+                    softly.assertThat(testee.search(allMailboxesSearchQuery, mailboxSession).toStream())
                         .hasOnlyOneElementSatisfying(mailboxMetaData -> {
                             softly.assertThat(mailboxMetaData.getId()).isEqualTo(inboxNewId);
                             softly.assertThat(mailboxMetaData.getPath()).isEqualTo(inboxPath);
diff --git a/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/mail/CassandraACLMapperTest.java b/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/mail/CassandraACLMapperTest.java
index f3f8b81..f5b3eb7 100644
--- a/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/mail/CassandraACLMapperTest.java
+++ b/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/mail/CassandraACLMapperTest.java
@@ -113,7 +113,7 @@ class CassandraACLMapperTest {
         MailboxACL.Rfc4314Rights rights = new MailboxACL.Rfc4314Rights(MailboxACL.Right.Read);
 
         cassandraACLMapper.updateACL(MAILBOX_ID,
-            MailboxACL.command().key(key).rights(rights).asAddition());
+            MailboxACL.command().key(key).rights(rights).asAddition()).block();
 
         assertThat(cassandraACLMapper.getACL(MAILBOX_ID).block())
             .isEqualTo(new MailboxACL().union(key, rights));
@@ -124,9 +124,9 @@ class CassandraACLMapperTest {
         MailboxACL.EntryKey keyBob = new MailboxACL.EntryKey("bob", MailboxACL.NameType.user, false);
         MailboxACL.Rfc4314Rights rights = new MailboxACL.Rfc4314Rights(MailboxACL.Right.Read);
 
-        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(keyBob).rights(rights).asAddition());
+        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(keyBob).rights(rights).asAddition()).block();
         MailboxACL.EntryKey keyAlice = new MailboxACL.EntryKey("alice", MailboxACL.NameType.user, false);
-        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(keyAlice).rights(rights).asAddition());
+        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(keyAlice).rights(rights).asAddition()).block();
 
         assertThat(cassandraACLMapper.getACL(MAILBOX_ID).block())
             .isEqualTo(new MailboxACL().union(keyBob, rights).union(keyAlice, rights));
@@ -137,8 +137,8 @@ class CassandraACLMapperTest {
         MailboxACL.EntryKey key = new MailboxACL.EntryKey("bob", MailboxACL.NameType.user, false);
         MailboxACL.Rfc4314Rights rights = new MailboxACL.Rfc4314Rights(MailboxACL.Right.Read);
 
-        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(key).rights(rights).asAddition());
-        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(key).rights(rights).asRemoval());
+        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(key).rights(rights).asAddition()).block();
+        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(key).rights(rights).asRemoval()).block();
 
         assertThat(cassandraACLMapper.getACL(MAILBOX_ID).block()).isEqualTo(MailboxACL.EMPTY);
     }
@@ -148,8 +148,8 @@ class CassandraACLMapperTest {
         MailboxACL.EntryKey key = new MailboxACL.EntryKey("bob", MailboxACL.NameType.user, false);
         MailboxACL.Rfc4314Rights rights = new MailboxACL.Rfc4314Rights(MailboxACL.Right.Read);
 
-        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(key).rights(rights).asAddition());
-        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(key).noRights().asReplacement());
+        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(key).rights(rights).asAddition()).block();
+        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(key).noRights().asReplacement()).block();
 
         assertThat(cassandraACLMapper.getACL(MAILBOX_ID).block()).isEqualTo(MailboxACL.EMPTY);
     }
@@ -159,7 +159,7 @@ class CassandraACLMapperTest {
         MailboxACL.EntryKey key = new MailboxACL.EntryKey("bob", MailboxACL.NameType.user, false);
         MailboxACL.Rfc4314Rights rights = new MailboxACL.Rfc4314Rights(MailboxACL.Right.Read);
 
-        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(key).rights(rights).asReplacement());
+        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(key).rights(rights).asReplacement()).block();
 
         assertThat(cassandraACLMapper.getACL(MAILBOX_ID).block()).isEqualTo(new MailboxACL().union(key, rights));
     }
@@ -174,7 +174,7 @@ class CassandraACLMapperTest {
         MailboxACL.EntryKey key = new MailboxACL.EntryKey("bob", MailboxACL.NameType.user, false);
         MailboxACL.Rfc4314Rights rights = new MailboxACL.Rfc4314Rights(MailboxACL.Right.Read);
 
-        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(key).rights(rights).asAddition());
+        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(key).rights(rights).asAddition()).block();
 
         assertThat(cassandraACLMapper.getACL(MAILBOX_ID).block()).isEqualTo(new MailboxACL().union(key, rights));
     }
@@ -207,7 +207,7 @@ class CassandraACLMapperTest {
     void twoConcurrentUpdatesWhenStoredShouldReturnACLWithTwoEntries(CassandraCluster cassandra) throws Exception {
         MailboxACL.EntryKey keyBenwa = new MailboxACL.EntryKey("benwa", MailboxACL.NameType.user, false);
         MailboxACL.Rfc4314Rights rights = new MailboxACL.Rfc4314Rights(MailboxACL.Right.Read);
-        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(keyBenwa).rights(rights).asAddition());
+        cassandraACLMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(keyBenwa).rights(rights).asAddition()).block();
 
         Barrier barrier = new Barrier(2);
         cassandra.getConf()
@@ -243,11 +243,8 @@ class CassandraACLMapperTest {
                 cassandra.getConf(),
                 new CassandraUserMailboxRightsDAO(cassandra.getConf(), CassandraUtils.WITH_DEFAULT_CONFIGURATION),
                 CassandraConfiguration.DEFAULT_CONFIGURATION);
-            try {
-                aclMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(key).rights(rights).asAddition());
-            } catch (MailboxException exception) {
-                throw new RuntimeException(exception);
-            }
+
+            aclMapper.updateACL(MAILBOX_ID, MailboxACL.command().key(key).rights(rights).asAddition()).block();
             return true;
         });
     }
diff --git a/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/mail/CassandraMailboxMapperConcurrencyTest.java b/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/mail/CassandraMailboxMapperConcurrencyTest.java
index 35400d8..313fdc2 100644
--- a/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/mail/CassandraMailboxMapperConcurrencyTest.java
+++ b/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/mail/CassandraMailboxMapperConcurrencyTest.java
@@ -65,7 +65,7 @@ class CassandraMailboxMapperConcurrencyTest {
     @Test
     void createShouldBeThreadSafe() throws Exception {
         ConcurrentTestRunner.builder()
-            .operation((a, b) -> testee.create(MAILBOX_PATH, UID_VALIDITY))
+            .operation((a, b) -> testee.create(MAILBOX_PATH, UID_VALIDITY).block())
             .threadCount(THREAD_COUNT)
             .operationCount(OPERATION_COUNT)
             .runAcceptingErrorsWithin(Duration.ofMinutes(1));
@@ -75,12 +75,12 @@ class CassandraMailboxMapperConcurrencyTest {
 
     @Test
     void renameWithUpdateShouldBeThreadSafe() throws Exception {
-        Mailbox mailbox = testee.create(MAILBOX_PATH, UID_VALIDITY);
+        Mailbox mailbox = testee.create(MAILBOX_PATH, UID_VALIDITY).block();
 
         mailbox.setName("newName");
 
         ConcurrentTestRunner.builder()
-            .operation((a, b) -> testee.rename(mailbox))
+            .operation((a, b) -> testee.rename(mailbox).block())
             .threadCount(THREAD_COUNT)
             .operationCount(OPERATION_COUNT)
             .runAcceptingErrorsWithin(Duration.ofMinutes(1));
diff --git a/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/mail/CassandraMailboxMapperTest.java b/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/mail/CassandraMailboxMapperTest.java
index f8e6839..29f4158 100644
--- a/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/mail/CassandraMailboxMapperTest.java
+++ b/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/mail/CassandraMailboxMapperTest.java
@@ -40,7 +40,6 @@ import org.apache.james.core.Username;
 import org.apache.james.mailbox.cassandra.ids.CassandraId;
 import org.apache.james.mailbox.cassandra.modules.CassandraAclModule;
 import org.apache.james.mailbox.cassandra.modules.CassandraMailboxModule;
-import org.apache.james.mailbox.exception.MailboxException;
 import org.apache.james.mailbox.exception.MailboxNotFoundException;
 import org.apache.james.mailbox.exception.TooLongMailboxNameException;
 import org.apache.james.mailbox.model.Mailbox;
@@ -140,8 +139,8 @@ class CassandraMailboxMapperTest {
         @Nested
         class Retries {
             @Test
-            void renameShouldRetryFailedDeleteMailboxPath(CassandraCluster cassandra) throws Exception {
-                Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+            void renameShouldRetryFailedDeleteMailboxPath(CassandraCluster cassandra) {
+                Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
                 MailboxId inboxId = inbox.getMailboxId();
                 Mailbox inboxRenamed = createInboxRenamedMailbox(inboxId);
 
@@ -150,11 +149,11 @@ class CassandraMailboxMapperTest {
                         .times(1)
                         .whenQueryStartsWith("DELETE FROM mailboxPathV2 WHERE namespace=:namespace AND user=:user AND mailboxName=:mailboxName IF EXISTS;"));
 
-                testee.rename(inboxRenamed);
+                testee.rename(inboxRenamed).block();
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
                     softly(softly)
-                        .assertThat(testee.findMailboxById(inboxId))
+                        .assertThat(testee.findMailboxById(inboxId).block())
                         .isEqualTo(inboxRenamed);
                     softly(softly)
                         .assertThat(testee.findMailboxByPath(inboxPathRenamed).block())
@@ -168,8 +167,8 @@ class CassandraMailboxMapperTest {
             }
 
             @Test
-            void renameShouldRetryFailedMailboxSaving(CassandraCluster cassandra) throws Exception {
-                Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+            void renameShouldRetryFailedMailboxSaving(CassandraCluster cassandra) {
+                Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
                 MailboxId inboxId = inbox.getMailboxId();
                 Mailbox inboxRenamed = createInboxRenamedMailbox(inboxId);
 
@@ -178,11 +177,11 @@ class CassandraMailboxMapperTest {
                     .times(1)
                     .whenQueryStartsWith("INSERT INTO mailbox (id,name,uidvalidity,mailboxbase) VALUES (:id,:name,:uidvalidity,:mailboxbase);"));
 
-                testee.rename(inboxRenamed);
+                testee.rename(inboxRenamed).block();
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
                     softly(softly)
-                        .assertThat(testee.findMailboxById(inboxId))
+                        .assertThat(testee.findMailboxById(inboxId).block())
                         .isEqualTo(inboxRenamed);
                     softly(softly)
                         .assertThat(testee.findMailboxByPath(inboxPathRenamed).block())
@@ -196,17 +195,17 @@ class CassandraMailboxMapperTest {
             }
 
             @Test
-            void createShouldRetryFailedMailboxSaving(CassandraCluster cassandra) throws Exception {
+            void createShouldRetryFailedMailboxSaving(CassandraCluster cassandra) {
                 cassandra.getConf()
                     .registerScenario(fail()
                         .times(1)
                         .whenQueryStartsWith("INSERT INTO mailbox (id,name,uidvalidity,mailboxbase) VALUES (:id,:name,:uidvalidity,:mailboxbase);"));
 
-                Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+                Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
                     softly(softly)
-                        .assertThat(testee.findMailboxById(inbox.getMailboxId()))
+                        .assertThat(testee.findMailboxById(inbox.getMailboxId()).block())
                         .isEqualTo(inbox);
                     softly(softly)
                         .assertThat(testee.findMailboxByPath(inboxPath).block())
@@ -220,19 +219,19 @@ class CassandraMailboxMapperTest {
             }
 
             @Test
-            void deleteShouldRetryFailedMailboxDeletion(CassandraCluster cassandra) throws Exception {
-                Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+            void deleteShouldRetryFailedMailboxDeletion(CassandraCluster cassandra) {
+                Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
 
                 cassandra.getConf()
                     .registerScenario(fail()
                     .times(1)
                     .whenQueryStartsWith("DELETE FROM mailbox WHERE id=:id;"));
 
-                testee.delete(inbox);
+                testee.delete(inbox).block();
 
                 SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                    softly.assertThatThrownBy(() -> testee.findMailboxById(inbox.getMailboxId()))
-                        .isInstanceOf(MailboxNotFoundException.class);
+                    softly.assertThatThrownBy(() -> testee.findMailboxById(inbox.getMailboxId()).block())
+                        .hasCauseInstanceOf(MailboxNotFoundException.class);
                     softly.assertThat(testee.findMailboxByPath(inboxPath).blockOptional())
                         .isEmpty();
                     softly.assertThat(testee.findMailboxWithPathLike(allMailboxesSearchQuery)
@@ -249,7 +248,7 @@ class CassandraMailboxMapperTest {
                     .times(10)
                     .whenQueryStartsWith("INSERT INTO mailbox (id,name,uidvalidity,mailboxbase) VALUES (:id,:name,:uidvalidity,:mailboxbase);"));
 
-            doQuietly(() -> testee.create(inboxPath, UID_VALIDITY));
+            doQuietly(() -> testee.create(inboxPath, UID_VALIDITY).block());
 
             SoftAssertions.assertSoftly(softly -> {
                 softly.assertThat(testee.findMailboxByPath(inboxPath).blockOptional())
@@ -264,8 +263,8 @@ class CassandraMailboxMapperTest {
         }
 
         @Test
-        void renameThenFailToRetrieveMailboxShouldBeConsistentWhenFindByInbox(CassandraCluster cassandra) throws Exception {
-            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+        void renameThenFailToRetrieveMailboxShouldBeConsistentWhenFindByInbox(CassandraCluster cassandra) {
+            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
             CassandraId inboxId = (CassandraId) inbox.getMailboxId();
             Mailbox inboxRenamed = createInboxRenamedMailbox(inboxId);
 
@@ -280,7 +279,7 @@ class CassandraMailboxMapperTest {
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
                 softly(softly)
-                    .assertThat(testee.findMailboxById(inboxId))
+                    .assertThat(testee.findMailboxById(inboxId).block())
                     .isEqualTo(inbox);
                 softly(softly)
                     .assertThat(testee.findMailboxByPath(inboxPath).block())
@@ -295,8 +294,8 @@ class CassandraMailboxMapperTest {
 
         @Disabled("JAMES-3056 returning two mailboxes with same name and id")
         @Test
-        void renameThenFailToRetrieveMailboxShouldBeConsistentWhenFindAll(CassandraCluster cassandra) throws Exception {
-            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+        void renameThenFailToRetrieveMailboxShouldBeConsistentWhenFindAll(CassandraCluster cassandra) {
+            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
             CassandraId inboxId = (CassandraId) inbox.getMailboxId();
             Mailbox inboxRenamed = createInboxRenamedMailbox(inboxId);
 
@@ -305,21 +304,21 @@ class CassandraMailboxMapperTest {
                     .times(TRY_COUNT_BEFORE_FAILURE)
                     .whenQueryStartsWith("SELECT id,mailboxbase,uidvalidity,name FROM mailbox WHERE id=:id;"));
 
-            doQuietly(() -> testee.rename(inboxRenamed));
+            doQuietly(() -> testee.rename(inboxRenamed).block());
 
-            SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
+            SoftAssertions.assertSoftly(Throwing.consumer(softly ->
                 softly.assertThat(testee.findMailboxWithPathLike(allMailboxesSearchQuery)
                     .collectList().block())
                     .hasOnlyOneElementSatisfying(searchMailbox -> softly(softly)
                         .assertThat(searchMailbox)
-                        .isEqualTo(inbox));
-            }));
+                        .isEqualTo(inbox))
+            ));
         }
 
         @Disabled("JAMES-3056 find by renamed name returns unexpected results")
         @Test
-        void renameThenFailToRetrieveMailboxShouldBeConsistentWhenFindByRenamedInbox(CassandraCluster cassandra) throws Exception {
-            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+        void renameThenFailToRetrieveMailboxShouldBeConsistentWhenFindByRenamedInbox(CassandraCluster cassandra) {
+            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
             CassandraId inboxId = (CassandraId) inbox.getMailboxId();
             Mailbox inboxRenamed = createInboxRenamedMailbox(inboxId);
 
@@ -328,10 +327,10 @@ class CassandraMailboxMapperTest {
                     .times(TRY_COUNT_BEFORE_FAILURE)
                     .whenQueryStartsWith("SELECT id,mailboxbase,uidvalidity,name FROM mailbox WHERE id=:id;"));
 
-            doQuietly(() -> testee.rename(inboxRenamed));
+            doQuietly(() -> testee.rename(inboxRenamed).block());
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                softly.assertThatThrownBy(() -> testee.findMailboxByPath(inboxPathRenamed))
+                softly.assertThatThrownBy(() -> testee.findMailboxByPath(inboxPathRenamed).block())
                     .isInstanceOf(MailboxNotFoundException.class);
                 softly.assertThat(testee.findMailboxWithPathLike(inboxRenamedSearchQuery)
                     .collectList().block())
@@ -340,8 +339,8 @@ class CassandraMailboxMapperTest {
         }
 
         @Test
-        void renameThenFailToDeleteMailboxPathShouldBeConsistentWhenFindByInbox(CassandraCluster cassandra) throws Exception {
-            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+        void renameThenFailToDeleteMailboxPathShouldBeConsistentWhenFindByInbox(CassandraCluster cassandra) {
+            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
             CassandraId inboxId = (CassandraId) inbox.getMailboxId();
             Mailbox inboxRenamed = createInboxRenamedMailbox(inboxId);
 
@@ -350,11 +349,11 @@ class CassandraMailboxMapperTest {
                     .times(TRY_COUNT_BEFORE_FAILURE)
                     .whenQueryStartsWith("DELETE FROM mailboxPathV2 WHERE namespace=:namespace AND user=:user AND mailboxName=:mailboxName IF EXISTS;"));
 
-            doQuietly(() -> testee.rename(inboxRenamed));
+            doQuietly(() -> testee.rename(inboxRenamed).block());
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
                 softly(softly)
-                    .assertThat(testee.findMailboxById(inboxId))
+                    .assertThat(testee.findMailboxById(inboxId).block())
                     .isEqualTo(inbox);
                 softly(softly)
                     .assertThat(testee.findMailboxByPath(inboxPath).block())
@@ -369,8 +368,8 @@ class CassandraMailboxMapperTest {
 
         @Disabled("JAMES-3056 returning two mailboxes with same name and id")
         @Test
-        void renameThenFailToDeleteMailboxPathShouldBeConsistentWhenFindAll(CassandraCluster cassandra) throws Exception {
-            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+        void renameThenFailToDeleteMailboxPathShouldBeConsistentWhenFindAll(CassandraCluster cassandra) {
+            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
             CassandraId inboxId = (CassandraId) inbox.getMailboxId();
             Mailbox inboxRenamed = createInboxRenamedMailbox(inboxId);
 
@@ -379,21 +378,20 @@ class CassandraMailboxMapperTest {
                     .times(TRY_COUNT_BEFORE_FAILURE)
                     .whenQueryStartsWith("DELETE FROM mailboxPathV2 WHERE namespace=:namespace AND user=:user AND mailboxName=:mailboxName IF EXISTS;"));
 
-            doQuietly(() -> testee.rename(inboxRenamed));
+            doQuietly(() -> testee.rename(inboxRenamed).block());
 
-            SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
+            SoftAssertions.assertSoftly(Throwing.consumer(softly ->
                 softly.assertThat(testee.findMailboxWithPathLike(allMailboxesSearchQuery)
                     .collectList().block())
                     .hasOnlyOneElementSatisfying(searchMailbox -> softly(softly)
                         .assertThat(searchMailbox)
-                        .isEqualTo(inbox));
-            }));
+                        .isEqualTo(inbox))));
         }
 
         @Disabled("JAMES-3056 find by renamed name returns unexpected results")
         @Test
-        void renameThenFailToDeleteMailboxPathShouldBeConsistentWhenFindByRenamedInbox(CassandraCluster cassandra) throws Exception {
-            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+        void renameThenFailToDeleteMailboxPathShouldBeConsistentWhenFindByRenamedInbox(CassandraCluster cassandra) {
+            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
             CassandraId inboxId = (CassandraId) inbox.getMailboxId();
             Mailbox inboxRenamed = createInboxRenamedMailbox(inboxId);
 
@@ -402,10 +400,10 @@ class CassandraMailboxMapperTest {
                     .times(TRY_COUNT_BEFORE_FAILURE)
                     .whenQueryStartsWith("DELETE FROM mailboxPathV2 WHERE namespace=:namespace AND user=:user AND mailboxName=:mailboxName IF EXISTS;"));
 
-            doQuietly(() -> testee.rename(inboxRenamed));
+            doQuietly(() -> testee.rename(inboxRenamed).block());
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                softly.assertThatThrownBy(() -> testee.findMailboxByPath(inboxPathRenamed))
+                softly.assertThatThrownBy(() -> testee.findMailboxByPath(inboxPathRenamed).block())
                     .isInstanceOf(MailboxNotFoundException.class);
                 softly.assertThat(testee.findMailboxWithPathLike(inboxRenamedSearchQuery)
                     .collectList().block())
@@ -415,8 +413,8 @@ class CassandraMailboxMapperTest {
 
         @Disabled("JAMES-3056 find by mailbox name returns unexpected results")
         @Test
-        void deleteShouldBeConsistentWhenFailToDeleteMailbox(CassandraCluster cassandra) throws Exception {
-            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+        void deleteShouldBeConsistentWhenFailToDeleteMailbox(CassandraCluster cassandra) {
+            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
             CassandraId inboxId = (CassandraId) inbox.getMailboxId();
 
             cassandra.getConf()
@@ -424,12 +422,12 @@ class CassandraMailboxMapperTest {
                     .times(TRY_COUNT_BEFORE_FAILURE)
                     .whenQueryStartsWith("DELETE FROM mailbox WHERE id=:id;"));
 
-            doQuietly(() -> testee.delete(inbox));
+            doQuietly(() -> testee.delete(inbox).block());
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                softly.assertThatCode(() -> testee.findMailboxById(inboxId))
+                softly.assertThatCode(() -> testee.findMailboxById(inboxId).block())
                     .doesNotThrowAnyException();
-                softly.assertThatCode(() -> testee.findMailboxByPath(inboxPath))
+                softly.assertThatCode(() -> testee.findMailboxByPath(inboxPath).block())
                     .doesNotThrowAnyException();
                 softly.assertThat(testee.findMailboxWithPathLike(inboxSearchQuery)
                     .collectList().block())
@@ -446,8 +444,8 @@ class CassandraMailboxMapperTest {
 
         @Disabled("JAMES-3056 both mailboxes of the same user have 'INBOX' name")
         @Test
-        void missedMigrationShouldNotLeadToGhostMailbox() throws Exception {
-            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+        void missedMigrationShouldNotLeadToGhostMailbox() {
+            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
             CassandraId inboxId = (CassandraId) inbox.getMailboxId();
             // simulate mailbox old data has not been migrated to v2
             mailboxPathDAO.save(inboxPath, inboxId).block();
@@ -457,23 +455,23 @@ class CassandraMailboxMapperTest {
             // => two mailboxes with same name but different ids
             CassandraId newId = CassandraId.timeBased();
             Mailbox mailboxHasSameNameWithInbox = new Mailbox(inboxPath, UID_VALIDITY, newId);
-            testee.rename(mailboxHasSameNameWithInbox);
+            testee.rename(mailboxHasSameNameWithInbox).block();
 
-            assertThat(testee.findMailboxById(newId).getName())
-                .isNotEqualTo(testee.findMailboxById(inboxId).getName());
+            assertThat(testee.findMailboxById(newId).block().getName())
+                .isNotEqualTo(testee.findMailboxById(inboxId).block().getName());
         }
 
         @Disabled("JAMES-3056 org.apache.james.mailbox.exception.MailboxNotFoundException: 'mailboxId' can not be found")
         @Test
-        void createAfterPreviousFailedCreateShouldCreateAMailbox(CassandraCluster cassandra) throws MailboxException {
+        void createAfterPreviousFailedCreateShouldCreateAMailbox(CassandraCluster cassandra) {
             cassandra.getConf()
                 .registerScenario(fail()
                     .times(TRY_COUNT_BEFORE_FAILURE)
                     .whenQueryStartsWith("INSERT INTO mailbox (id,name,uidvalidity,mailboxbase) VALUES (:id,:name,:uidvalidity,:mailboxbase);"));
 
-            doQuietly(() -> testee.create(inboxPath, UID_VALIDITY));
+            doQuietly(() -> testee.create(inboxPath, UID_VALIDITY).block());
 
-            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
                 softly(softly)
@@ -493,16 +491,16 @@ class CassandraMailboxMapperTest {
         }
 
         @Test
-        void createAfterPreviousDeleteOnFailedCreateShouldCreateAMailbox(CassandraCluster cassandra) throws MailboxException {
+        void createAfterPreviousDeleteOnFailedCreateShouldCreateAMailbox(CassandraCluster cassandra) {
             cassandra.getConf()
                 .registerScenario(fail()
                     .times(TRY_COUNT_BEFORE_FAILURE)
                     .whenQueryStartsWith("INSERT INTO mailbox (id,name,uidvalidity,mailboxbase) VALUES (:id,:name,:uidvalidity,:mailboxbase);"));
 
-            doQuietly(() -> testee.create(inboxPath, UID_VALIDITY));
-            doQuietly(() -> testee.delete(new Mailbox(inboxPath, UID_VALIDITY, CassandraId.timeBased())));
+            doQuietly(() -> testee.create(inboxPath, UID_VALIDITY).block());
+            doQuietly(() -> testee.delete(new Mailbox(inboxPath, UID_VALIDITY, CassandraId.timeBased())).block());
 
-            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
                 softly(softly)
@@ -522,8 +520,8 @@ class CassandraMailboxMapperTest {
         }
 
         @Test
-        void deleteAfterAFailedDeleteShouldDeleteTheMailbox(CassandraCluster cassandra) throws Exception {
-            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+        void deleteAfterAFailedDeleteShouldDeleteTheMailbox(CassandraCluster cassandra) {
+            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
             CassandraId inboxId = (CassandraId) inbox.getMailboxId();
 
             cassandra.getConf()
@@ -531,13 +529,13 @@ class CassandraMailboxMapperTest {
                     .times(TRY_COUNT_BEFORE_FAILURE)
                     .whenQueryStartsWith("DELETE FROM mailbox WHERE id=:id;"));
 
-            doQuietly(() -> testee.delete(inbox));
+            doQuietly(() -> testee.delete(inbox).block());
 
-            doQuietly(() -> testee.delete(inbox));
+            doQuietly(() -> testee.delete(inbox).block());
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
-                softly.assertThatThrownBy(() -> testee.findMailboxById(inboxId))
-                    .isInstanceOf(MailboxNotFoundException.class);
+                softly.assertThatThrownBy(() -> testee.findMailboxById(inboxId).block())
+                    .hasCauseInstanceOf(MailboxNotFoundException.class);
                     softly.assertThat(testee.findMailboxByPath(inboxPath).blockOptional())
                         .isEmpty();
                 softly.assertThat(testee.findMailboxWithPathLike(inboxSearchQuery)
@@ -552,8 +550,8 @@ class CassandraMailboxMapperTest {
         @Disabled("JAMES-3056 mailbox name is not updated to INBOX_RENAMED).isEqualTo(" +
             "findMailboxWithPathLike() returns a list with two same mailboxes")
         @Test
-        void renameAfterRenameFailOnRetrieveMailboxShouldRenameTheMailbox(CassandraCluster cassandra) throws Exception {
-            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+        void renameAfterRenameFailOnRetrieveMailboxShouldRenameTheMailbox(CassandraCluster cassandra) {
+            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
             CassandraId inboxId = (CassandraId) inbox.getMailboxId();
             Mailbox inboxRenamed = createInboxRenamedMailbox(inboxId);
 
@@ -562,13 +560,13 @@ class CassandraMailboxMapperTest {
                     .times(TRY_COUNT_BEFORE_FAILURE)
                     .whenQueryStartsWith("SELECT id,mailboxbase,uidvalidity,name FROM mailbox WHERE id=:id;"));
 
-            doQuietly(() -> testee.rename(inboxRenamed));
+            doQuietly(() -> testee.rename(inboxRenamed).block());
 
-            doQuietly(() -> testee.rename(inboxRenamed));
+            doQuietly(() -> testee.rename(inboxRenamed).block());
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
                 softly(softly)
-                    .assertThat(testee.findMailboxById(inboxId))
+                    .assertThat(testee.findMailboxById(inboxId).block())
                     .isEqualTo(inboxRenamed);
                 softly(softly)
                     .assertThat(testee.findMailboxByPath(inboxPathRenamed).block())
@@ -591,8 +589,8 @@ class CassandraMailboxMapperTest {
 
         @Disabled("JAMES-3056 mailbox name is not updated to INBOX_RENAMED")
         @Test
-        void renameAfterRenameFailOnDeletePathShouldRenameTheMailbox(CassandraCluster cassandra) throws Exception {
-            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY);
+        void renameAfterRenameFailOnDeletePathShouldRenameTheMailbox(CassandraCluster cassandra) {
+            Mailbox inbox = testee.create(inboxPath, UID_VALIDITY).block();
             CassandraId inboxId = (CassandraId) inbox.getMailboxId();
             Mailbox inboxRenamed = createInboxRenamedMailbox(inboxId);
 
@@ -601,13 +599,13 @@ class CassandraMailboxMapperTest {
                     .times(TRY_COUNT_BEFORE_FAILURE)
                     .whenQueryStartsWith("DELETE FROM mailboxPathV2 WHERE namespace=:namespace AND user=:user AND mailboxName=:mailboxName IF EXISTS;"));
 
-            doQuietly(() -> testee.rename(inboxRenamed));
+            doQuietly(() -> testee.rename(inboxRenamed).block());
 
-            doQuietly(() -> testee.rename(inboxRenamed));
+            doQuietly(() -> testee.rename(inboxRenamed).block());
 
             SoftAssertions.assertSoftly(Throwing.consumer(softly -> {
                 softly(softly)
-                    .assertThat(testee.findMailboxById(inboxId))
+                    .assertThat(testee.findMailboxById(inboxId).block())
                     .isEqualTo(inboxRenamed);
                 softly(softly)
                     .assertThat(testee.findMailboxByPath(inboxPathRenamed).block())
@@ -644,12 +642,12 @@ class CassandraMailboxMapperTest {
 
     @Disabled("JAMES-2514 Cassandra 3 supports long mailbox names. Hence we can not rely on this for failing")
     @Test
-    void renameShouldNotRemoveOldMailboxPathWhenCreatingTheNewMailboxPathFails() throws Exception {
-        testee.create(MAILBOX_PATH, UID_VALIDITY);
+    void renameShouldNotRemoveOldMailboxPathWhenCreatingTheNewMailboxPathFails() {
+        testee.create(MAILBOX_PATH, UID_VALIDITY).block();
         Mailbox mailbox = testee.findMailboxByPath(MAILBOX_PATH).block();
 
         Mailbox newMailbox = new Mailbox(tooLongMailboxPath(mailbox.generateAssociatedPath()), UID_VALIDITY, mailbox.getMailboxId());
-        assertThatThrownBy(() -> testee.rename(newMailbox))
+        assertThatThrownBy(() -> testee.rename(newMailbox).block())
             .isInstanceOf(TooLongMailboxNameException.class);
 
         assertThat(mailboxPathV2DAO.retrieveId(MAILBOX_PATH).blockOptional())
@@ -667,7 +665,7 @@ class CassandraMailboxMapperTest {
         mailboxPathDAO.save(MAILBOX_PATH, MAILBOX_ID)
             .block();
 
-        testee.delete(MAILBOX);
+        testee.delete(MAILBOX).block();
 
         assertThat(testee.findMailboxByPath(MAILBOX_PATH).blockOptional())
             .isEmpty();
@@ -680,7 +678,7 @@ class CassandraMailboxMapperTest {
         mailboxPathV2DAO.save(MAILBOX_PATH, MAILBOX_ID)
             .block();
 
-        testee.delete(MAILBOX);
+        testee.delete(MAILBOX).block();
 
         assertThat(testee.findMailboxByPath(MAILBOX_PATH).blockOptional())
             .isEmpty();
@@ -733,7 +731,7 @@ class CassandraMailboxMapperTest {
         mailboxPathV2DAO.save(MAILBOX_PATH, MAILBOX_ID)
             .block();
 
-        testee.delete(MAILBOX);
+        testee.delete(MAILBOX).block();
 
         assertThat(testee.findMailboxByPath(MAILBOX_PATH).blockOptional())
             .isEmpty();
@@ -746,7 +744,7 @@ class CassandraMailboxMapperTest {
         mailboxPathDAO.save(MAILBOX_PATH, MAILBOX_ID)
             .block();
 
-        testee.delete(MAILBOX);
+        testee.delete(MAILBOX).block();
 
         assertThat(testee.findMailboxByPath(MAILBOX_PATH).blockOptional())
             .isEmpty();
@@ -759,7 +757,7 @@ class CassandraMailboxMapperTest {
         mailboxPathV2DAO.save(MAILBOX_PATH, MAILBOX_ID)
             .block();
 
-        testee.delete(MAILBOX);
+        testee.delete(MAILBOX).block();
 
         assertThat(testee.findMailboxByPath(MAILBOX_PATH).blockOptional())
             .isEmpty();
@@ -780,7 +778,7 @@ class CassandraMailboxMapperTest {
             .block();
         mailboxPathDAO.save(MAILBOX_PATH, MAILBOX_ID)
             .block();
-    
+
         List<Mailbox> mailboxes = testee.findMailboxWithPathLike(MailboxQuery.builder()
             .privateNamespace()
             .username(USER)
@@ -818,7 +816,7 @@ class CassandraMailboxMapperTest {
             .block();
         mailboxPathV2DAO.save(MAILBOX_PATH, MAILBOX_ID)
             .block();
-    
+
         List<Mailbox> mailboxes = testee.findMailboxWithPathLike(MailboxQuery.builder()
             .privateNamespace()
             .username(USER)
@@ -844,7 +842,7 @@ class CassandraMailboxMapperTest {
         mailboxPathDAO.save(childMailboxPath, childMailboxId)
             .block();
     
-        boolean hasChildren = testee.hasChildren(MAILBOX, '.');
+        boolean hasChildren = testee.hasChildren(MAILBOX, '.').block();
 
         assertThat(hasChildren).isTrue();
     }
@@ -865,7 +863,7 @@ class CassandraMailboxMapperTest {
         mailboxPathDAO.save(childMailboxPath, childMailboxId)
             .block();
 
-        boolean hasChildren = testee.hasChildren(MAILBOX, '.');
+        boolean hasChildren = testee.hasChildren(MAILBOX, '.').block();
 
         assertThat(hasChildren).isTrue();
     }
@@ -884,7 +882,7 @@ class CassandraMailboxMapperTest {
         mailboxPathV2DAO.save(childMailboxPath, childMailboxId)
             .block();
     
-        boolean hasChildren = testee.hasChildren(MAILBOX, '.');
+        boolean hasChildren = testee.hasChildren(MAILBOX, '.').block();
     
         assertThat(hasChildren).isTrue();
     }
diff --git a/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/mail/migration/MailboxPathV2MigrationTest.java b/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/mail/migration/MailboxPathV2MigrationTest.java
index e018eb1..ee4be70 100644
--- a/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/mail/migration/MailboxPathV2MigrationTest.java
+++ b/mailbox/cassandra/src/test/java/org/apache/james/mailbox/cassandra/mail/migration/MailboxPathV2MigrationTest.java
@@ -40,7 +40,6 @@ import org.apache.james.mailbox.cassandra.mail.CassandraMailboxPathV2DAO;
 import org.apache.james.mailbox.cassandra.mail.CassandraUserMailboxRightsDAO;
 import org.apache.james.mailbox.cassandra.modules.CassandraAclModule;
 import org.apache.james.mailbox.cassandra.modules.CassandraMailboxModule;
-import org.apache.james.mailbox.exception.MailboxException;
 import org.apache.james.mailbox.model.Mailbox;
 import org.apache.james.mailbox.model.MailboxPath;
 import org.apache.james.mailbox.model.UidValidity;
@@ -90,7 +89,7 @@ class MailboxPathV2MigrationTest {
     }
 
     @Test
-    void newValuesShouldBeSavedInMostRecentDAO() throws Exception {
+    void newValuesShouldBeSavedInMostRecentDAO() {
         Mailbox mailbox = createMailbox();
         CassandraId mailboxId = (CassandraId) mailbox.getMailboxId();
 
@@ -99,7 +98,7 @@ class MailboxPathV2MigrationTest {
     }
 
     @Test
-    void newValuesShouldNotBeSavedInOldDAO() throws Exception {
+    void newValuesShouldNotBeSavedInOldDAO() {
         createMailbox();
 
         assertThat(daoV1.retrieveId(MAILBOX_PATH_1).blockOptional())
@@ -107,7 +106,7 @@ class MailboxPathV2MigrationTest {
     }
 
     @Test
-    void readingOldValuesShouldMigrateThem() throws Exception {
+    void readingOldValuesShouldMigrateThem() {
         Mailbox mailbox = new Mailbox(MAILBOX_PATH_1, UID_VALIDITY_1, MAILBOX_ID_1);
 
         daoV1.save(MAILBOX_PATH_1, MAILBOX_ID_1).block();
@@ -135,7 +134,7 @@ class MailboxPathV2MigrationTest {
         softly.assertAll();
     }
 
-    private Mailbox createMailbox() throws MailboxException {
-        return mailboxMapper.create(MAILBOX_PATH_1, UID_VALIDITY_1);
+    private Mailbox createMailbox() {
+        return mailboxMapper.create(MAILBOX_PATH_1, UID_VALIDITY_1).block();
     }
 }
\ No newline at end of file
diff --git a/mailbox/elasticsearch/src/test/java/org/apache/james/mailbox/elasticsearch/events/ElasticSearchListeningMessageSearchIndexTest.java b/mailbox/elasticsearch/src/test/java/org/apache/james/mailbox/elasticsearch/events/ElasticSearchListeningMessageSearchIndexTest.java
index b934ec3..c9ea4e6 100644
--- a/mailbox/elasticsearch/src/test/java/org/apache/james/mailbox/elasticsearch/events/ElasticSearchListeningMessageSearchIndexTest.java
+++ b/mailbox/elasticsearch/src/test/java/org/apache/james/mailbox/elasticsearch/events/ElasticSearchListeningMessageSearchIndexTest.java
@@ -187,7 +187,7 @@ class ElasticSearchListeningMessageSearchIndexTest {
             messageToElasticSearchJson, sessionProvider, new MailboxIdRoutingKeyFactory());
         session = sessionProvider.createSystemSession(USERNAME);
 
-        mailbox = mapperFactory.getMailboxMapper(session).create(MailboxPath.forUser(USERNAME, DefaultMailboxes.INBOX), UidValidity.generate());
+        mailbox = mapperFactory.getMailboxMapper(session).create(MailboxPath.forUser(USERNAME, DefaultMailboxes.INBOX), UidValidity.generate()).block();
     }
 
     @Test
diff --git a/mailbox/jpa/src/main/java/org/apache/james/mailbox/jpa/mail/JPAMailboxMapper.java b/mailbox/jpa/src/main/java/org/apache/james/mailbox/jpa/mail/JPAMailboxMapper.java
index d5bfe96..f9c9f44 100644
--- a/mailbox/jpa/src/main/java/org/apache/james/mailbox/jpa/mail/JPAMailboxMapper.java
+++ b/mailbox/jpa/src/main/java/org/apache/james/mailbox/jpa/mail/JPAMailboxMapper.java
@@ -84,39 +84,31 @@ public class JPAMailboxMapper extends JPATransactionalMapper implements MailboxM
     }
     
     @Override
-    public Mailbox create(MailboxPath mailboxPath, UidValidity uidValidity) throws MailboxException {
-        try {
-            if (isPathAlreadyUsedByAnotherMailbox(mailboxPath)) {
-                throw new MailboxExistsException(mailboxPath.getName());
-            }
-
-            this.lastMailboxName = mailboxPath.getName();
-            JPAMailbox persistedMailbox = new JPAMailbox(mailboxPath, uidValidity);
-            getEntityManager().persist(persistedMailbox);
+    public Mono<Mailbox> create(MailboxPath mailboxPath, UidValidity uidValidity) {
+        return assertPathIsNotAlreadyUsedByAnotherMailbox(mailboxPath)
+            .then(Mono.fromCallable(() -> {
+                this.lastMailboxName = mailboxPath.getName();
+                JPAMailbox persistedMailbox = new JPAMailbox(mailboxPath, uidValidity);
+                getEntityManager().persist(persistedMailbox);
 
-            return new Mailbox(mailboxPath, uidValidity, persistedMailbox.getMailboxId());
-        } catch (PersistenceException e) {
-            throw new MailboxException("Save of mailbox " + mailboxPath.getName() + " failed", e);
-        }
+                return new Mailbox(mailboxPath, uidValidity, persistedMailbox.getMailboxId());
+            }))
+            .onErrorMap(PersistenceException.class, e -> new MailboxException("Save of mailbox " + mailboxPath.getName() + " failed", e));
     }
 
     @Override
-    public MailboxId rename(Mailbox mailbox) throws MailboxException {
+    public Mono<MailboxId> rename(Mailbox mailbox) {
         Preconditions.checkNotNull(mailbox.getMailboxId(), "A mailbox we want to rename should have a defined mailboxId");
 
-        try {
-            if (isPathAlreadyUsedByAnotherMailbox(mailbox.generateAssociatedPath())) {
-                throw new MailboxExistsException(mailbox.getName());
-            }
-
-            this.lastMailboxName = mailbox.getName();
-            JPAMailbox persistedMailbox = jpaMailbox(mailbox);
+        return assertPathIsNotAlreadyUsedByAnotherMailbox(mailbox.generateAssociatedPath())
+            .then(Mono.fromCallable(() -> {
+                this.lastMailboxName = mailbox.getName();
+                JPAMailbox persistedMailbox = jpaMailbox(mailbox);
 
-            getEntityManager().persist(persistedMailbox);
-            return persistedMailbox.getMailboxId();
-        } catch (PersistenceException e) {
-            throw new MailboxException("Save of mailbox " + mailbox.getName() + " failed", e);
-        } 
+                getEntityManager().persist(persistedMailbox);
+                return (MailboxId) persistedMailbox.getMailboxId();
+            }))
+            .onErrorMap(PersistenceException.class, e -> new MailboxException("Save of mailbox " + mailbox.getName() + " failed", e));
     }
 
     private JPAMailbox jpaMailbox(Mailbox mailbox) throws MailboxException {
@@ -127,36 +119,27 @@ public class JPAMailboxMapper extends JPATransactionalMapper implements MailboxM
         return result;
     }
 
-    private boolean isPathAlreadyUsedByAnotherMailbox(MailboxPath mailboxPath) throws MailboxException {
+    private Mono<Void> assertPathIsNotAlreadyUsedByAnotherMailbox(MailboxPath mailboxPath) {
         return findMailboxByPath(mailboxPath)
-            .blockOptional()
-            .isPresent();
+            .flatMap(ignored -> Mono.error(new MailboxExistsException(mailboxPath.getName())));
     }
 
     @Override
     public Mono<Mailbox> findMailboxByPath(MailboxPath mailboxPath)  {
-        try {
-            return Mono.just(getEntityManager().createNamedQuery("findMailboxByNameWithUser", JPAMailbox.class)
-                .setParameter("nameParam", mailboxPath.getName())
-                .setParameter("namespaceParam", mailboxPath.getNamespace())
-                .setParameter("userParam", mailboxPath.getUser().asString())
-                .getSingleResult()
-                .toMailbox());
-        } catch (NoResultException e) {
-            return Mono.empty();
-        } catch (PersistenceException e) {
-            return Mono.error(new MailboxException("Exception upon JPA execution", e));
-        }
+        return Mono.fromCallable(() -> getEntityManager().createNamedQuery("findMailboxByNameWithUser", JPAMailbox.class)
+            .setParameter("nameParam", mailboxPath.getName())
+            .setParameter("namespaceParam", mailboxPath.getNamespace())
+            .setParameter("userParam", mailboxPath.getUser().asString())
+            .getSingleResult()
+            .toMailbox())
+            .onErrorResume(NoResultException.class, e -> Mono.empty())
+            .onErrorResume(PersistenceException.class, e -> Mono.error(new MailboxException("Exception upon JPA execution", e)));
     }
 
     @Override
-    public Mailbox findMailboxById(MailboxId id) throws MailboxException, MailboxNotFoundException {
-
-        try {
-            return loadJpaMailbox(id).toMailbox();
-        } catch (PersistenceException e) {
-            throw new MailboxException("Search of mailbox " + id.serialize() + " failed", e);
-        } 
+    public Mono<Mailbox> findMailboxById(MailboxId id) {
+        return Mono.fromCallable(() -> loadJpaMailbox(id).toMailbox())
+            .onErrorMap(PersistenceException.class, e -> new MailboxException("Search of mailbox " + id.serialize() + " failed", e));
     }
 
     private JPAMailbox loadJpaMailbox(MailboxId id) throws MailboxNotFoundException {
@@ -171,28 +154,25 @@ public class JPAMailboxMapper extends JPATransactionalMapper implements MailboxM
     }
 
     @Override
-    public void delete(Mailbox mailbox) throws MailboxException {
-        try {  
+    public Mono<Void> delete(Mailbox mailbox) {
+        return Mono.fromRunnable(() -> {
             JPAId mailboxId = (JPAId) mailbox.getMailboxId();
             getEntityManager().createNamedQuery("deleteMessages").setParameter("idParam", mailboxId.getRawId()).executeUpdate();
             JPAMailbox jpaMailbox = getEntityManager().find(JPAMailbox.class, mailboxId.getRawId());
             getEntityManager().remove(jpaMailbox);
-        } catch (PersistenceException e) {
-            throw new MailboxException("Delete of mailbox " + mailbox + " failed", e);
-        } 
+        })
+        .onErrorMap(PersistenceException.class, e -> new MailboxException("Delete of mailbox " + mailbox + " failed", e))
+        .then();
     }
 
     @Override
-    public Flux<Mailbox> findMailboxWithPathLike(MailboxQuery.UserBound query) throws MailboxException {
-        try {
-            String pathLike = MailboxExpressionBackwardCompatibility.getPathLike(query);
-            return Flux.fromIterable(findMailboxWithPathLikeTypedQuery(query.getFixedNamespace(), query.getFixedUser(), pathLike)
-                .getResultList())
-                .map(JPAMailbox::toMailbox)
-                .filter(query::matches);
-        } catch (PersistenceException e) {
-            throw new MailboxException("Search of mailbox " + query + " failed", e);
-        }
+    public Flux<Mailbox> findMailboxWithPathLike(MailboxQuery.UserBound query) {
+        String pathLike = MailboxExpressionBackwardCompatibility.getPathLike(query);
+        return Mono.fromCallable(() -> findMailboxWithPathLikeTypedQuery(query.getFixedNamespace(), query.getFixedUser(), pathLike))
+            .flatMapIterable(TypedQuery::getResultList)
+            .map(JPAMailbox::toMailbox)
+            .filter(query::matches)
+            .onErrorMap(PersistenceException.class, e -> new MailboxException("Search of mailbox " + query + " failed", e));
     }
 
     private TypedQuery<JPAMailbox> findMailboxWithPathLikeTypedQuery(String namespace, Username username, String pathLike) {
@@ -203,45 +183,44 @@ public class JPAMailboxMapper extends JPATransactionalMapper implements MailboxM
     }
     
     @Override
-    public boolean hasChildren(Mailbox mailbox, char delimiter) throws MailboxException, MailboxNotFoundException {
+    public Mono<Boolean> hasChildren(Mailbox mailbox, char delimiter) {
         final String name = mailbox.getName() + delimiter + SQL_WILDCARD_CHAR; 
-        final Long numberOfChildMailboxes;
-
-        numberOfChildMailboxes = (Long) getEntityManager()
-            .createNamedQuery("countMailboxesWithNameLikeWithUser")
-            .setParameter("nameParam", name)
-            .setParameter("namespaceParam", mailbox.getNamespace())
-            .setParameter("userParam", mailbox.getUser().asString())
-            .getSingleResult();
 
-        return numberOfChildMailboxes != null && numberOfChildMailboxes > 0;
+        return Mono.defer(() -> Mono.justOrEmpty((Long) getEntityManager()
+                .createNamedQuery("countMailboxesWithNameLikeWithUser")
+                .setParameter("nameParam", name)
+                .setParameter("namespaceParam", mailbox.getNamespace())
+                .setParameter("userParam", mailbox.getUser().asString())
+                .getSingleResult()))
+            .filter(numberOfChildMailboxes -> numberOfChildMailboxes > 0)
+            .hasElement();
     }
 
     @Override
     public Flux<Mailbox> list() {
-        try {
-            return Flux.fromIterable(getEntityManager()
-                    .createNamedQuery("listMailboxes", JPAMailbox.class)
-                    .getResultList())
-                .map(JPAMailbox::toMailbox);
-        } catch (PersistenceException e) {
-            return Flux.error(new MailboxException("Delete of mailboxes failed", e));
-        } 
+        return Mono.fromCallable(() -> getEntityManager().createNamedQuery("listMailboxes", JPAMailbox.class))
+            .flatMapIterable(TypedQuery::getResultList)
+            .onErrorMap(PersistenceException.class, e -> new MailboxException("Delete of mailboxes failed", e))
+            .map(JPAMailbox::toMailbox);
     }
 
     @Override
-    public ACLDiff updateACL(Mailbox mailbox, MailboxACL.ACLCommand mailboxACLCommand) throws MailboxException {
-        MailboxACL oldACL = mailbox.getACL();
-        MailboxACL newACL = mailbox.getACL().apply(mailboxACLCommand);
-        mailbox.setACL(newACL);
-        return ACLDiff.computeDiff(oldACL, newACL);
+    public Mono<ACLDiff> updateACL(Mailbox mailbox, MailboxACL.ACLCommand mailboxACLCommand) {
+        return Mono.fromCallable(() -> {
+            MailboxACL oldACL = mailbox.getACL();
+            MailboxACL newACL = mailbox.getACL().apply(mailboxACLCommand);
+            mailbox.setACL(newACL);
+            return ACLDiff.computeDiff(oldACL, newACL);
+        });
     }
 
     @Override
-    public ACLDiff setACL(Mailbox mailbox, MailboxACL mailboxACL) throws MailboxException {
-        MailboxACL oldMailboxAcl = mailbox.getACL();
-        mailbox.setACL(mailboxACL);
-        return ACLDiff.computeDiff(oldMailboxAcl, mailboxACL);
+    public Mono<ACLDiff> setACL(Mailbox mailbox, MailboxACL mailboxACL) {
+        return Mono.fromCallable(() -> {
+            MailboxACL oldMailboxAcl = mailbox.getACL();
+            mailbox.setACL(mailboxACL);
+            return ACLDiff.computeDiff(oldMailboxAcl, mailboxACL);
+        });
     }
 
     @Override
diff --git a/mailbox/jpa/src/test/java/org/apache/james/mailbox/jpa/mail/TransactionalMailboxMapper.java b/mailbox/jpa/src/test/java/org/apache/james/mailbox/jpa/mail/TransactionalMailboxMapper.java
index f876158..5b6f9b8 100644
--- a/mailbox/jpa/src/test/java/org/apache/james/mailbox/jpa/mail/TransactionalMailboxMapper.java
+++ b/mailbox/jpa/src/test/java/org/apache/james/mailbox/jpa/mail/TransactionalMailboxMapper.java
@@ -22,8 +22,6 @@ package org.apache.james.mailbox.jpa.mail;
 import org.apache.commons.lang3.NotImplementedException;
 import org.apache.james.core.Username;
 import org.apache.james.mailbox.acl.ACLDiff;
-import org.apache.james.mailbox.exception.MailboxException;
-import org.apache.james.mailbox.exception.MailboxNotFoundException;
 import org.apache.james.mailbox.model.Mailbox;
 import org.apache.james.mailbox.model.MailboxACL;
 import org.apache.james.mailbox.model.MailboxACL.Right;
@@ -32,7 +30,6 @@ import org.apache.james.mailbox.model.MailboxPath;
 import org.apache.james.mailbox.model.UidValidity;
 import org.apache.james.mailbox.model.search.MailboxQuery;
 import org.apache.james.mailbox.store.mail.MailboxMapper;
-import org.apache.james.mailbox.store.transaction.Mapper;
 
 import reactor.core.publisher.Flux;
 import reactor.core.publisher.Mono;
@@ -50,23 +47,23 @@ public class TransactionalMailboxMapper implements MailboxMapper {
     }
 
     @Override
-    public <T> T execute(Transaction<T> transaction) throws MailboxException {
+    public <T> T execute(Transaction<T> transaction) {
         throw new NotImplementedException("not implemented");
     }
 
     @Override
-    public Mailbox create(MailboxPath mailboxPath, UidValidity uidValidity) throws MailboxException {
-        return wrapped.execute(() -> wrapped.create(mailboxPath, uidValidity));
+    public Mono<Mailbox> create(MailboxPath mailboxPath, UidValidity uidValidity) {
+        return wrapped.executeReactive(wrapped.create(mailboxPath, uidValidity));
     }
 
     @Override
-    public MailboxId rename(Mailbox mailbox) throws MailboxException {
-        return wrapped.execute(() -> wrapped.rename(mailbox));
+    public Mono<MailboxId> rename(Mailbox mailbox) {
+        return wrapped.executeReactive(wrapped.rename(mailbox));
     }
 
     @Override
-    public void delete(Mailbox mailbox) throws MailboxException {
-        wrapped.execute(Mapper.toTransaction(() -> wrapped.delete(mailbox)));
+    public Mono<Void> delete(Mailbox mailbox) {
+        return wrapped.executeReactiveVoid(wrapped.delete(mailbox));
     }
 
     @Override
@@ -75,27 +72,27 @@ public class TransactionalMailboxMapper implements MailboxMapper {
     }
 
     @Override
-    public Mailbox findMailboxById(MailboxId mailboxId) throws MailboxException, MailboxNotFoundException {
+    public Mono<Mailbox> findMailboxById(MailboxId mailboxId) {
         return wrapped.findMailboxById(mailboxId);
     }
 
     @Override
-    public Flux<Mailbox> findMailboxWithPathLike(MailboxQuery.UserBound query) throws MailboxException {
+    public Flux<Mailbox> findMailboxWithPathLike(MailboxQuery.UserBound query) {
         return wrapped.findMailboxWithPathLike(query);
     }
 
     @Override
-    public boolean hasChildren(Mailbox mailbox, char delimiter) throws MailboxException, MailboxNotFoundException {
+    public Mono<Boolean> hasChildren(Mailbox mailbox, char delimiter) {
         return wrapped.hasChildren(mailbox, delimiter);
     }
 
     @Override
-    public ACLDiff updateACL(Mailbox mailbox, MailboxACL.ACLCommand mailboxACLCommand) throws MailboxException {
+    public Mono<ACLDiff> updateACL(Mailbox mailbox, MailboxACL.ACLCommand mailboxACLCommand) {
         return wrapped.updateACL(mailbox, mailboxACLCommand);
     }
 
     @Override
-    public ACLDiff setACL(Mailbox mailbox, MailboxACL mailboxACL) throws MailboxException {
+    public Mono<ACLDiff> setACL(Mailbox mailbox, MailboxACL mailboxACL) {
         return wrapped.setACL(mailbox, mailboxACL);
     }
 
diff --git a/mailbox/maildir/src/main/java/org/apache/james/mailbox/maildir/mail/MaildirMailboxMapper.java b/mailbox/maildir/src/main/java/org/apache/james/mailbox/maildir/mail/MaildirMailboxMapper.java
index b0f2238..9e02cf0 100644
--- a/mailbox/maildir/src/main/java/org/apache/james/mailbox/maildir/mail/MaildirMailboxMapper.java
+++ b/mailbox/maildir/src/main/java/org/apache/james/mailbox/maildir/mail/MaildirMailboxMapper.java
@@ -24,6 +24,7 @@ import java.io.IOException;
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.List;
+import java.util.function.Function;
 import java.util.regex.Pattern;
 import java.util.stream.Stream;
 
@@ -76,25 +77,26 @@ public class MaildirMailboxMapper extends NonTransactionalMapper implements Mail
     }
 
     @Override
-    public void delete(Mailbox mailbox) throws MailboxException {
-        String folderName = maildirStore.getFolderName(mailbox);
-        File folder = new File(folderName);
-        if (folder.isDirectory()) {
-            // Shouldn't fail on file deletion, else the mailbox will never be deleted
-            if (mailbox.getName().equals(MailboxConstants.INBOX)) {
-                // We must only delete cur, new, tmp and metadata for top INBOX mailbox.
-                delete(new File(folder, MaildirFolder.CUR), 
-                        new File(folder, MaildirFolder.NEW),
-                        new File(folder, MaildirFolder.TMP),
-                        new File(folder, MaildirFolder.UIDLIST_FILE),
-                        new File(folder, MaildirFolder.VALIDITY_FILE));
-            } else {
-                // We simply delete all the folder for non INBOX mailboxes.
-                delete(folder);
-            }
-        } else {
-            throw new MailboxNotFoundException(mailbox.generateAssociatedPath());
-        }
+    public Mono<Void> delete(Mailbox mailbox) {
+        return Mono.fromCallable(() -> new File(maildirStore.getFolderName(mailbox)))
+            .filter(File::isDirectory)
+            .map(folder -> {
+                // Shouldn't fail on file deletion, else the mailbox will never be deleted
+                if (mailbox.getName().equals(MailboxConstants.INBOX)) {
+                    // We must only delete cur, new, tmp and metadata for top INBOX mailbox.
+                    delete(new File(folder, MaildirFolder.CUR),
+                            new File(folder, MaildirFolder.NEW),
+                            new File(folder, MaildirFolder.TMP),
+                            new File(folder, MaildirFolder.UIDLIST_FILE),
+                            new File(folder, MaildirFolder.VALIDITY_FILE));
+                } else {
+                    // We simply delete all the folder for non INBOX mailboxes.
+                    delete(folder);
+                }
+                return true;
+            })
+            .switchIfEmpty(Mono.error(new MailboxNotFoundException(mailbox.generateAssociatedPath())))
+            .then();
     }
 
     private void delete(File...files) {
@@ -121,156 +123,161 @@ public class MaildirMailboxMapper extends NonTransactionalMapper implements Mail
     }
     
     @Override
-    public Mailbox findMailboxById(MailboxId id) throws MailboxException, MailboxNotFoundException {
+    public Mono<Mailbox> findMailboxById(MailboxId id) {
         if (id == null) {
-            throw new MailboxNotFoundException("null");
+            return Mono.error(new MailboxNotFoundException("null"));
         }
         return list()
             .filter(mailbox -> mailbox.getMailboxId().equals(id))
             .next()
-            .blockOptional()
-            .orElseThrow(() -> new MailboxNotFoundException(id));
+            .switchIfEmpty(Mono.error(new MailboxNotFoundException(id)));
     }
     
     @Override
-    public Flux<Mailbox> findMailboxWithPathLike(MailboxQuery.UserBound query) throws MailboxException {
-        String pathLike = MailboxExpressionBackwardCompatibility.getPathLike(query);
-        final Pattern searchPattern = Pattern.compile("[" + MaildirStore.maildirDelimiter + "]"
-                + pathLike.replace(".", "\\.").replace(MaildirStore.WILDCARD, ".*"));
-        FilenameFilter filter = MaildirMessageName.createRegexFilter(searchPattern);
-        File root = maildirStore.getMailboxRootForUser(query.getFixedUser());
-        File[] folders = root.listFiles(filter);
-        ArrayList<Mailbox> mailboxList = new ArrayList<>();
-        for (File folder : folders) {
-            if (folder.isDirectory()) {
-                Mailbox mailbox = maildirStore.loadMailbox(session, root, query.getFixedNamespace(), query.getFixedUser(), folder.getName());
-                mailboxList.add(mailbox);
+    public Flux<Mailbox> findMailboxWithPathLike(MailboxQuery.UserBound query) {
+        return Mono.fromCallable(() -> {
+            String pathLike = MailboxExpressionBackwardCompatibility.getPathLike(query);
+            final Pattern searchPattern = Pattern.compile("[" + MaildirStore.maildirDelimiter + "]"
+                    + pathLike.replace(".", "\\.").replace(MaildirStore.WILDCARD, ".*"));
+            FilenameFilter filter = MaildirMessageName.createRegexFilter(searchPattern);
+            File root = maildirStore.getMailboxRootForUser(query.getFixedUser());
+            File[] folders = root.listFiles(filter);
+            ArrayList<Mailbox> mailboxList = new ArrayList<>();
+            for (File folder : folders) {
+                if (folder.isDirectory()) {
+                    Mailbox mailbox = maildirStore.loadMailbox(session, root, query.getFixedNamespace(), query.getFixedUser(), folder.getName());
+                    mailboxList.add(mailbox);
+                }
             }
-        }
-        // INBOX is in the root of the folder
-        if (Pattern.matches(pathLike.replace(MaildirStore.WILDCARD, ".*"), MailboxConstants.INBOX)) {
-            Mailbox mailbox = maildirStore.loadMailbox(session, root, query.getFixedNamespace(), query.getFixedUser(), "");
-            mailboxList.add(0, mailbox);
-        }
-        return Flux.fromIterable(mailboxList)
-            .filter(query::matches);
+            // INBOX is in the root of the folder
+            if (Pattern.matches(pathLike.replace(MaildirStore.WILDCARD, ".*"), MailboxConstants.INBOX)) {
+                Mailbox mailbox = maildirStore.loadMailbox(session, root, query.getFixedNamespace(), query.getFixedUser(), "");
+                mailboxList.add(0, mailbox);
+            }
+            return mailboxList;
+        })
+        .flatMapIterable(Function.identity());
     }
 
     @Override
-    public boolean hasChildren(Mailbox mailbox, char delimiter) throws MailboxException, MailboxNotFoundException {
-        List<Mailbox> mailboxes = findMailboxWithPathLike(
+    public Mono<Boolean> hasChildren(Mailbox mailbox, char delimiter) {
+        return findMailboxWithPathLike(
             MailboxQuery.builder()
             .userAndNamespaceFrom(mailbox.generateAssociatedPath())
             .expression(new PrefixedWildcard(mailbox.getName() + delimiter))
             .build()
             .asUserBound())
-            .collectList().block();
-        return mailboxes.size() > 0;
+            .hasElements();
     }
 
     @Override
-    public Mailbox create(MailboxPath mailboxPath, UidValidity uidValidity) throws MailboxException {
-        MaildirId maildirId = MaildirId.random();
-        Mailbox mailbox = new Mailbox(mailboxPath, uidValidity, maildirId);
-        MaildirFolder folder = maildirStore.createMaildirFolder(mailbox);
-
-        if (!folder.exists()) {
-            boolean folderExist = folder.getRootFile().exists();
-            if (!folderExist && !folder.getRootFile().mkdirs()) {
-                throw new MailboxException("Failed to save Mailbox " + mailbox);
-            }
+    public Mono<Mailbox> create(MailboxPath mailboxPath, UidValidity uidValidity) {
+        return Mono.fromCallable(() -> {
+            MaildirId maildirId = MaildirId.random();
+            Mailbox mailbox = new Mailbox(mailboxPath, uidValidity, maildirId);
+            MaildirFolder folder = maildirStore.createMaildirFolder(mailbox);
+
+            if (!folder.exists()) {
+                boolean folderExist = folder.getRootFile().exists();
+                if (!folderExist && !folder.getRootFile().mkdirs()) {
+                    throw new MailboxException("Failed to save Mailbox " + mailbox);
+                }
 
-            boolean isCreated = folder.getCurFolder().mkdir()
-                && folder.getNewFolder().mkdir()
-                && folder.getTmpFolder().mkdir();
-            if (!isCreated) {
-                throw new MailboxException("Failed to save Mailbox " + mailbox, new IOException("Needed folder structure can not be created"));
+                boolean isCreated = folder.getCurFolder().mkdir()
+                        && folder.getNewFolder().mkdir()
+                        && folder.getTmpFolder().mkdir();
+                if (!isCreated) {
+                    throw new MailboxException("Failed to save Mailbox " + mailbox, new IOException("Needed folder structure can not be created"));
+                }
             }
-        }
 
-        try {
-            folder.setUidValidity(mailbox.getUidValidity());
-            folder.setMailboxId(maildirId);
-        } catch (IOException ioe) {
-            throw new MailboxException("Failed to save Mailbox " + mailbox, ioe);
+            try {
+                folder.setUidValidity(mailbox.getUidValidity());
+                folder.setMailboxId(maildirId);
+            } catch (IOException ioe) {
+                throw new MailboxException("Failed to save Mailbox " + mailbox, ioe);
 
-        }
-        folder.setACL(mailbox.getACL());
+            }
+            folder.setACL(mailbox.getACL());
 
-        return mailbox;
+            return mailbox;
+        });
     }
 
     @Override
-    public MailboxId rename(Mailbox mailbox) throws MailboxException {
+    public Mono<MailboxId> rename(Mailbox mailbox) {
         MaildirId maildirId = (MaildirId) mailbox.getMailboxId();
 
-        Mailbox originalMailbox = findMailboxById(mailbox.getMailboxId());
-        MaildirFolder folder = maildirStore.createMaildirFolder(mailbox);
-        // equals with null check
-        if (originalMailbox.getName() == null ? mailbox.getName() != null : !originalMailbox.getName().equals(mailbox.getName())) {
-            if (folder.exists()) {
-                throw new MailboxExistsException(mailbox.getName());
-            }
-
-            MaildirFolder originalFolder = maildirStore.createMaildirFolder(originalMailbox);
-            // renaming the INBOX means to move its contents to the new folder
-            if (originalMailbox.getName().equals(MailboxConstants.INBOX)) {
-                try {
-                    File inboxFolder = originalFolder.getRootFile();
-                    File newFolder = folder.getRootFile();
-                    FileUtils.forceMkdir(newFolder);
-                    if (!originalFolder.getCurFolder().renameTo(folder.getCurFolder())) {
-                        throw new IOException("Could not rename folder " + originalFolder.getCurFolder() + " to " + folder.getCurFolder());
-                    }
-                    if (!originalFolder.getMailboxIdFile().renameTo(folder.getMailboxIdFile())) {
-                        throw new IOException("Could not rename folder " + originalFolder.getCurFolder() + " to " + folder.getCurFolder());
+        return findMailboxById(mailbox.getMailboxId())
+            .flatMap(originalMailbox -> Mono.fromCallable(() -> {
+                MaildirFolder folder = maildirStore.createMaildirFolder(mailbox);
+                // equals with null check
+                if (originalMailbox.getName() == null ? mailbox.getName() != null : !originalMailbox.getName().equals(mailbox.getName())) {
+                    if (folder.exists()) {
+                        throw new MailboxExistsException(mailbox.getName());
                     }
-                    if (!originalFolder.getNewFolder().renameTo(folder.getNewFolder())) {
-                        throw new IOException("Could not rename folder " + originalFolder.getNewFolder() + " to " + folder.getNewFolder());
-                    }
-                    if (!originalFolder.getTmpFolder().renameTo(folder.getTmpFolder())) {
-                        throw new IOException("Could not rename folder " + originalFolder.getTmpFolder() + " to " + folder.getTmpFolder());
-                    }
-                    File oldUidListFile = new File(inboxFolder, MaildirFolder.UIDLIST_FILE);
-                    File newUidListFile = new File(newFolder, MaildirFolder.UIDLIST_FILE);
-                    if (!oldUidListFile.renameTo(newUidListFile)) {
-                        throw new IOException("Could not rename file " + oldUidListFile + " to " + newUidListFile);
-                    }
-                    File oldValidityFile = new File(inboxFolder, MaildirFolder.VALIDITY_FILE);
-                    File newValidityFile = new File(newFolder, MaildirFolder.VALIDITY_FILE);
-                    if (!oldValidityFile.renameTo(newValidityFile)) {
-                        throw new IOException("Could not rename file " + oldValidityFile + " to " + newValidityFile);
+
+                    MaildirFolder originalFolder = maildirStore.createMaildirFolder(originalMailbox);
+                    // renaming the INBOX means to move its contents to the new folder
+                    if (originalMailbox.getName().equals(MailboxConstants.INBOX)) {
+                        try {
+                            File inboxFolder = originalFolder.getRootFile();
+                            File newFolder = folder.getRootFile();
+                            FileUtils.forceMkdir(newFolder);
+                            if (!originalFolder.getCurFolder().renameTo(folder.getCurFolder())) {
+                                throw new IOException("Could not rename folder " + originalFolder.getCurFolder() + " to " + folder.getCurFolder());
+                            }
+                            if (!originalFolder.getMailboxIdFile().renameTo(folder.getMailboxIdFile())) {
+                                throw new IOException("Could not rename folder " + originalFolder.getCurFolder() + " to " + folder.getCurFolder());
+                            }
+                            if (!originalFolder.getNewFolder().renameTo(folder.getNewFolder())) {
+                                throw new IOException("Could not rename folder " + originalFolder.getNewFolder() + " to " + folder.getNewFolder());
+                            }
+                            if (!originalFolder.getTmpFolder().renameTo(folder.getTmpFolder())) {
+                                throw new IOException("Could not rename folder " + originalFolder.getTmpFolder() + " to " + folder.getTmpFolder());
+                            }
+                            File oldUidListFile = new File(inboxFolder, MaildirFolder.UIDLIST_FILE);
+                            File newUidListFile = new File(newFolder, MaildirFolder.UIDLIST_FILE);
+                            if (!oldUidListFile.renameTo(newUidListFile)) {
+                                throw new IOException("Could not rename file " + oldUidListFile + " to " + newUidListFile);
+                            }
+                            File oldValidityFile = new File(inboxFolder, MaildirFolder.VALIDITY_FILE);
+                            File newValidityFile = new File(newFolder, MaildirFolder.VALIDITY_FILE);
+                            if (!oldValidityFile.renameTo(newValidityFile)) {
+                                throw new IOException("Could not rename file " + oldValidityFile + " to " + newValidityFile);
+                            }
+                            // recreate the INBOX folders, uidvalidity and uidlist will
+                            // automatically be recreated later
+                            FileUtils.forceMkdir(originalFolder.getCurFolder());
+                            FileUtils.forceMkdir(originalFolder.getNewFolder());
+                            FileUtils.forceMkdir(originalFolder.getTmpFolder());
+                            originalFolder.setMailboxId(MaildirId.random());
+                        } catch (IOException e) {
+                            throw new MailboxException("Failed to save Mailbox " + mailbox, e);
+                        }
+                    } else {
+                        if (!originalFolder.getRootFile().renameTo(folder.getRootFile())) {
+                            throw new MailboxException("Failed to save Mailbox " + mailbox,
+                                    new IOException("Could not rename folder " + originalFolder));
+                        }
                     }
-                    // recreate the INBOX folders, uidvalidity and uidlist will
-                    // automatically be recreated later
-                    FileUtils.forceMkdir(originalFolder.getCurFolder());
-                    FileUtils.forceMkdir(originalFolder.getNewFolder());
-                    FileUtils.forceMkdir(originalFolder.getTmpFolder());
-                    originalFolder.setMailboxId(MaildirId.random());
-                } catch (IOException e) {
-                    throw new MailboxException("Failed to save Mailbox " + mailbox, e);
                 }
-            } else {
-                if (!originalFolder.getRootFile().renameTo(folder.getRootFile())) {
-                    throw new MailboxException("Failed to save Mailbox " + mailbox,
-                        new IOException("Could not rename folder " + originalFolder));
-                }
-            }
-        }
-        folder.setACL(mailbox.getACL());
+                folder.setACL(mailbox.getACL());
 
-        return maildirId;
+                return maildirId;
+            }));
     }
 
     @Override
     public Flux<Mailbox> list() {
-        File maildirRoot = maildirStore.getMaildirRoot();
-        return Mono.fromCallable(maildirStore::getMaildirLocation)
-            .filter(dir -> dir.endsWith("/" + MaildirStore.PATH_DOMAIN + "/" + MaildirStore.PATH_USER))
-            .map(ignored -> Arrays.stream(maildirRoot.listFiles())
-                .flatMap(Throwing.<File, Stream<Mailbox>>function(domain -> visitUsersForMailboxList(domain, domain.listFiles()).stream()).sneakyThrow()))
-            .switchIfEmpty(Mono.fromCallable(() -> visitUsersForMailboxList(null, maildirRoot.listFiles()).stream()))
-            .flatMapIterable(mailboxes -> mailboxes.collect(Guavate.toImmutableList()));
+       File maildirRoot = maildirStore.getMaildirRoot();
+
+       return Mono.fromCallable(maildirStore::getMaildirLocation)
+           .filter(dir -> dir.endsWith("/" + MaildirStore.PATH_DOMAIN + "/" + MaildirStore.PATH_USER))
+               .map(ignored -> Arrays.stream(maildirRoot.listFiles())
+                       .flatMap(Throwing.<File, Stream<Mailbox>>function(domain -> visitUsersForMailboxList(domain, domain.listFiles()).stream()).sneakyThrow()))
+               .switchIfEmpty(Mono.fromCallable(() -> visitUsersForMailboxList(null, maildirRoot.listFiles()).stream()))
+               .flatMapIterable(mailboxes -> mailboxes.collect(Guavate.toImmutableList()));
     }
 
     @Override
@@ -280,7 +287,7 @@ public class MaildirMailboxMapper extends NonTransactionalMapper implements Mail
 
     private List<Mailbox> visitUsersForMailboxList(File domain, File[] users) throws MailboxException {
         ImmutableList.Builder<Mailbox> mailboxList = ImmutableList.builder();
-        
+
         for (File user: users) {
             String userName = retrieveUsername(domain, user);
 
@@ -292,16 +299,17 @@ public class MaildirMailboxMapper extends NonTransactionalMapper implements Mail
             } catch (MailboxException e) {
                 //do nothing, we should still be able to list the mailboxes even if INBOX does not exist
             }
-            
+
             // List all INBOX sub folders.
             File[] mailboxes = user.listFiles(pathname -> pathname.getName().startsWith("."));
-            
+
             for (File mailbox: mailboxes) {
                 MailboxPath mailboxPath = MailboxPath.forUser(Username.of(userName),
                     mailbox.getName().substring(1));
                 mailboxList.add(maildirStore.loadMailbox(session, mailboxPath));
             }
         }
+
         return mailboxList.build();
     }
 
@@ -314,22 +322,26 @@ public class MaildirMailboxMapper extends NonTransactionalMapper implements Mail
     }
 
     @Override
-    public ACLDiff updateACL(Mailbox mailbox, MailboxACL.ACLCommand mailboxACLCommand) throws MailboxException {
-        MaildirFolder folder = maildirStore.createMaildirFolder(mailbox);
-        MailboxACL oldACL = mailbox.getACL();
-        MailboxACL newACL = mailbox.getACL().apply(mailboxACLCommand);
-        folder.setACL(newACL);
-        mailbox.setACL(newACL);
-        return ACLDiff.computeDiff(oldACL, newACL);
+    public Mono<ACLDiff> updateACL(Mailbox mailbox, MailboxACL.ACLCommand mailboxACLCommand) {
+        return Mono.fromCallable(() -> {
+            MaildirFolder folder = maildirStore.createMaildirFolder(mailbox);
+            MailboxACL oldACL = mailbox.getACL();
+            MailboxACL newACL = mailbox.getACL().apply(mailboxACLCommand);
+            folder.setACL(newACL);
+            mailbox.setACL(newACL);
+            return ACLDiff.computeDiff(oldACL, newACL);
+        });
     }
 
     @Override
-    public ACLDiff setACL(Mailbox mailbox, MailboxACL mailboxACL) throws MailboxException {
-        MailboxACL oldAcl = mailbox.getACL();
-        MaildirFolder folder = maildirStore.createMaildirFolder(mailbox);
-        folder.setACL(mailboxACL);
-        mailbox.setACL(mailboxACL);
-        return ACLDiff.computeDiff(oldAcl, mailboxACL);
+    public Mono<ACLDiff> setACL(Mailbox mailbox, MailboxACL mailboxACL) {
+        return Mono.fromCallable(() -> {
+            MailboxACL oldAcl = mailbox.getACL();
+            MaildirFolder folder = maildirStore.createMaildirFolder(mailbox);
+            folder.setACL(mailboxACL);
+            mailbox.setACL(mailboxACL);
+            return ACLDiff.computeDiff(oldAcl, mailboxACL);
+        });
     }
 
     @Override
diff --git a/mailbox/maildir/src/test/java/org/apache/james/mailbox/maildir/DomainUserMaildirMailboxManagerTest.java b/mailbox/maildir/src/test/java/org/apache/james/mailbox/maildir/DomainUserMaildirMailboxManagerTest.java
index e7f5a42..c54dd2c 100644
--- a/mailbox/maildir/src/test/java/org/apache/james/mailbox/maildir/DomainUserMaildirMailboxManagerTest.java
+++ b/mailbox/maildir/src/test/java/org/apache/james/mailbox/maildir/DomainUserMaildirMailboxManagerTest.java
@@ -47,6 +47,11 @@ class DomainUserMaildirMailboxManagerTest extends MailboxManagerTest<StoreMailbo
         protected void renameMailboxByIdShouldChangeTheMailboxPathOfAMailbox() {
         }
 
+        @Disabled("MAILBOX-389 Mailbox rename fails with Maildir")
+        @Test
+        protected void renameMailboxShouldChangeTheMailboxPathOfTheChildMailbox() {
+        }
+
         @Disabled("MAILBOX-393 mailboxId support for mailDir is partial")
         @Test
         protected void user1ShouldBeAbleToDeleteSubmailboxByid() {
diff --git a/mailbox/memory/src/main/java/org/apache/james/mailbox/inmemory/InMemoryMailboxSessionMapperFactory.java b/mailbox/memory/src/main/java/org/apache/james/mailbox/inmemory/InMemoryMailboxSessionMapperFactory.java
index 3513c66..42967ee 100644
--- a/mailbox/memory/src/main/java/org/apache/james/mailbox/inmemory/InMemoryMailboxSessionMapperFactory.java
+++ b/mailbox/memory/src/main/java/org/apache/james/mailbox/inmemory/InMemoryMailboxSessionMapperFactory.java
@@ -87,7 +87,7 @@ public class InMemoryMailboxSessionMapperFactory extends MailboxSessionMapperFac
     }
 
     public void deleteAll() throws MailboxException {
-        ((InMemoryMailboxMapper) mailboxMapper).deleteAll();
+        ((InMemoryMailboxMapper) mailboxMapper).deleteAll().block();
         ((InMemoryMessageMapper) messageMapper).deleteAll();
         ((InMemorySubscriptionMapper) subscriptionMapper).deleteAll();
     }
diff --git a/mailbox/memory/src/main/java/org/apache/james/mailbox/inmemory/mail/InMemoryMailboxMapper.java b/mailbox/memory/src/main/java/org/apache/james/mailbox/inmemory/mail/InMemoryMailboxMapper.java
index 1606798..0f76a8f 100644
--- a/mailbox/memory/src/main/java/org/apache/james/mailbox/inmemory/mail/InMemoryMailboxMapper.java
+++ b/mailbox/memory/src/main/java/org/apache/james/mailbox/inmemory/mail/InMemoryMailboxMapper.java
@@ -21,6 +21,7 @@ package org.apache.james.mailbox.inmemory.mail;
 import java.util.Optional;
 import java.util.concurrent.ConcurrentHashMap;
 import java.util.concurrent.atomic.AtomicLong;
+import java.util.function.Function;
 
 import org.apache.james.core.Username;
 import org.apache.james.mailbox.acl.ACLDiff;
@@ -55,67 +56,61 @@ public class InMemoryMailboxMapper implements MailboxMapper {
     }
 
     @Override
-    public void delete(Mailbox mailbox) throws MailboxException {
-        mailboxesByPath.remove(mailbox.generateAssociatedPath());
+    public Mono<Void> delete(Mailbox mailbox) {
+        return Mono.fromRunnable(() -> mailboxesByPath.remove(mailbox.generateAssociatedPath()));
     }
 
-    public void deleteAll() throws MailboxException {
-        mailboxesByPath.clear();
+    public Mono<Void> deleteAll() {
+        return Mono.fromRunnable(mailboxesByPath::clear);
     }
 
     @Override
-    public synchronized Mono<Mailbox> findMailboxByPath(MailboxPath path) {
-        Mailbox result = mailboxesByPath.get(path);
-        return Mono.justOrEmpty(result)
+    public Mono<Mailbox> findMailboxByPath(MailboxPath path) {
+        return Mono.defer(() -> Mono.justOrEmpty(mailboxesByPath.get(path)))
             .map(Mailbox::new);
     }
 
     @Override
-    public synchronized Mailbox findMailboxById(MailboxId id) throws MailboxException {
-        InMemoryId mailboxId = (InMemoryId) id;
-        for (Mailbox mailbox: mailboxesByPath.values()) {
-            if (mailbox.getMailboxId().equals(mailboxId)) {
-                return new Mailbox(mailbox);
-            }
-        }
-        throw new MailboxNotFoundException(mailboxId);
+    public Mono<Mailbox> findMailboxById(MailboxId id) {
+        return Mono.fromCallable(mailboxesByPath::values)
+            .flatMapIterable(Function.identity())
+            .filter(mailbox -> mailbox.getMailboxId().equals(id))
+            .next()
+            .map(Mailbox::new)
+            .switchIfEmpty(Mono.error(() -> new MailboxNotFoundException(id)));
     }
 
     @Override
     public Flux<Mailbox> findMailboxWithPathLike(MailboxQuery.UserBound query) {
-        return Flux.fromIterable(mailboxesByPath.values())
-            .filter(query::matches)
-            .map(Mailbox::new);
+        return Mono.fromCallable(mailboxesByPath::values)
+                .flatMapIterable(Function.identity())
+                .filter(query::matches)
+                .map(Mailbox::new);
     }
 
     @Override
-    public Mailbox create(MailboxPath mailboxPath, UidValidity uidValidity) throws MailboxException {
+    public Mono<Mailbox> create(MailboxPath mailboxPath, UidValidity uidValidity) {
         InMemoryId id = InMemoryId.of(mailboxIdGenerator.incrementAndGet());
         Mailbox mailbox = new Mailbox(mailboxPath, uidValidity, id);
 
-        saveMailbox(mailbox);
-
-        return mailbox;
+        return saveMailbox(mailbox)
+            .thenReturn(mailbox);
     }
 
     @Override
-    public MailboxId rename(Mailbox mailbox) throws MailboxException {
+    public Mono<MailboxId> rename(Mailbox mailbox) {
         Preconditions.checkNotNull(mailbox.getMailboxId(), "A mailbox we want to rename should have a defined mailboxId");
 
         InMemoryId id = (InMemoryId) mailbox.getMailboxId();
-        Mailbox mailboxWithPreviousName = findMailboxById(id);
-
-        saveMailbox(mailbox);
-        mailboxesByPath.remove(mailboxWithPreviousName.generateAssociatedPath());
-
-        return mailbox.getMailboxId();
+        return findMailboxById(id)
+            .flatMap(mailboxWithPreviousName -> saveMailbox(mailbox)
+                .then(Mono.fromCallable(() -> mailboxesByPath.remove(mailboxWithPreviousName.generateAssociatedPath()))))
+            .thenReturn(mailbox.getMailboxId());
     }
 
-    private void saveMailbox(Mailbox mailbox) throws MailboxException {
-        Mailbox previousMailbox = mailboxesByPath.putIfAbsent(mailbox.generateAssociatedPath(), mailbox);
-        if (previousMailbox != null) {
-            throw new MailboxExistsException(mailbox.getName());
-        }
+    private Mono<Void> saveMailbox(Mailbox mailbox) {
+        return Mono.defer(() -> Mono.justOrEmpty(mailboxesByPath.putIfAbsent(mailbox.generateAssociatedPath(), mailbox)))
+            .flatMap(ignored -> Mono.error(new MailboxExistsException(mailbox.getName())));
     }
 
     @Override
@@ -124,11 +119,12 @@ public class InMemoryMailboxMapper implements MailboxMapper {
     }
 
     @Override
-    public boolean hasChildren(Mailbox mailbox, char delimiter) throws MailboxException {
+    public Mono<Boolean> hasChildren(Mailbox mailbox, char delimiter) {
         String mailboxName = mailbox.getName() + delimiter;
-        return mailboxesByPath.values()
-            .stream()
-            .anyMatch(box -> belongsToSameUser(mailbox, box) && box.getName().startsWith(mailboxName));
+        return Mono.fromCallable(mailboxesByPath::values)
+            .flatMapIterable(Function.identity())
+            .filter(box -> belongsToSameUser(mailbox, box) && box.getName().startsWith(mailboxName))
+            .hasElements();
     }
 
     private boolean belongsToSameUser(Mailbox mailbox, Mailbox otherMailbox) {
@@ -138,7 +134,8 @@ public class InMemoryMailboxMapper implements MailboxMapper {
 
     @Override
     public Flux<Mailbox> list() {
-        return Flux.fromIterable(mailboxesByPath.values());
+        return Mono.fromCallable(mailboxesByPath::values)
+            .flatMapIterable(Function.identity());
     }
 
     @Override
@@ -147,23 +144,28 @@ public class InMemoryMailboxMapper implements MailboxMapper {
     }
 
     @Override
-    public ACLDiff updateACL(Mailbox mailbox, MailboxACL.ACLCommand mailboxACLCommand) throws MailboxException {
-        MailboxACL oldACL = mailbox.getACL();
-        MailboxACL newACL = mailbox.getACL().apply(mailboxACLCommand);
-        mailboxesByPath.get(mailbox.generateAssociatedPath()).setACL(newACL);
-        return ACLDiff.computeDiff(oldACL, newACL);
+    public Mono<ACLDiff> updateACL(Mailbox mailbox, MailboxACL.ACLCommand mailboxACLCommand) {
+        return Mono.fromCallable(() -> {
+            MailboxACL oldACL = mailbox.getACL();
+            MailboxACL newACL = mailbox.getACL().apply(mailboxACLCommand);
+            mailboxesByPath.get(mailbox.generateAssociatedPath()).setACL(newACL);
+            return ACLDiff.computeDiff(oldACL, newACL);
+        });
     }
 
     @Override
-    public ACLDiff setACL(Mailbox mailbox, MailboxACL mailboxACL) throws MailboxException {
-        MailboxACL oldMailboxAcl = mailbox.getACL();
-        mailboxesByPath.get(mailbox.generateAssociatedPath()).setACL(mailboxACL);
-        return ACLDiff.computeDiff(oldMailboxAcl, mailboxACL);
+    public Mono<ACLDiff> setACL(Mailbox mailbox, MailboxACL mailboxACL) {
+        return Mono.fromCallable(() -> {
+            MailboxACL oldMailboxAcl = mailbox.getACL();
+            mailboxesByPath.get(mailbox.generateAssociatedPath()).setACL(mailboxACL);
+            return ACLDiff.computeDiff(oldMailboxAcl, mailboxACL);
+        });
     }
 
     @Override
     public Flux<Mailbox> findNonPersonalMailboxes(Username userName, Right right) {
-        return Flux.fromIterable(mailboxesByPath.values())
+        return Mono.fromCallable(mailboxesByPath::values)
+            .flatMapIterable(Function.identity())
             .filter(mailbox -> hasRightOn(mailbox, userName, right));
     }
 
diff --git a/mailbox/memory/src/main/java/org/apache/james/mailbox/inmemory/mail/InMemoryMessageIdMapper.java b/mailbox/memory/src/main/java/org/apache/james/mailbox/inmemory/mail/InMemoryMessageIdMapper.java
index 4c8e0af..2fe2bee 100644
--- a/mailbox/memory/src/main/java/org/apache/james/mailbox/inmemory/mail/InMemoryMessageIdMapper.java
+++ b/mailbox/memory/src/main/java/org/apache/james/mailbox/inmemory/mail/InMemoryMessageIdMapper.java
@@ -36,6 +36,7 @@ import org.apache.james.mailbox.model.MessageId;
 import org.apache.james.mailbox.model.MessageRange;
 import org.apache.james.mailbox.model.UpdatedFlags;
 import org.apache.james.mailbox.store.FlagsUpdateCalculator;
+import org.apache.james.mailbox.store.MailboxReactorUtils;
 import org.apache.james.mailbox.store.mail.MailboxMapper;
 import org.apache.james.mailbox.store.mail.MessageIdMapper;
 import org.apache.james.mailbox.store.mail.MessageMapper;
@@ -81,7 +82,7 @@ public class InMemoryMessageIdMapper implements MessageIdMapper {
 
     @Override
     public void save(MailboxMessage mailboxMessage) throws MailboxException {
-        Mailbox mailbox = mailboxMapper.findMailboxById(mailboxMessage.getMailboxId());
+        Mailbox mailbox = MailboxReactorUtils.block(mailboxMapper.findMailboxById(mailboxMessage.getMailboxId()));
         messageMapper.save(mailbox, mailboxMessage);
     }
 
@@ -98,7 +99,7 @@ public class InMemoryMessageIdMapper implements MessageIdMapper {
         find(ImmutableList.of(messageId), MessageMapper.FetchType.Metadata)
             .forEach(Throwing.consumer(
                 message -> messageMapper.delete(
-                    mailboxMapper.findMailboxById(message.getMailboxId()),
+                    MailboxReactorUtils.block(mailboxMapper.findMailboxById(message.getMailboxId())),
                     message)));
     }
 
@@ -109,7 +110,7 @@ public class InMemoryMessageIdMapper implements MessageIdMapper {
             .filter(message -> mailboxIds.contains(message.getMailboxId()))
             .forEach(Throwing.consumer(
                 message -> messageMapper.delete(
-                    mailboxMapper.findMailboxById(message.getMailboxId()),
+                    MailboxReactorUtils.block(mailboxMapper.findMailboxById(message.getMailboxId())),
                     message)));
     }
 
@@ -140,7 +141,7 @@ public class InMemoryMessageIdMapper implements MessageIdMapper {
             }
             return Pair.of(message.getMailboxId(),
                 messageMapper.updateFlags(
-                    mailboxMapper.findMailboxById(message.getMailboxId()),
+                    MailboxReactorUtils.block(mailboxMapper.findMailboxById(message.getMailboxId())),
                     flagsUpdateCalculator,
                     message.getUid().toRange())
                     .next());
diff --git a/mailbox/plugin/deleted-messages-vault/src/main/java/org/apache/james/vault/DeletedMessageVaultHook.java b/mailbox/plugin/deleted-messages-vault/src/main/java/org/apache/james/vault/DeletedMessageVaultHook.java
index ff536a8..99858f1 100644
--- a/mailbox/plugin/deleted-messages-vault/src/main/java/org/apache/james/vault/DeletedMessageVaultHook.java
+++ b/mailbox/plugin/deleted-messages-vault/src/main/java/org/apache/james/vault/DeletedMessageVaultHook.java
@@ -24,7 +24,6 @@ import java.time.ZoneOffset;
 import java.time.ZonedDateTime;
 import java.util.List;
 import java.util.Objects;
-import java.util.Optional;
 
 import javax.inject.Inject;
 
@@ -33,14 +32,12 @@ import org.apache.james.core.Username;
 import org.apache.james.mailbox.MailboxSession;
 import org.apache.james.mailbox.MetadataWithMailboxId;
 import org.apache.james.mailbox.SessionProvider;
-import org.apache.james.mailbox.exception.MailboxException;
 import org.apache.james.mailbox.extension.PreDeletionHook;
 import org.apache.james.mailbox.model.Mailbox;
 import org.apache.james.mailbox.model.MailboxId;
 import org.apache.james.mailbox.model.MessageId;
 import org.apache.james.mailbox.store.MailboxSessionMapperFactory;
 import org.apache.james.mailbox.store.mail.MessageMapper;
-import org.apache.james.mailbox.store.mail.model.MailboxMessage;
 import org.reactivestreams.Publisher;
 
 import com.github.fge.lambdas.Throwing;
@@ -130,32 +127,30 @@ public class DeletedMessageVaultHook implements PreDeletionHook {
         Preconditions.checkNotNull(deleteOperation);
 
         return groupMetadataByOwnerAndMessageId(deleteOperation)
-            .flatMap(Throwing.function(this::appendToTheVault).sneakyThrow())
+            .flatMap(this::appendToTheVault)
             .then();
     }
 
     private Mono<Void> appendToTheVault(DeletedMessageMailboxContext deletedMessageMailboxContext) {
-        Optional<MailboxMessage> maybeMailboxMessage = mapperFactory.getMessageIdMapper(session)
-            .find(ImmutableList.of(deletedMessageMailboxContext.getMessageId()), MessageMapper.FetchType.Full).stream()
-            .findFirst();
-
-        return maybeMailboxMessage.map(Throwing.function(mailboxMessage -> Pair.of(mailboxMessage,
+        return mapperFactory.getMessageIdMapper(session)
+            .findReactive(ImmutableList.of(deletedMessageMailboxContext.getMessageId()), MessageMapper.FetchType.Full)
+            .next()
+            .map(Throwing.function(mailboxMessage -> Pair.of(mailboxMessage,
                 deletedMessageConverter.convert(deletedMessageMailboxContext, mailboxMessage,
                     ZonedDateTime.ofInstant(clock.instant(), ZoneOffset.UTC)))))
-            .map(Throwing.function(pairs -> Mono.from(deletedMessageVault
-                .append(pairs.getRight(), pairs.getLeft().getFullContent()))))
-            .orElse(Mono.empty());
+            .flatMap(Throwing.function(pairs -> Mono.from(deletedMessageVault
+                .append(pairs.getRight(), pairs.getLeft().getFullContent()))));
     }
 
     private Flux<DeletedMessageMailboxContext> groupMetadataByOwnerAndMessageId(DeleteOperation deleteOperation) {
         return Flux.fromIterable(deleteOperation.getDeletionMetadataList())
             .groupBy(MetadataWithMailboxId::getMailboxId)
-            .flatMap(Throwing.function(this::addOwnerToMetadata).sneakyThrow())
+            .flatMap(this::addOwnerToMetadata)
             .groupBy(this::toMessageIdUserPair)
             .flatMap(groupFlux -> groupFlux.reduce(DeletedMessageMailboxContext::combine));
     }
 
-    private Flux<DeletedMessageMailboxContext> addOwnerToMetadata(GroupedFlux<MailboxId, MetadataWithMailboxId> groupedFlux) throws MailboxException {
+    private Flux<DeletedMessageMailboxContext> addOwnerToMetadata(GroupedFlux<MailboxId, MetadataWithMailboxId> groupedFlux) {
         return retrieveMailboxUser(groupedFlux.key())
             .flatMapMany(owner -> groupedFlux.map(metadata ->
                 new DeletedMessageMailboxContext(metadata.getMessageMetaData().getMessageId(), owner, ImmutableList.of(metadata.getMailboxId()))));
@@ -167,7 +162,7 @@ public class DeletedMessageVaultHook implements PreDeletionHook {
 
     private Mono<Username> retrieveMailboxUser(MailboxId mailboxId) {
         return mapperFactory.getMailboxMapper(session)
-            .findMailboxByIdReactive(mailboxId)
+            .findMailboxById(mailboxId)
             .map(Mailbox::getUser);
     }
-}
\ No newline at end of file
+}
diff --git a/mailbox/plugin/spamassassin/src/main/java/org/apache/james/mailbox/spamassassin/SpamAssassinListener.java b/mailbox/plugin/spamassassin/src/main/java/org/apache/james/mailbox/spamassassin/SpamAssassinListener.java
index 4ccb808..a842a30 100644
--- a/mailbox/plugin/spamassassin/src/main/java/org/apache/james/mailbox/spamassassin/SpamAssassinListener.java
+++ b/mailbox/plugin/spamassassin/src/main/java/org/apache/james/mailbox/spamassassin/SpamAssassinListener.java
@@ -102,9 +102,9 @@ public class SpamAssassinListener implements SpamEventListener {
         }
     }
 
-    private void handleAdded(Event event, MailboxSession session, Added addedEvent) throws MailboxException {
+    private void handleAdded(Event event, MailboxSession session, Added addedEvent) {
         if (isAppendedToInbox(addedEvent)) {
-            Mailbox mailbox = mapperFactory.getMailboxMapper(session).findMailboxById(addedEvent.getMailboxId());
+            Mailbox mailbox = mapperFactory.getMailboxMapper(session).findMailboxById(addedEvent.getMailboxId()).block();
             MessageMapper messageMapper = mapperFactory.getMessageMapper(session);
 
             List<InputStream> contents = MessageRange.toRanges(addedEvent.getUids())
diff --git a/mailbox/plugin/spamassassin/src/test/java/org/apache/james/mailbox/spamassassin/SpamAssassinListenerTest.java b/mailbox/plugin/spamassassin/src/test/java/org/apache/james/mailbox/spamassassin/SpamAssassinListenerTest.java
index 4227d3b..e159800 100644
--- a/mailbox/plugin/spamassassin/src/test/java/org/apache/james/mailbox/spamassassin/SpamAssassinListenerTest.java
+++ b/mailbox/plugin/spamassassin/src/test/java/org/apache/james/mailbox/spamassassin/SpamAssassinListenerTest.java
@@ -86,14 +86,14 @@ class SpamAssassinListenerTest {
         spamAssassin = mock(SpamAssassin.class);
         mapperFactory = mailboxManager.getMapperFactory();
         MailboxMapper mailboxMapper = mapperFactory.createMailboxMapper(MAILBOX_SESSION);
-        inbox = mailboxMapper.create(MailboxPath.forUser(USER, DefaultMailboxes.INBOX), UID_VALIDITY);
-        mailbox1 = mailboxMapper.create(MailboxPath.forUser(USER, "mailbox1"), UID_VALIDITY);
-        mailbox2 = mailboxMapper.create(MailboxPath.forUser(USER, "mailbox2"), UID_VALIDITY);
+        inbox = mailboxMapper.create(MailboxPath.forUser(USER, DefaultMailboxes.INBOX), UID_VALIDITY).block();
+        mailbox1 = mailboxMapper.create(MailboxPath.forUser(USER, "mailbox1"), UID_VALIDITY).block();
+        mailbox2 = mailboxMapper.create(MailboxPath.forUser(USER, "mailbox2"), UID_VALIDITY).block();
         mailboxId1 = mailbox1.getMailboxId();
         mailboxId2 = mailbox2.getMailboxId();
-        spamMailboxId = mailboxMapper.create(MailboxPath.forUser(USER, "Spam"), UID_VALIDITY).getMailboxId();
-        spamCapitalMailboxId = mailboxMapper.create(MailboxPath.forUser(USER, "SPAM"), UID_VALIDITY).getMailboxId();
-        trashMailboxId = mailboxMapper.create(MailboxPath.forUser(USER, "Trash"), UID_VALIDITY).getMailboxId();
+        spamMailboxId = mailboxMapper.create(MailboxPath.forUser(USER, "Spam"), UID_VALIDITY).block().getMailboxId();
+        spamCapitalMailboxId = mailboxMapper.create(MailboxPath.forUser(USER, "SPAM"), UID_VALIDITY).block().getMailboxId();
+        trashMailboxId = mailboxMapper.create(MailboxPath.forUser(USER, "Trash"), UID_VALIDITY).block().getMailboxId();
 
         listener = new SpamAssassinListener(spamAssassin, systemMailboxesProvider, mailboxManager, mapperFactory, MailboxListener.ExecutionMode.SYNCHRONOUS);
     }
diff --git a/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreMailboxAnnotationManager.java b/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreMailboxAnnotationManager.java
index 2b1a52f..b189778 100644
--- a/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreMailboxAnnotationManager.java
+++ b/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreMailboxAnnotationManager.java
@@ -29,6 +29,7 @@ import org.apache.james.mailbox.MailboxSession;
 import org.apache.james.mailbox.exception.AnnotationException;
 import org.apache.james.mailbox.exception.InsufficientRightsException;
 import org.apache.james.mailbox.exception.MailboxException;
+import org.apache.james.mailbox.exception.MailboxNotFoundException;
 import org.apache.james.mailbox.model.Mailbox;
 import org.apache.james.mailbox.model.MailboxACL.Right;
 import org.apache.james.mailbox.model.MailboxAnnotation;
@@ -69,7 +70,9 @@ public class StoreMailboxAnnotationManager implements MailboxAnnotationManager {
 
     public MailboxId checkThenGetMailboxId(MailboxPath path, MailboxSession session) throws MailboxException {
         MailboxMapper mailboxMapper = mailboxSessionMapperFactory.getMailboxMapper(session);
-        Mailbox mailbox = mailboxMapper.findMailboxByPathBlocking(path);
+        Mailbox mailbox = mailboxMapper.findMailboxByPath(path)
+            .blockOptional()
+            .orElseThrow(() -> new MailboxNotFoundException(path));
         if (!rightManager.hasRight(mailbox, Right.Read, session)) {
             throw new InsufficientRightsException("Not enough rights on " + path);
         }
diff --git a/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreMailboxManager.java b/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreMailboxManager.java
index 09ea5eb..ced75f7 100644
--- a/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreMailboxManager.java
+++ b/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreMailboxManager.java
@@ -19,6 +19,8 @@
 
 package org.apache.james.mailbox.store;
 
+import static org.apache.james.mailbox.store.MailboxReactorUtils.block;
+import static org.apache.james.mailbox.store.MailboxReactorUtils.blockOptional;
 import static org.apache.james.mailbox.store.mail.AbstractMessageMapper.UNLIMITED;
 
 import java.util.ArrayList;
@@ -80,20 +82,18 @@ import org.apache.james.mailbox.store.mail.model.impl.MessageParser;
 import org.apache.james.mailbox.store.quota.QuotaComponents;
 import org.apache.james.mailbox.store.search.MessageSearchIndex;
 import org.apache.james.mailbox.store.transaction.Mapper;
-import org.apache.james.util.streams.Iterators;
+import org.apache.james.util.FunctionalUtils;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
 import com.github.fge.lambdas.Throwing;
 import com.github.steveash.guavate.Guavate;
 import com.google.common.base.Preconditions;
-import com.google.common.collect.ImmutableMap;
 import com.google.common.collect.ImmutableSet;
 import com.google.common.collect.Iterables;
 
 import reactor.core.publisher.Flux;
 import reactor.core.publisher.Mono;
-import reactor.core.scheduler.Schedulers;
 
 /**
  * This base class of an {@link MailboxManager} implementation provides a high-level api for writing your own
@@ -278,12 +278,7 @@ public class StoreMailboxManager implements MailboxManager {
     public MessageManager getMailbox(MailboxId mailboxId, MailboxSession session)
             throws MailboxException {
         MailboxMapper mapper = mailboxSessionMapperFactory.getMailboxMapper(session);
-        Mailbox mailboxRow = mapper.findMailboxById(mailboxId);
-
-        if (mailboxRow == null) {
-            LOGGER.info("Mailbox '{}' not found.", mailboxId.serialize());
-            throw new MailboxNotFoundException(mailboxId);
-        }
+        Mailbox mailboxRow = block(mapper.findMailboxById(mailboxId));
 
         if (!assertUserHasAccessTo(mailboxRow, session)) {
             LOGGER.info("Mailbox '{}' does not belong to user '{}' but to '{}'", mailboxId.serialize(), session.getUser(), mailboxRow.getUser());
@@ -320,7 +315,7 @@ public class StoreMailboxManager implements MailboxManager {
             MailboxPath sanitizedMailboxPath = mailboxPath.sanitize(mailboxSession.getPathDelimiter());
             sanitizedMailboxPath.assertAcceptable(mailboxSession.getPathDelimiter());
 
-            if (mailboxExists(sanitizedMailboxPath, mailboxSession).block()) {
+            if (block(mailboxExists(sanitizedMailboxPath, mailboxSession))) {
                 throw new MailboxExistsException(sanitizedMailboxPath.asString());
             }
 
@@ -348,7 +343,7 @@ public class StoreMailboxManager implements MailboxManager {
 
     private Stream<MailboxId> manageMailboxCreation(MailboxSession mailboxSession, boolean isRootPath, MailboxPath mailboxPath) throws MailboxException {
         if (mailboxPath.isInbox()) {
-            if (Mono.from(hasInbox(mailboxSession)).block()) {
+            if (block(Mono.from(hasInbox(mailboxSession)))) {
                 return duplicatedINBOXCreation(isRootPath, mailboxPath);
             }
 
@@ -369,30 +364,34 @@ public class StoreMailboxManager implements MailboxManager {
 
     private List<MailboxId> performConcurrentMailboxCreation(MailboxSession mailboxSession, MailboxPath mailboxPath) throws MailboxException {
         List<MailboxId> mailboxIds = new ArrayList<>();
-        locker.executeWithLock(mailboxPath, (LockAwareExecution<Void>) () -> {
-            if (!mailboxExists(mailboxPath, mailboxSession).block()) {
-                MailboxMapper mapper = mailboxSessionMapperFactory.getMailboxMapper(mailboxSession);
-                try {
-                    mapper.execute(Mapper.toTransaction(() -> {
-                        Mailbox mailbox = mapper.create(mailboxPath, UidValidity.generate());
-                        mailboxIds.add(mailbox.getMailboxId());
-                        // notify listeners
-                        eventBus.dispatch(EventFactory.mailboxAdded()
-                                .randomEventId()
-                                .mailboxSession(mailboxSession)
-                                .mailbox(mailbox)
-                                .build(),
-                                new MailboxIdRegistrationKey(mailbox.getMailboxId()))
-                            .subscribeOn(Schedulers.elastic())
-                            .block();
-                    }));
-                } catch (MailboxExistsException e) {
-                    LOGGER.info("{} mailbox was created concurrently", mailboxPath.asString());
-                }
-            }
-            return null;
-
-        }, MailboxPathLocker.LockType.Write);
+        locker.executeWithLock(mailboxPath, () ->
+            block(mailboxExists(mailboxPath, mailboxSession)
+                .filter(FunctionalUtils.identityPredicate().negate())
+                .map(Throwing.<Boolean, MailboxMapper>function(ignored -> mailboxSessionMapperFactory.getMailboxMapper(mailboxSession)).sneakyThrow())
+                .flatMap(mapper -> {
+                    try {
+                        mapper.execute(Mapper.toTransaction(() ->
+                            block(mapper.create(mailboxPath, UidValidity.generate())
+                                .doOnNext(mailbox -> mailboxIds.add(mailbox.getMailboxId()))
+                                .flatMap(mailbox ->
+                                    // notify listeners
+                                    eventBus.dispatch(EventFactory.mailboxAdded()
+                                                    .randomEventId()
+                                                    .mailboxSession(mailboxSession)
+                                                    .mailbox(mailbox)
+                                                    .build(),
+                                            new MailboxIdRegistrationKey(mailbox.getMailboxId()))))));
+                    } catch (Exception e) {
+                        if (e instanceof MailboxExistsException) {
+                            LOGGER.info("{} mailbox was created concurrently", mailboxPath.asString());
+                        } else if (e instanceof MailboxException) {
+                            return Mono.error(e);
+                        }
+                    }
+
+                    return Mono.empty();
+                })
+                .then()), MailboxPathLocker.LockType.Write);
 
         return mailboxIds;
     }
@@ -410,10 +409,10 @@ public class StoreMailboxManager implements MailboxManager {
         assertIsOwner(session, mailboxPath);
         MailboxMapper mailboxMapper = mailboxSessionMapperFactory.getMailboxMapper(session);
 
-        mailboxMapper.execute(() -> {
-            Mailbox mailbox = mailboxMapper.findMailboxByPathBlocking(mailboxPath);
-            return doDeleteMailbox(mailboxMapper, mailbox, session);
-        });
+        mailboxMapper.execute(() -> block(mailboxMapper.findMailboxByPath(mailboxPath)
+            .flatMap(Throwing.<Mailbox, Mono<Mailbox>>function(mailbox ->
+                doDeleteMailbox(mailboxMapper, mailbox, session)).sneakyThrow())
+            .switchIfEmpty(Mono.error(new MailboxNotFoundException(mailboxPath)))));
     }
 
     @Override
@@ -421,49 +420,45 @@ public class StoreMailboxManager implements MailboxManager {
         LOGGER.info("deleteMailbox {}", mailboxId);
         MailboxMapper mailboxMapper = mailboxSessionMapperFactory.getMailboxMapper(session);
 
-        return mailboxMapper.execute(() -> {
-            Mailbox mailbox = mailboxMapper.findMailboxById(mailboxId);
-            if (mailbox == null) {
-                throw new MailboxNotFoundException(mailboxId);
-            }
-            assertIsOwner(session, mailbox.generateAssociatedPath());
-            return doDeleteMailbox(mailboxMapper, mailbox, session);
-        });
+        return mailboxMapper.execute(() -> block(mailboxMapper.findMailboxById(mailboxId)
+                .map(Throwing.<Mailbox, Mailbox>function(mailbox -> {
+                    assertIsOwner(session, mailbox.generateAssociatedPath());
+                    return mailbox;
+                }).sneakyThrow())
+                .flatMap(Throwing.<Mailbox, Mono<Mailbox>>function(mailbox ->
+                    doDeleteMailbox(mailboxMapper, mailbox, session)).sneakyThrow())));
     }
 
-    private Mailbox doDeleteMailbox(MailboxMapper mailboxMapper, Mailbox mailbox, MailboxSession session) throws MailboxException {
+    private Mono<Mailbox> doDeleteMailbox(MailboxMapper mailboxMapper, Mailbox mailbox, MailboxSession session) throws MailboxException {
         MessageMapper messageMapper = mailboxSessionMapperFactory.getMessageMapper(session);
 
         QuotaRoot quotaRoot = quotaRootResolver.getQuotaRoot(mailbox.generateAssociatedPath());
         long messageCount = messageMapper.countMessagesInMailbox(mailbox);
 
-        List<MetadataWithMailboxId> metadata = Iterators.toStream(messageMapper.findInMailbox(mailbox, MessageRange.all(), MessageMapper.FetchType.Metadata, UNLIMITED))
+        return messageMapper.findInMailboxReactive(mailbox, MessageRange.all(), MessageMapper.FetchType.Metadata, UNLIMITED)
             .map(message -> MetadataWithMailboxId.from(message.metaData(), message.getMailboxId()))
-            .collect(Guavate.toImmutableList());
-
-        long totalSize = metadata.stream()
-            .map(MetadataWithMailboxId::getMessageMetaData)
-            .mapToLong(MessageMetaData::getSize)
-            .sum();
-
-        preDeletionHooks.runHooks(PreDeletionHook.DeleteOperation.from(metadata)).block();
-
-        // We need to create a copy of the mailbox as maybe we can not refer to the real
-        // mailbox once we remove it
-        Mailbox m = new Mailbox(mailbox);
-        mailboxMapper.delete(mailbox);
-        eventBus.dispatch(EventFactory.mailboxDeleted()
-                .randomEventId()
-                .mailboxSession(session)
-                .mailbox(mailbox)
-                .quotaRoot(quotaRoot)
-                .quotaCount(QuotaCountUsage.count(messageCount))
-                .quotaSize(QuotaSizeUsage.size(totalSize))
-                .build(),
-                new MailboxIdRegistrationKey(mailbox.getMailboxId()))
-            .subscribeOn(Schedulers.elastic())
-            .block();
-        return m;
+            .collect(Guavate.toImmutableList())
+            .flatMap(metadata -> {
+                long totalSize = metadata.stream()
+                    .map(MetadataWithMailboxId::getMessageMetaData)
+                    .mapToLong(MessageMetaData::getSize)
+                    .sum();
+
+                return preDeletionHooks.runHooks(PreDeletionHook.DeleteOperation.from(metadata))
+                    .then(mailboxMapper.delete(mailbox))
+                    .then(eventBus.dispatch(EventFactory.mailboxDeleted()
+                        .randomEventId()
+                        .mailboxSession(session)
+                        .mailbox(mailbox)
+                        .quotaRoot(quotaRoot)
+                        .quotaCount(QuotaCountUsage.count(messageCount))
+                        .quotaSize(QuotaSizeUsage.size(totalSize))
+                        .build(),
+                            new MailboxIdRegistrationKey(mailbox.getMailboxId())));
+            })
+            // We need to create a copy of the mailbox as maybe we can not refer to the real
+            // mailbox once we remove it
+            .thenReturn(new Mailbox(mailbox));
     }
 
     @Override
@@ -476,7 +471,8 @@ public class StoreMailboxManager implements MailboxManager {
         MailboxMapper mapper = mailboxSessionMapperFactory.getMailboxMapper(session);
 
         mapper.execute(Mapper.toTransaction(() -> {
-            Mailbox mailbox = mapper.findMailboxByPathBlocking(from);
+            Mailbox mailbox = blockOptional(mapper.findMailboxByPath(from))
+                .orElseThrow(() -> new MailboxNotFoundException(from));
             doRenameMailbox(mailbox, sanitizedMailboxPath, session, mapper);
         }));
     }
@@ -490,15 +486,14 @@ public class StoreMailboxManager implements MailboxManager {
         MailboxMapper mapper = mailboxSessionMapperFactory.getMailboxMapper(session);
 
         mapper.execute(Mapper.toTransaction(() -> {
-            Mailbox mailbox = Optional.ofNullable(mapper.findMailboxById(mailboxId))
-                .orElseThrow(() -> new MailboxNotFoundException(mailboxId));
+            Mailbox mailbox = block(mapper.findMailboxById(mailboxId));
             assertIsOwner(session, mailbox.generateAssociatedPath());
             doRenameMailbox(mailbox, sanitizedMailboxPath, session, mapper);
         }));
     }
 
     private void validateDestinationPath(MailboxPath newMailboxPath, MailboxSession session) throws MailboxException {
-        if (mailboxExists(newMailboxPath, session).block()) {
+        if (block(mailboxExists(newMailboxPath, session))) {
             throw new MailboxExistsException(newMailboxPath.toString());
         }
         assertIsOwner(session, newMailboxPath);
@@ -519,18 +514,15 @@ public class StoreMailboxManager implements MailboxManager {
         mailbox.setNamespace(newMailboxPath.getNamespace());
         mailbox.setUser(newMailboxPath.getUser());
         mailbox.setName(newMailboxPath.getName());
-        mapper.rename(mailbox);
-
-        eventBus.dispatch(EventFactory.mailboxRenamed()
+        block(mapper.rename(mailbox)
+            .then(eventBus.dispatch(EventFactory.mailboxRenamed()
                 .randomEventId()
                 .mailboxSession(session)
                 .mailboxId(mailbox.getMailboxId())
                 .oldPath(from)
                 .newPath(newMailboxPath)
                 .build(),
-                new MailboxIdRegistrationKey(mailbox.getMailboxId()))
-            .subscribeOn(Schedulers.elastic())
-            .block();
+                new MailboxIdRegistrationKey(mailbox.getMailboxId()))));
 
         // rename submailboxes
         MailboxQuery.UserBound query = MailboxQuery.builder()
@@ -539,26 +531,25 @@ public class StoreMailboxManager implements MailboxManager {
             .build()
             .asUserBound();
         locker.executeWithLock(from, (LockAwareExecution<Void>) () -> {
-            List<Mailbox> subMailboxes = mapper.findMailboxWithPathLike(query).collectList().block();
-            for (Mailbox sub : subMailboxes) {
-                String subOriginalName = sub.getName();
-                String subNewName = newMailboxPath.getName() + subOriginalName.substring(from.getName().length());
-                MailboxPath fromPath = new MailboxPath(from, subOriginalName);
-                sub.setName(subNewName);
-                mapper.rename(sub);
-                eventBus.dispatch(EventFactory.mailboxRenamed()
-                        .randomEventId()
-                        .mailboxSession(session)
-                        .mailboxId(sub.getMailboxId())
-                        .oldPath(fromPath)
-                        .newPath(sub.generateAssociatedPath())
-                        .build(),
-                        new MailboxIdRegistrationKey(sub.getMailboxId()))
-                    .subscribeOn(Schedulers.elastic())
-                    .block();
+            block(mapper.findMailboxWithPathLike(query)
+                .flatMap(sub -> {
+                    String subOriginalName = sub.getName();
+                    String subNewName = newMailboxPath.getName() + subOriginalName.substring(from.getName().length());
+                    MailboxPath fromPath = new MailboxPath(from, subOriginalName);
+                    sub.setName(subNewName);
+                    return mapper.rename(sub)
+                        .then(eventBus.dispatch(EventFactory.mailboxRenamed()
+                            .randomEventId()
+                            .mailboxSession(session)
+                            .mailboxId(sub.getMailboxId())
+                            .oldPath(fromPath)
+                            .newPath(sub.generateAssociatedPath())
+                            .build(),
+                            new MailboxIdRegistrationKey(sub.getMailboxId())))
+                        .then(Mono.fromRunnable(() -> LOGGER.debug("Rename mailbox sub-mailbox {} to {}", subOriginalName, subNewName)));
+                })
+                .then());
 
-                LOGGER.debug("Rename mailbox sub-mailbox {} to {}", subOriginalName, subNewName);
-            }
             return null;
 
         }, MailboxPathLocker.LockType.Write);
@@ -595,28 +586,13 @@ public class StoreMailboxManager implements MailboxManager {
     }
 
     @Override
-    public List<MailboxMetaData> search(MailboxQuery mailboxExpression, MailboxSession session) throws MailboxException {
-        return searchMailboxesMetadata(mailboxExpression, session, Right.Lookup)
-            .collect(Guavate.toImmutableList())
-            .block();
-    }
-
-    @Override
-    public Flux<MailboxMetaData> searchReactive(MailboxQuery expression, MailboxSession session) {
-        try {
-            return searchMailboxesMetadata(expression, session, Right.Lookup);
-        } catch (MailboxException e) {
-            return Flux.error(e);
-        }
-    }
-
-    private Flux<MailboxMetaData> searchMailboxesMetadata(MailboxQuery mailboxQuery, MailboxSession session, Right right) throws MailboxException {
-        Mono<List<Mailbox>> mailboxesMono = searchMailboxes(mailboxQuery, session, right).collectList();
+    public Flux<MailboxMetaData> search(MailboxQuery expression, MailboxSession session) {
+        Mono<List<Mailbox>> mailboxesMono = searchMailboxes(expression, session, Right.Lookup).collectList();
         MessageMapper messageMapper = mailboxSessionMapperFactory.getMessageMapper(session);
 
         return mailboxesMono
             .flatMapMany(mailboxes -> Flux.fromIterable(mailboxes)
-                .filter(mailboxQuery::matches)
+                .filter(expression::matches)
                 .flatMap(mailbox -> retrieveCounters(messageMapper, mailbox, session)
                     .map(Throwing.<MailboxCounters, MailboxMetaData>function(
                         counters -> toMailboxMetadata(session, mailboxes, mailbox, counters))
@@ -635,11 +611,12 @@ public class StoreMailboxManager implements MailboxManager {
                 .build()));
     }
 
-    private Flux<Mailbox> searchMailboxes(MailboxQuery mailboxQuery, MailboxSession session, Right right) throws MailboxException {
+    private Flux<Mailbox> searchMailboxes(MailboxQuery mailboxQuery, MailboxSession session, Right right) {
         MailboxMapper mailboxMapper = mailboxSessionMapperFactory.getMailboxMapper(session);
-        Flux<Mailbox> baseMailboxes = mailboxMapper.findMailboxWithPathLike(toSingleUserQuery(mailboxQuery, session));
+        Flux<Mailbox> baseMailboxes = mailboxMapper
+            .findMailboxWithPathLike(toSingleUserQuery(mailboxQuery, session));
         Flux<Mailbox> delegatedMailboxes = getDelegatedMailboxes(mailboxMapper, mailboxQuery, right, session);
-        return Flux.merge(baseMailboxes, delegatedMailboxes)
+        return Flux.concat(baseMailboxes, delegatedMailboxes)
             .distinct()
             .filter(Throwing.predicate(mailbox -> storeRightManager.hasRight(mailbox, right, session)));
     }
@@ -654,14 +631,6 @@ public class StoreMailboxManager implements MailboxManager {
             .asUserBound();
     }
 
-    private MailboxCounters retrieveCounters(ImmutableMap<MailboxId, MailboxCounters> counters, Mailbox mailbox) {
-        return counters.getOrDefault(mailbox.getMailboxId(), MailboxCounters.builder()
-            .mailboxId(mailbox.getMailboxId())
-            .count(0)
-            .unseen(0)
-            .build());
-    }
-
     private Flux<Mailbox> getDelegatedMailboxes(MailboxMapper mailboxMapper, MailboxQuery mailboxQuery,
                                                 Right right, MailboxSession session) {
         if (mailboxQuery.isPrivateMailboxes(session)) {
@@ -719,7 +688,7 @@ public class StoreMailboxManager implements MailboxManager {
     private Flux<MailboxId> filterReadable(ImmutableSet<MailboxId> inMailboxes, MailboxSession session) throws MailboxException {
         MailboxMapper mailboxMapper = mailboxSessionMapperFactory.getMailboxMapper(session);
         return Flux.fromIterable(inMailboxes)
-            .concatMap(mailboxMapper::findMailboxByIdReactive)
+            .concatMap(mailboxMapper::findMailboxById)
             .filter(Throwing.<Mailbox>predicate(mailbox -> storeRightManager.hasRight(mailbox, Right.Read, session)).sneakyThrow())
             .map(Mailbox::getMailboxId);
     }
@@ -749,12 +718,11 @@ public class StoreMailboxManager implements MailboxManager {
 
     @Override
     public List<MailboxPath> list(MailboxSession session) throws MailboxException {
-        return mailboxSessionMapperFactory.getMailboxMapper(session)
+        return block(mailboxSessionMapperFactory.getMailboxMapper(session)
             .list()
             .map(Mailbox::generateAssociatedPath)
             .distinct()
-            .collect(Guavate.toImmutableList())
-            .block();
+            .collect(Guavate.toImmutableList()));
     }
 
     @Override
@@ -773,16 +741,11 @@ public class StoreMailboxManager implements MailboxManager {
     }
 
     @Override
-    public Rfc4314Rights myRights(MailboxId mailboxId, MailboxSession session) throws MailboxException {
+    public Mono<Rfc4314Rights> myRights(MailboxId mailboxId, MailboxSession session) {
         return storeRightManager.myRights(mailboxId, session);
     }
 
     @Override
-    public Mono<Rfc4314Rights> myRightsReactive(MailboxId mailboxId, MailboxSession session) {
-        return storeRightManager.myRightsReactive(mailboxId, session);
-    }
-
-    @Override
     public List<Rfc4314Rights> listRights(MailboxPath mailboxPath, MailboxACL.EntryKey key, MailboxSession session) throws MailboxException {
         return storeRightManager.listRights(mailboxPath, key, session);
     }
@@ -845,7 +808,7 @@ public class StoreMailboxManager implements MailboxManager {
     @Override
     public boolean hasChildren(MailboxPath mailboxPath, MailboxSession session) throws MailboxException {
         MailboxMapper mapper = mailboxSessionMapperFactory.getMailboxMapper(session);
-        Mailbox mailbox = mapper.findMailboxByPathBlocking(mailboxPath);
-        return mapper.hasChildren(mailbox, session.getPathDelimiter());
+        return block(mapper.findMailboxByPath(mailboxPath)
+            .flatMap(mailbox -> mapper.hasChildren(mailbox, session.getPathDelimiter())));
     }
 }
diff --git a/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreMessageIdManager.java b/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreMessageIdManager.java
index 17c0477..4ed6fb9 100644
--- a/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreMessageIdManager.java
+++ b/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreMessageIdManager.java
@@ -19,6 +19,8 @@
 
 package org.apache.james.mailbox.store;
 
+import static org.apache.james.mailbox.store.MailboxReactorUtils.block;
+
 import java.util.Collection;
 import java.util.HashMap;
 import java.util.List;
@@ -45,7 +47,7 @@ import org.apache.james.mailbox.exception.MailboxNotFoundException;
 import org.apache.james.mailbox.extension.PreDeletionHook;
 import org.apache.james.mailbox.model.DeleteResult;
 import org.apache.james.mailbox.model.FetchGroup;
-import org.apache.james.mailbox.model.Mailbox;
+import org.apache.james.mailbox.model.MailboxACL;
 import org.apache.james.mailbox.model.MailboxACL.Right;
 import org.apache.james.mailbox.model.MailboxId;
 import org.apache.james.mailbox.model.MessageId;
@@ -226,15 +228,14 @@ public class StoreMessageIdManager implements MessageIdManager {
 
         MailboxMapper mailboxMapper = mailboxSessionMapperFactory.getMailboxMapper(mailboxSession);
         Flux.fromIterable(metadataWithMailbox)
-            .flatMap(Throwing.<MetadataWithMailboxId, Mono<Void>>function(
-                metadataWithMailboxId -> eventBus.dispatch(EventFactory.expunged()
-                    .randomEventId()
-                    .mailboxSession(mailboxSession)
-                    .mailbox(mailboxMapper.findMailboxById(metadataWithMailboxId.getMailboxId()))
-                    .addMetaData(metadataWithMailboxId.getMessageMetaData())
-                    .build(),
-                new MailboxIdRegistrationKey(metadataWithMailboxId.getMailboxId())))
-                .sneakyThrow())
+            .flatMap(metadataWithMailboxId -> mailboxMapper.findMailboxById(metadataWithMailboxId.getMailboxId())
+                .flatMap(mailbox -> eventBus.dispatch(EventFactory.expunged()
+                        .randomEventId()
+                        .mailboxSession(mailboxSession)
+                        .mailbox(mailbox)
+                        .addMetaData(metadataWithMailboxId.getMessageMetaData())
+                        .build(),
+                    new MailboxIdRegistrationKey(metadataWithMailboxId.getMailboxId()))))
             .then()
             .subscribeOn(Schedulers.elastic())
             .block();
@@ -318,13 +319,14 @@ public class StoreMessageIdManager implements MessageIdManager {
 
         for (MailboxId mailboxId: mailboxesToRemove) {
             messageIdMapper.delete(message.getMessageId(), mailboxesToRemove);
-            eventBus.dispatch(EventFactory.expunged()
-                .randomEventId()
-                .mailboxSession(mailboxSession)
-                .mailbox(mailboxMapper.findMailboxById(mailboxId))
-                .addMetaData(eventPayload)
-                .build(),
-                new MailboxIdRegistrationKey(mailboxId))
+            mailboxMapper.findMailboxById(mailboxId)
+                .flatMap(mailbox -> eventBus.dispatch(EventFactory.expunged()
+                        .randomEventId()
+                        .mailboxSession(mailboxSession)
+                        .mailbox(mailbox)
+                        .addMetaData(eventPayload)
+                        .build(),
+                    new MailboxIdRegistrationKey(mailboxId)))
             .subscribeOn(Schedulers.elastic())
             .block();
         }
@@ -332,15 +334,14 @@ public class StoreMessageIdManager implements MessageIdManager {
     
     private void dispatchFlagsChange(MailboxSession mailboxSession, MailboxId mailboxId, ImmutableList<UpdatedFlags> updatedFlags) throws MailboxException {
         if (updatedFlags.stream().anyMatch(UpdatedFlags::flagsChanged)) {
-            Mailbox mailbox = mailboxSessionMapperFactory.getMailboxMapper(mailboxSession).findMailboxById(mailboxId);
-
-            eventBus.dispatch(EventFactory.flagsUpdated()
-                    .randomEventId()
-                    .mailboxSession(mailboxSession)
-                    .mailbox(mailbox)
-                    .updatedFlags(updatedFlags)
-                    .build(),
-                new MailboxIdRegistrationKey(mailboxId))
+            mailboxSessionMapperFactory.getMailboxMapper(mailboxSession).findMailboxById(mailboxId)
+                .flatMap(mailbox -> eventBus.dispatch(EventFactory.flagsUpdated()
+                        .randomEventId()
+                        .mailboxSession(mailboxSession)
+                        .mailbox(mailbox)
+                        .updatedFlags(updatedFlags)
+                        .build(),
+                    new MailboxIdRegistrationKey(mailboxId)))
                 .subscribeOn(Schedulers.elastic())
                 .block();
         }
@@ -380,7 +381,8 @@ public class StoreMessageIdManager implements MessageIdManager {
         MailboxMapper mailboxMapper = mailboxSessionMapperFactory.getMailboxMapper(mailboxSession);
 
         for (MailboxId mailboxId : mailboxIds) {
-            boolean shouldPreserveFlags = rightManager.myRights(mailboxId, mailboxSession).contains(Right.Write);
+            MailboxACL.Rfc4314Rights myRights = block(Mono.from(rightManager.myRights(mailboxId, mailboxSession)));
+            boolean shouldPreserveFlags = myRights.contains(Right.Write);
             SimpleMailboxMessage copy =
                 SimpleMailboxMessage.from(mailboxMessage)
                     .mailboxId(mailboxId)
@@ -397,14 +399,14 @@ public class StoreMessageIdManager implements MessageIdManager {
                     .build();
             save(messageIdMapper, copy);
 
-            eventBus.dispatch(EventFactory.added()
+            mailboxMapper.findMailboxById(mailboxId)
+                .flatMap(mailbox -> eventBus.dispatch(EventFactory.added()
                     .randomEventId()
                     .mailboxSession(mailboxSession)
-                    .mailbox(mailboxMapper.findMailboxById(mailboxId))
+                    .mailbox(mailbox)
                     .addMetaData(copy.metaData())
                     .build(),
-                    new MailboxIdRegistrationKey(mailboxId))
-                .subscribeOn(Schedulers.elastic())
+                    new MailboxIdRegistrationKey(mailboxId)))
                 .block();
         }
     }
@@ -431,12 +433,12 @@ public class StoreMessageIdManager implements MessageIdManager {
 
 
     private Predicate<MailboxId> hasRightsOnMailbox(MailboxSession session, Right... rights) {
-        return Throwing.predicate((MailboxId mailboxId) -> rightManager.myRights(mailboxId, session).contains(rights))
+        return Throwing.predicate((MailboxId mailboxId) -> block(Mono.from(rightManager.myRights(mailboxId, session))).contains(rights))
             .fallbackTo(any -> false);
     }
 
     private Function<MailboxId, Mono<Boolean>> hasRightsOnMailboxReactive(MailboxSession session, Right... rights) {
-        return mailboxId -> Mono.from(rightManager.myRightsReactive(mailboxId, session))
+        return mailboxId -> Mono.from(rightManager.myRights(mailboxId, session))
             .map(myRights -> myRights.contains(rights))
             .onErrorResume(any -> Mono.just(false));
     }
diff --git a/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreRightManager.java b/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreRightManager.java
index 0d68316..8dd303e 100644
--- a/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreRightManager.java
+++ b/mailbox/store/src/main/java/org/apache/james/mailbox/store/StoreRightManager.java
@@ -19,6 +19,8 @@
 
 package org.apache.james.mailbox.store;
 
+import static org.apache.james.mailbox.store.MailboxReactorUtils.block;
+
 import java.util.List;
 import java.util.Map;
 import java.util.Optional;
@@ -30,7 +32,6 @@ import org.apache.james.core.Domain;
 import org.apache.james.core.Username;
 import org.apache.james.mailbox.MailboxSession;
 import org.apache.james.mailbox.RightManager;
-import org.apache.james.mailbox.acl.ACLDiff;
 import org.apache.james.mailbox.acl.GroupMembershipResolver;
 import org.apache.james.mailbox.acl.MailboxACLResolver;
 import org.apache.james.mailbox.events.EventBus;
@@ -55,7 +56,6 @@ import com.google.common.annotations.VisibleForTesting;
 import com.google.common.collect.ImmutableMap;
 
 import reactor.core.publisher.Mono;
-import reactor.core.scheduler.Schedulers;
 
 public class StoreRightManager implements RightManager {
     public static final boolean GROUP_FOLDER = true;
@@ -83,35 +83,28 @@ public class StoreRightManager implements RightManager {
 
     @Override
     public boolean hasRight(MailboxId mailboxId, Right right, MailboxSession session) throws MailboxException {
-        return myRights(mailboxId, session).contains(right);
+        return block(Mono.from(myRights(mailboxId, session))).contains(right);
     }
 
-    public boolean hasRight(Mailbox mailbox, Right right, MailboxSession session) throws MailboxException {
+    public boolean hasRight(Mailbox mailbox, Right right, MailboxSession session) {
         return myRights(mailbox, session).contains(right);
     }
 
     @Override
     public Rfc4314Rights myRights(MailboxPath mailboxPath, MailboxSession session) throws MailboxException {
         MailboxMapper mapper = mailboxSessionMapperFactory.getMailboxMapper(session);
-        Mailbox mailbox = mapper.findMailboxByPathBlocking(mailboxPath);
-        return myRights(mailbox, session);
-    }
-
-    @Override
-    public Rfc4314Rights myRights(MailboxId mailboxId, MailboxSession session) throws MailboxException {
-        MailboxMapper mapper = mailboxSessionMapperFactory.getMailboxMapper(session);
-        Mailbox mailbox = mapper.findMailboxById(mailboxId);
+        Mailbox mailbox = block(mapper.findMailboxByPath(mailboxPath));
         return myRights(mailbox, session);
     }
 
     @Override
-    public Mono<Rfc4314Rights> myRightsReactive(MailboxId mailboxId, MailboxSession session) {
+    public Mono<Rfc4314Rights> myRights(MailboxId mailboxId, MailboxSession session) {
         MailboxMapper mapper = mailboxSessionMapperFactory.getMailboxMapper(session);
-        return mapper.findMailboxByIdReactive(mailboxId)
+        return mapper.findMailboxById(mailboxId)
             .map(Throwing.function(mailbox -> myRights(mailbox, session)));
     }
 
-    public Rfc4314Rights myRights(Mailbox mailbox, MailboxSession session) throws UnsupportedRightException {
+    public Rfc4314Rights myRights(Mailbox mailbox, MailboxSession session) {
         Username username = session.getUser();
 
         return Optional.ofNullable(username)
@@ -129,7 +122,7 @@ public class StoreRightManager implements RightManager {
     @Override
     public List<Rfc4314Rights> listRights(MailboxPath mailboxPath, EntryKey key, MailboxSession session) throws MailboxException {
         MailboxMapper mapper = mailboxSessionMapperFactory.getMailboxMapper(session);
-        Mailbox mailbox = mapper.findMailboxByPathBlocking(mailboxPath);
+        Mailbox mailbox = block(mapper.findMailboxByPath(mailboxPath));
 
         return aclResolver.listRights(key,
             groupMembershipResolver,
@@ -140,7 +133,7 @@ public class StoreRightManager implements RightManager {
     @Override
     public MailboxACL listRights(MailboxPath mailboxPath, MailboxSession session) throws MailboxException {
         MailboxMapper mapper = mailboxSessionMapperFactory.getMailboxMapper(session);
-        Mailbox mailbox = mapper.findMailboxByPathBlocking(mailboxPath);
+        Mailbox mailbox = block(mapper.findMailboxByPath(mailboxPath));
         return mailbox.getACL();
     }
 
@@ -148,18 +141,15 @@ public class StoreRightManager implements RightManager {
     public void applyRightsCommand(MailboxPath mailboxPath, ACLCommand mailboxACLCommand, MailboxSession session) throws MailboxException {
         assertSharesBelongsToUserDomain(mailboxPath.getUser(), mailboxACLCommand);
         MailboxMapper mapper = mailboxSessionMapperFactory.getMailboxMapper(session);
-        Mailbox mailbox = mapper.findMailboxByPathBlocking(mailboxPath);
-        ACLDiff aclDiff = mapper.updateACL(mailbox, mailboxACLCommand);
-
-        eventBus.dispatch(EventFactory.aclUpdated()
-            .randomEventId()
-            .mailboxSession(session)
-            .mailbox(mailbox)
-            .aclDiff(aclDiff)
-            .build(),
-            new MailboxIdRegistrationKey(mailbox.getMailboxId()))
-            .subscribeOn(Schedulers.elastic())
-            .block();
+        block(mapper.findMailboxByPath(mailboxPath)
+            .flatMap(mailbox -> mapper.updateACL(mailbox, mailboxACLCommand)
+                .flatMap(aclDiff -> eventBus.dispatch(EventFactory.aclUpdated()
+                        .randomEventId()
+                        .mailboxSession(session)
+                        .mailbox(mailbox)
+                        .aclDiff(aclDiff)
+                        .build(),
+                    new MailboxIdRegistrationKey(mailbox.getMailboxId())))));
     }
 
     private void assertSharesBelongsToUserDomain(Username user, ACLCommand mailboxACLCommand) throws DifferentDomainException {
@@ -203,7 +193,7 @@ public class StoreRightManager implements RightManager {
     @Override
     public void setRights(MailboxId mailboxId, MailboxACL mailboxACL, MailboxSession session) throws MailboxException {
         MailboxMapper mapper = mailboxSessionMapperFactory.getMailboxMapper(session);
-        Mailbox mailbox = mapper.findMailboxById(mailboxId);
+        Mailbox mailbox = block(mapper.findMailboxById(mailboxId));
 
         setRights(mailbox.generateAssociatedPath(), mailboxACL, session);
     }
@@ -212,9 +202,9 @@ public class StoreRightManager implements RightManager {
     public void setRights(MailboxPath mailboxPath, MailboxACL mailboxACL, MailboxSession session) throws MailboxException {
         assertSharesBelongsToUserDomain(mailboxPath.getUser(), mailboxACL.getEntries());
         MailboxMapper mapper = mailboxSessionMapperFactory.getMailboxMapper(session);
-        Mailbox mailbox = mapper.findMailboxByPathBlocking(mailboxPath);
 
-        setRights(mailboxACL, mapper, mailbox, session);
+        block(mapper.findMailboxByPath(mailboxPath)
+            .flatMap(mailbox -> setRights(mailboxACL, mapper, mailbox, session)));
     }
 
     @VisibleForTesting
@@ -234,18 +224,15 @@ public class StoreRightManager implements RightManager {
         return !domain.equals(otherDomain);
     }
 
-    private void setRights(MailboxACL mailboxACL, MailboxMapper mapper, Mailbox mailbox, MailboxSession session) throws MailboxException {
-        ACLDiff aclDiff = mapper.setACL(mailbox, mailboxACL);
-
-        eventBus.dispatch(EventFactory.aclUpdated()
-            .randomEventId()
-            .mailboxSession(session)
-            .mailbox(mailbox)
-            .aclDiff(aclDiff)
-            .build(),
-            new MailboxIdRegistrationKey(mailbox.getMailboxId()))
-            .subscribeOn(Schedulers.elastic())
-            .block();
+    private Mono<Void> setRights(MailboxACL mailboxACL, MailboxMapper mapper, Mailbox mailbox, MailboxSession session) {
+        return mapper.setACL(mailbox, mailboxACL)
+            .flatMap(aclDiff -> eventBus.dispatch(EventFactory.aclUpdated()
+                    .randomEventId()
+                    .mailboxSession(session)
+                    .mailbox(mailbox)
+                    .aclDiff(aclDiff)
+                    .build(),
+                new MailboxIdRegistrationKey(mailbox.getMailboxId())));
     }
 
     /**
diff --git a/mailbox/store/src/main/java/org/apache/james/mailbox/store/SystemMailboxesProviderImpl.java b/mailbox/store/src/main/java/org/apache/james/mailbox/store/SystemMailboxesProviderImpl.java
index 235c04c..01eb2dc 100644
--- a/mailbox/store/src/main/java/org/apache/james/mailbox/store/SystemMailboxesProviderImpl.java
+++ b/mailbox/store/src/main/java/org/apache/james/mailbox/store/SystemMailboxesProviderImpl.java
@@ -74,7 +74,7 @@ public class SystemMailboxesProviderImpl implements SystemMailboxesProvider {
             .expression(new PrefixedWildcard(aRole.getDefaultMailbox()))
             .build();
         return mailboxManager.search(mailboxQuery, session)
-            .stream()
+            .toStream()
             .map(MailboxMetaData::getPath)
             .filter(path -> hasRole(aRole, path))
             .map(Throwing.function(loadMailbox).sneakyThrow());
diff --git a/mailbox/store/src/main/java/org/apache/james/mailbox/store/mail/MailboxMapper.java b/mailbox/store/src/main/java/org/apache/james/mailbox/store/mail/MailboxMapper.java
index 059356e..8743be6 100644
--- a/mailbox/store/src/main/java/org/apache/james/mailbox/store/mail/MailboxMapper.java
+++ b/mailbox/store/src/main/java/org/apache/james/mailbox/store/mail/MailboxMapper.java
@@ -22,8 +22,6 @@ import java.util.List;
 
 import org.apache.james.core.Username;
 import org.apache.james.mailbox.acl.ACLDiff;
-import org.apache.james.mailbox.exception.MailboxException;
-import org.apache.james.mailbox.exception.MailboxNotFoundException;
 import org.apache.james.mailbox.model.Mailbox;
 import org.apache.james.mailbox.model.MailboxACL;
 import org.apache.james.mailbox.model.MailboxACL.Right;
@@ -46,17 +44,17 @@ public interface MailboxMapper extends Mapper {
     /**
      * Create a {@link Mailbox} with the given {@link MailboxPath} and uid to the underlying storage
      */
-    Mailbox create(MailboxPath mailboxPath, UidValidity uidValidity) throws MailboxException;
+    Mono<Mailbox> create(MailboxPath mailboxPath, UidValidity uidValidity);
 
     /**
      * Rename the given {@link Mailbox} to the underlying storage
      */
-    MailboxId rename(Mailbox mailbox) throws MailboxException;
+    Mono<MailboxId> rename(Mailbox mailbox);
     
     /**
      * Delete the given {@link Mailbox} from the underlying storage
      */
-    void delete(Mailbox mailbox) throws MailboxException;
+    Mono<Void> delete(Mailbox mailbox);
 
   
     /**
@@ -68,35 +66,10 @@ public interface MailboxMapper extends Mapper {
         return findMailboxByPath(mailboxName).hasElement();
     }
 
-    default Mailbox findMailboxByPathBlocking(MailboxPath mailboxPath) throws MailboxException, MailboxNotFoundException {
-        try {
-            return findMailboxByPath(mailboxPath)
-                .blockOptional()
-                .orElseThrow(() -> new MailboxNotFoundException(mailboxPath));
-        } catch (Exception e) {
-            Throwable cause = e.getCause();
-            if (cause instanceof MailboxException) {
-                throw (MailboxException) cause;
-            }
-            throw e;
-        }
-    }
-
     /**
      * Return the {@link Mailbox} for the given name
      */
-    Mailbox findMailboxById(MailboxId mailboxId)
-            throws MailboxException, MailboxNotFoundException;
-
-    default Mono<Mailbox> findMailboxByIdReactive(MailboxId id) {
-        try {
-            return Mono.justOrEmpty(findMailboxById(id));
-        } catch (MailboxNotFoundException e) {
-            return Mono.empty();
-        } catch (MailboxException e) {
-            return Mono.error(e);
-        }
-    }
+    Mono<Mailbox> findMailboxById(MailboxId mailboxId);
 
     /**
      * Return a List of {@link Mailbox} for the given userName and matching the right
@@ -106,8 +79,7 @@ public interface MailboxMapper extends Mapper {
     /**
      * Return a List of {@link Mailbox} which name is like the given name
      */
-    Flux<Mailbox> findMailboxWithPathLike(MailboxQuery.UserBound query)
-            throws MailboxException;
+    Flux<Mailbox> findMailboxWithPathLike(MailboxQuery.UserBound query);
 
     /**
      * Return if the given {@link Mailbox} has children
@@ -116,27 +88,25 @@ public interface MailboxMapper extends Mapper {
      * @param delimiter path delimiter
      * @return true when the mailbox has children, false otherwise
      */
-    boolean hasChildren(Mailbox mailbox, char delimiter)
-            throws MailboxException, MailboxNotFoundException;
+    Mono<Boolean> hasChildren(Mailbox mailbox, char delimiter);
 
     /**
      * Update the ACL of the stored mailbox.
-     *
      * @param mailbox Mailbox for whom we want to update ACL
      * @param mailboxACLCommand Update to perform
      */
-    ACLDiff updateACL(Mailbox mailbox, MailboxACL.ACLCommand mailboxACLCommand) throws MailboxException;
+    Mono<ACLDiff> updateACL(Mailbox mailbox, MailboxACL.ACLCommand mailboxACLCommand);
 
     /**
      * Reset the ACL of the stored mailbox.
-     *
-     * @param mailbox Mailbox for whom we want to update ACL
+     *  @param mailbox Mailbox for whom we want to update ACL
      * @param mailboxACL New value of the ACL for this mailbox
+     * @return
      */
-    ACLDiff setACL(Mailbox mailbox, MailboxACL mailboxACL) throws MailboxException;
+    Mono<ACLDiff> setACL(Mailbox mailbox, MailboxACL mailboxACL);
 
     /**
      * Return a unmodifable {@link List} of all {@link Mailbox}
      */
     Flux<Mailbox> list();
-}
\ No newline at end of file
+}
diff --git a/mailbox/store/src/main/java/org/apache/james/mailbox/store/quota/DefaultUserQuotaRootResolver.java b/mailbox/store/src/main/java/org/apache/james/mailbox/store/quota/DefaultUserQuotaRootResolver.java
index 773a8b0..9587c87 100644
--- a/mailbox/store/src/main/java/org/apache/james/mailbox/store/quota/DefaultUserQuotaRootResolver.java
+++ b/mailbox/store/src/main/java/org/apache/james/mailbox/store/quota/DefaultUserQuotaRootResolver.java
@@ -104,7 +104,7 @@ public class DefaultUserQuotaRootResolver implements UserQuotaRootResolver {
         MailboxSession session = sessionProvider.createSystemSession(Username.of("DefaultUserQuotaRootResolver"));
 
         return factory.getMailboxMapper(session)
-            .findMailboxByIdReactive(mailboxId)
+            .findMailboxById(mailboxId)
             .map(Mailbox::generateAssociatedPath)
             .map(MailboxPath::getUser)
             .map(this::forUser);
diff --git a/mailbox/store/src/main/java/org/apache/james/mailbox/store/search/ListeningMessageSearchIndex.java b/mailbox/store/src/main/java/org/apache/james/mailbox/store/search/ListeningMessageSearchIndex.java
index 59f4260..7f9db4c 100644
--- a/mailbox/store/src/main/java/org/apache/james/mailbox/store/search/ListeningMessageSearchIndex.java
+++ b/mailbox/store/src/main/java/org/apache/james/mailbox/store/search/ListeningMessageSearchIndex.java
@@ -77,19 +77,19 @@ public abstract class ListeningMessageSearchIndex implements MessageSearchIndex,
 
         if (event instanceof Added) {
             return factory.getMailboxMapper(session)
-                .findMailboxByIdReactive(mailboxId)
+                .findMailboxById(mailboxId)
                 .flatMap(mailbox -> handleAdded(session, mailbox, (Added) event));
         } else if (event instanceof Expunged) {
             Expunged expunged = (Expunged) event;
 
             return factory.getMailboxMapper(session)
-                .findMailboxByIdReactive(mailboxId)
+                .findMailboxById(mailboxId)
                 .flatMap(mailbox -> delete(session, mailbox, expunged.getUids()));
         } else if (event instanceof FlagsUpdated) {
             FlagsUpdated flagsUpdated = (FlagsUpdated) event;
 
             return factory.getMailboxMapper(session)
-                .findMailboxByIdReactive(mailboxId)
+                .findMailboxById(mailboxId)
                 .flatMap(mailbox -> update(session, mailbox, flagsUpdated.getUpdatedFlags()));
         } else if (event instanceof MailboxDeletion) {
             return deleteAll(session, mailboxId);
diff --git a/mailbox/store/src/main/java/org/apache/james/mailbox/store/search/SimpleMessageSearchIndex.java b/mailbox/store/src/main/java/org/apache/james/mailbox/store/search/SimpleMessageSearchIndex.java
index f3d52bb..e4719f9 100644
--- a/mailbox/store/src/main/java/org/apache/james/mailbox/store/search/SimpleMessageSearchIndex.java
+++ b/mailbox/store/src/main/java/org/apache/james/mailbox/store/search/SimpleMessageSearchIndex.java
@@ -53,7 +53,6 @@ import org.apache.james.mailbox.store.mail.MessageMapper.FetchType;
 import org.apache.james.mailbox.store.mail.MessageMapperFactory;
 import org.apache.james.mailbox.store.mail.model.MailboxMessage;
 
-import com.github.fge.lambdas.Throwing;
 import com.google.common.base.Preconditions;
 import com.google.common.collect.ImmutableList;
 
@@ -151,7 +150,7 @@ public class SimpleMessageSearchIndex implements MessageSearchIndex {
         MailboxMapper mailboxMapper = mailboxMapperFactory.getMailboxMapper(session);
 
         Flux<Mailbox> filteredMailboxes = Flux.fromIterable(mailboxIds)
-            .concatMap(Throwing.function(mailboxMapper::findMailboxByIdReactive).sneakyThrow());
+            .concatMap(mailboxMapper::findMailboxById);
 
         return getAsMessageIds(searchResults(session, filteredMailboxes, searchQuery), limit);
     }
diff --git a/mailbox/store/src/main/java/org/apache/james/mailbox/store/transaction/Mapper.java b/mailbox/store/src/main/java/org/apache/james/mailbox/store/transaction/Mapper.java
index d5733bf..1560e83 100644
--- a/mailbox/store/src/main/java/org/apache/james/mailbox/store/transaction/Mapper.java
+++ b/mailbox/store/src/main/java/org/apache/james/mailbox/store/transaction/Mapper.java
@@ -35,7 +35,7 @@ public interface Mapper {
      * Execute the given Transaction
      */
     <T> T execute(Transaction<T> transaction) throws MailboxException;
-        
+
     /**
      * Unit of work executed in a Transaction
      *
diff --git a/mailbox/store/src/main/java/org/apache/james/mailbox/store/transaction/TransactionalMapper.java b/mailbox/store/src/main/java/org/apache/james/mailbox/store/transaction/TransactionalMapper.java
index c9e53c6..139d8e7 100644
--- a/mailbox/store/src/main/java/org/apache/james/mailbox/store/transaction/TransactionalMapper.java
+++ b/mailbox/store/src/main/java/org/apache/james/mailbox/store/transaction/TransactionalMapper.java
@@ -21,6 +21,10 @@ package org.apache.james.mailbox.store.transaction;
 
 import org.apache.james.mailbox.exception.MailboxException;
 
+import com.github.fge.lambdas.Throwing;
+
+import reactor.core.publisher.Mono;
+
 /**
  *
  * Run Transaction and handle begin, commit and rollback in the right order
@@ -39,7 +43,21 @@ public abstract class TransactionalMapper implements Mapper {
             throw e;
         }
     }
-    
+
+    public final <T> Mono<T> executeReactive(Mono<T> transaction) {
+        return Mono.fromRunnable(Throwing.runnable(this::begin).sneakyThrow())
+            .then(transaction)
+            .doOnNext(Throwing.consumer(ignored -> commit()).sneakyThrow())
+            .doOnError(MailboxException.class, Throwing.consumer(e -> rollback()).sneakyThrow());
+    }
+
+    public final Mono<Void> executeReactiveVoid(Mono<Void> transaction) {
+        return Mono.fromRunnable(Throwing.runnable(this::begin).sneakyThrow())
+                .then(transaction)
+                .thenEmpty(Mono.fromRunnable(Throwing.runnable(this::commit).sneakyThrow()))
+                .doOnError(MailboxException.class, Throwing.consumer(e -> rollback()).sneakyThrow());
+    }
+
     /**
      * Begin transaction
      */
diff --git a/mailbox/store/src/test/java/org/apache/james/mailbox/store/MessageIdManagerTestSystem.java b/mailbox/store/src/test/java/org/apache/james/mailbox/store/MessageIdManagerTestSystem.java
index 420e94a..24ccc3c 100644
--- a/mailbox/store/src/test/java/org/apache/james/mailbox/store/MessageIdManagerTestSystem.java
+++ b/mailbox/store/src/test/java/org/apache/james/mailbox/store/MessageIdManagerTestSystem.java
@@ -56,8 +56,6 @@ public class MessageIdManagerTestSystem {
      * Should persist flags 
      * Should keep track of flag state for setFlags
      * 
-     * @param mailboxId
-     * @param flags
      * @return the id of persisted message
      */
 
@@ -84,7 +82,7 @@ public class MessageIdManagerTestSystem {
     public MessageId persist(MailboxId mailboxId, MessageUid uid, Flags flags, MailboxSession mailboxSession) {
         try {
             MessageId messageId = messageIdFactory.generate();
-            Mailbox mailbox = mapperFactory.getMailboxMapper(mailboxSession).findMailboxById(mailboxId);
+            Mailbox mailbox = mapperFactory.getMailboxMapper(mailboxSession).findMailboxById(mailboxId).block();
             MailboxMessage message = createMessage(mailboxId, flags, messageId, uid);
             mapperFactory.getMessageMapper(mailboxSession).add(mailbox, message);
             mailboxManager.getEventBus().dispatch(EventFactory.added()
@@ -107,7 +105,7 @@ public class MessageIdManagerTestSystem {
 
     public void deleteMailbox(MailboxId mailboxId, MailboxSession mailboxSession) {
         try {
-            Mailbox mailbox = mapperFactory.getMailboxMapper(mailboxSession).findMailboxById(mailboxId);
+            Mailbox mailbox = mapperFactory.getMailboxMapper(mailboxSession).findMailboxById(mailboxId).block();
             mailboxManager.deleteMailbox(new MailboxPath(mailbox.getNamespace(), mailbox.getUser(), mailbox.getName()), mailboxSession);
         } catch (Exception e) {
             throw new RuntimeException(e);
diff --git a/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreMailboxManagerAnnotationTest.java b/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreMailboxManagerAnnotationTest.java
index ee73f44..0424b4c 100644
--- a/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreMailboxManagerAnnotationTest.java
+++ b/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreMailboxManagerAnnotationTest.java
@@ -23,8 +23,6 @@ import static org.assertj.core.api.Assertions.assertThat;
 import static org.assertj.core.api.Assertions.assertThatThrownBy;
 import static org.mockito.ArgumentMatchers.any;
 import static org.mockito.ArgumentMatchers.eq;
-import static org.mockito.Mockito.doReturn;
-import static org.mockito.Mockito.doThrow;
 import static org.mockito.Mockito.spy;
 import static org.mockito.Mockito.times;
 import static org.mockito.Mockito.verify;
@@ -103,16 +101,16 @@ class StoreMailboxManagerAnnotationTest {
     }
 
     @Test
-    void updateAnnotationsShouldThrowExceptionWhenDoesNotLookupMailbox() throws Exception {
-        doThrow(MailboxException.class).when(mailboxMapper).findMailboxByPathBlocking(eq(mailboxPath));
+    void updateAnnotationsShouldThrowExceptionWhenDoesNotLookupMailbox() {
+        when(mailboxMapper.findMailboxByPath(eq(mailboxPath))).thenReturn(Mono.error(new MailboxException()));
 
         assertThatThrownBy(() -> annotationManager.updateAnnotations(mailboxPath, session, ImmutableList.of(PRIVATE_ANNOTATION)))
-            .isInstanceOf(MailboxException.class);
+            .hasCauseInstanceOf(MailboxException.class);
     }
 
     @Test
     void updateAnnotationsShouldCallAnnotationMapperToInsertAnnotation() throws Exception {
-        when(mailboxMapper.findMailboxByPathBlocking(eq(mailboxPath))).thenReturn(mailbox);
+        when(mailboxMapper.findMailboxByPath(eq(mailboxPath))).thenReturn(Mono.just(mailbox));
         annotationManager.updateAnnotations(mailboxPath, session, ANNOTATIONS);
 
         verify(annotationMapper, times(2)).insertAnnotation(eq(mailboxId), any(MailboxAnnotation.class));
@@ -120,7 +118,7 @@ class StoreMailboxManagerAnnotationTest {
 
     @Test
     void updateAnnotationsShouldCallAnnotationMapperToDeleteAnnotation() throws Exception {
-        when(mailboxMapper.findMailboxByPathBlocking(eq(mailboxPath))).thenReturn(mailbox);
+        when(mailboxMapper.findMailboxByPath(eq(mailboxPath))).thenReturn(Mono.just(mailbox));
         annotationManager.updateAnnotations(mailboxPath, session, ANNOTATIONS_WITH_NIL_ENTRY);
 
         verify(annotationMapper, times(1)).insertAnnotation(eq(mailboxId), eq(PRIVATE_ANNOTATION));
@@ -129,15 +127,15 @@ class StoreMailboxManagerAnnotationTest {
 
     @Test
     void getAllAnnotationsShouldThrowExceptionWhenDoesNotLookupMailbox() throws Exception {
-        doThrow(MailboxException.class).when(mailboxMapper).findMailboxByPathBlocking(eq(mailboxPath));
+        when(mailboxMapper.findMailboxByPath(eq(mailboxPath))).thenReturn(Mono.error(new MailboxException()));
 
         assertThatThrownBy(() -> annotationManager.getAllAnnotations(mailboxPath, session))
-            .isInstanceOf(MailboxException.class);
+            .hasCauseInstanceOf(MailboxException.class);
     }
 
     @Test
     void getAllAnnotationsShouldReturnEmptyForNonStoredAnnotation() throws Exception {
-        when(mailboxMapper.findMailboxByPathBlocking(eq(mailboxPath))).thenReturn(mailbox);
+        when(mailboxMapper.findMailboxByPath(eq(mailboxPath))).thenReturn(Mono.just(mailbox));
         when(annotationMapper.getAllAnnotations(eq(mailboxId))).thenReturn(Collections.<MailboxAnnotation>emptyList());
 
         assertThat(annotationManager.getAllAnnotations(mailboxPath, session)).isEmpty();
@@ -145,23 +143,23 @@ class StoreMailboxManagerAnnotationTest {
 
     @Test
     void getAllAnnotationsShouldReturnStoredAnnotation() throws Exception {
-        when(mailboxMapper.findMailboxByPathBlocking(eq(mailboxPath))).thenReturn(mailbox);
+        when(mailboxMapper.findMailboxByPath(eq(mailboxPath))).thenReturn(Mono.just(mailbox));
         when(annotationMapper.getAllAnnotations(eq(mailboxId))).thenReturn(ANNOTATIONS);
 
         assertThat(annotationManager.getAllAnnotations(mailboxPath, session)).isEqualTo(ANNOTATIONS);
     }
 
     @Test
-    void getAnnotationsByKeysShouldThrowExceptionWhenDoesNotLookupMailbox() throws Exception {
-        doThrow(MailboxException.class).when(mailboxMapper).findMailboxByPathBlocking(eq(mailboxPath));
+    void getAnnotationsByKeysShouldThrowExceptionWhenDoesNotLookupMailbox() {
+        when(mailboxMapper.findMailboxByPath(eq(mailboxPath))).thenReturn(Mono.error(new MailboxException()));
 
         assertThatThrownBy(() -> annotationManager.getAnnotationsByKeys(mailboxPath, session, KEYS))
-            .isInstanceOf(MailboxException.class);
+            .hasCauseInstanceOf(MailboxException.class);
     }
 
     @Test
     void getAnnotationsByKeysShouldRetrieveStoreAnnotationsByKey() throws Exception {
-        when(mailboxMapper.findMailboxByPathBlocking(eq(mailboxPath))).thenReturn(mailbox);
+        when(mailboxMapper.findMailboxByPath(eq(mailboxPath))).thenReturn(Mono.just(mailbox));
         when(annotationMapper.getAnnotationsByKeys(eq(mailboxId), eq(KEYS))).thenReturn(ANNOTATIONS);
 
         assertThat(annotationManager.getAnnotationsByKeys(mailboxPath, session, KEYS)).isEqualTo(ANNOTATIONS);
diff --git a/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreMailboxManagerTest.java b/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreMailboxManagerTest.java
index 7feaceb..0143de2 100644
--- a/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreMailboxManagerTest.java
+++ b/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreMailboxManagerTest.java
@@ -107,8 +107,8 @@ class StoreMailboxManagerTest {
     }
 
     @Test
-    void getMailboxShouldThrowWhenUnknownId() throws Exception {
-        when(mockedMailboxMapper.findMailboxById(MAILBOX_ID)).thenReturn(null);
+    void getMailboxShouldThrowWhenUnknownId() {
+        when(mockedMailboxMapper.findMailboxById(MAILBOX_ID)).thenReturn(Mono.error(new MailboxNotFoundException(MAILBOX_ID)));
 
         assertThatThrownBy(() -> storeMailboxManager.getMailbox(MAILBOX_ID, mockedMailboxSession))
             .isInstanceOf(MailboxNotFoundException.class);
@@ -120,7 +120,7 @@ class StoreMailboxManagerTest {
         when(mockedMailbox.generateAssociatedPath())
             .thenReturn(MailboxPath.forUser(CURRENT_USER, "mailboxName"));
         when(mockedMailbox.getMailboxId()).thenReturn(MAILBOX_ID);
-        when(mockedMailboxMapper.findMailboxById(MAILBOX_ID)).thenReturn(mockedMailbox);
+        when(mockedMailboxMapper.findMailboxById(MAILBOX_ID)).thenReturn(Mono.just(mockedMailbox));
 
         MessageManager expected = storeMailboxManager.getMailbox(MAILBOX_ID, mockedMailboxSession);
 
@@ -133,7 +133,7 @@ class StoreMailboxManagerTest {
         when(mockedMailbox.generateAssociatedPath())
             .thenReturn(MailboxPath.forUser(Username.of("uSEr"), "mailboxName"));
         when(mockedMailbox.getMailboxId()).thenReturn(MAILBOX_ID);
-        when(mockedMailboxMapper.findMailboxById(MAILBOX_ID)).thenReturn(mockedMailbox);
+        when(mockedMailboxMapper.findMailboxById(MAILBOX_ID)).thenReturn(Mono.just(mockedMailbox));
 
         MessageManager expected = storeMailboxManager.getMailbox(MAILBOX_ID, mockedMailboxSession);
 
@@ -141,7 +141,7 @@ class StoreMailboxManagerTest {
     }
 
     @Test
-    void getMailboxShouldThrowWhenMailboxDoesNotMatchUserWithoutRight() throws Exception {
+    void getMailboxShouldThrowWhenMailboxDoesNotMatchUserWithoutRight() {
         Username otherUser = Username.of("other.user");
         Mailbox mockedMailbox = mock(Mailbox.class);
         when(mockedMailbox.getACL()).thenReturn(new MailboxACL());
@@ -149,7 +149,7 @@ class StoreMailboxManagerTest {
             .thenReturn(MailboxPath.forUser(otherUser, "mailboxName"));
         when(mockedMailbox.getMailboxId()).thenReturn(MAILBOX_ID);
         when(mockedMailbox.getUser()).thenReturn(otherUser);
-        when(mockedMailboxMapper.findMailboxById(MAILBOX_ID)).thenReturn(mockedMailbox);
+        when(mockedMailboxMapper.findMailboxById(MAILBOX_ID)).thenReturn(Mono.just(mockedMailbox));
         when(mockedMailboxMapper.findMailboxByPath(any())).thenReturn(Mono.just(mockedMailbox));
 
         assertThatThrownBy(() -> storeMailboxManager.getMailbox(MAILBOX_ID, mockedMailboxSession))
diff --git a/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreRightManagerTest.java b/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreRightManagerTest.java
index a880c3a..465da65 100644
--- a/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreRightManagerTest.java
+++ b/mailbox/store/src/test/java/org/apache/james/mailbox/store/StoreRightManagerTest.java
@@ -70,7 +70,7 @@ class StoreRightManagerTest {
     MailboxMapper mockedMailboxMapper;
 
     @BeforeEach
-    void setup() throws MailboxException {
+    void setup() {
         aliceSession = MailboxSessionUtil.create(MailboxFixture.ALICE);
         MailboxSessionMapperFactory mockedMapperFactory = mock(MailboxSessionMapperFactory.class);
         mockedMailboxMapper = mock(MailboxMapper.class);
@@ -84,10 +84,10 @@ class StoreRightManagerTest {
     }
 
     @Test
-    void hasRightShouldThrowMailboxNotFoundExceptionWhenMailboxDoesNotExist() throws MailboxException {
+    void hasRightShouldThrowMailboxNotFoundExceptionWhenMailboxDoesNotExist() {
         MailboxPath mailboxPath = MailboxPath.forUser(MailboxFixture.ALICE, "unexisting mailbox");
-        when(mockedMailboxMapper.findMailboxByPathBlocking(mailboxPath))
-            .thenThrow(new MailboxNotFoundException(""));
+        when(mockedMailboxMapper.findMailboxByPath(mailboxPath))
+            .thenReturn(Mono.error(new MailboxNotFoundException("")));
 
         assertThatThrownBy(() ->
             storeRightManager.hasRight(mailboxPath, Right.Read, aliceSession))
@@ -95,7 +95,7 @@ class StoreRightManagerTest {
     }
 
     @Test
-    void hasRightShouldReturnTrueWhenTheUserOwnTheMailbox() throws MailboxException {
+    void hasRightShouldReturnTrueWhenTheUserOwnTheMailbox() {
         Mailbox mailbox = new Mailbox(MailboxPath.forUser(ALICE, MailboxConstants.INBOX), UID_VALIDITY, MAILBOX_ID);
 
         assertThat(storeRightManager.hasRight(mailbox, Right.Write, aliceSession))
@@ -121,7 +121,7 @@ class StoreRightManagerTest {
     }
 
     @Test
-    void hasRightShouldReturnFalseWhenTheUserDoesNotOwnTheMailboxAndHasNoRightOnIt() throws MailboxException {
+    void hasRightShouldReturnFalseWhenTheUserDoesNotOwnTheMailboxAndHasNoRightOnIt() {
         Mailbox mailbox = new Mailbox(MailboxPath.forUser(BOB, MailboxConstants.INBOX), UID_VALIDITY, MAILBOX_ID);
 
         assertThat(storeRightManager.hasRight(mailbox, Right.Write, aliceSession))
diff --git a/mailbox/store/src/test/java/org/apache/james/mailbox/store/SystemMailboxesProviderImplTest.java b/mailbox/store/src/test/java/org/apache/james/mailbox/store/SystemMailboxesProviderImplTest.java
index 48b16f6..fc0ca0d 100644
--- a/mailbox/store/src/test/java/org/apache/james/mailbox/store/SystemMailboxesProviderImplTest.java
+++ b/mailbox/store/src/test/java/org/apache/james/mailbox/store/SystemMailboxesProviderImplTest.java
@@ -20,6 +20,7 @@
 package org.apache.james.mailbox.store;
 
 import static org.assertj.core.api.Assertions.assertThat;
+import static org.mockito.ArgumentMatchers.any;
 import static org.mockito.ArgumentMatchers.eq;
 import static org.mockito.Mockito.mock;
 import static org.mockito.Mockito.when;
@@ -34,6 +35,8 @@ import org.apache.james.mailbox.fixture.MailboxFixture;
 import org.junit.jupiter.api.BeforeEach;
 import org.junit.jupiter.api.Test;
 
+import reactor.core.publisher.Flux;
+
 class SystemMailboxesProviderImplTest {
 
     MailboxSession mailboxSession = MailboxSessionUtil.create(MailboxFixture.ALICE);
@@ -55,6 +58,7 @@ class SystemMailboxesProviderImplTest {
     void getMailboxByRoleShouldReturnEmptyWhenNoMailbox() throws Exception {
         when(mailboxManager.createSystemSession(MailboxFixture.ALICE)).thenReturn(mailboxSession);
         when(mailboxManager.getMailbox(eq(MailboxFixture.INBOX_ALICE), eq(mailboxSession))).thenThrow(MailboxNotFoundException.class);
+        when(mailboxManager.search(any(), any())).thenReturn(Flux.empty());
 
         assertThat(systemMailboxProvider.getMailboxByRole(Role.INBOX, mailboxSession.getUser())).isEmpty();
     }
diff --git a/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MailboxMapperACLTest.java b/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MailboxMapperACLTest.java
index c8aef54..2725022 100644
--- a/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MailboxMapperACLTest.java
+++ b/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MailboxMapperACLTest.java
@@ -52,29 +52,31 @@ public abstract class MailboxMapperACLTest {
     protected abstract MailboxMapper createMailboxMapper();
 
     @BeforeEach
-    void setUp() throws Exception {
+    void setUp() {
         mailboxMapper = createMailboxMapper();
         MailboxPath benwaInboxPath = MailboxPath.forUser(Username.of("benwa"), "INBOX");
-        benwaInboxMailbox = mailboxMapper.create(benwaInboxPath, UID_VALIDITY);
+        benwaInboxMailbox = mailboxMapper.create(benwaInboxPath, UID_VALIDITY).block();
     }
 
     @Test
-    void storedAclShouldBeEmptyByDefault() throws MailboxException {
+    void storedAclShouldBeEmptyByDefault() {
         assertThat(
             mailboxMapper.findMailboxById(benwaInboxMailbox.getMailboxId())
+                .block()
                 .getACL()
                 .getEntries())
             .isEmpty();
     }
 
     @Test
-    void updateAclShouldSaveAclWhenReplace() throws MailboxException {
+    void updateAclShouldSaveAclWhenReplace() {
         EntryKey key = EntryKey.createUserEntryKey(USER);
         Rfc4314Rights rights = new Rfc4314Rights(Right.Administer, Right.PerformExpunge, Right.Write, Right.WriteSeenFlag);
-        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(rights).asReplacement());
+        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(rights).asReplacement()).block();
 
         assertThat(
             mailboxMapper.findMailboxById(benwaInboxMailbox.getMailboxId())
+                .block()
                 .getACL()
                 .getEntries())
             .hasSize(1)
@@ -82,16 +84,17 @@ public abstract class MailboxMapperACLTest {
     }
 
     @Test
-    void updateAclShouldOverwriteStoredAclWhenReplace() throws MailboxException {
+    void updateAclShouldOverwriteStoredAclWhenReplace() {
         EntryKey key = EntryKey.createUserEntryKey(USER);
         Rfc4314Rights rights = new Rfc4314Rights(Right.Administer, Right.PerformExpunge, Right.Write, Right.WriteSeenFlag);
         Rfc4314Rights newRights = new Rfc4314Rights(Right.WriteSeenFlag, Right.CreateMailbox, Right.Administer, Right.PerformExpunge, Right.DeleteMessages);
 
-        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(rights).asReplacement());
-        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(newRights).asReplacement());
+        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(rights).asReplacement()).block();
+        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(newRights).asReplacement()).block();
 
         assertThat(
             mailboxMapper.findMailboxById(benwaInboxMailbox.getMailboxId())
+                .block()
                 .getACL()
                 .getEntries())
             .hasSize(1)
@@ -99,16 +102,17 @@ public abstract class MailboxMapperACLTest {
     }
 
     @Test
-    void updateAclShouldTreatNegativeAndPositiveRightSeparately() throws MailboxException {
+    void updateAclShouldTreatNegativeAndPositiveRightSeparately() {
         EntryKey key1 = EntryKey.createUserEntryKey(USER, NEGATIVE);
         EntryKey key2 = EntryKey.createUserEntryKey(USER, POSITIVE);
         Rfc4314Rights rights = new Rfc4314Rights(Right.Administer, Right.PerformExpunge, Right.Write, Right.WriteSeenFlag);
         Rfc4314Rights newRights = new Rfc4314Rights(Right.WriteSeenFlag, Right.CreateMailbox, Right.Administer, Right.PerformExpunge, Right.DeleteMessages);
-        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key1).rights(rights).asReplacement());
-        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key2).rights(newRights).asReplacement());
+        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key1).rights(rights).asReplacement()).block();
+        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key2).rights(newRights).asReplacement()).block();
 
         assertThat(
             mailboxMapper.findMailboxById(benwaInboxMailbox.getMailboxId())
+                .block()
                 .getACL()
                 .getEntries())
             .hasSize(2)
@@ -117,16 +121,17 @@ public abstract class MailboxMapperACLTest {
     }
 
     @Test
-    void updateAclShouldTreatNameTypesRightSeparately() throws MailboxException {
+    void updateAclShouldTreatNameTypesRightSeparately() {
         EntryKey key1 = EntryKey.createUserEntryKey(USER);
         EntryKey key2 = EntryKey.createGroupEntryKey(USER.asString());
         Rfc4314Rights rights = new Rfc4314Rights(Right.Administer, Right.PerformExpunge, Right.Write, Right.WriteSeenFlag);
         Rfc4314Rights newRights = new Rfc4314Rights(Right.WriteSeenFlag, Right.CreateMailbox, Right.Administer, Right.PerformExpunge, Right.DeleteMessages);
-        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key1).rights(rights).asReplacement());
-        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key2).rights(newRights).asReplacement());
+        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key1).rights(rights).asReplacement()).block();
+        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key2).rights(newRights).asReplacement()).block();
 
         assertThat(
             mailboxMapper.findMailboxById(benwaInboxMailbox.getMailboxId())
+                .block()
                 .getACL()
                 .getEntries())
             .hasSize(2)
@@ -135,31 +140,33 @@ public abstract class MailboxMapperACLTest {
     }
 
     @Test
-    void updateAclShouldCleanAclEntryWhenEmptyReplace() throws MailboxException {
+    void updateAclShouldCleanAclEntryWhenEmptyReplace() {
         EntryKey key = EntryKey.createUserEntryKey(USER);
         Rfc4314Rights rights = new Rfc4314Rights(Right.Administer, Right.PerformExpunge, Right.Write, Right.WriteSeenFlag);
         Rfc4314Rights newRights = new Rfc4314Rights();
-        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(rights).asReplacement());
-        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(newRights).asReplacement());
+        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(rights).asReplacement()).block();
+        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(newRights).asReplacement()).block();
 
         assertThat(
             mailboxMapper.findMailboxById(benwaInboxMailbox.getMailboxId())
+                .block()
                 .getACL()
                 .getEntries())
             .isEmpty();
     }
 
     @Test
-    void updateAclShouldCombineStoredAclWhenAdd() throws MailboxException {
+    void updateAclShouldCombineStoredAclWhenAdd() {
         EntryKey key = EntryKey.createUserEntryKey(USER);
         Rfc4314Rights rights = new Rfc4314Rights(Right.Administer, Right.PerformExpunge, Right.Write, Right.WriteSeenFlag);
         Rfc4314Rights newRights = new Rfc4314Rights(Right.WriteSeenFlag, Right.CreateMailbox, Right.Administer, Right.PerformExpunge, Right.DeleteMessages);
         Rfc4314Rights bothRights = new Rfc4314Rights(Right.Administer, Right.WriteSeenFlag, Right.PerformExpunge, Right.Write, Right.CreateMailbox, Right.DeleteMessages);
-        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(rights).asReplacement());
-        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(newRights).asAddition());
+        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(rights).asReplacement()).block();
+        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(newRights).asAddition()).block();
 
         assertThat(
             mailboxMapper.findMailboxById(benwaInboxMailbox.getMailboxId())
+                .block()
                 .getACL()
                 .getEntries())
             .hasSize(1)
@@ -167,16 +174,17 @@ public abstract class MailboxMapperACLTest {
     }
 
     @Test
-    void removeAclShouldRemoveSomeStoredAclWhenAdd() throws MailboxException {
+    void removeAclShouldRemoveSomeStoredAclWhenAdd() {
         EntryKey key = EntryKey.createUserEntryKey(USER);
         Rfc4314Rights rights = new Rfc4314Rights(Right.Administer, Right.PerformExpunge, Right.Write, Right.WriteSeenFlag);
         Rfc4314Rights removedRights = new Rfc4314Rights(Right.WriteSeenFlag, Right.PerformExpunge);
         Rfc4314Rights finalRights = new Rfc4314Rights(Right.Administer, Right.Write);
-        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(rights).asReplacement());
-        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(removedRights).asRemoval());
+        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(rights).asReplacement()).block();
+        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(removedRights).asRemoval()).block();
 
         assertThat(
             mailboxMapper.findMailboxById(benwaInboxMailbox.getMailboxId())
+                .block()
                 .getACL()
                 .getEntries())
             .hasSize(1)
@@ -184,16 +192,17 @@ public abstract class MailboxMapperACLTest {
     }
 
     @Test
-    void removeAclShouldNotFailWhenRemovingNonExistingRight() throws MailboxException {
+    void removeAclShouldNotFailWhenRemovingNonExistingRight() {
         EntryKey key = EntryKey.createUserEntryKey(USER);
         Rfc4314Rights rights = new Rfc4314Rights(Right.Administer, Right.PerformExpunge, Right.Write, Right.WriteSeenFlag);
         Rfc4314Rights removedRights = new Rfc4314Rights(Right.WriteSeenFlag, Right.PerformExpunge, Right.Lookup);
         Rfc4314Rights finalRights = new Rfc4314Rights(Right.Administer, Right.Write);
-        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(rights).asReplacement());
-        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(removedRights).asRemoval());
+        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(rights).asReplacement()).block();
+        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(removedRights).asRemoval()).block();
 
         assertThat(
             mailboxMapper.findMailboxById(benwaInboxMailbox.getMailboxId())
+                .block()
                 .getACL()
                 .getEntries())
             .hasSize(1)
@@ -201,15 +210,16 @@ public abstract class MailboxMapperACLTest {
     }
 
     @Test
-    void resetAclShouldReplaceStoredAcl() throws MailboxException {
+    void resetAclShouldReplaceStoredAcl() {
         EntryKey key = EntryKey.createUserEntryKey(USER);
         Rfc4314Rights rights = new Rfc4314Rights(Right.Administer, Right.PerformExpunge, Right.Write, Right.WriteSeenFlag);
         Rfc4314Rights newRights = new Rfc4314Rights(Right.WriteSeenFlag, Right.CreateMailbox, Right.Administer, Right.PerformExpunge, Right.DeleteMessages);
-        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(rights).asReplacement());
-        mailboxMapper.setACL(benwaInboxMailbox, new MailboxACL(ImmutableMap.of(key, newRights)));
+        mailboxMapper.updateACL(benwaInboxMailbox, MailboxACL.command().key(key).rights(rights).asReplacement()).block();
+        mailboxMapper.setACL(benwaInboxMailbox, new MailboxACL(ImmutableMap.of(key, newRights))).block();
 
         assertThat(
             mailboxMapper.findMailboxById(benwaInboxMailbox.getMailboxId())
+                .block()
                 .getACL()
                 .getEntries())
             .hasSize(1)
@@ -217,14 +227,15 @@ public abstract class MailboxMapperACLTest {
     }
     
     @Test
-    void resetAclShouldInitializeStoredAcl() throws MailboxException {
+    void resetAclShouldInitializeStoredAcl() {
         EntryKey key = EntryKey.createUserEntryKey(USER);
         Rfc4314Rights rights = new Rfc4314Rights(Right.WriteSeenFlag, Right.CreateMailbox, Right.Administer, Right.PerformExpunge, Right.DeleteMessages);
         mailboxMapper.setACL(benwaInboxMailbox,
-            new MailboxACL(ImmutableMap.of(key, rights)));
+            new MailboxACL(ImmutableMap.of(key, rights))).block();
 
         assertThat(
             mailboxMapper.findMailboxById(benwaInboxMailbox.getMailboxId())
+                .block()
                 .getACL()
                 .getEntries())
             .hasSize(1)
@@ -232,51 +243,53 @@ public abstract class MailboxMapperACLTest {
     }
 
     @Test
-    void findMailboxesShouldReturnEmptyWhenNone() throws MailboxException {
-        assertThat(mailboxMapper.findNonPersonalMailboxes(USER, Right.Administer).collectList().block()).isEmpty();
+    void findMailboxesShouldReturnEmptyWhenNone() {
+        assertThat(mailboxMapper.findNonPersonalMailboxes(USER, Right.Administer).collectList().block())
+            .isEmpty();
     }
 
     @Test
-    void findMailboxesShouldReturnEmptyWhenRightDoesntMatch() throws MailboxException {
+    void findMailboxesShouldReturnEmptyWhenRightDoesntMatch() {
         EntryKey key = EntryKey.createUserEntryKey(USER);
         Rfc4314Rights rights = new Rfc4314Rights(Right.Administer);
         mailboxMapper.updateACL(benwaInboxMailbox,
             MailboxACL.command()
                 .key(key)
                 .rights(rights)
-                .asReplacement());
+                .asReplacement()).block();
 
-        assertThat(mailboxMapper.findNonPersonalMailboxes(USER, Right.Read).collectList().block()).isEmpty();
+        assertThat(mailboxMapper.findNonPersonalMailboxes(USER, Right.Read).collectList().block())
+            .isEmpty();
     }
 
     @Test
-    void updateACLShouldInsertUsersRights() throws MailboxException {
+    void updateACLShouldInsertUsersRights() {
         Rfc4314Rights rights = new Rfc4314Rights(Right.Administer, Right.PerformExpunge);
         mailboxMapper.updateACL(benwaInboxMailbox,
             MailboxACL.command()
                 .key(EntryKey.createUserEntryKey(USER))
                 .rights(rights)
-                .asAddition());
+                .asAddition()).block();
 
         assertThat(mailboxMapper.findNonPersonalMailboxes(USER, Right.Administer).collectList().block())
             .containsOnly(benwaInboxMailbox);
     }
 
     @Test
-    void updateACLShouldOverwriteUsersRights() throws MailboxException {
+    void updateACLShouldOverwriteUsersRights() {
         EntryKey key = EntryKey.createUserEntryKey(USER);
         Rfc4314Rights initialRights = new Rfc4314Rights(Right.Administer);
         mailboxMapper.updateACL(benwaInboxMailbox,
             MailboxACL.command()
                 .key(key)
                 .rights(initialRights)
-                .asReplacement());
+                .asReplacement()).block();
         Rfc4314Rights newRights = new Rfc4314Rights(Right.Read);
         mailboxMapper.updateACL(benwaInboxMailbox,
             MailboxACL.command()
                 .key(key)
                 .rights(newRights)
-                .asReplacement());
+                .asReplacement()).block();
 
         assertThat(mailboxMapper.findNonPersonalMailboxes(USER, Right.Read).collectList().block())
             .containsOnly(benwaInboxMailbox);
@@ -286,7 +299,7 @@ public abstract class MailboxMapperACLTest {
     }
 
     @Test
-    void findMailboxesShouldNotReportDeletedACLViaReplace() throws MailboxException {
+    void findMailboxesShouldNotReportDeletedACLViaReplace() {
         EntryKey key = EntryKey.createUserEntryKey(USER);
         Rfc4314Rights initialRights = new Rfc4314Rights(Right.Administer);
         mailboxMapper.updateACL(benwaInboxMailbox,
@@ -294,60 +307,60 @@ public abstract class MailboxMapperACLTest {
                 .key(key)
                 .mode(MailboxACL.EditMode.REPLACE)
                 .rights(initialRights)
-                .build());
+                .build()).block();
         mailboxMapper.updateACL(benwaInboxMailbox,
             MailboxACL.command()
                 .key(key)
                 .mode(MailboxACL.EditMode.REPLACE)
                 .rights(new Rfc4314Rights())
-                .build());
+                .build()).block();
 
         assertThat(mailboxMapper.findNonPersonalMailboxes(USER, Right.Administer).collectList().block())
             .isEmpty();
     }
 
     @Test
-    void findMailboxesShouldNotReportDeletedACLViaRemove() throws MailboxException {
+    void findMailboxesShouldNotReportDeletedACLViaRemove() {
         EntryKey key = EntryKey.createUserEntryKey(USER);
         Rfc4314Rights initialRights = new Rfc4314Rights(Right.Administer);
         mailboxMapper.updateACL(benwaInboxMailbox,
             MailboxACL.command()
                 .key(key)
                 .rights(initialRights)
-                .asReplacement());
+                .asReplacement()).block();
         mailboxMapper.updateACL(benwaInboxMailbox,
             MailboxACL.command()
                 .key(key)
                 .rights(initialRights)
-                .asRemoval());
+                .asRemoval()).block();
 
         assertThat(mailboxMapper.findNonPersonalMailboxes(USER, Right.Administer).collectList().block())
             .isEmpty();
     }
 
     @Test
-    void findMailboxesShouldNotReportDeletedMailboxes() throws MailboxException {
+    void findMailboxesShouldNotReportDeletedMailboxes() {
         EntryKey key = EntryKey.createUserEntryKey(USER);
         Rfc4314Rights initialRights = new Rfc4314Rights(Right.Administer);
         mailboxMapper.updateACL(benwaInboxMailbox,
             MailboxACL.command()
                 .key(key)
                 .rights(initialRights)
-                .asReplacement());
-        mailboxMapper.delete(benwaInboxMailbox);
+                .asReplacement()).block();
+        mailboxMapper.delete(benwaInboxMailbox).block();
 
         assertThat(mailboxMapper.findNonPersonalMailboxes(USER, Right.Administer).collectList().block())
             .isEmpty();
     }
 
     @Test
-    void setACLShouldStoreMultipleUsersRights() throws MailboxException {
+    void setACLShouldStoreMultipleUsersRights() {
         EntryKey user1 = EntryKey.createUserEntryKey(USER_1);
         EntryKey user2 = EntryKey.createUserEntryKey(USER_2);
 
         mailboxMapper.setACL(benwaInboxMailbox, new MailboxACL(
             new MailboxACL.Entry(user1, new Rfc4314Rights(Right.Administer)),
-            new MailboxACL.Entry(user2, new Rfc4314Rights(Right.Read))));
+            new MailboxACL.Entry(user2, new Rfc4314Rights(Right.Read)))).block();
 
         assertThat(mailboxMapper.findNonPersonalMailboxes(USER_1, Right.Administer).collectList().block())
             .containsOnly(benwaInboxMailbox);
@@ -356,43 +369,43 @@ public abstract class MailboxMapperACLTest {
     }
 
     @Test
-    void findMailboxesShouldNotReportRightsRemovedViaSetAcl() throws MailboxException {
+    void findMailboxesShouldNotReportRightsRemovedViaSetAcl() {
         EntryKey user1 = EntryKey.createUserEntryKey(USER_1);
         EntryKey user2 = EntryKey.createUserEntryKey(USER_2);
 
         mailboxMapper.setACL(benwaInboxMailbox, new MailboxACL(
             new MailboxACL.Entry(user1, new Rfc4314Rights(Right.Administer)),
-            new MailboxACL.Entry(user2, new Rfc4314Rights(Right.Read))));
+            new MailboxACL.Entry(user2, new Rfc4314Rights(Right.Read)))).block();
 
         mailboxMapper.setACL(benwaInboxMailbox, new MailboxACL(
-            new MailboxACL.Entry(user2, new Rfc4314Rights(Right.Read))));
+            new MailboxACL.Entry(user2, new Rfc4314Rights(Right.Read)))).block();
 
         assertThat(mailboxMapper.findNonPersonalMailboxes(USER_1, Right.Administer).collectList().block())
             .isEmpty();
     }
 
     @Test
-    void findMailboxesShouldReportRightsUpdatedViaSetAcl() throws MailboxException {
+    void findMailboxesShouldReportRightsUpdatedViaSetAcl() {
         EntryKey user1 = EntryKey.createUserEntryKey(USER_1);
         EntryKey user2 = EntryKey.createUserEntryKey(USER_2);
 
         mailboxMapper.setACL(benwaInboxMailbox, new MailboxACL(
             new MailboxACL.Entry(user1, new Rfc4314Rights(Right.Administer)),
-            new MailboxACL.Entry(user2, new Rfc4314Rights(Right.Read))));
+            new MailboxACL.Entry(user2, new Rfc4314Rights(Right.Read)))).block();
 
         mailboxMapper.setACL(benwaInboxMailbox, new MailboxACL(
-            new MailboxACL.Entry(user2, new Rfc4314Rights(Right.Write))));
+            new MailboxACL.Entry(user2, new Rfc4314Rights(Right.Write)))).block();
 
         assertThat(mailboxMapper.findNonPersonalMailboxes(USER_2, Right.Write).collectList().block())
             .containsOnly(benwaInboxMailbox);
     }
 
     @Test
-    void findMailboxByPathShouldReturnMailboxWithACL() throws MailboxException {
+    void findMailboxByPathShouldReturnMailboxWithACL() {
         EntryKey key = EntryKey.createUserEntryKey(USER);
         Rfc4314Rights rights = new Rfc4314Rights(Right.WriteSeenFlag, Right.CreateMailbox, Right.Administer, Right.PerformExpunge, Right.DeleteMessages);
         mailboxMapper.setACL(benwaInboxMailbox,
-            new MailboxACL(ImmutableMap.of(key, rights)));
+            new MailboxACL(ImmutableMap.of(key, rights))).block();
 
         assertThat(
             mailboxMapper.findMailboxByPath(benwaInboxMailbox.generateAssociatedPath())
@@ -415,7 +428,7 @@ public abstract class MailboxMapperACLTest {
                 .asAddition()));
 
         assertThat(mailboxMapper.setACL(benwaInboxMailbox,
-            new MailboxACL(ImmutableMap.of(key, rights)))).isEqualTo(expectAclDiff);
+            new MailboxACL(ImmutableMap.of(key, rights))).block()).isEqualTo(expectAclDiff);
     }
 
     @Test
@@ -430,6 +443,6 @@ public abstract class MailboxMapperACLTest {
 
         ACLDiff expectAclDiff = ACLDiff.computeDiff(MailboxACL.EMPTY, MailboxACL.EMPTY.apply(aclCommand));
 
-        assertThat(mailboxMapper.updateACL(benwaInboxMailbox, aclCommand)).isEqualTo(expectAclDiff);
+        assertThat(mailboxMapper.updateACL(benwaInboxMailbox, aclCommand).block()).isEqualTo(expectAclDiff);
     }
 }
diff --git a/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MailboxMapperTest.java b/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MailboxMapperTest.java
index 749dbf3..a5a13d1 100644
--- a/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MailboxMapperTest.java
+++ b/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MailboxMapperTest.java
@@ -27,7 +27,6 @@ import static org.assertj.core.api.Assertions.assertThatThrownBy;
 import java.util.List;
 
 import org.apache.james.core.Username;
-import org.apache.james.mailbox.exception.MailboxException;
 import org.apache.james.mailbox.exception.MailboxExistsException;
 import org.apache.james.mailbox.exception.MailboxNotFoundException;
 import org.apache.james.mailbox.model.Mailbox;
@@ -87,23 +86,23 @@ public abstract class MailboxMapperTest {
     }
 
     @Test
-    void createShouldPersistTheMailbox() throws MailboxException {
+    void createShouldPersistTheMailbox() {
         benwaInboxMailbox = createMailbox(benwaInboxPath);
 
         assertThat(mailboxMapper.findMailboxByPath(benwaInboxPath).blockOptional()).contains(benwaInboxMailbox);
-        assertThat(mailboxMapper.findMailboxById(benwaInboxMailbox.getMailboxId())).isEqualTo(benwaInboxMailbox);
+        assertThat(mailboxMapper.findMailboxById(benwaInboxMailbox.getMailboxId()).block()).isEqualTo(benwaInboxMailbox);
     }
 
     @Test
-    void createShouldThrowWhenMailboxAlreadyExists() throws MailboxException {
+    void createShouldThrowWhenMailboxAlreadyExists() {
         benwaInboxMailbox = createMailbox(benwaInboxPath);
 
         assertThatThrownBy(() -> createMailbox(benwaInboxPath))
-            .isInstanceOf(MailboxExistsException.class);
+            .hasCauseInstanceOf(MailboxExistsException.class);
     }
 
     @Test
-    void createShouldSetAMailboxIdForMailbox() throws MailboxException {
+    void createShouldSetAMailboxIdForMailbox() {
         benwaInboxMailbox = createMailbox(benwaInboxPath);
 
         assertThat(benwaInboxMailbox.getMailboxId()).isNotNull();
@@ -111,50 +110,50 @@ public abstract class MailboxMapperTest {
 
     @Test
     void renameShouldThrowWhenMailboxIdIsNull() {
-        assertThatThrownBy(() -> mailboxMapper.rename(benwaInboxMailbox))
+        assertThatThrownBy(() -> mailboxMapper.rename(benwaInboxMailbox).block())
             .isInstanceOf(NullPointerException.class);
     }
 
     @Test
-    void renameShouldRenameTheMailbox() throws MailboxException {
+    void renameShouldRenameTheMailbox() {
         benwaInboxMailbox = createMailbox(benwaInboxPath);
         MailboxId mailboxId = benwaInboxMailbox.getMailboxId();
 
         benwaWorkMailbox = new Mailbox(benwaWorkPath, UID_VALIDITY, mailboxId);
-        mailboxMapper.rename(benwaWorkMailbox);
+        mailboxMapper.rename(benwaWorkMailbox).block();
 
-        assertThat(mailboxMapper.findMailboxById(mailboxId)).isEqualTo(benwaWorkMailbox);
+        assertThat(mailboxMapper.findMailboxById(mailboxId).block()).isEqualTo(benwaWorkMailbox);
     }
 
     @Test
-    void renameShouldThrowWhenMailboxAlreadyExist() throws MailboxException {
+    void renameShouldThrowWhenMailboxAlreadyExist() {
         benwaInboxMailbox = createMailbox(benwaInboxPath);
 
-        assertThatThrownBy(() -> mailboxMapper.rename(benwaInboxMailbox))
-            .isInstanceOf(MailboxExistsException.class);
+        assertThatThrownBy(() -> mailboxMapper.rename(benwaInboxMailbox).block())
+            .hasCauseInstanceOf(MailboxExistsException.class);
     }
 
     @Test
     void renameShouldThrowWhenMailboxDoesNotExist() {
         benwaInboxMailbox = new Mailbox(benwaInboxPath, UID_VALIDITY, generateId());
 
-        assertThatThrownBy(() -> mailboxMapper.rename(benwaInboxMailbox))
-            .isInstanceOf(MailboxNotFoundException.class);
+        assertThatThrownBy(() -> mailboxMapper.rename(benwaInboxMailbox).block())
+            .hasCauseInstanceOf(MailboxNotFoundException.class);
     }
 
     @Test
-    void renameShouldRemoveOldMailboxPath() throws MailboxException {
+    void renameShouldRemoveOldMailboxPath() {
         MailboxId mailboxId = createMailbox(benwaInboxPath).getMailboxId();
 
         benwaWorkMailbox = new Mailbox(benwaWorkPath, UID_VALIDITY, mailboxId);
-        mailboxMapper.rename(benwaWorkMailbox);
+        mailboxMapper.rename(benwaWorkMailbox).block();
 
         assertThat(mailboxMapper.findMailboxByPath(benwaInboxPath).blockOptional())
             .isEmpty();
     }
 
     @Test
-    void listShouldRetrieveAllMailbox() throws MailboxException {
+    void listShouldRetrieveAllMailbox() {
         createAll();
         List<Mailbox> mailboxes = mailboxMapper.list().collectList().block();
 
@@ -164,25 +163,25 @@ public abstract class MailboxMapperTest {
     }
     
     @Test
-    void hasChildrenShouldReturnFalseWhenNoChildrenExists() throws MailboxException {
+    void hasChildrenShouldReturnFalseWhenNoChildrenExists() {
         createAll();
-        assertThat(mailboxMapper.hasChildren(benwaWorkTodoMailbox, DELIMITER)).isFalse();
+        assertThat(mailboxMapper.hasChildren(benwaWorkTodoMailbox, DELIMITER).block()).isFalse();
     }
 
     @Test
-    void hasChildrenShouldReturnTrueWhenChildrenExists() throws MailboxException {
+    void hasChildrenShouldReturnTrueWhenChildrenExists() {
         createAll();
-        assertThat(mailboxMapper.hasChildren(benwaInboxMailbox, DELIMITER)).isTrue();
+        assertThat(mailboxMapper.hasChildren(benwaInboxMailbox, DELIMITER).block()).isTrue();
     }
 
     @Test
-    void hasChildrenShouldNotBeAcrossUsersAndNamespace() throws MailboxException {
+    void hasChildrenShouldNotBeAcrossUsersAndNamespace() {
         createAll();
-        assertThat(mailboxMapper.hasChildren(bobInboxMailbox, '.')).isFalse();
+        assertThat(mailboxMapper.hasChildren(bobInboxMailbox, '.').block()).isFalse();
     }
 
     @Test
-    void findMailboxWithPathLikeShouldBeLimitedToUserAndNamespace() throws MailboxException {
+    void findMailboxWithPathLikeShouldBeLimitedToUserAndNamespace() {
         createAll();
         MailboxQuery.UserBound mailboxQuery = MailboxQuery.builder()
             .userAndNamespaceFrom(bobInboxPath)
@@ -195,18 +194,18 @@ public abstract class MailboxMapperTest {
 
         assertMailboxes(mailboxes).containOnly(bobInboxMailbox);
     }
-    
+
     @Test
-    void deleteShouldEraseTheGivenMailbox() throws MailboxException {
+    void deleteShouldEraseTheGivenMailbox() {
         createAll();
-        mailboxMapper.delete(benwaInboxMailbox);
+        mailboxMapper.delete(benwaInboxMailbox).block();
 
         assertThat(mailboxMapper.findMailboxByPath(benwaInboxPath).blockOptional())
             .isEmpty();
     }
 
     @Test
-    void findMailboxWithPathLikeWithChildRegexShouldRetrieveChildren() throws MailboxException {
+    void findMailboxWithPathLikeWithChildRegexShouldRetrieveChildren() {
         createAll();
         MailboxQuery.UserBound mailboxQuery = MailboxQuery.builder()
             .userAndNamespaceFrom(benwaWorkPath)
@@ -221,7 +220,7 @@ public abstract class MailboxMapperTest {
     }
 
     @Test
-    void findMailboxWithPathLikeWithRegexShouldRetrieveCorrespondingMailbox() throws MailboxException {
+    void findMailboxWithPathLikeWithRegexShouldRetrieveCorrespondingMailbox() {
         createAll();
         MailboxQuery.UserBound mailboxQuery = MailboxQuery.builder()
             .userAndNamespaceFrom(benwaWorkPath)
@@ -236,7 +235,7 @@ public abstract class MailboxMapperTest {
     }
 
     @Test
-    void findMailboxWithPathLikeShouldEscapeMailboxName() throws MailboxException {
+    void findMailboxWithPathLikeShouldEscapeMailboxName() {
         createAll();
         MailboxQuery.UserBound mailboxQuery = MailboxQuery.builder()
             .userAndNamespaceFrom(benwaInboxPath)
@@ -249,22 +248,22 @@ public abstract class MailboxMapperTest {
     }
 
     @Test
-    void findMailboxByIdShouldReturnExistingMailbox() throws MailboxException {
+    void findMailboxByIdShouldReturnExistingMailbox() {
         createAll();
-        Mailbox actual = mailboxMapper.findMailboxById(benwaInboxMailbox.getMailboxId());
+        Mailbox actual = mailboxMapper.findMailboxById(benwaInboxMailbox.getMailboxId()).block();
         assertThat(actual).isEqualTo(benwaInboxMailbox);
     }
     
     @Test
-    void findMailboxByIdShouldFailWhenAbsent() throws MailboxException {
+    void findMailboxByIdShouldFailWhenAbsent() {
         createAll();
         MailboxId removed = benwaInboxMailbox.getMailboxId();
-        mailboxMapper.delete(benwaInboxMailbox);
-        assertThatThrownBy(() -> mailboxMapper.findMailboxById(removed))
-            .isInstanceOf(MailboxNotFoundException.class);
+        mailboxMapper.delete(benwaInboxMailbox).block();
+        assertThatThrownBy(() -> mailboxMapper.findMailboxById(removed).block())
+            .hasCauseInstanceOf(MailboxNotFoundException.class);
     }
 
-    private void createAll() throws MailboxException {
+    private void createAll() {
         benwaInboxMailbox = createMailbox(benwaInboxPath);
         benwaWorkMailbox = createMailbox(benwaWorkPath);
         benwaWorkTodoMailbox = createMailbox(benwaWorkTodoPath);
@@ -275,8 +274,8 @@ public abstract class MailboxMapperTest {
         bobDifferentNamespaceMailbox = createMailbox(bobDifferentNamespacePath);
     }
 
-    private Mailbox createMailbox(MailboxPath mailboxPath) throws MailboxException {
-        return mailboxMapper.create(mailboxPath, UID_VALIDITY);
+    private Mailbox createMailbox(MailboxPath mailboxPath) {
+        return mailboxMapper.create(mailboxPath, UID_VALIDITY).block();
     }
 
 }
diff --git a/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MessageIdMapperTest.java b/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MessageIdMapperTest.java
index 57b90f9..944301b 100644
--- a/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MessageIdMapperTest.java
+++ b/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MessageIdMapperTest.java
@@ -986,7 +986,7 @@ public abstract class MessageIdMapperTest {
     }
 
     private Mailbox createMailbox(MailboxPath mailboxPath) throws MailboxException {
-        return mailboxMapper.create(mailboxPath, UID_VALIDITY);
+        return mailboxMapper.create(mailboxPath, UID_VALIDITY).block();
     }
     
     protected void saveMessages() throws MailboxException {
diff --git a/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MessageMapperTest.java b/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MessageMapperTest.java
index 99c7186..7f0d1ed 100644
--- a/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MessageMapperTest.java
+++ b/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MessageMapperTest.java
@@ -1180,7 +1180,7 @@ public abstract class MessageMapperTest {
     }
 
     private Mailbox createMailbox(MailboxPath mailboxPath) throws MailboxException {
-        return mailboxMapper.create(mailboxPath, UID_VALIDITY);
+        return mailboxMapper.create(mailboxPath, UID_VALIDITY).block();
     }
 
     protected void saveMessages() throws MailboxException {
diff --git a/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MessageMoveTest.java b/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MessageMoveTest.java
index d640246..a9b2182 100644
--- a/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MessageMoveTest.java
+++ b/mailbox/store/src/test/java/org/apache/james/mailbox/store/mail/model/MessageMoveTest.java
@@ -134,8 +134,8 @@ public abstract class MessageMoveTest {
         assertThat(messageMapper.getMailboxCounters(benwaWorkMailbox).getUnseen()).isEqualTo(0);
     }
 
-    private Mailbox createMailbox(MailboxPath mailboxPath) throws MailboxException {
-        return mailboxMapper.create(mailboxPath, UID_VALIDITY);
+    private Mailbox createMailbox(MailboxPath mailboxPath) {
+        return mailboxMapper.create(mailboxPath, UID_VALIDITY).block();
     }
 
     private MailboxMessage retrieveMessageFromStorage(Mailbox mailbox, MailboxMessage message) throws MailboxException {
diff --git a/mailbox/store/src/test/java/org/apache/james/mailbox/store/quota/DefaultUserQuotaRootResolverTest.java b/mailbox/store/src/test/java/org/apache/james/mailbox/store/quota/DefaultUserQuotaRootResolverTest.java
index 3a2cfbc..596a86f 100644
--- a/mailbox/store/src/test/java/org/apache/james/mailbox/store/quota/DefaultUserQuotaRootResolverTest.java
+++ b/mailbox/store/src/test/java/org/apache/james/mailbox/store/quota/DefaultUserQuotaRootResolverTest.java
@@ -99,7 +99,7 @@ class DefaultUserQuotaRootResolverTest {
     }
 
     @Test
-    void retrieveAssociatedMailboxesShouldThrowWhenQuotaRootContainsSeparator2Times() throws Exception {
+    void retrieveAssociatedMailboxesShouldThrowWhenQuotaRootContainsSeparator2Times() {
         assertThatThrownBy(() -> testee.retrieveAssociatedMailboxes(
                     QuotaRoot.quotaRoot("#private&be&nwa", Optional.empty()), MAILBOX_SESSION)
                 .collectList().block())
@@ -110,7 +110,7 @@ class DefaultUserQuotaRootResolverTest {
     void getQuotaRootShouldReturnUserValueWhenCalledWithMailboxId() throws Exception {
         MailboxMapper mockedMapper = mock(MailboxMapper.class);
         when(mockedFactory.getMailboxMapper(any())).thenReturn(mockedMapper);
-        when(mockedMapper.findMailboxByIdReactive(MAILBOX_ID)).thenReturn(Mono.just(MAILBOX));
+        when(mockedMapper.findMailboxById(MAILBOX_ID)).thenReturn(Mono.just(MAILBOX));
 
         assertThat(testee.getQuotaRoot(MAILBOX_ID)).isEqualTo(QUOTA_ROOT);
     }
diff --git a/mailbox/tools/indexer/src/main/java/org/apache/mailbox/tools/indexer/ReIndexerImpl.java b/mailbox/tools/indexer/src/main/java/org/apache/mailbox/tools/indexer/ReIndexerImpl.java
index f09050a..f557602 100644
--- a/mailbox/tools/indexer/src/main/java/org/apache/mailbox/tools/indexer/ReIndexerImpl.java
+++ b/mailbox/tools/indexer/src/main/java/org/apache/mailbox/tools/indexer/ReIndexerImpl.java
@@ -30,6 +30,7 @@ import org.apache.james.mailbox.indexer.ReIndexer;
 import org.apache.james.mailbox.indexer.ReIndexingExecutionFailures;
 import org.apache.james.mailbox.model.MailboxId;
 import org.apache.james.mailbox.model.MailboxPath;
+import org.apache.james.mailbox.store.MailboxReactorUtils;
 import org.apache.james.mailbox.store.MailboxSessionMapperFactory;
 import org.apache.james.task.Task;
 
@@ -104,6 +105,6 @@ public class ReIndexerImpl implements ReIndexer {
 
     private void validateIdExists(MailboxId mailboxId) throws MailboxException {
         MailboxSession mailboxSession = mailboxManager.createSystemSession(Username.of("ReIndexingImap"));
-        mapperFactory.getMailboxMapper(mailboxSession).findMailboxById(mailboxId);
+        MailboxReactorUtils.block(mapperFactory.getMailboxMapper(mailboxSession).findMailboxById(mailboxId));
     }
 }
diff --git a/mailbox/tools/indexer/src/main/java/org/apache/mailbox/tools/indexer/ReIndexerPerformer.java b/mailbox/tools/indexer/src/main/java/org/apache/mailbox/tools/indexer/ReIndexerPerformer.java
index d50b2ee..124238c 100644
--- a/mailbox/tools/indexer/src/main/java/org/apache/mailbox/tools/indexer/ReIndexerPerformer.java
+++ b/mailbox/tools/indexer/src/main/java/org/apache/mailbox/tools/indexer/ReIndexerPerformer.java
@@ -159,7 +159,7 @@ public class ReIndexerPerformer {
         MailboxSession mailboxSession = mailboxManager.createSystemSession(RE_INDEXER_PERFORMER_USER);
 
         Flux<Either<Failure, ReIndexingEntry>> entriesToIndex = mailboxSessionMapperFactory.getMailboxMapper(mailboxSession)
-            .findMailboxByIdReactive(mailboxId)
+            .findMailboxById(mailboxId)
             .flatMapMany(mailbox -> reIndexingEntriesForMailbox(mailbox, mailboxSession));
 
         return reIndexMessages(entriesToIndex, runningOptions, reprocessingContext);
@@ -188,7 +188,7 @@ public class ReIndexerPerformer {
         MailboxSession mailboxSession = mailboxManager.createSystemSession(RE_INDEXER_PERFORMER_USER);
 
         return mailboxSessionMapperFactory.getMailboxMapper(mailboxSession)
-            .findMailboxByIdReactive(mailboxId)
+            .findMailboxById(mailboxId)
             .flatMap(mailbox -> fullyReadMessage(mailboxSession, mailbox, uid)
                 .map(message -> Either.<Failure, ReIndexingEntry>right(new ReIndexingEntry(mailbox, mailboxSession, message)))
                 .flatMap(entryOrFailure -> reIndex(entryOrFailure, reprocessingContext)))
@@ -217,7 +217,7 @@ public class ReIndexerPerformer {
             Flux.fromIterable(previousReIndexingFailures.messageFailures())
                 .flatMap(this::createReindexingEntryFromFailure),
             Flux.fromIterable(previousReIndexingFailures.mailboxFailures())
-                .flatMap(mailboxId -> mapper.findMailboxByIdReactive(mailboxId)
+                .flatMap(mailboxId -> mapper.findMailboxById(mailboxId)
                     .flatMapMany(mailbox -> reIndexingEntriesForMailbox(mailbox, mailboxSession))
                     .onErrorResume(e -> {
                         LOGGER.warn("Failed to re-index {}", mailboxId, e);
@@ -229,7 +229,7 @@ public class ReIndexerPerformer {
 
     private Mono<Result> reIndex(MailboxMessage mailboxMessage, MailboxSession session) {
         return mailboxSessionMapperFactory.getMailboxMapper(session)
-            .findMailboxByIdReactive(mailboxMessage.getMailboxId())
+            .findMailboxById(mailboxMessage.getMailboxId())
             .flatMap(mailbox -> messageSearchIndex.add(session, mailbox, mailboxMessage))
             .thenReturn(Result.COMPLETED)
             .onErrorResume(e -> {
@@ -248,7 +248,7 @@ public class ReIndexerPerformer {
         MailboxSession mailboxSession = mailboxManager.createSystemSession(RE_INDEXER_PERFORMER_USER);
 
         return mailboxSessionMapperFactory.getMailboxMapper(mailboxSession)
-            .findMailboxByIdReactive(previousFailure.getMailboxId())
+            .findMailboxById(previousFailure.getMailboxId())
             .flatMap(mailbox -> fullyReadMessage(mailboxSession, mailbox, previousFailure.getUid())
                 .map(message -> Either.<Failure, ReIndexingEntry>right(new ReIndexingEntry(mailbox, mailboxSession, message))))
             .onErrorResume(e -> {
diff --git a/protocols/imap/src/main/java/org/apache/james/imap/processor/ListProcessor.java b/protocols/imap/src/main/java/org/apache/james/imap/processor/ListProcessor.java
index bf96dc9..b489a68 100644
--- a/protocols/imap/src/main/java/org/apache/james/imap/processor/ListProcessor.java
+++ b/protocols/imap/src/main/java/org/apache/james/imap/processor/ListProcessor.java
@@ -20,7 +20,6 @@
 package org.apache.james.imap.processor;
 
 import java.io.Closeable;
-import java.util.List;
 
 import org.apache.james.imap.api.ImapMessage;
 import org.apache.james.imap.api.display.HumanReadableText;
@@ -131,18 +130,17 @@ public class ListProcessor extends AbstractMailboxProcessor<ListRequest> {
 
         MailboxPath basePath = computeBasePath(session, finalReferencename, isRelative);
 
-        List<MailboxMetaData> results = getMailboxManager().search(
+        getMailboxManager().search(
                 MailboxQuery.builder()
                     .userAndNamespaceFrom(basePath)
                     .expression(new PrefixedRegex(
                         basePath.getName(),
                         ModifiedUtf7.decodeModifiedUTF7(mailboxName),
                         mailboxSession.getPathDelimiter()))
-                    .build(), mailboxSession);
-
-        for (MailboxMetaData metaData : results) {
-            processResult(responder, isRelative, metaData, getMailboxType(session, metaData.getPath()));
-        }
+                    .build(), mailboxSession)
+            .doOnNext(metaData -> processResult(responder, isRelative, metaData, getMailboxType(session, metaData.getPath())))
+            .then()
+            .block();
     }
 
     private MailboxPath computeBasePath(ImapSession session, String finalReferencename, boolean isRelative) {
diff --git a/server/container/guice/mailbox/src/main/java/org/apache/james/modules/MailboxProbeImpl.java b/server/container/guice/mailbox/src/main/java/org/apache/james/modules/MailboxProbeImpl.java
index b267c0c..1f5a540 100644
--- a/server/container/guice/mailbox/src/main/java/org/apache/james/modules/MailboxProbeImpl.java
+++ b/server/container/guice/mailbox/src/main/java/org/apache/james/modules/MailboxProbeImpl.java
@@ -19,10 +19,11 @@
 
 package org.apache.james.modules;
 
+import static org.apache.james.mailbox.store.MailboxReactorUtils.block;
+
 import java.io.InputStream;
 import java.util.Collection;
 import java.util.Date;
-import java.util.List;
 import java.util.stream.Collectors;
 
 import javax.inject.Inject;
@@ -43,6 +44,8 @@ import org.apache.james.mailbox.model.search.Wildcard;
 import org.apache.james.mailbox.probe.MailboxProbe;
 import org.apache.james.utils.GuiceProbe;
 
+import reactor.core.publisher.Flux;
+
 public class MailboxProbeImpl implements GuiceProbe, MailboxProbe {
     private final MailboxManager mailboxManager;
     private final SubscriptionManager subscriptionManager;
@@ -102,11 +105,10 @@ public class MailboxProbeImpl implements GuiceProbe, MailboxProbe {
         try {
             mailboxSession = mailboxManager.createSystemSession(Username.of(user));
             mailboxManager.startProcessingRequest(mailboxSession);
-            return searchUserMailboxes(mailboxSession)
-                    .stream()
+            return block(searchUserMailboxes(mailboxSession)
                     .map(MailboxMetaData::getPath)
                     .map(MailboxPath::getName)
-                    .collect(Collectors.toList());
+                    .collect(Collectors.toList()));
         } catch (MailboxException e) {
             throw new RuntimeException(e);
         } finally {
@@ -114,7 +116,7 @@ public class MailboxProbeImpl implements GuiceProbe, MailboxProbe {
         }
     }
 
-    private List<MailboxMetaData> searchUserMailboxes(MailboxSession session) throws MailboxException {
+    private Flux<MailboxMetaData> searchUserMailboxes(MailboxSession session) {
         return mailboxManager.search(
             MailboxQuery.privateMailboxesBuilder(session)
                 .expression(Wildcard.INSTANCE)
diff --git a/server/container/mailbox-jmx/src/main/java/org/apache/james/adapter/mailbox/MailboxManagerManagement.java b/server/container/mailbox-jmx/src/main/java/org/apache/james/adapter/mailbox/MailboxManagerManagement.java
index 435397d..a482d5f 100644
--- a/server/container/mailbox-jmx/src/main/java/org/apache/james/adapter/mailbox/MailboxManagerManagement.java
+++ b/server/container/mailbox-jmx/src/main/java/org/apache/james/adapter/mailbox/MailboxManagerManagement.java
@@ -205,7 +205,9 @@ public class MailboxManagerManagement extends StandardMBean implements MailboxMa
             MailboxQuery.privateMailboxesBuilder(session)
                 .matchesAllMailboxNames()
                 .build(),
-            session);
+            session)
+            .collect(Guavate.toImmutableList())
+            .block();
     }
 
     private void checkMailboxArguments(String namespace, String user, String name) {
diff --git a/server/container/mailbox-jmx/src/test/java/org/apache/james/adapter/mailbox/MailboxManagementTest.java b/server/container/mailbox-jmx/src/test/java/org/apache/james/adapter/mailbox/MailboxManagementTest.java
index d38bbc7..39b00f5 100644
--- a/server/container/mailbox-jmx/src/test/java/org/apache/james/adapter/mailbox/MailboxManagementTest.java
+++ b/server/container/mailbox-jmx/src/test/java/org/apache/james/adapter/mailbox/MailboxManagementTest.java
@@ -67,42 +67,42 @@ public class MailboxManagementTest {
 
     @Test
     void deleteMailboxesShouldDeleteMailboxes() throws Exception {
-        mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "name"), UID_VALIDITY);
+        mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "name"), UID_VALIDITY).block();
         mailboxManagerManagement.deleteMailboxes(USER.asString());
         assertThat(mapperFactory.createMailboxMapper(session).list().collectList().block()).isEmpty();
     }
 
     @Test
     void deleteMailboxesShouldDeleteInbox() throws Exception {
-        mapperFactory.createMailboxMapper(session).create(MailboxPath.inbox(USER), UID_VALIDITY);
+        mapperFactory.createMailboxMapper(session).create(MailboxPath.inbox(USER), UID_VALIDITY).block();
         mailboxManagerManagement.deleteMailboxes(USER.asString());
         assertThat(mapperFactory.createMailboxMapper(session).list().collectList().block()).isEmpty();
     }
 
     @Test
     void deleteMailboxesShouldDeleteMailboxesChildren() throws Exception {
-        mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "INBOX.test"), UID_VALIDITY);
+        mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "INBOX.test"), UID_VALIDITY).block();
         mailboxManagerManagement.deleteMailboxes(USER.asString());
         assertThat(mapperFactory.createMailboxMapper(session).list().collectList().block()).isEmpty();
     }
 
     @Test
     void deleteMailboxesShouldNotDeleteMailboxesBelongingToNotPrivateNamespace() throws Exception {
-        Mailbox mailbox = mapperFactory.createMailboxMapper(session).create(new MailboxPath("#top", USER, "name"), UID_VALIDITY);
+        Mailbox mailbox = mapperFactory.createMailboxMapper(session).create(new MailboxPath("#top", USER, "name"), UID_VALIDITY).block();
         mailboxManagerManagement.deleteMailboxes(USER.asString());
         assertThat(mapperFactory.createMailboxMapper(session).list().collectList().block()).containsExactly(mailbox);
     }
 
     @Test
     void deleteMailboxesShouldNotDeleteMailboxesBelongingToOtherUsers() throws Exception {
-        Mailbox mailbox = mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(Username.of("userbis"), "name"), UID_VALIDITY);
+        Mailbox mailbox = mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(Username.of("userbis"), "name"), UID_VALIDITY).block();
         mailboxManagerManagement.deleteMailboxes(USER.asString());
         assertThat(mapperFactory.createMailboxMapper(session).list().collectList().block()).containsExactly(mailbox);
     }
 
     @Test
     void deleteMailboxesShouldDeleteMailboxesWithEmptyNames() throws Exception {
-        mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, ""), UID_VALIDITY);
+        mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, ""), UID_VALIDITY).block();
         mailboxManagerManagement.deleteMailboxes(USER.asString());
         assertThat(mapperFactory.createMailboxMapper(session).list().collectList().block()).isEmpty();
     }
@@ -121,9 +121,9 @@ public class MailboxManagementTest {
 
     @Test
     void deleteMailboxesShouldDeleteMultipleMailboxes() throws Exception {
-        mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "name"), UID_VALIDITY);
-        mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "INBOX"), UID_VALIDITY);
-        mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "INBOX.test"), UID_VALIDITY);
+        mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "name"), UID_VALIDITY).block();
+        mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "INBOX"), UID_VALIDITY).block();
+        mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "INBOX.test"), UID_VALIDITY).block();
         mailboxManagerManagement.deleteMailboxes(USER.asString());
         assertThat(mapperFactory.createMailboxMapper(session).list().collectList().block()).isEmpty();
     }
@@ -141,7 +141,7 @@ public class MailboxManagementTest {
     @Test
     void createMailboxShouldThrowIfMailboxAlreadyExists() throws Exception {
         MailboxPath path = MailboxPath.forUser(USER, "name");
-        mapperFactory.createMailboxMapper(session).create(path, UID_VALIDITY);
+        mapperFactory.createMailboxMapper(session).create(path, UID_VALIDITY).block();
 
         assertThatThrownBy(() -> mailboxManagerManagement.createMailbox(MailboxConstants.USER_NAMESPACE, USER.asString(), "name"))
             .isInstanceOf(RuntimeException.class)
@@ -151,7 +151,7 @@ public class MailboxManagementTest {
     @Test
     void createMailboxShouldNotCreateAdditionalMailboxesIfMailboxAlreadyExists() throws Exception {
         MailboxPath path = MailboxPath.forUser(USER, "name");
-        Mailbox mailbox = mapperFactory.createMailboxMapper(session).create(path, UID_VALIDITY);
+        Mailbox mailbox = mapperFactory.createMailboxMapper(session).create(path, UID_VALIDITY).block();
 
         assertThat(mapperFactory.createMailboxMapper(session).list().collectList().block()).containsExactly(mailbox);
     }
@@ -195,12 +195,12 @@ public class MailboxManagementTest {
     @Test
     void listMailboxesShouldReturnUserMailboxes() throws Exception {
         MailboxMapper mapper = mapperFactory.createMailboxMapper(session);
-        mapper.create(new MailboxPath("#top", USER, "name1"), UID_VALIDITY);
-        mapper.create(MailboxPath.forUser(USER, "name2"), UID_VALIDITY);
-        mapper.create(MailboxPath.forUser(Username.of("other_user"), "name3"), UID_VALIDITY);
-        mapper.create(MailboxPath.forUser(USER, "name4"), UID_VALIDITY);
-        mapper.create(MailboxPath.forUser(USER, "INBOX"), UID_VALIDITY);
-        mapper.create(MailboxPath.forUser(USER, "INBOX.toto"), UID_VALIDITY);
+        mapper.create(new MailboxPath("#top", USER, "name1"), UID_VALIDITY).block();
+        mapper.create(MailboxPath.forUser(USER, "name2"), UID_VALIDITY).block();
+        mapper.create(MailboxPath.forUser(Username.of("other_user"), "name3"), UID_VALIDITY).block();
+        mapper.create(MailboxPath.forUser(USER, "name4"), UID_VALIDITY).block();
+        mapper.create(MailboxPath.forUser(USER, "INBOX"), UID_VALIDITY).block();
+        mapper.create(MailboxPath.forUser(USER, "INBOX.toto"), UID_VALIDITY).block();
         assertThat(mailboxManagerManagement.listMailboxes(USER.asString())).containsOnly("name2", "name4", "INBOX", "INBOX.toto");
     }
 
@@ -218,35 +218,35 @@ public class MailboxManagementTest {
 
     @Test
     void deleteMailboxShouldDeleteGivenMailbox() throws Exception {
-        mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "name"), UID_VALIDITY);
+        mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "name"), UID_VALIDITY).block();
         mailboxManagerManagement.deleteMailbox(MailboxConstants.USER_NAMESPACE, USER.asString(), "name");
         assertThat(mapperFactory.createMailboxMapper(session).list().collectList().block()).isEmpty();
     }
 
     @Test
     void deleteMailboxShouldNotDeleteGivenMailboxIfWrongNamespace() throws Exception {
-        Mailbox mailbox = mapperFactory.createMailboxMapper(session).create(new MailboxPath("#top", USER, "name"), UID_VALIDITY);
+        Mailbox mailbox = mapperFactory.createMailboxMapper(session).create(new MailboxPath("#top", USER, "name"), UID_VALIDITY).block();
         mailboxManagerManagement.deleteMailbox(MailboxConstants.USER_NAMESPACE, USER.asString(), "name");
         assertThat(mapperFactory.createMailboxMapper(session).list().collectList().block()).containsOnly(mailbox);
     }
 
     @Test
     void deleteMailboxShouldNotDeleteGivenMailboxIfWrongUser() throws Exception {
-        Mailbox mailbox = mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(Username.of("userbis"), "name"), UID_VALIDITY);
+        Mailbox mailbox = mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(Username.of("userbis"), "name"), UID_VALIDITY).block();
         mailboxManagerManagement.deleteMailbox(MailboxConstants.USER_NAMESPACE, USER.asString(), "name");
         assertThat(mapperFactory.createMailboxMapper(session).list().collectList().block()).containsOnly(mailbox);
     }
 
     @Test
     void deleteMailboxShouldNotDeleteGivenMailboxIfWrongName() throws Exception {
-        Mailbox mailbox = mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "wrong_name"), UID_VALIDITY);
+        Mailbox mailbox = mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "wrong_name"), UID_VALIDITY).block();
         mailboxManagerManagement.deleteMailbox(MailboxConstants.USER_NAMESPACE, USER.asString(), "name");
         assertThat(mapperFactory.createMailboxMapper(session).list().collectList().block()).containsOnly(mailbox);
     }
 
     @Test
     void importEmlFileToMailboxShouldImportEmlFileToGivenMailbox() throws Exception {
-        Mailbox mailbox = mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "name"), UID_VALIDITY);
+        Mailbox mailbox = mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "name"), UID_VALIDITY).block();
         String emlpath = ClassLoader.getSystemResource("eml/frnog.eml").getFile();
         mailboxManagerManagement.importEmlFileToMailbox(MailboxConstants.USER_NAMESPACE, USER.asString(), "name", emlpath);
 
@@ -261,7 +261,7 @@ public class MailboxManagementTest {
 
     @Test
     void importEmlFileToMailboxShouldNotImportEmlFileWithWrongPathToGivenMailbox() throws Exception {
-        Mailbox mailbox = mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "name"), UID_VALIDITY);
+        Mailbox mailbox = mapperFactory.createMailboxMapper(session).create(MailboxPath.forUser(USER, "name"), UID_VALIDITY).block();
         String emlpath = ClassLoader.getSystemResource("eml/frnog.eml").getFile();
         mailboxManagerManagement.importEmlFileToMailbox(MailboxConstants.USER_NAMESPACE, USER.asString(), "name", "wrong_path" + emlpath);
 
diff --git a/server/mailet/mailets/src/main/java/org/apache/james/transport/mailets/RandomStoring.java b/server/mailet/mailets/src/main/java/org/apache/james/transport/mailets/RandomStoring.java
index 6501e03..683e853 100644
--- a/server/mailet/mailets/src/main/java/org/apache/james/transport/mailets/RandomStoring.java
+++ b/server/mailet/mailets/src/main/java/org/apache/james/transport/mailets/RandomStoring.java
@@ -117,7 +117,7 @@ public class RandomStoring extends GenericMailet {
             MailboxSession session = mailboxManager.createSystemSession(username);
             return mailboxManager
                 .search(MailboxQuery.privateMailboxesBuilder(session).build(), session)
-                .stream()
+                .toStream()
                 .map(metaData -> new ReroutingInfos(metaData.getPath().getName(), username));
         } catch (Exception e) {
             throw new RuntimeException(e);
diff --git a/server/protocols/jmap-draft/src/main/java/org/apache/james/jmap/draft/methods/GetMailboxesMethod.java b/server/protocols/jmap-draft/src/main/java/org/apache/james/jmap/draft/methods/GetMailboxesMethod.java
index 43396a7..aa87311 100644
--- a/server/protocols/jmap-draft/src/main/java/org/apache/james/jmap/draft/methods/GetMailboxesMethod.java
+++ b/server/protocols/jmap-draft/src/main/java/org/apache/james/jmap/draft/methods/GetMailboxesMethod.java
@@ -167,7 +167,7 @@ public class GetMailboxesMethod implements Method {
     }
 
     private Flux<MailboxMetaData> getAllMailboxesMetaData(MailboxSession mailboxSession) {
-        return mailboxManager.searchReactive(
+        return mailboxManager.search(
             MailboxQuery.builder()
                 .matchesAllMailboxNames()
                 .build(),
diff --git a/server/protocols/jmap-draft/src/test/java/org/apache/james/jmap/draft/methods/GetMailboxesMethodTest.java b/server/protocols/jmap-draft/src/test/java/org/apache/james/jmap/draft/methods/GetMailboxesMethodTest.java
index f47ede8..58c795c 100644
--- a/server/protocols/jmap-draft/src/test/java/org/apache/james/jmap/draft/methods/GetMailboxesMethodTest.java
+++ b/server/protocols/jmap-draft/src/test/java/org/apache/james/jmap/draft/methods/GetMailboxesMethodTest.java
@@ -109,7 +109,7 @@ public class GetMailboxesMethodTest {
             .thenReturn(ImmutableList.of(new MailboxPath("namespace", Username.of("user"), "name")));
         when(mockedMailboxManager.getMailbox(any(MailboxPath.class), any()))
             .thenThrow(new MailboxException());
-        when(mockedMailboxManager.searchReactive(any(), any()))
+        when(mockedMailboxManager.search(any(), any()))
             .thenReturn(Flux.empty());
         GetMailboxesMethod testee = new GetMailboxesMethod(mockedMailboxManager, quotaRootResolver, quotaManager, mailboxFactory, new DefaultMetricFactory());
 
diff --git a/server/protocols/jmap-draft/src/test/java/org/apache/james/jmap/draft/model/MailboxFactoryTest.java b/server/protocols/jmap-draft/src/test/java/org/apache/james/jmap/draft/model/MailboxFactoryTest.java
index f235996..bf7feb4 100644
--- a/server/protocols/jmap-draft/src/test/java/org/apache/james/jmap/draft/model/MailboxFactoryTest.java
+++ b/server/protocols/jmap-draft/src/test/java/org/apache/james/jmap/draft/model/MailboxFactoryTest.java
@@ -353,7 +353,7 @@ public class MailboxFactoryTest {
                 .asAddition()),
             mailboxSession);
         MailboxMetaData metaData = mailboxManager.search(MailboxQuery.privateMailboxesBuilder(mailboxSession).build(), mailboxSession)
-            .stream()
+            .toStream()
             .filter(metadata -> metadata.getPath().equals(mailboxPath))
             .findFirst()
             .get();
diff --git a/server/protocols/jmap-draft/src/test/java/org/apache/james/jmap/event/PropagateLookupRightListenerTest.java b/server/protocols/jmap-draft/src/test/java/org/apache/james/jmap/event/PropagateLookupRightListenerTest.java
index 8f9ad5f..a9381a4 100644
--- a/server/protocols/jmap-draft/src/test/java/org/apache/james/jmap/event/PropagateLookupRightListenerTest.java
+++ b/server/protocols/jmap-draft/src/test/java/org/apache/james/jmap/event/PropagateLookupRightListenerTest.java
@@ -121,9 +121,9 @@ public class PropagateLookupRightListenerTest {
 
     @Test
     public void eventShouldDoNothingWhenNewACLIsTheSameAsTheOldOne() throws Exception {
-        Mailbox grandChildMailbox = mailboxMapper.getMailboxMapper(mailboxSession).findMailboxById(grandChildMailboxId);
+        Mailbox grandChildMailbox = mailboxMapper.getMailboxMapper(mailboxSession).findMailboxById(grandChildMailboxId).block();
         mailboxMapper.getMailboxMapper(mailboxSession).setACL(grandChildMailbox, new MailboxACL(
-            new Entry(SHARED_USER_KEY, new Rfc4314Rights(Right.Lookup))));
+            new Entry(SHARED_USER_KEY, new Rfc4314Rights(Right.Lookup)))).block();
 
         storeRightManager.applyRightsCommand(
             GRAND_CHILD_MAILBOX,
@@ -162,9 +162,9 @@ public class PropagateLookupRightListenerTest {
 
     @Test
     public void eventShouldUpdateParentWhenMailboxACLUpdateLookupRight() throws Exception {
-        Mailbox grandChildMailbox = mailboxMapper.getMailboxMapper(mailboxSession).findMailboxById(grandChildMailboxId);
+        Mailbox grandChildMailbox = mailboxMapper.getMailboxMapper(mailboxSession).findMailboxById(grandChildMailboxId).block();
         mailboxMapper.getMailboxMapper(mailboxSession).setACL(grandChildMailbox, new MailboxACL(
-            new Entry(SHARED_USER_KEY, new Rfc4314Rights(Right.Write))));
+            new Entry(SHARED_USER_KEY, new Rfc4314Rights(Right.Write)))).block();
 
         storeRightManager.setRights(
             GRAND_CHILD_MAILBOX,
@@ -183,9 +183,9 @@ public class PropagateLookupRightListenerTest {
 
     @Test
     public void eventShouldUpdateAllParentWhenMailboxACLUpdateLookupRight() throws Exception {
-        Mailbox grandChildMailbox = mailboxMapper.getMailboxMapper(mailboxSession).findMailboxById(grandChildMailboxId);
+        Mailbox grandChildMailbox = mailboxMapper.getMailboxMapper(mailboxSession).findMailboxById(grandChildMailboxId).block();
         mailboxMapper.getMailboxMapper(mailboxSession).setACL(grandChildMailbox, new MailboxACL(
-            new Entry(SHARED_USER_KEY, new Rfc4314Rights(Right.Write))));
+            new Entry(SHARED_USER_KEY, new Rfc4314Rights(Right.Write)))).block();
 
         storeRightManager.setRights(
             GRAND_CHILD_MAILBOX,
@@ -209,9 +209,9 @@ public class PropagateLookupRightListenerTest {
 
     @Test
     public void eventShouldDoNothingWhenMailboxACLRemoveLookupRight() throws Exception {
-        Mailbox grandChildMailbox = mailboxMapper.getMailboxMapper(mailboxSession).findMailboxById(grandChildMailboxId);
+        Mailbox grandChildMailbox = mailboxMapper.getMailboxMapper(mailboxSession).findMailboxById(grandChildMailboxId).block();
         mailboxMapper.getMailboxMapper(mailboxSession).setACL(grandChildMailbox, new MailboxACL(
-            new Entry(SHARED_USER_KEY, new Rfc4314Rights(Right.Write, Right.Lookup))));
+            new Entry(SHARED_USER_KEY, new Rfc4314Rights(Right.Write, Right.Lookup)))).block();
 
         storeRightManager.applyRightsCommand(
             GRAND_CHILD_MAILBOX,
@@ -267,9 +267,9 @@ public class PropagateLookupRightListenerTest {
 
     @Test
     public void eventShouldUpdateNewParentWhenRenameMailboxWhichContainLookupRight() throws Exception {
-        Mailbox childMailbox = mailboxMapper.getMailboxMapper(mailboxSession).findMailboxById(childMailboxId);
+        Mailbox childMailbox = mailboxMapper.getMailboxMapper(mailboxSession).findMailboxById(childMailboxId).block();
         mailboxMapper.getMailboxMapper(mailboxSession).setACL(childMailbox, new MailboxACL(
-            new Entry(SHARED_USER_KEY, new Rfc4314Rights(Right.Write, Right.Lookup))));
+            new Entry(SHARED_USER_KEY, new Rfc4314Rights(Right.Write, Right.Lookup)))).block();
 
         storeMailboxManager.renameMailbox(CHILD_MAILBOX, MailboxPath.forUser(OWNER_USER, "shared1.sub1New"), mailboxSession);
 
@@ -283,9 +283,9 @@ public class PropagateLookupRightListenerTest {
 
     @Test
     public void eventShouldNotUpdateNewParentWhenRenameMailboxWhichDoesContainLookupRight() throws Exception {
-        Mailbox childMailbox = mailboxMapper.getMailboxMapper(mailboxSession).findMailboxById(childMailboxId);
+        Mailbox childMailbox = mailboxMapper.getMailboxMapper(mailboxSession).findMailboxById(childMailboxId).block();
         mailboxMapper.getMailboxMapper(mailboxSession).setACL(childMailbox, new MailboxACL(
-            new Entry(SHARED_USER_KEY, new Rfc4314Rights(Right.Write))));
+            new Entry(SHARED_USER_KEY, new Rfc4314Rights(Right.Write)))).block();
 
         storeMailboxManager.renameMailbox(CHILD_MAILBOX, MailboxPath.forUser(OWNER_USER, "shared1.sub1New"), mailboxSession);
 
@@ -299,9 +299,9 @@ public class PropagateLookupRightListenerTest {
 
     @Test
     public void eventShouldUpdateAllNewParentWhenRenameMailboxWhichContainLookupRight() throws Exception {
-        Mailbox grandChildMailbox = mailboxMapper.getMailboxMapper(mailboxSession).findMailboxById(grandChildMailboxId);
+        Mailbox grandChildMailbox = mailboxMapper.getMailboxMapper(mailboxSession).findMailboxById(grandChildMailboxId).block();
         mailboxMapper.getMailboxMapper(mailboxSession).setACL(grandChildMailbox, new MailboxACL(
-            new Entry(SHARED_USER_KEY, new Rfc4314Rights(Right.Write, Right.Lookup))));
+            new Entry(SHARED_USER_KEY, new Rfc4314Rights(Right.Write, Right.Lookup)))).block();
 
         storeMailboxManager.renameMailbox(GRAND_CHILD_MAILBOX, MailboxPath.forUser(OWNER_USER, "shared1.sub1.sub2"), mailboxSession);
 
diff --git a/server/protocols/jmap-rfc-8621/src/main/scala/org/apache/james/jmap/method/MailboxGetMethod.scala b/server/protocols/jmap-rfc-8621/src/main/scala/org/apache/james/jmap/method/MailboxGetMethod.scala
index 5b72d8f..a37cb19 100644
--- a/server/protocols/jmap-rfc-8621/src/main/scala/org/apache/james/jmap/method/MailboxGetMethod.scala
+++ b/server/protocols/jmap-rfc-8621/src/main/scala/org/apache/james/jmap/method/MailboxGetMethod.scala
@@ -86,7 +86,7 @@ class MailboxGetMethod @Inject() (serializer: Serializer,
   }
 
   private def getAllMailboxesMetaData(mailboxSession: MailboxSession): SMono[Seq[MailboxMetaData]] =
-    SFlux.fromPublisher(mailboxManager.searchReactive(MailboxQuery.builder.matchesAllMailboxNames.build, mailboxSession))
+    SFlux.fromPublisher(mailboxManager.search(MailboxQuery.builder.matchesAllMailboxNames.build, mailboxSession))
       .collectSeq()
 
   private def getMailboxOrThrow(mailboxSession: MailboxSession,
diff --git a/server/protocols/webadmin/webadmin-jmap/src/main/java/org/apache/james/webadmin/data/jmap/MessageFastViewProjectionCorrector.java b/server/protocols/webadmin/webadmin-jmap/src/main/java/org/apache/james/webadmin/data/jmap/MessageFastViewProjectionCorrector.java
index 5bfd792..f23e13c 100644
--- a/server/protocols/webadmin/webadmin-jmap/src/main/java/org/apache/james/webadmin/data/jmap/MessageFastViewProjectionCorrector.java
+++ b/server/protocols/webadmin/webadmin-jmap/src/main/java/org/apache/james/webadmin/data/jmap/MessageFastViewProjectionCorrector.java
@@ -187,16 +187,15 @@ public class MessageFastViewProjectionCorrector {
     }
 
     private Flux<ProjectionEntry> listUserMailboxMessages(Progress progress, MailboxSession session) {
-        try {
-            return listUsersMailboxes(session)
-                .flatMap(mailboxMetadata -> retrieveMailbox(session, mailboxMetadata), MAILBOX_CONCURRENCY)
-                .flatMap(Throwing.function(messageManager -> listAllMailboxMessages(messageManager, session)
-                    .map(message -> new ProjectionEntry(messageManager, message.getUid(), session))), MAILBOX_CONCURRENCY);
-        } catch (MailboxException e) {
-            LOGGER.error("JMAP fastview re-computation aborted for {} as we failed listing user mailboxes", session.getUser(), e);
-            progress.incrementFailedUserCount();
-            return Flux.empty();
-        }
+        return listUsersMailboxes(session)
+            .flatMap(mailboxMetadata -> retrieveMailbox(session, mailboxMetadata), MAILBOX_CONCURRENCY)
+            .flatMap(Throwing.function(messageManager -> listAllMailboxMessages(messageManager, session)
+                .map(message -> new ProjectionEntry(messageManager, message.getUid(), session))), MAILBOX_CONCURRENCY)
+            .onErrorResume(MailboxException.class, e -> {
+                LOGGER.error("JMAP fastview re-computation aborted for {} as we failed listing user mailboxes", session.getUser(), e);
+                progress.incrementFailedUserCount();
+                return Flux.empty();
+            });
     }
 
     private Mono<Result> correctProjection(ProjectionEntry entry, Progress progress) {
@@ -223,8 +222,8 @@ public class MessageFastViewProjectionCorrector {
             .switchIfEmpty(Mono.just(Result.COMPLETED));
     }
 
-    private Flux<MailboxMetaData> listUsersMailboxes(MailboxSession session) throws MailboxException {
-        return Flux.fromIterable(mailboxManager.search(MailboxQuery.privateMailboxesBuilder(session).build(), session));
+    private Flux<MailboxMetaData> listUsersMailboxes(MailboxSession session) {
+        return mailboxManager.search(MailboxQuery.privateMailboxesBuilder(session).build(), session);
     }
 
     private Mono<MessageManager> retrieveMailbox(MailboxSession session, MailboxMetaData mailboxMetadata) {
diff --git a/server/protocols/webadmin/webadmin-mailbox/src/main/java/org/apache/james/webadmin/service/UserMailboxesService.java b/server/protocols/webadmin/webadmin-mailbox/src/main/java/org/apache/james/webadmin/service/UserMailboxesService.java
index 8f78beb..6938f5e 100644
--- a/server/protocols/webadmin/webadmin-mailbox/src/main/java/org/apache/james/webadmin/service/UserMailboxesService.java
+++ b/server/protocols/webadmin/webadmin-mailbox/src/main/java/org/apache/james/webadmin/service/UserMailboxesService.java
@@ -128,7 +128,7 @@ public class UserMailboxesService {
         return mailboxManager.search(
             MailboxQuery.privateMailboxesBuilder(mailboxSession).build(),
             mailboxSession)
-            .stream();
+            .toStream();
     }
 
 }
diff --git a/server/protocols/webadmin/webadmin-mailbox/src/test/java/org/apache/james/webadmin/routes/UserMailboxesRoutesTest.java b/server/protocols/webadmin/webadmin-mailbox/src/test/java/org/apache/james/webadmin/routes/UserMailboxesRoutesTest.java
index f6eb6b5..ff3dbfb 100644
--- a/server/protocols/webadmin/webadmin-mailbox/src/test/java/org/apache/james/webadmin/routes/UserMailboxesRoutesTest.java
+++ b/server/protocols/webadmin/webadmin-mailbox/src/test/java/org/apache/james/webadmin/routes/UserMailboxesRoutesTest.java
@@ -44,6 +44,7 @@ import static org.mockito.Mockito.when;
 
 import java.util.List;
 import java.util.Map;
+import java.util.stream.Stream;
 
 import org.apache.james.core.Username;
 import org.apache.james.json.DTOConverter;
@@ -86,10 +87,10 @@ import org.junit.jupiter.api.Test;
 import org.mockito.ArgumentCaptor;
 import org.mockito.Mockito;
 
-import com.google.common.collect.ImmutableList;
 import com.google.common.collect.ImmutableSet;
 
 import io.restassured.RestAssured;
+import reactor.core.publisher.Flux;
 import reactor.core.publisher.Mono;
 
 class UserMailboxesRoutesTest {
@@ -895,7 +896,7 @@ class UserMailboxesRoutesTest {
             MailboxId mailboxId = InMemoryId.of(12);
             when(mailboxManager.search(any(MailboxQuery.class), any()))
                 .thenReturn(
-                        ImmutableList.of(
+                        Flux.just(
                                 MailboxMetaData.unselectableMailbox(
                                         MailboxPath.forUser(USERNAME, MAILBOX_NAME), mailboxId, '.')));
             doThrow(new RuntimeException()).when(mailboxManager).deleteMailbox(any(MailboxPath.class), any());
@@ -908,7 +909,7 @@ class UserMailboxesRoutesTest {
 
         @Test
         void deleteShouldGenerateInternalErrorOnUnknownExceptionOnSearch() throws Exception {
-            when(mailboxManager.search(any(MailboxQuery.class), any())).thenThrow(new RuntimeException());
+            when(mailboxManager.search(any(MailboxQuery.class), any())).thenReturn(Flux.error(new RuntimeException()));
 
             when()
                 .delete(MAILBOX_NAME)
@@ -921,7 +922,7 @@ class UserMailboxesRoutesTest {
             MailboxId mailboxId = InMemoryId.of(12);
             when(mailboxManager.search(any(MailboxQuery.class), any()))
                 .thenReturn(
-                        ImmutableList.of(
+                        Flux.just(
                                 MailboxMetaData.unselectableMailbox(MailboxPath.forUser(USERNAME, MAILBOX_NAME), mailboxId, '.')));
             doThrow(new MailboxException()).when(mailboxManager).deleteMailbox(any(MailboxPath.class), any());
 
@@ -933,7 +934,7 @@ class UserMailboxesRoutesTest {
 
         @Test
         void deleteShouldGenerateInternalErrorOnUnknownMailboxExceptionOnSearch() throws Exception {
-            when(mailboxManager.search(any(MailboxQuery.class), any())).thenThrow(new MailboxException());
+            when(mailboxManager.search(any(MailboxQuery.class), any())).thenReturn(Flux.error(new MailboxException()));
 
             when()
                 .delete(MAILBOX_NAME)
@@ -943,6 +944,10 @@ class UserMailboxesRoutesTest {
 
         @Test
         void deleteShouldReturnOkOnMailboxDoesNotExists() throws Exception {
+            MailboxMetaData metaData = mock(MailboxMetaData.class);
+            when(metaData.getPath()).thenReturn(MailboxPath.forUser(USERNAME, MAILBOX_NAME));
+            doReturn(Flux.just(metaData))
+                .when(mailboxManager).search(any(MailboxQuery.class), any(MailboxSession.class));
             doThrow(new MailboxNotFoundException(MAILBOX_NAME)).when(mailboxManager).deleteMailbox(any(MailboxPath.class), any());
 
             when()
@@ -953,7 +958,7 @@ class UserMailboxesRoutesTest {
 
         @Test
         void deleteShouldGenerateInternalErrorOnUnknownExceptionWhenListingMailboxes() throws Exception {
-            doThrow(new RuntimeException()).when(mailboxManager).search(any(MailboxQuery.class), any());
+            when(mailboxManager.search(any(MailboxQuery.class), any())).thenReturn(Flux.error(new RuntimeException()));
 
             when()
                 .delete()
@@ -963,7 +968,7 @@ class UserMailboxesRoutesTest {
 
         @Test
         void deleteShouldGenerateInternalErrorOnMailboxExceptionWhenListingMailboxes() throws Exception {
-            doThrow(new MailboxException()).when(mailboxManager).search(any(MailboxQuery.class), any());
+            when(mailboxManager.search(any(MailboxQuery.class), any())).thenReturn(Flux.error(new MailboxException()));
 
             when()
                 .delete()
@@ -977,7 +982,7 @@ class UserMailboxesRoutesTest {
             MailboxId mailboxId = InMemoryId.of(12);
             when(mailboxManager.search(any(MailboxQuery.class), any()))
                 .thenReturn(
-                        ImmutableList.of(
+                        Flux.just(
                                 MailboxMetaData.unselectableMailbox(MailboxPath.forUser(USERNAME, "any"), mailboxId, '.')));
             doThrow(new RuntimeException()).when(mailboxManager).deleteMailbox(any(MailboxPath.class), any());
 
@@ -992,7 +997,7 @@ class UserMailboxesRoutesTest {
             MailboxId mailboxId = InMemoryId.of(12);
             when(mailboxManager.search(any(MailboxQuery.class), any()))
                 .thenReturn(
-                        ImmutableList.of(MailboxMetaData.unselectableMailbox(MailboxPath.forUser(USERNAME, "any"), mailboxId, '.')));
+                        Flux.just(MailboxMetaData.unselectableMailbox(MailboxPath.forUser(USERNAME, "any"), mailboxId, '.')));
             doThrow(new MailboxNotFoundException("any")).when(mailboxManager).deleteMailbox(any(MailboxPath.class), any());
 
             when()
@@ -1006,7 +1011,7 @@ class UserMailboxesRoutesTest {
             MailboxId mailboxId = InMemoryId.of(12);
             when(mailboxManager.search(any(MailboxQuery.class), any()))
                 .thenReturn(
-                        ImmutableList.of(MailboxMetaData.unselectableMailbox(MailboxPath.forUser(USERNAME, "any"), mailboxId, '.')));
+                        Flux.just(MailboxMetaData.unselectableMailbox(MailboxPath.forUser(USERNAME, "any"), mailboxId, '.')));
             doThrow(new MailboxException()).when(mailboxManager).deleteMailbox(any(MailboxPath.class), any());
 
             when()
@@ -1037,7 +1042,7 @@ class UserMailboxesRoutesTest {
 
         @Test
         void getMailboxesShouldGenerateInternalErrorOnUnknownException() throws Exception {
-            doThrow(new RuntimeException()).when(mailboxManager).search(any(MailboxQuery.class), any());
+            when(mailboxManager.search(any(MailboxQuery.class), any())).thenReturn(Flux.error(new RuntimeException()));
 
             when()
                 .get()
@@ -1047,7 +1052,7 @@ class UserMailboxesRoutesTest {
 
         @Test
         void getMailboxesShouldGenerateInternalErrorOnUnknownMailboxException() throws Exception {
-            doThrow(new MailboxException()).when(mailboxManager).search(any(MailboxQuery.class), any());
+            when(mailboxManager.search(any(MailboxQuery.class), any())).thenReturn(Flux.error(new MailboxException()));
 
             when()
                 .get()


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