diff --git a/client/src/test/kotlin/io/flamenet/client/LiveConversationTest.kt b/client/src/test/kotlin/io/flamenet/client/LiveConversationTest.kt index f097b0b..c8b7168 100644 --- a/client/src/test/kotlin/io/flamenet/client/LiveConversationTest.kt +++ b/client/src/test/kotlin/io/flamenet/client/LiveConversationTest.kt @@ -69,6 +69,23 @@ class LiveConversationTest { ) } + /** + * What a person would see, which is what every assertion below means. + * + * ๐Ÿ”ด **`poll` returns control traffic too**, and since key-log checking + * became automatic there is reliably some: the first send to a contact now + * gossips this device's view of the transparency log (ยง19.4), because + * enforcement sets the head pin that gossip had nothing to send without. + * That envelope is consumed by the client and never shown, and asserting on + * the raw list counted it as a message โ€” so these tests failed on a change + * that made the product more correct, not less. + * + * The app has always filtered this way; the tests were reading a layer + * lower than the thing they were describing. + */ + private fun Conversations.readable(): List = + poll().filter { it.content.isRenderable } + @Test fun `two people exchange messages through a real relay`() { val base = fleet ?: return @@ -81,7 +98,7 @@ class LiveConversationTest { assertTrue(sent.reachedSomeone, "nothing was delivered: ${sent.failed}") assertEquals(listOf(bob.identity.deviceId), sent.delivered) - val received = bob.conversations.poll() + val received = bob.conversations.readable() assertEquals(1, received.size, "Bob's inbox had ${received.size} messages") assertEquals("hello from the Android engine ๐Ÿ‘‹", received[0].text) assertEquals(alice.userId, received[0].fromUser) @@ -90,16 +107,16 @@ class LiveConversationTest { // Bob replies on the session he just established, which is the step // that turns a handshake into a conversation. assertTrue(bob.conversations.send(alice.userId, "and hello back").reachedSomeone) - val back = alice.conversations.poll() + val back = alice.conversations.readable() assertEquals(1, back.size) assertEquals("and hello back", back[0].text) // Several turns, so the ratchet is exercised past the handshake. for (turn in 1..3) { alice.conversations.send(bob.userId, "alice $turn") - assertEquals("alice $turn", bob.conversations.poll().single().text) + assertEquals("alice $turn", bob.conversations.readable().single().text) bob.conversations.send(alice.userId, "bob $turn") - assertEquals("bob $turn", alice.conversations.poll().single().text) + assertEquals("bob $turn", alice.conversations.readable().single().text) } } @@ -116,8 +133,8 @@ class LiveConversationTest { val bob = signUp(base, "d") alice.conversations.send(bob.userId, "only once please") - assertEquals(1, bob.conversations.poll().size) - assertEquals(0, bob.conversations.poll().size, "the relay re-delivered a read message") + assertEquals(1, bob.conversations.readable().size) + assertEquals(0, bob.conversations.readable().size, "the relay re-delivered a read message") } /** @@ -146,8 +163,8 @@ class LiveConversationTest { val sent = alice.conversations.send(bob.userId, "to both of your devices") assertEquals(2, sent.delivered.size, "only reached ${sent.delivered}; failed: ${sent.failed}") - assertEquals("to both of your devices", bob.conversations.poll().single().text) - assertEquals("to both of your devices", secondConversations.poll().single().text) + assertEquals("to both of your devices", bob.conversations.readable().single().text) + assertEquals("to both of your devices", secondConversations.readable().single().text) } /** @@ -198,7 +215,7 @@ class LiveConversationTest { bob.userId, picture, "image/png", width = 64, height = 48) assertTrue(sent.reachedSomeone, "nothing delivered: ${sent.failed}") - val received = bob.conversations.poll().single() + val received = bob.conversations.readable().single() val ref = received.content.attachment assertTrue(ref != null, "no attachment reference arrived; text was '${received.text}'") assertEquals("image/png", ref!!.mime) @@ -249,7 +266,7 @@ class LiveConversationTest { assertTrue(sent.reachedSomeone, "nothing delivered: ${sent.failed}") for (member in listOf(bob, carol)) { - val got = member.conversations.poll().single() + val got = member.conversations.readable().single() assertEquals("hello everyone", got.text) assertEquals(group.id, got.content.groupId, "the message did not carry group routing, so it would file under the sender") diff --git a/client/src/test/kotlin/io/flamenet/client/LiveShapesTest.kt b/client/src/test/kotlin/io/flamenet/client/LiveShapesTest.kt index 723e8a3..bdc6581 100644 --- a/client/src/test/kotlin/io/flamenet/client/LiveShapesTest.kt +++ b/client/src/test/kotlin/io/flamenet/client/LiveShapesTest.kt @@ -284,7 +284,14 @@ class LiveShapesTest { val sent = alice.second.send(bob.first, text) assertTrue(sent.reachedSomeone, "$base delivered nothing: ${sent.failed}") - val got = bob.second.poll() + // ๐Ÿ”ด What a PERSON would see. `poll` also returns control traffic, and + // since key-log checking became automatic there is reliably some: the + // first send to a contact gossips this device's view of the + // transparency log (ยง19.4), which enforcement is what sets the pin for. + // The client consumes that envelope and never shows it โ€” counting it as + // a message made this test fail on a change that made the product more + // correct. + val got = bob.second.poll().filter { it.content.isRenderable } assertEquals(1, got.size, "$base: expected one message, got ${got.size}") assertEquals(text, got.single().text) }