#284 Jul 27, 2026

284. try_recv — Poll the Channel Without Stalling the Loop

Your render loop can’t afford to block on recv() — but it still needs to pick up messages. try_recv checks the channel and returns immediately, message or not.

Bite 283 put a deadline on the wait. But some loops can’t wait at all: a game tick, a UI frame, a simulation step that must keep running whether or not a worker has reported in. Even recv_timeout(1ms) steals a millisecond you don’t have.

try_recv never blocks. Either a message is ready now, or you get an error telling you why not:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
use std::sync::mpsc::{self, TryRecvError};
use std::thread;

let (tx, rx) = mpsc::channel();

// nothing sent yet — returns instantly, no waiting
assert_eq!(rx.try_recv(), Err(TryRecvError::Empty));

tx.send("loaded: level.dat").unwrap();
assert_eq!(rx.try_recv(), Ok("loaded: level.dat"));

Like recv_timeout, the error type carries the signal. Empty means “nothing right now, sender still alive — check again next tick.” Disconnected means “every sender is gone — stop checking”:

1
2
3
drop(tx); // last sender gone

assert_eq!(rx.try_recv(), Err(TryRecvError::Disconnected));

That’s the shape of the classic frame loop — drain whatever arrived since last tick, then get on with the frame:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
loop {
    // drain all pending messages, never block
    loop {
        match rx.try_recv() {
            Ok(msg) => apply(msg),
            Err(TryRecvError::Empty) => break,
            Err(TryRecvError::Disconnected) => return,
        }
    }
    render_frame();
}

The trap to avoid: treating Empty and Disconnected the same. Match only on Ok and you’ll happily poll a dead channel forever — a busy-loop that can never receive anything. Disconnected is your exit condition; use it.

Rule of thumb: recv() when you have nothing better to do, recv_timeout when you can wait a little, try_recv when the loop must not stop.

← Previous 283. recv_timeout — Wait for a Message, But Not Forever Next → 285. try_iter — The Drain Loop You Wrote This Morning, as One Line