Channel
Fundamentals:
By Default Channel is UnBuffered and Rendezvous (Blocks Sender until Receive)
From Channel default is: Unbuffered and Rendezvous (Blocks sender until Receive)
Go to text ā
The default capacity of channel is called RENDEZVOUS
public fun <E> Channel(capacity: Int = RENDEZVOUS,...)
RENDEZVOUS is defined as a meeting at an agreed time and place, typically between two people. - google defintion.
Unbuffered channels transfer elements when sender and receiver meet each other (aka rendezvous). If send is invoked first, then it is suspended until receive is invoked, if receive is invoked first, it is suspended until send is invoked. - kotlin-doc
In Rendezvous Setting: Sender will get blocked until Receiver picks up the message.
In Action
Code
fun main(args: Array<String>) {
runBlocking {
// Default capacity of Channel is:
//
// capacity: Int = RENDEZVOUS,
val channel = Channel<Int>()
val sender = launch(CoroutineName("${Emoji.LETTER}-sender")) {
repeat(2) {
delay(100)
out.info("starting_to_send: $it")
channel.send(it)
// Notice:
// - in first message that sent is not going to be let go until it is received.
// - second message we never get out of send as nobody is listening for 2nd receive.
out.info("sent: $it")
}
}
val listener = launch(CoroutineName("${Emoji.MAILBOX}-listener")) {
repeat(1) {
delay(500)
out.info("received: ${channel.receive()}")
}
}
delay(3000)
listener.cancel()
sender.cancel()
out.info("Main completed")
}
}
Command to reproduce:
gt.sandbox.checkout.commit 3f134b24cc26858fe8c6 \
&& cd "${GT_SANDBOX_REPO}" \
&& cmd.run.announce "./gradlew run --quiet"
Recorded output of command:
[elapsed: 152ms][coroutine:āļø-sender] starting_to_send: 0
[elapsed: 543ms][coroutine:š¬-listener] received: 0
[elapsed: 545ms][coroutine:āļø-sender] sent: 0
[elapsed: 649ms][coroutine:āļø-sender] starting_to_send: 1
[elapsed: 3040ms][coroutine:unnamed] Main completed
Allows buffering
From allows-buffering
Go to text ā
Code
fun main(args: Array<String>) {
runBlocking {
val channel = Channel<Int>(Channel.UNLIMITED)
val sender = launch(CoroutineName("${Emoji.LETTER}-sender")) {
repeat(5) {
delay(50)
out.info("starting_to_send: $it")
channel.send(it)
out.info("sent: $it")
}
}
val listener = launch(CoroutineName("${Emoji.MAILBOX}-listener")) {
repeat(2) {
delay(500)
out.info("received: ${channel.receive()}")
}
}
delay(3000)
listener.cancel()
sender.cancel()
out.info("Main completed")
}
}
Command to reproduce:
gt.sandbox.checkout.commit e067a37e2aa019ce5451 \
&& cd "${GT_SANDBOX_REPO}" \
&& cmd.run.announce "./gradlew run --quiet"
Recorded output of command:
[elapsed: 100ms][coroutine:āļø-sender] starting_to_send: 0
[elapsed: 116ms][coroutine:āļø-sender] sent: 0
[elapsed: 170ms][coroutine:āļø-sender] starting_to_send: 1
[elapsed: 170ms][coroutine:āļø-sender] sent: 1
[elapsed: 226ms][coroutine:āļø-sender] starting_to_send: 2
[elapsed: 226ms][coroutine:āļø-sender] sent: 2
[elapsed: 279ms][coroutine:āļø-sender] starting_to_send: 3
[elapsed: 279ms][coroutine:āļø-sender] sent: 3
[elapsed: 334ms][coroutine:āļø-sender] starting_to_send: 4
[elapsed: 334ms][coroutine:āļø-sender] sent: 4
[elapsed: 542ms][coroutine:š¬-listener] received: 0
[elapsed: 1048ms][coroutine:š¬-listener] received: 1
[elapsed: 3043ms][coroutine:unnamed] Main completed
Closing Channel
From Closing Channel
Go to text ā
Traits:
- Channel.send() will throw exception if channel is closed.
- Channel.receive() will throw exception if channel is closed.
- Receiver will get out of for loop if channel is closed.
In Action
GIVEN channel is closed:
- WHEN sender attempts to write THEN exception is thrown on sender
- WHEN receiver uses for loop on channel THEN Receiver gets out of for loop.
Code
package com.glassthought.sandbox
import com.glassthought.sandbox.util.out.impl.OutSettings
import gt.sandbox.util.output.Out
import kotlinx.coroutines.CoroutineName
import kotlinx.coroutines.channels.Channel
import kotlinx.coroutines.delay
import kotlinx.coroutines.launch
import kotlinx.coroutines.runBlocking
val out = Out.standard(OutSettings(printCoroutineName = true, printThreadInfo = false))
fun main(args: Array<String>) {
runBlocking {
val channel = Channel<Int>(Channel.UNLIMITED)
val sender = launch(CoroutineName("${Emoji.LETTER}-sender")) {
try {
repeat(10) {
delay(500)
out.info("starting_to_send: $it")
channel.send(it)
out.info("sent: $it")
}
} catch (e: Exception) {
out.infoRed("sender exception: $e")
}
}
val listener = launch(CoroutineName("${Emoji.MAILBOX}-listener")) {
try {
for (i in channel) {
out.info("received: $i")
}
out.info("Listener Done - ${Emoji.CHECKERED_FLAG}")
} catch (e: Exception) {
out.infoRed("listener exception: $e")
}
}
delay(1700)
out.info("Closing channel from Main")
channel.close()
delay(2000)
out.info("Main completed. Exiting...")
System.exit(0)
}
}
class Emoji {
companion object {
const val LETTER = "ā\uFE0F"
const val MAILBOX = "\uD83D\uDCEC"
const val CHECKERED_FLAG = "\uD83C\uDFC1"
}
}
Command to reproduce:
gt.sandbox.checkout.commit 58e15651b7326dc65946 \
&& cd "${GT_SANDBOX_REPO}" \
&& cmd.run.announce "./gradlew run --quiet"
Recorded output of command:
[elapsed: 559ms][coroutine:āļø-sender] starting_to_send: 0
[elapsed: 583ms][coroutine:āļø-sender] sent: 0
[elapsed: 583ms][coroutine:š¬-listener] received: 0
[elapsed: 1088ms][coroutine:āļø-sender] starting_to_send: 1
[elapsed: 1089ms][coroutine:āļø-sender] sent: 1
[elapsed: 1090ms][coroutine:š¬-listener] received: 1
[elapsed: 1593ms][coroutine:āļø-sender] starting_to_send: 2
[elapsed: 1594ms][coroutine:āļø-sender] sent: 2
[elapsed: 1594ms][coroutine:š¬-listener] received: 2
[elapsed: 1742ms][coroutine:unnamed] Closing channel from Main
[elapsed: 1746ms][coroutine:š¬-listener] Listener Done - š
[elapsed: 2099ms][coroutine:āļø-sender] starting_to_send: 3
[elapsed: 2105ms][coroutine:āļø-sender] sender exception: kotlinx.coroutines.channels.ClosedSendChannelException: Channel was closed
[elapsed: 3752ms][coroutine:unnamed] Main completed. Exiting...
GIVEN channel is closed:
- WHEN receiver uses receive THEN Exception is thrown.
Code
package com.glassthought.sandbox
import com.glassthought.sandbox.util.out.impl.OutSettings
import gt.sandbox.util.output.Out
import kotlinx.coroutines.CoroutineName
import kotlinx.coroutines.channels.Channel
import kotlinx.coroutines.delay
import kotlinx.coroutines.launch
import kotlinx.coroutines.runBlocking
val out = Out.standard(OutSettings(printCoroutineName = true, printThreadInfo = false))
fun main(args: Array<String>) {
runBlocking {
val channel = Channel<Int>(Channel.UNLIMITED)
val sender = launch(CoroutineName("${Emoji.LETTER}-sender")) {
try {
repeat(1) {
delay(500)
out.info("starting_to_send: $it")
channel.send(it)
out.info("sent: $it")
}
} catch (e: Exception) {
out.infoRed("sender exception: $e")
}
}
val listener = launch(CoroutineName("${Emoji.MAILBOX}-listener")) {
try {
repeat(100){
out.info("received: ${channel.receive()}")
}
out.info("Listener Done - ${Emoji.CHECKERED_FLAG}")
} catch (e: Exception) {
out.infoRed("listener exception: $e")
}
}
delay(1700)
out.info("Closing channel from Main")
channel.close()
delay(2000)
out.info("Main completed. Exiting...")
System.exit(0)
}
}
class Emoji {
companion object {
const val LETTER = "ā\uFE0F"
const val MAILBOX = "\uD83D\uDCEC"
const val CHECKERED_FLAG = "\uD83C\uDFC1"
}
}
Command to reproduce:
gt.sandbox.checkout.commit 0a95e9908782f3bef115 \
&& cd "${GT_SANDBOX_REPO}" \
&& cmd.run.announce "./gradlew run --quiet"
Recorded output of command:
[elapsed: 564ms][coroutine:āļø-sender] starting_to_send: 0
[elapsed: 588ms][coroutine:āļø-sender] sent: 0
[elapsed: 589ms][coroutine:š¬-listener] received: 0
[elapsed: 1740ms][coroutine:unnamed] Closing channel from Main
[elapsed: 1746ms][coroutine:š¬-listener] listener exception: kotlinx.coroutines.channels.ClosedReceiveChannelException: Channel was closed
[elapsed: 3748ms][coroutine:unnamed] Main completed. Exiting...
Support Fan-in from multiple co-routines
Multiple coroutines may send to the same channel. - kotlin-doc
Additional Snapshots
Rough Benchmark
From rough_benchmark
Go to text ā
Code
package com.glassthought.sandbox
import com.glassthought.sandbox.util.out.impl.OutSettings
import gt.sandbox.util.output.Out
import kotlinx.coroutines.CoroutineName
import kotlinx.coroutines.channels.Channel
import kotlinx.coroutines.delay
import kotlinx.coroutines.launch
import kotlinx.coroutines.runBlocking
val out = Out.standard(OutSettings(printCoroutineName = true, printThreadInfo = false))
fun main(args: Array<String>) {
runBlocking {
val channel = Channel<Int>(Channel.UNLIMITED)
var stampBeforeSent = System.nanoTime()
val sender = launch(CoroutineName("${Emoji.LETTER}-sender")) {
repeat(100) {
delay(50)
out.info("starting_to_send: $it")
stampBeforeSent = System.nanoTime()
channel.send(it)
out.info("sent: $it")
}
}
val listener = launch(CoroutineName("${Emoji.MAILBOX}-listener")) {
for (i in channel) {
val stampAtReceive = System.nanoTime()
out.info("received: $i (time: ${(stampAtReceive - stampBeforeSent) / 1000}micro-seconds)")
}
}
delay(10000)
System.exit(0)
out.info("Main completed")
}
}
class Emoji {
companion object {
const val LETTER = "ā\uFE0F"
const val MAILBOX = "\uD83D\uDCEC"
}
}
Command to reproduce:
gt.sandbox.checkout.commit 9f4da35cd0ec7c7776d2 \
&& cd "${GT_SANDBOX_REPO}" \
&& cmd.run.announce "./gradlew run --quiet"
Recorded output of command:
[elapsed: 94ms][coroutine:āļø-sender] starting_to_send: 0
[elapsed: 108ms][coroutine:āļø-sender] sent: 0
[elapsed: 110ms][coroutine:š¬-listener] received: 0 (time: 915micro-seconds)
[elapsed: 162ms][coroutine:āļø-sender] starting_to_send: 1
[elapsed: 162ms][coroutine:āļø-sender] sent: 1
[elapsed: 162ms][coroutine:š¬-listener] received: 1 (time: 166micro-seconds)
[elapsed: 217ms][coroutine:āļø-sender] starting_to_send: 2
[elapsed: 217ms][coroutine:āļø-sender] sent: 2
[elapsed: 217ms][coroutine:š¬-listener] received: 2 (time: 147micro-seconds)
[elapsed: 272ms][coroutine:āļø-sender] starting_to_send: 3
[elapsed: 272ms][coroutine:āļø-sender] sent: 3
[elapsed: 272ms][coroutine:š¬-listener] received: 3 (time: 197micro-seconds)
[elapsed: 327ms][coroutine:āļø-sender] starting_to_send: 4
[elapsed: 327ms][coroutine:āļø-sender] sent: 4
[elapsed: 327ms][coroutine:š¬-listener] received: 4 (time: 227micro-seconds)
[elapsed: 382ms][coroutine:āļø-sender] starting_to_send: 5
[elapsed: 383ms][coroutine:āļø-sender] sent: 5
[elapsed: 383ms][coroutine:š¬-listener] received: 5 (time: 397micro-seconds)
[elapsed: 437ms][coroutine:āļø-sender] starting_to_send: 6
[elapsed: 438ms][coroutine:āļø-sender] sent: 6
[elapsed: 438ms][coroutine:š¬-listener] received: 6 (time: 527micro-seconds)
[elapsed: 489ms][coroutine:āļø-sender] starting_to_send: 7
[elapsed: 490ms][coroutine:āļø-sender] sent: 7
[elapsed: 490ms][coroutine:š¬-listener] received: 7 (time: 635micro-seconds)
[elapsed: 543ms][coroutine:āļø-sender] starting_to_send: 8
[elapsed: 544ms][coroutine:āļø-sender] sent: 8
[elapsed: 544ms][coroutine:š¬-listener] received: 8 (time: 392micro-seconds)
[elapsed: 594ms][coroutine:āļø-sender] starting_to_send: 9
[elapsed: 595ms][coroutine:āļø-sender] sent: 9
[elapsed: 595ms][coroutine:š¬-listener] received: 9 (time: 335micro-seconds)
[elapsed: 649ms][coroutine:āļø-sender] starting_to_send: 10
[elapsed: 650ms][coroutine:āļø-sender] sent: 10
[elapsed: 650ms][coroutine:š¬-listener] received: 10 (time: 282micro-seconds)
[elapsed: 705ms][coroutine:āļø-sender] starting_to_send: 11
[elapsed: 706ms][coroutine:āļø-sender] sent: 11
[elapsed: 706ms][coroutine:š¬-listener] received: 11 (time: 463micro-seconds)
[elapsed: 761ms][coroutine:āļø-sender] starting_to_send: 12
[elapsed: 762ms][coroutine:āļø-sender] sent: 12
[elapsed: 763ms][coroutine:š¬-listener] received: 12 (time: 601micro-seconds)
[elapsed: 818ms][coroutine:āļø-sender] starting_to_send: 13
[elapsed: 819ms][coroutine:āļø-sender] sent: 13
[elapsed: 819ms][coroutine:š¬-listener] received: 13 (time: 528micro-seconds)
[elapsed: 870ms][coroutine:āļø-sender] starting_to_send: 14
[elapsed: 871ms][coroutine:āļø-sender] sent: 14
[elapsed: 871ms][coroutine:š¬-listener] received: 14 (time: 263micro-seconds)
[elapsed: 926ms][coroutine:āļø-sender] starting_to_send: 15
[elapsed: 927ms][coroutine:āļø-sender] sent: 15
[elapsed: 927ms][coroutine:š¬-listener] received: 15 (time: 456micro-seconds)
[elapsed: 982ms][coroutine:āļø-sender] starting_to_send: 16
[elapsed: 982ms][coroutine:āļø-sender] sent: 16
[elapsed: 982ms][coroutine:š¬-listener] received: 16 (time: 316micro-seconds)
[elapsed: 1036ms][coroutine:āļø-sender] starting_to_send: 17
[elapsed: 1036ms][coroutine:āļø-sender] sent: 17
[elapsed: 1037ms][coroutine:š¬-listener] received: 17 (time: 533micro-seconds)
[elapsed: 1090ms][coroutine:āļø-sender] starting_to_send: 18
[elapsed: 1090ms][coroutine:āļø-sender] sent: 18
[elapsed: 1091ms][coroutine:š¬-listener] received: 18 (time: 255micro-seconds)
[elapsed: 1145ms][coroutine:āļø-sender] starting_to_send: 19
[elapsed: 1146ms][coroutine:āļø-sender] sent: 19
[elapsed: 1146ms][coroutine:š¬-listener] received: 19 (time: 259micro-seconds)
[elapsed: 1201ms][coroutine:āļø-sender] starting_to_send: 20
[elapsed: 1202ms][coroutine:āļø-sender] sent: 20
[elapsed: 1202ms][coroutine:š¬-listener] received: 20 (time: 519micro-seconds)
[elapsed: 1252ms][coroutine:āļø-sender] starting_to_send: 21
[elapsed: 1253ms][coroutine:āļø-sender] sent: 21
[elapsed: 1253ms][coroutine:š¬-listener] received: 21 (time: 388micro-seconds)
[elapsed: 1305ms][coroutine:āļø-sender] starting_to_send: 22
[elapsed: 1305ms][coroutine:āļø-sender] sent: 22
[elapsed: 1306ms][coroutine:š¬-listener] received: 22 (time: 399micro-seconds)
[elapsed: 1356ms][coroutine:āļø-sender] starting_to_send: 23
[elapsed: 1357ms][coroutine:āļø-sender] sent: 23
[elapsed: 1357ms][coroutine:š¬-listener] received: 23 (time: 416micro-seconds)
[elapsed: 1412ms][coroutine:āļø-sender] starting_to_send: 24
[elapsed: 1413ms][coroutine:āļø-sender] sent: 24
[elapsed: 1413ms][coroutine:š¬-listener] received: 24 (time: 518micro-seconds)
[elapsed: 1466ms][coroutine:āļø-sender] starting_to_send: 25
[elapsed: 1467ms][coroutine:āļø-sender] sent: 25
[elapsed: 1467ms][coroutine:š¬-listener] received: 25 (time: 438micro-seconds)
[elapsed: 1520ms][coroutine:āļø-sender] starting_to_send: 26
[elapsed: 1520ms][coroutine:āļø-sender] sent: 26
[elapsed: 1520ms][coroutine:š¬-listener] received: 26 (time: 231micro-seconds)
[elapsed: 1576ms][coroutine:āļø-sender] starting_to_send: 27
[elapsed: 1576ms][coroutine:āļø-sender] sent: 27
[elapsed: 1577ms][coroutine:š¬-listener] received: 27 (time: 377micro-seconds)
[elapsed: 1632ms][coroutine:āļø-sender] starting_to_send: 28
[elapsed: 1632ms][coroutine:āļø-sender] sent: 28
[elapsed: 1632ms][coroutine:š¬-listener] received: 28 (time: 229micro-seconds)
[elapsed: 1687ms][coroutine:āļø-sender] starting_to_send: 29
[elapsed: 1687ms][coroutine:āļø-sender] sent: 29
[elapsed: 1687ms][coroutine:š¬-listener] received: 29 (time: 185micro-seconds)
[elapsed: 1742ms][coroutine:āļø-sender] starting_to_send: 30
[elapsed: 1743ms][coroutine:āļø-sender] sent: 30
[elapsed: 1743ms][coroutine:š¬-listener] received: 30 (time: 334micro-seconds)
[elapsed: 1796ms][coroutine:āļø-sender] starting_to_send: 31
[elapsed: 1797ms][coroutine:āļø-sender] sent: 31
[elapsed: 1797ms][coroutine:š¬-listener] received: 31 (time: 407micro-seconds)
[elapsed: 1848ms][coroutine:āļø-sender] starting_to_send: 32
[elapsed: 1848ms][coroutine:āļø-sender] sent: 32
[elapsed: 1849ms][coroutine:š¬-listener] received: 32 (time: 459micro-seconds)
[elapsed: 1904ms][coroutine:āļø-sender] starting_to_send: 33
[elapsed: 1904ms][coroutine:āļø-sender] sent: 33
[elapsed: 1904ms][coroutine:š¬-listener] received: 33 (time: 249micro-seconds)
[elapsed: 1956ms][coroutine:āļø-sender] starting_to_send: 34
[elapsed: 1956ms][coroutine:āļø-sender] sent: 34
[elapsed: 1957ms][coroutine:š¬-listener] received: 34 (time: 196micro-seconds)
[elapsed: 2012ms][coroutine:āļø-sender] starting_to_send: 35
[elapsed: 2013ms][coroutine:āļø-sender] sent: 35
[elapsed: 2013ms][coroutine:š¬-listener] received: 35 (time: 394micro-seconds)
[elapsed: 2068ms][coroutine:āļø-sender] starting_to_send: 36
[elapsed: 2069ms][coroutine:āļø-sender] sent: 36
[elapsed: 2069ms][coroutine:š¬-listener] received: 36 (time: 399micro-seconds)
[elapsed: 2121ms][coroutine:āļø-sender] starting_to_send: 37
[elapsed: 2121ms][coroutine:āļø-sender] sent: 37
[elapsed: 2121ms][coroutine:š¬-listener] received: 37 (time: 197micro-seconds)
[elapsed: 2173ms][coroutine:āļø-sender] starting_to_send: 38
[elapsed: 2173ms][coroutine:āļø-sender] sent: 38
[elapsed: 2174ms][coroutine:š¬-listener] received: 38 (time: 222micro-seconds)
[elapsed: 2225ms][coroutine:āļø-sender] starting_to_send: 39
[elapsed: 2226ms][coroutine:āļø-sender] sent: 39
[elapsed: 2226ms][coroutine:š¬-listener] received: 39 (time: 400micro-seconds)
[elapsed: 2279ms][coroutine:āļø-sender] starting_to_send: 40
[elapsed: 2279ms][coroutine:āļø-sender] sent: 40
[elapsed: 2279ms][coroutine:š¬-listener] received: 40 (time: 192micro-seconds)
[elapsed: 2334ms][coroutine:āļø-sender] starting_to_send: 41
[elapsed: 2335ms][coroutine:āļø-sender] sent: 41
[elapsed: 2335ms][coroutine:š¬-listener] received: 41 (time: 394micro-seconds)
[elapsed: 2389ms][coroutine:āļø-sender] starting_to_send: 42
[elapsed: 2389ms][coroutine:āļø-sender] sent: 42
[elapsed: 2390ms][coroutine:š¬-listener] received: 42 (time: 583micro-seconds)
[elapsed: 2442ms][coroutine:āļø-sender] starting_to_send: 43
[elapsed: 2443ms][coroutine:āļø-sender] sent: 43
[elapsed: 2443ms][coroutine:š¬-listener] received: 43 (time: 323micro-seconds)
[elapsed: 2496ms][coroutine:āļø-sender] starting_to_send: 44
[elapsed: 2496ms][coroutine:āļø-sender] sent: 44
[elapsed: 2496ms][coroutine:š¬-listener] received: 44 (time: 201micro-seconds)
[elapsed: 2551ms][coroutine:āļø-sender] starting_to_send: 45
[elapsed: 2552ms][coroutine:āļø-sender] sent: 45
[elapsed: 2552ms][coroutine:š¬-listener] received: 45 (time: 329micro-seconds)
[elapsed: 2603ms][coroutine:āļø-sender] starting_to_send: 46
[elapsed: 2604ms][coroutine:āļø-sender] sent: 46
[elapsed: 2604ms][coroutine:š¬-listener] received: 46 (time: 344micro-seconds)
[elapsed: 2658ms][coroutine:āļø-sender] starting_to_send: 47
[elapsed: 2659ms][coroutine:āļø-sender] sent: 47
[elapsed: 2659ms][coroutine:š¬-listener] received: 47 (time: 361micro-seconds)
[elapsed: 2712ms][coroutine:āļø-sender] starting_to_send: 48
[elapsed: 2713ms][coroutine:āļø-sender] sent: 48
[elapsed: 2713ms][coroutine:š¬-listener] received: 48 (time: 169micro-seconds)
[elapsed: 2768ms][coroutine:āļø-sender] starting_to_send: 49
[elapsed: 2768ms][coroutine:āļø-sender] sent: 49
[elapsed: 2768ms][coroutine:š¬-listener] received: 49 (time: 153micro-seconds)
[elapsed: 2820ms][coroutine:āļø-sender] starting_to_send: 50
[elapsed: 2820ms][coroutine:āļø-sender] sent: 50
[elapsed: 2821ms][coroutine:š¬-listener] received: 50 (time: 195micro-seconds)
[elapsed: 2871ms][coroutine:āļø-sender] starting_to_send: 51
[elapsed: 2871ms][coroutine:āļø-sender] sent: 51
[elapsed: 2871ms][coroutine:š¬-listener] received: 51 (time: 183micro-seconds)
[elapsed: 2927ms][coroutine:āļø-sender] starting_to_send: 52
[elapsed: 2927ms][coroutine:āļø-sender] sent: 52
[elapsed: 2928ms][coroutine:š¬-listener] received: 52 (time: 440micro-seconds)
[elapsed: 2981ms][coroutine:āļø-sender] starting_to_send: 53
[elapsed: 2981ms][coroutine:āļø-sender] sent: 53
[elapsed: 2982ms][coroutine:š¬-listener] received: 53 (time: 343micro-seconds)
[elapsed: 3034ms][coroutine:āļø-sender] starting_to_send: 54
[elapsed: 3035ms][coroutine:āļø-sender] sent: 54
[elapsed: 3035ms][coroutine:š¬-listener] received: 54 (time: 353micro-seconds)
[elapsed: 3089ms][coroutine:āļø-sender] starting_to_send: 55
[elapsed: 3089ms][coroutine:āļø-sender] sent: 55
[elapsed: 3090ms][coroutine:š¬-listener] received: 55 (time: 359micro-seconds)
[elapsed: 3145ms][coroutine:āļø-sender] starting_to_send: 56
[elapsed: 3145ms][coroutine:āļø-sender] sent: 56
[elapsed: 3146ms][coroutine:š¬-listener] received: 56 (time: 327micro-seconds)
[elapsed: 3198ms][coroutine:āļø-sender] starting_to_send: 57
[elapsed: 3198ms][coroutine:āļø-sender] sent: 57
[elapsed: 3198ms][coroutine:š¬-listener] received: 57 (time: 250micro-seconds)
[elapsed: 3253ms][coroutine:āļø-sender] starting_to_send: 58
[elapsed: 3254ms][coroutine:āļø-sender] sent: 58
[elapsed: 3254ms][coroutine:š¬-listener] received: 58 (time: 327micro-seconds)
[elapsed: 3306ms][coroutine:āļø-sender] starting_to_send: 59
[elapsed: 3306ms][coroutine:āļø-sender] sent: 59
[elapsed: 3307ms][coroutine:š¬-listener] received: 59 (time: 360micro-seconds)
[elapsed: 3360ms][coroutine:āļø-sender] starting_to_send: 60
[elapsed: 3361ms][coroutine:āļø-sender] sent: 60
[elapsed: 3361ms][coroutine:š¬-listener] received: 60 (time: 470micro-seconds)
[elapsed: 3416ms][coroutine:āļø-sender] starting_to_send: 61
[elapsed: 3417ms][coroutine:āļø-sender] sent: 61
[elapsed: 3417ms][coroutine:š¬-listener] received: 61 (time: 364micro-seconds)
[elapsed: 3472ms][coroutine:āļø-sender] starting_to_send: 62
[elapsed: 3472ms][coroutine:āļø-sender] sent: 62
[elapsed: 3473ms][coroutine:š¬-listener] received: 62 (time: 447micro-seconds)
[elapsed: 3528ms][coroutine:āļø-sender] starting_to_send: 63
[elapsed: 3528ms][coroutine:āļø-sender] sent: 63
[elapsed: 3529ms][coroutine:š¬-listener] received: 63 (time: 400micro-seconds)
[elapsed: 3579ms][coroutine:āļø-sender] starting_to_send: 64
[elapsed: 3580ms][coroutine:āļø-sender] sent: 64
[elapsed: 3580ms][coroutine:š¬-listener] received: 64 (time: 321micro-seconds)
[elapsed: 3631ms][coroutine:āļø-sender] starting_to_send: 65
[elapsed: 3631ms][coroutine:āļø-sender] sent: 65
[elapsed: 3631ms][coroutine:š¬-listener] received: 65 (time: 164micro-seconds)
[elapsed: 3683ms][coroutine:āļø-sender] starting_to_send: 66
[elapsed: 3683ms][coroutine:āļø-sender] sent: 66
[elapsed: 3684ms][coroutine:š¬-listener] received: 66 (time: 157micro-seconds)
[elapsed: 3739ms][coroutine:āļø-sender] starting_to_send: 67
[elapsed: 3739ms][coroutine:āļø-sender] sent: 67
[elapsed: 3740ms][coroutine:š¬-listener] received: 67 (time: 315micro-seconds)
[elapsed: 3794ms][coroutine:āļø-sender] starting_to_send: 68
[elapsed: 3794ms][coroutine:āļø-sender] sent: 68
[elapsed: 3795ms][coroutine:š¬-listener] received: 68 (time: 505micro-seconds)
[elapsed: 3846ms][coroutine:āļø-sender] starting_to_send: 69
[elapsed: 3847ms][coroutine:āļø-sender] sent: 69
[elapsed: 3847ms][coroutine:š¬-listener] received: 69 (time: 309micro-seconds)
[elapsed: 3902ms][coroutine:āļø-sender] starting_to_send: 70
[elapsed: 3902ms][coroutine:āļø-sender] sent: 70
[elapsed: 3903ms][coroutine:š¬-listener] received: 70 (time: 246micro-seconds)
[elapsed: 3956ms][coroutine:āļø-sender] starting_to_send: 71
[elapsed: 3957ms][coroutine:āļø-sender] sent: 71
[elapsed: 3957ms][coroutine:š¬-listener] received: 71 (time: 390micro-seconds)
[elapsed: 4008ms][coroutine:āļø-sender] starting_to_send: 72
[elapsed: 4008ms][coroutine:āļø-sender] sent: 72
[elapsed: 4009ms][coroutine:š¬-listener] received: 72 (time: 304micro-seconds)
[elapsed: 4062ms][coroutine:āļø-sender] starting_to_send: 73
[elapsed: 4062ms][coroutine:āļø-sender] sent: 73
[elapsed: 4063ms][coroutine:š¬-listener] received: 73 (time: 322micro-seconds)
[elapsed: 4117ms][coroutine:āļø-sender] starting_to_send: 74
[elapsed: 4117ms][coroutine:āļø-sender] sent: 74
[elapsed: 4117ms][coroutine:š¬-listener] received: 74 (time: 210micro-seconds)
[elapsed: 4170ms][coroutine:āļø-sender] starting_to_send: 75
[elapsed: 4170ms][coroutine:āļø-sender] sent: 75
[elapsed: 4171ms][coroutine:š¬-listener] received: 75 (time: 319micro-seconds)
[elapsed: 4224ms][coroutine:āļø-sender] starting_to_send: 76
[elapsed: 4225ms][coroutine:āļø-sender] sent: 76
[elapsed: 4225ms][coroutine:š¬-listener] received: 76 (time: 235micro-seconds)
[elapsed: 4275ms][coroutine:āļø-sender] starting_to_send: 77
[elapsed: 4276ms][coroutine:āļø-sender] sent: 77
[elapsed: 4276ms][coroutine:š¬-listener] received: 77 (time: 383micro-seconds)
[elapsed: 4331ms][coroutine:āļø-sender] starting_to_send: 78
[elapsed: 4332ms][coroutine:āļø-sender] sent: 78
[elapsed: 4332ms][coroutine:š¬-listener] received: 78 (time: 413micro-seconds)
[elapsed: 4387ms][coroutine:āļø-sender] starting_to_send: 79
[elapsed: 4388ms][coroutine:āļø-sender] sent: 79
[elapsed: 4388ms][coroutine:š¬-listener] received: 79 (time: 322micro-seconds)
[elapsed: 4443ms][coroutine:āļø-sender] starting_to_send: 80
[elapsed: 4443ms][coroutine:āļø-sender] sent: 80
[elapsed: 4444ms][coroutine:š¬-listener] received: 80 (time: 287micro-seconds)
[elapsed: 4494ms][coroutine:āļø-sender] starting_to_send: 81
[elapsed: 4494ms][coroutine:āļø-sender] sent: 81
[elapsed: 4494ms][coroutine:š¬-listener] received: 81 (time: 298micro-seconds)
[elapsed: 4550ms][coroutine:āļø-sender] starting_to_send: 82
[elapsed: 4550ms][coroutine:āļø-sender] sent: 82
[elapsed: 4551ms][coroutine:š¬-listener] received: 82 (time: 424micro-seconds)
[elapsed: 4604ms][coroutine:āļø-sender] starting_to_send: 83
[elapsed: 4604ms][coroutine:āļø-sender] sent: 83
[elapsed: 4605ms][coroutine:š¬-listener] received: 83 (time: 405micro-seconds)
[elapsed: 4658ms][coroutine:āļø-sender] starting_to_send: 84
[elapsed: 4658ms][coroutine:āļø-sender] sent: 84
[elapsed: 4658ms][coroutine:š¬-listener] received: 84 (time: 282micro-seconds)
[elapsed: 4713ms][coroutine:āļø-sender] starting_to_send: 85
[elapsed: 4713ms][coroutine:āļø-sender] sent: 85
[elapsed: 4714ms][coroutine:š¬-listener] received: 85 (time: 286micro-seconds)
[elapsed: 4769ms][coroutine:āļø-sender] starting_to_send: 86
[elapsed: 4770ms][coroutine:āļø-sender] sent: 86
[elapsed: 4770ms][coroutine:š¬-listener] received: 86 (time: 433micro-seconds)
[elapsed: 4825ms][coroutine:āļø-sender] starting_to_send: 87
[elapsed: 4826ms][coroutine:āļø-sender] sent: 87
[elapsed: 4826ms][coroutine:š¬-listener] received: 87 (time: 428micro-seconds)
[elapsed: 4881ms][coroutine:āļø-sender] starting_to_send: 88
[elapsed: 4881ms][coroutine:āļø-sender] sent: 88
[elapsed: 4881ms][coroutine:š¬-listener] received: 88 (time: 412micro-seconds)
[elapsed: 4937ms][coroutine:āļø-sender] starting_to_send: 89
[elapsed: 4937ms][coroutine:āļø-sender] sent: 89
[elapsed: 4937ms][coroutine:š¬-listener] received: 89 (time: 245micro-seconds)
[elapsed: 4992ms][coroutine:āļø-sender] starting_to_send: 90
[elapsed: 4993ms][coroutine:āļø-sender] sent: 90
[elapsed: 4993ms][coroutine:š¬-listener] received: 90 (time: 231micro-seconds)
[elapsed: 5048ms][coroutine:āļø-sender] starting_to_send: 91
[elapsed: 5049ms][coroutine:āļø-sender] sent: 91
[elapsed: 5049ms][coroutine:š¬-listener] received: 91 (time: 319micro-seconds)
[elapsed: 5103ms][coroutine:āļø-sender] starting_to_send: 92
[elapsed: 5104ms][coroutine:āļø-sender] sent: 92
[elapsed: 5104ms][coroutine:š¬-listener] received: 92 (time: 278micro-seconds)
[elapsed: 5159ms][coroutine:āļø-sender] starting_to_send: 93
[elapsed: 5160ms][coroutine:āļø-sender] sent: 93
[elapsed: 5160ms][coroutine:š¬-listener] received: 93 (time: 355micro-seconds)
[elapsed: 5215ms][coroutine:āļø-sender] starting_to_send: 94
[elapsed: 5215ms][coroutine:āļø-sender] sent: 94
[elapsed: 5216ms][coroutine:š¬-listener] received: 94 (time: 183micro-seconds)
[elapsed: 5267ms][coroutine:āļø-sender] starting_to_send: 95
[elapsed: 5267ms][coroutine:āļø-sender] sent: 95
[elapsed: 5267ms][coroutine:š¬-listener] received: 95 (time: 150micro-seconds)
[elapsed: 5321ms][coroutine:āļø-sender] starting_to_send: 96
[elapsed: 5321ms][coroutine:āļø-sender] sent: 96
[elapsed: 5321ms][coroutine:š¬-listener] received: 96 (time: 236micro-seconds)
[elapsed: 5372ms][coroutine:āļø-sender] starting_to_send: 97
[elapsed: 5373ms][coroutine:āļø-sender] sent: 97
[elapsed: 5373ms][coroutine:š¬-listener] received: 97 (time: 221micro-seconds)
[elapsed: 5428ms][coroutine:āļø-sender] starting_to_send: 98
[elapsed: 5429ms][coroutine:āļø-sender] sent: 98
[elapsed: 5429ms][coroutine:š¬-listener] received: 98 (time: 362micro-seconds)
[elapsed: 5484ms][coroutine:āļø-sender] starting_to_send: 99
[elapsed: 5484ms][coroutine:āļø-sender] sent: 99
[elapsed: 5487ms][coroutine:š¬-listener] received: 99 (time: 2198micro-seconds)
Children