Skip to content

Add watch channel with latest-value semantics#1241

Open
veeceey wants to merge 2 commits into
crossbeam-rs:mainfrom
veeceey:feat/issue-942-watch-channel
Open

Add watch channel with latest-value semantics#1241
veeceey wants to merge 2 commits into
crossbeam-rs:mainfrom
veeceey:feat/issue-942-watch-channel

Conversation

@veeceey

@veeceey veeceey commented Feb 23, 2026

Copy link
Copy Markdown

Adds a watch channel type that stores only the latest value. Sending never blocks (overwrites the previous value), and receiving blocks until a new value is available.

This is useful for scenarios like refresh signals where you only care about the most recent value - if multiple sends happen while the receiver is busy, the receiver processes just one iteration instead of N.

The implementation uses Mutex<Option<T>> + Condvar as suggested in #942. Key points:

  • WatchSender and WatchReceiver are both Clone
  • Each receiver independently tracks which version it has seen
  • Disconnection is properly detected (recv returns RecvError when all senders are dropped, send returns SendError when all receivers are dropped)
  • try_recv is available for non-blocking checks
let (tx, mut rx) = crossbeam_channel::watch::<i32>();
tx.send(1);
tx.send(2);
assert_eq!(rx.recv(), Ok(2)); // only latest value

Closes #942

Implements a watch channel where send never blocks (overwrites the
latest value) and recv blocks until a new value arrives. Uses
Mutex<Option<T>> + Condvar internally. Supports multiple senders and
receivers (cloneable), with proper disconnect detection.

Closes crossbeam-rs#942
@veeceey

veeceey commented Feb 23, 2026

Copy link
Copy Markdown
Author

Test results:

running 12 tests
test watch_clone_receiver ... ok
test watch_clone_sender ... ok
test watch_multiple_sends_between_recvs ... ok
test watch_overwrites_value ... ok
test watch_recv_error_on_disconnect ... ok
test watch_send_error_when_no_receivers ... ok
test watch_send_recv_basic ... ok
test watch_multithreaded ... ok
test watch_try_recv_disconnected ... ok
test watch_try_recv_empty ... ok
test watch_try_recv_value ... ok
test watch_recv_blocks_until_send ... ok

test result: ok. 12 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out

Full existing test suite also passes (74 doc+unit tests).

@veeceey

veeceey commented Mar 15, 2026

Copy link
Copy Markdown
Author

checking in on this - the watch channel is a pretty commonly requested primitive. open to design feedback

@veeceey

veeceey commented Apr 9, 2026

Copy link
Copy Markdown
Author

friendly bump on this - happy to make any design changes if needed

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Development

Successfully merging this pull request may close these issues.

Channel that only stores latest message, blocking on Recv, but not Send

1 participant