appChannel

fun appChannel(name: String): Seam

Returns the application Seam for the channel named name, idempotent per name.

The returned seam is single-collection like any other: collect its Seam.incoming once, fan out with shareIn if needed.

Throws

if name's UTF-8 encoding is empty or exceeds 255 bytes.

Samples

runTest(StandardTestDispatcher(), timeout = 5.seconds) {
    val loom = InMemoryLoom()
    val seamAlice = loom.host(Pattern("my-game"))
    val seamBob = loom.join(InMemoryTag("bob"))

    val id1 = NodeId(seamAlice.selfId.value)
    val id2 = NodeId(seamBob.selfId.value)
    val voterIds = setOf(id1, id2)

    val alice = backgroundScope.gameNode(seamAlice, voterIds, raftConfig = RaftConfig(expectVirtualTime = true))
    val bob = backgroundScope.gameNode(seamBob, voterIds, raftConfig = RaftConfig(expectVirtualTime = true))

    // Both peers attach a Quilter<Rga<String>> to the "chat" app channel.
    val chatMsgSer = QuiltMessage.serializer(Rga.wireSerializer(serializer<String>()))
    val aliceChat = Quilter(
        replica = ReplicaId(seamAlice.selfId.value),
        seam = alice.appChannel("chat"),
        initial = Rga.empty(),
        messageSerializer = chatMsgSer,
        scope = backgroundScope,
        config = QuilterConfig(expectVirtualTime = true),
    )
    val bobChat = Quilter(
        replica = ReplicaId(seamBob.selfId.value),
        seam = bob.appChannel("chat"),
        initial = Rga.empty(),
        messageSerializer = chatMsgSer,
        scope = backgroundScope,
        config = QuilterConfig(expectVirtualTime = true),
    )

    // Each peer appends a message to its local RGA replica, then broadcasts the delta.
    fun Quilter<Rga<String>>.chat(msg: String) {
        val (_, op) = state.value.insertAfter(replica, RgaId.HEAD, msg)
        apply(Patch(Rga.empty<String>().apply(op)))
    }
    aliceChat.chat("alice: hello")
    bobChat.chat("bob: hello")
    delay(10) // advance virtual time so delta broadcasts deliver to both peers

    // Both RGAs converge to the same ordered log of two messages.
    assertEquals(aliceChat.state.value.toList(), bobChat.state.value.toList())
    assertEquals(2, aliceChat.state.value.toList().size)

    alice.close()
    bob.close()
}