Repository: softwaremill/elasticmq
Pull request #913 (2023-11-19 12:38:08)

Fix empty attributes being present in output json of ReceiveMessages

micossow: fixes #906

Patch:
diff --git a/rest/rest-sqs/src/main/scala/org/elasticmq/rest/sqs/ReceiveMessageDirectives.scala b/rest/rest-sqs/src/main/scala/org/elasticmq/rest/sqs/ReceiveMessageDirectives.scala
index 09848b73..b15f124b 100644
--- a/rest/rest-sqs/src/main/scala/org/elasticmq/rest/sqs/ReceiveMessageDirectives.scala
+++ b/rest/rest-sqs/src/main/scala/org/elasticmq/rest/sqs/ReceiveMessageDirectives.scala
@@ -135,14 +135,15 @@ trait ReceiveMessageDirectives {
               .map(_.receipt)
               .getOrElse(throw new RuntimeException("No receipt for a received msg."))
             val filteredMessageAttributes = getFilteredAttributeNames(messageAttributeNames, message)
+            val calculatedAttributes = calculateAttributeValues(message).toMap
 
             ReceivedMessage(
-              Attributes = calculateAttributeValues(message).toMap,
+              Attributes = if (calculatedAttributes.nonEmpty) Some(calculatedAttributes) else None,
               Body = message.content,
               MD5OfBody = md5Digest(message.content),
               MD5OfMessageAttributes =
                 if (filteredMessageAttributes.nonEmpty) Some(md5AttributeDigest(filteredMessageAttributes)) else None,
-              MessageAttributes = filteredMessageAttributes,
+              MessageAttributes = if (filteredMessageAttributes.nonEmpty) Some(filteredMessageAttributes) else None,
               MessageId = message.id.id,
               ReceiptHandle = receipt
             )
@@ -247,11 +248,11 @@ object ReceiveMessageResponse {
 }
 
 case class ReceivedMessage(
-    Attributes: Map[String, String],
+    Attributes: Option[Map[String, String]],
     Body: String,
     MD5OfBody: String,
     MD5OfMessageAttributes: Option[String],
-    MessageAttributes: Map[String, MessageAttribute],
+    MessageAttributes: Option[Map[String, MessageAttribute]],
     MessageId: String,
     ReceiptHandle: String
 )
@@ -266,9 +267,9 @@ object ReceivedMessage extends MessageAttributesSupport {
         <ReceiptHandle>{msg.ReceiptHandle}</ReceiptHandle>
         <MD5OfBody>{msg.MD5OfBody}</MD5OfBody>
         <Body>{XmlUtil.convertTexWithCRToNodeSeq(msg.Body)}</Body>
-        {attributesToXmlConverter.convert(msg.Attributes.toList)}
+        {attributesToXmlConverter.convert(msg.Attributes.getOrElse(Map.empty).toList)}
         {msg.MD5OfMessageAttributes.map(md5 => <MD5OfMessageAttributes>{md5}</MD5OfMessageAttributes>).getOrElse("")}
-        {messageAttributesToXmlConverter.convert(msg.MessageAttributes.toList)}
+        {messageAttributesToXmlConverter.convert(msg.MessageAttributes.getOrElse(Map.empty).toList)}
       </Message>
   }
 }


Test patch:
diff --git a/rest/rest-sqs-testing-amazon-java-sdk/src/test/scala/org/elasticmq/rest/sqs/AmazonCliTestSuite.scala b/rest/rest-sqs-testing-amazon-java-sdk/src/test/scala/org/elasticmq/rest/sqs/AmazonCliTestSuite.scala
index 116b3986..c026341a 100644
--- a/rest/rest-sqs-testing-amazon-java-sdk/src/test/scala/org/elasticmq/rest/sqs/AmazonCliTestSuite.scala
+++ b/rest/rest-sqs-testing-amazon-java-sdk/src/test/scala/org/elasticmq/rest/sqs/AmazonCliTestSuite.scala
@@ -348,14 +348,14 @@ class AmazonCliTestSuite
         ReceiptHandle.nonEmpty shouldBe true
         MD5OfBody shouldBe firstMessage.MD5OfMessageBody
         Body shouldBe firstMessageBody
-        Attributes.size shouldBe 4
-        Attributes.get("SentTimestamp").map(v => v.nonEmpty shouldBe true)
-        Attributes.get("ApproximateReceiveCount").map(_ shouldBe "1")
-        Attributes.get("ApproximateFirstReceiveTimestamp").map(v => v.nonEmpty shouldBe true)
-        Attributes.get("SenderId").map(_ shouldBe "127.0.0.1")
+        Attributes.get.size shouldBe 4
+        Attributes.get.get("SentTimestamp").map(v => v.nonEmpty shouldBe true)
+        Attributes.get.get("ApproximateReceiveCount").map(_ shouldBe "1")
+        Attributes.get.get("ApproximateFirstReceiveTimestamp").map(v => v.nonEmpty shouldBe true)
+        Attributes.get.get("SenderId").map(_ shouldBe "127.0.0.1")
         MD5OfMessageAttributes.nonEmpty shouldBe true
-        MessageAttributes.nonEmpty shouldBe true
-        MessageAttributes.get("firstAttribute").map { msgAtt =>
+        MessageAttributes.get.nonEmpty shouldBe true
+        MessageAttributes.get.get("firstAttribute").map { msgAtt =>
           msgAtt.getDataType() shouldBe "String"
           msgAtt shouldBe a[StringMessageAttribute]
           inside(msgAtt) { case stringMessageAttribute: StringMessageAttribute =>
@@ -369,14 +369,14 @@ class AmazonCliTestSuite
         ReceiptHandle.nonEmpty shouldBe true
         MD5OfBody shouldBe secondMessage.MD5OfMessageBody
         Body shouldBe secondMessageBody
-        Attributes.size shouldBe 4
-        Attributes.get("SentTimestamp").map(v => v.nonEmpty shouldBe true)
-        Attributes.get("ApproximateReceiveCount").map(_ shouldBe "1")
-        Attributes.get("ApproximateFirstReceiveTimestamp").map(v => v.nonEmpty shouldBe true)
-        Attributes.get("SenderId").map(_ shouldBe "127.0.0.1")
+        Attributes.get.size shouldBe 4
+        Attributes.get.get("SentTimestamp").map(v => v.nonEmpty shouldBe true)
+        Attributes.get.get("ApproximateReceiveCount").map(_ shouldBe "1")
+        Attributes.get.get("ApproximateFirstReceiveTimestamp").map(v => v.nonEmpty shouldBe true)
+        Attributes.get.get("SenderId").map(_ shouldBe "127.0.0.1")
         MD5OfMessageAttributes.nonEmpty shouldBe true
-        MessageAttributes.nonEmpty shouldBe true
-        MessageAttributes.get("secondAttribute").map { msgAtt =>
+        MessageAttributes.get.nonEmpty shouldBe true
+        MessageAttributes.get.get("secondAttribute").map { msgAtt =>
           msgAtt.getDataType() shouldBe "String"
           msgAtt shouldBe a[StringMessageAttribute]
           inside(msgAtt) { case stringMessageAttribute: StringMessageAttribute =>
diff --git a/rest/rest-sqs-testing-amazon-java-sdk/src/test/scala/org/elasticmq/rest/sqs/AmazonJavaSdkV2TestSuite.scala b/rest/rest-sqs-testing-amazon-java-sdk/src/test/scala/org/elasticmq/rest/sqs/AmazonJavaSdkV2TestSuite.scala
index e2fb482c..36c5a835 100644
--- a/rest/rest-sqs-testing-amazon-java-sdk/src/test/scala/org/elasticmq/rest/sqs/AmazonJavaSdkV2TestSuite.scala
+++ b/rest/rest-sqs-testing-amazon-java-sdk/src/test/scala/org/elasticmq/rest/sqs/AmazonJavaSdkV2TestSuite.scala
@@ -31,4 +31,17 @@ class AmazonJavaSdkV2TestSuite extends SqsClientServerWithSdkV2Communication wit
     thrown.awsErrorDetails().errorCode() shouldBe "QueueDoesNotExist"
     thrown.awsErrorDetails().errorMessage() shouldBe "The specified queue does not exist."
   }
+
+  test("should send and receive message") {
+    val queue = clientV2.createQueue(CreateQueueRequest.builder().queueName("testQueue1").build())
+
+    clientV2.sendMessage(SendMessageRequest.builder().queueUrl(queue.queueUrl()).messageBody("test msg 123").build())
+
+    val messages = clientV2.receiveMessage(ReceiveMessageRequest.builder().queueUrl(queue.queueUrl()).build())
+
+    System.err.println(messages)
+
+    messages.messages().size() shouldBe 1
+    messages.messages().get(0).body() shouldBe "test msg 123"
+  }
 }
diff --git a/rest/rest-sqs-testing-amazon-java-sdk/src/test/scala/org/elasticmq/rest/sqs/SqsClientServerWithSdkV2Communication.scala b/rest/rest-sqs-testing-amazon-java-sdk/src/test/scala/org/elasticmq/rest/sqs/SqsClientServerWithSdkV2Communication.scala
index 9ba80125..217f0427 100644
--- a/rest/rest-sqs-testing-amazon-java-sdk/src/test/scala/org/elasticmq/rest/sqs/SqsClientServerWithSdkV2Communication.scala
+++ b/rest/rest-sqs-testing-amazon-java-sdk/src/test/scala/org/elasticmq/rest/sqs/SqsClientServerWithSdkV2Communication.scala
@@ -26,8 +26,6 @@ trait SqsClientServerWithSdkV2Communication extends AnyFunSuite with BeforeAndAf
   val ServiceEndpoint = "http://localhost:9321"
 
   before {
-    logger.info(s"\n---\nRunning test: $currentTestName\n---\n")
-
     strictServer = SQSRestServerBuilder
       .withPort(9321)
       .withServerAddress(NodeAddress(port = 9321))
@@ -65,7 +63,5 @@ trait SqsClientServerWithSdkV2Communication extends AnyFunSuite with BeforeAndAf
 
     Try(strictServer.stopAndWait())
     Try(relaxedServer.stopAndWait())
-
-    logger.info(s"\n---\nTest done: $currentTestName\n---\n")
   }
 }