A drain report records nonblocking receives from a channel. This program fills a channel, then uses try_recv a selected number of times and reports drained versus empty receives.

Program

Play the program to choose how many receive attempts run and watch the queue drain and then report empty.

mpsc_try_recv_coordination_report.rs
use std::sync::mpsc::channel;

fn main() {
    let attempts = ;
    let (tx, rx) = channel();
    for value in 0..3 {
        let _ = tx.send(value);
    }
    let mut drained = 0;
    let mut empty_hits = 0;
    for _ in 0..attempts {
        match rx.try_recv() {
            Ok(_) => drained += 1,
            Err(_) => empty_hits += 1,
        }
    }
    let status = if drained == 0 {
        "idle"
    } else if empty_hits > 0 {
        "drained"
    } else {
        "draining"
    };
    println!("attempts={attempts} drained={drained} empty={empty_hits} {status}");
}
use std::sync::mpsc::channel;

fn main() {
    let attempts = ;
    let (tx, rx) = channel();
    for value in 0..3 {
        let _ = tx.send(value);
    }
    let mut drained = 0;
    let mut empty_hits = 0;
    for _ in 0..attempts {
        match rx.try_recv() {
            Ok(_) => drained += 1,
            Err(_) => empty_hits += 1,
        }
    }
    let status = if drained == 0 {
        "idle"
    } else if empty_hits > 0 {
        "drained"
    } else {
        "draining"
    };
    println!("attempts={attempts} drained={drained} empty={empty_hits} {status}");
}
use std::sync::mpsc::channel;

fn main() {
    let attempts = ;
    let (tx, rx) = channel();
    for value in 0..3 {
        let _ = tx.send(value);
    }
    let mut drained = 0;
    let mut empty_hits = 0;
    for _ in 0..attempts {
        match rx.try_recv() {
            Ok(_) => drained += 1,
            Err(_) => empty_hits += 1,
        }
    }
    let status = if drained == 0 {
        "idle"
    } else if empty_hits > 0 {
        "drained"
    } else {
        "draining"
    };
    println!("attempts={attempts} drained={drained} empty={empty_hits} {status}");
}
nonblocking receive `try_recv` returns `Ok` while messages remain and `Err` once the queue is empty, so it never blocks the caller.
drain report Counting `Ok` results reports how many buffered messages were drained by the selected number of attempts.
empty signal Extra attempts past the buffered messages report empty receives instead of waiting for new data.