A question: I have several coroutines (~100) sending a message to a channel. This channel reads the...
d
A question: I have several coroutines (~100) sending a message to a channel. This channel reads the messages in a
for( message in myChannel){ ... }
loop. I can see, via logging, that the events are being send and I see that they are read in the for loop. However, all except for one of the sending coroutines do not continue and keep being stuck in the suspended state. Any idea what could cause this ? Adding a buffer to the channel seems to help, but I would like to know what causes my issue ?
z
How are you creating your channel?
d
Channel()
z
The channel docs say:
The
Channel(capacity)
factory function is used to create channels of different kinds depending on the value of the
capacity
integer:
• When
capacity
is 0 — it creates a rendezvous channel. This channel does not have any buffer at all. An element is transferred from the sender to the receiver only when send and receive invocations meet in time (rendezvous), so send suspends until another coroutine invokes receive, and receive suspends until another coroutine invokes send.
(bold added) In
RENDEZVOUS
mode, “Send suspends until another coroutine invokes receive” And if you look at the docs for the
Channel()
function, you’ll see the default capacity is
RENDEZVOUS
.
d
yes
and that is how I expect it to work
the messages are received, but the sending coroutines remains suspended
z
What dispatcher are you using?
d
DefaultDispatcher
z
Are all the threads blocked somehow? If not, I’m not sure what’s going on
d
No idea what could block them ....
j
Can you share some code that reproduces the issue? As @Zach Klippenstein (he/him) [MOD] suggested it might be due to thread starvation. For instance if what you do in the loop blocks the thread
d
I will provide a snippet later today
👀 1
s
Are you sending messages back to the original source 'actor' (ie process that puts messages into the source Channel)? A circular graph of actors can cause locks.
d
Unfortunately, no :S
@Joffrey @Zach Klippenstein (he/him) [MOD] @Stylianos Gakis @streetsofboston Sorry for not posting sooner. I have found the cause and the solution of my problem. The cause was Ktor. The client starts blocking after a certain number of calls. I was running a test in which I did 100 simultaneous calls using Ktor's 2.0
testApplication
function.
The solution was to configure the client to use the CIO engine
Copy code
val client = createClient {
                engine { CIO }
                install(WebSockets)
            }
(also using websockets)