diff --git a/library/src/androidTest/java/org/xmtp/android/library/ConversationTest.kt b/library/src/androidTest/java/org/xmtp/android/library/ConversationTest.kt index f62e68c0f..9080cee1f 100644 --- a/library/src/androidTest/java/org/xmtp/android/library/ConversationTest.kt +++ b/library/src/androidTest/java/org/xmtp/android/library/ConversationTest.kt @@ -7,6 +7,7 @@ import kotlinx.coroutines.ExperimentalCoroutinesApi import org.junit.Assert import org.junit.Assert.assertEquals import org.junit.Assert.assertThrows +import org.junit.Assert.assertTrue import org.junit.Before import org.junit.Ignore import org.junit.Test @@ -180,13 +181,11 @@ class ConversationTest { @Test fun testCanLoadV2Messages() { val bobConversation = bobClient.conversations.newConversation( - aliceWallet.address, - InvitationV1ContextBuilder.buildFromConversation("hi") + aliceWallet.address, InvitationV1ContextBuilder.buildFromConversation("hi") ) val aliceConversation = aliceClient.conversations.newConversation( - bobWallet.address, - InvitationV1ContextBuilder.buildFromConversation("hi") + bobWallet.address, InvitationV1ContextBuilder.buildFromConversation("hi") ) bobConversation.send(content = "hey alice") val messages = aliceConversation.messages() @@ -214,31 +213,23 @@ class ConversationTest { val preKey = aliceClient.keys?.preKeysList?.get(0) val signature = preKey?.sign(digest) val bundle = aliceClient.privateKeyBundleV1?.toV2()?.getPublicKeyBundle() - val signedContent = - SignedContentBuilder.builderFromPayload( - payload = originalPayload, - sender = bundle, - signature = signature - ) + val signedContent = SignedContentBuilder.builderFromPayload( + payload = originalPayload, sender = bundle, signature = signature + ) val signedBytes = signedContent.toByteArray() - val ciphertext = - Crypto.encrypt( - aliceConversation.keyMaterial!!, - signedBytes, - additionalData = headerBytes - ) + val ciphertext = Crypto.encrypt( + aliceConversation.keyMaterial!!, signedBytes, additionalData = headerBytes + ) val tamperedMessage = MessageV2Builder.buildFromCipherText(headerBytes = headerBytes, ciphertext = ciphertext) - val tamperedEnvelope = - EnvelopeBuilder.buildFromString( - topic = aliceConversation.topic, - timestamp = Date(), - message = MessageBuilder.buildFromMessageV2(v2 = tamperedMessage).toByteArray() - ) + val tamperedEnvelope = EnvelopeBuilder.buildFromString( + topic = aliceConversation.topic, + timestamp = Date(), + message = MessageBuilder.buildFromMessageV2(v2 = tamperedMessage).toByteArray() + ) aliceClient.publish(envelopes = listOf(tamperedEnvelope)) val bobConversation = bobClient.conversations.newConversation( - aliceWallet.address, - InvitationV1ContextBuilder.buildFromConversation("hi") + aliceWallet.address, InvitationV1ContextBuilder.buildFromConversation("hi") ) assertThrows("Invalid signature", XMTPException::class.java) { bobConversation.decode(tamperedEnvelope) @@ -330,11 +321,11 @@ class ConversationTest { val invitationContext = Invitation.InvitationV1.Context.newBuilder().also { it.conversationId = "https://example.com/1" }.build() - val invitationv1 = - InvitationV1.newBuilder().build().createDeterministic( - sender = client.keys, - recipient = fakeContactClient.keys.getPublicKeyBundle(), context = invitationContext - ) + val invitationv1 = InvitationV1.newBuilder().build().createDeterministic( + sender = client.keys, + recipient = fakeContactClient.keys.getPublicKeyBundle(), + context = invitationContext + ) val senderBundle = client.privateKeyBundleV1?.toV2() assertEquals( senderBundle?.identityKey?.publicKey?.recoverWalletSignerPublicKey()?.walletAddress, @@ -397,13 +388,11 @@ class ConversationTest { @Test fun testCanPaginateV2Messages() { val bobConversation = bobClient.conversations.newConversation( - alice.walletAddress, - context = InvitationV1ContextBuilder.buildFromConversation("hi") + alice.walletAddress, context = InvitationV1ContextBuilder.buildFromConversation("hi") ) val aliceConversation = aliceClient.conversations.newConversation( - bob.walletAddress, - context = InvitationV1ContextBuilder.buildFromConversation("hi") + bob.walletAddress, context = InvitationV1ContextBuilder.buildFromConversation("hi") ) val date = Date() date.time = date.time - 1000000 @@ -421,18 +410,24 @@ class ConversationTest { @Test fun testListBatchMessages() { val bobConversation = aliceClient.conversations.newConversation(bob.walletAddress) - val steveConversation = aliceClient.conversations.newConversation(fixtures.steve.walletAddress) + val steveConversation = + aliceClient.conversations.newConversation(fixtures.steve.walletAddress) bobConversation.send(text = "hey alice 1") bobConversation.send(text = "hey alice 2") steveConversation.send(text = "hey alice 3") val messages = aliceClient.conversations.listBatchMessages( listOf( - Pair(steveConversation.topic, null), - Pair(bobConversation.topic, null) + Pair(steveConversation.topic, null), Pair(bobConversation.topic, null) ) ) + val isSteveOrBobConversation = { topic: String -> + (topic.equals(steveConversation.topic) || topic.equals(bobConversation.topic)) + } assertEquals(3, messages.size) + assertTrue(isSteveOrBobConversation(messages[0].topic)) + assertTrue(isSteveOrBobConversation(messages[1].topic)) + assertTrue(isSteveOrBobConversation(messages[2].topic)) } @Test @@ -586,9 +581,7 @@ class ConversationTest { header = Invitation.SealedInvitationHeaderV1.newBuilder().build() ) val envelope = EnvelopeBuilder.buildFromString( - topic = topic, - timestamp = Date(), - message = envelopeMessage + topic = topic, timestamp = Date(), message = envelopeMessage ) assertThrows("pre-key not signed by identity key", XMTPException::class.java) { conversation.decodeEnvelope(envelope) @@ -627,8 +620,38 @@ class ConversationTest { fun testFetchConversation() { // Generated from JS script val ints = arrayOf( - 31, 116, 198, 193, 189, 122, 19, 254, 191, 189, 211, 215, 255, 131, - 171, 239, 243, 33, 4, 62, 143, 86, 18, 195, 251, 61, 128, 90, 34, 126, 219, 236 + 31, + 116, + 198, + 193, + 189, + 122, + 19, + 254, + 191, + 189, + 211, + 215, + 255, + 131, + 171, + 239, + 243, + 33, + 4, + 62, + 143, + 86, + 18, + 195, + 251, + 61, + 128, + 90, + 34, + 126, + 219, + 236 ) val bytes = ints.foldIndexed(ByteArray(ints.size)) { i, a, v -> a.apply { set(i, v.toByte()) } } diff --git a/library/src/androidTest/java/org/xmtp/android/library/MessageTest.kt b/library/src/androidTest/java/org/xmtp/android/library/MessageTest.kt index 6ce34f015..0e0440f57 100644 --- a/library/src/androidTest/java/org/xmtp/android/library/MessageTest.kt +++ b/library/src/androidTest/java/org/xmtp/android/library/MessageTest.kt @@ -242,6 +242,7 @@ class MessageTest { val messages = convo.messages() assertEquals(1, messages.size) assertEquals("hello from kotlin", messages[0].body) + assertEquals(convo.topic.description, messages[0].topic) } @Test @@ -257,6 +258,7 @@ class MessageTest { val messages = convo.messages() assertEquals(1, messages.size) assertEquals("hello from kotlin", messages[0].body) + assertEquals(convo.topic, messages[0].topic) } @Test diff --git a/library/src/main/java/org/xmtp/android/library/ConversationV1.kt b/library/src/main/java/org/xmtp/android/library/ConversationV1.kt index d0441c36f..357b54dfb 100644 --- a/library/src/main/java/org/xmtp/android/library/ConversationV1.kt +++ b/library/src/main/java/org/xmtp/android/library/ConversationV1.kt @@ -59,6 +59,7 @@ data class ConversationV1( val encodedMessage = EncodedContent.parseFrom(decrypted) val header = message.v1.header val decoded = DecodedMessage( + topic = envelope.contentTopic, encodedContent = encodedMessage, senderAddress = header.sender.walletAddress, sent = message.v1.sentAt diff --git a/library/src/main/java/org/xmtp/android/library/DecodedMessage.kt b/library/src/main/java/org/xmtp/android/library/DecodedMessage.kt index 79a0e3735..6b5122ea6 100644 --- a/library/src/main/java/org/xmtp/android/library/DecodedMessage.kt +++ b/library/src/main/java/org/xmtp/android/library/DecodedMessage.kt @@ -6,15 +6,17 @@ import org.xmtp.proto.message.contents.Content import java.util.Date data class DecodedMessage( + var topic: String, var encodedContent: Content.EncodedContent, var senderAddress: String, var sent: Date ) { var id: String = "" companion object { - fun preview(body: String, senderAddress: String, sent: Date): DecodedMessage { + fun preview(topic: String, body: String, senderAddress: String, sent: Date): DecodedMessage { val encoded = TextCodec().encode(content = body) return DecodedMessage( + topic = topic, encodedContent = encoded, senderAddress = senderAddress, sent = sent diff --git a/library/src/main/java/org/xmtp/android/library/messages/MessageV2.kt b/library/src/main/java/org/xmtp/android/library/messages/MessageV2.kt index 701f02d28..8cd528664 100644 --- a/library/src/main/java/org/xmtp/android/library/messages/MessageV2.kt +++ b/library/src/main/java/org/xmtp/android/library/messages/MessageV2.kt @@ -74,6 +74,7 @@ class MessageV2Builder { throw XMTPException("Topic mismatch") } return DecodedMessage( + topic = header.topic, encodedContent = encodedMessage, senderAddress = signed.sender.walletAddress, sent = Date(header.createdNs / 1_000_000)