TEST+FIX: Unknown ChatRoom
authorKai Moritz <kai@juplo.de>
Sun, 20 Aug 2023 10:20:55 +0000 (12:20 +0200)
committerKai Moritz <kai@juplo.de>
Wed, 23 Aug 2023 05:37:03 +0000 (07:37 +0200)
src/main/java/de/juplo/kafka/chat/backend/persistence/kafka/ChatRoomChannel.java
src/main/java/de/juplo/kafka/chat/backend/persistence/kafka/KafkaChatHome.java
src/test/java/de/juplo/kafka/chat/backend/AbstractConfigurationIT.java
src/test/java/de/juplo/kafka/chat/backend/AbstractConfigurationWithShardingIT.java

index 7f93ad8..7659d1e 100644 (file)
@@ -360,6 +360,14 @@ public class ChatRoomChannel implements Runnable, ConsumerRebalanceListener
     }
   }
 
+  int[] getOwnedShards()
+  {
+    return IntStream
+        .range(0, numShards)
+        .filter(shard -> isShardOwned[shard])
+        .toArray();
+  }
+
   Mono<ChatRoom> getChatRoom(int shard, UUID id)
   {
     if (loadInProgress)
index 6799040..ab72269 100644 (file)
@@ -2,6 +2,7 @@ package de.juplo.kafka.chat.backend.persistence.kafka;
 
 import de.juplo.kafka.chat.backend.domain.ChatHome;
 import de.juplo.kafka.chat.backend.domain.ChatRoom;
+import de.juplo.kafka.chat.backend.domain.UnknownChatroomException;
 import lombok.RequiredArgsConstructor;
 import lombok.extern.slf4j.Slf4j;
 import org.apache.kafka.common.utils.Utils;
@@ -23,7 +24,9 @@ public class KafkaChatHome implements ChatHome
   public Mono<ChatRoom> getChatRoom(UUID id)
   {
     int shard = selectShard(id);
-    return chatRoomChannel.getChatRoom(shard, id);
+    return chatRoomChannel
+        .getChatRoom(shard, id)
+        .switchIfEmpty(Mono.error(() -> new UnknownChatroomException(id)));
   }
 
   int selectShard(UUID chatRoomId)
index 53ad04e..d255d6e 100644 (file)
@@ -10,6 +10,8 @@ import org.testcontainers.shaded.org.awaitility.Awaitility;
 
 import java.time.Duration;
 
+import static org.hamcrest.Matchers.endsWith;
+
 
 public abstract class AbstractConfigurationIT
 {
@@ -18,6 +20,7 @@ public abstract class AbstractConfigurationIT
   @Autowired
   WebTestClient webTestClient;
 
+
   @Test
   @DisplayName("The app starts, the data is restored and accessible")
   void testAppStartsDataIsRestoredAndAccessible()
@@ -79,4 +82,30 @@ public abstract class AbstractConfigurationIT
               .expectBody().jsonPath("$.text").isEqualTo("Hallo, ich heiße Peter!");
         });
   }
+
+  @Test
+  @DisplayName("A PUT-message for a non-existent chat-room yields 404 NOT FOUND")
+  void testNotFoundForPutMessageToNonExistentChatRoom()
+  {
+    String otherChatRoomId = "7f59ec77-832e-4a17-8d22-55ef46242c17";
+
+    Awaitility
+        .await()
+        .atMost(Duration.ofSeconds(15))
+        .untilAsserted(() ->
+          webTestClient
+              .put()
+              .uri(
+                  "http://localhost:{port}/{chatRoomId}/otto/66",
+                  port,
+                  otherChatRoomId)
+              .contentType(MediaType.TEXT_PLAIN)
+              .accept(MediaType.APPLICATION_JSON)
+              .bodyValue("The devil rules route 66")
+              .exchange()
+              .expectStatus().isNotFound()
+              .expectBody()
+              .jsonPath("$.type").value(endsWith("/problem/unknown-chatroom"))
+              .jsonPath("$.chatroomId").isEqualTo(otherChatRoomId));
+  }
 }
index e6fd95a..5c9ac13 100644 (file)
@@ -7,6 +7,8 @@ import org.testcontainers.shaded.org.awaitility.Awaitility;
 
 import java.time.Duration;
 
+import static org.hamcrest.Matchers.endsWith;
+
 
 public abstract class AbstractConfigurationWithShardingIT extends AbstractConfigurationIT
 {
@@ -15,6 +17,7 @@ public abstract class AbstractConfigurationWithShardingIT extends AbstractConfig
   void testNotFoundForPutMessageToAChatRoomInNotOwnedShard()
   {
     String otherChatRoomId = "4e7246a6-29ae-43ea-b56f-669c3481ac19";
+    int shard = 0;
 
     Awaitility
         .await()
@@ -30,6 +33,9 @@ public abstract class AbstractConfigurationWithShardingIT extends AbstractConfig
               .accept(MediaType.APPLICATION_JSON)
               .bodyValue("The devil rules route 66")
               .exchange()
-              .expectStatus().isNotFound());
+              .expectStatus().isNotFound()
+              .expectBody()
+              .jsonPath("$.type").value(endsWith("/problem/shard-not-owned"))
+              .jsonPath("$.shard").isEqualTo(shard));
   }
 }