Struct holochain::prelude::dependencies::kitsune_p2p_types::dependencies::lair_keystore_api::dependencies::tokio::sync::watch::Receiver
source · pub struct Receiver<T> { /* private fields */ }
Expand description
Receives values from the associated Sender
.
Instances are created by the channel
function.
To turn this receiver into a Stream
, you can use the WatchStream
wrapper.
Implementations
sourceimpl<T> Receiver<T>
impl<T> Receiver<T>
sourcepub fn borrow(&self) -> Ref<'_, T>
pub fn borrow(&self) -> Ref<'_, T>
Returns a reference to the most recently sent value.
This method does not mark the returned value as seen, so future calls to
changed
may return immediately even if you have already seen the
value with a call to borrow
.
Outstanding borrows hold a read lock. This means that long lived borrows
could cause the send half to block. It is recommended to keep the borrow
as short lived as possible. Additionally, if you are running in an
environment that allows !Send
futures, you must ensure that the
returned Ref
type is never held alive across an .await
point.
The priority policy of the lock is dependent on the underlying lock
implementation, and this type does not guarantee that any particular policy
will be used. In particular, a producer which is waiting to acquire the lock
in send
might or might not block concurrent calls to borrow
, e.g.:
Potential deadlock example
// Task 1 (on thread A) | // Task 2 (on thread B)
let _ref1 = rx.borrow(); |
| // will block
| let _ = tx.send(());
// may deadlock |
let _ref2 = rx.borrow(); |
Examples
use tokio::sync::watch;
let (_, rx) = watch::channel("hello");
assert_eq!(*rx.borrow(), "hello");
sourcepub fn borrow_and_update(&mut self) -> Ref<'_, T>
pub fn borrow_and_update(&mut self) -> Ref<'_, T>
Returns a reference to the most recently sent value and marks that value as seen.
This method marks the current value as seen. Subsequent calls to changed
will not return immediately until the Sender
has modified the shared
value again.
Outstanding borrows hold a read lock. This means that long lived borrows
could cause the send half to block. It is recommended to keep the borrow
as short lived as possible. Additionally, if you are running in an
environment that allows !Send
futures, you must ensure that the
returned Ref
type is never held alive across an .await
point.
The priority policy of the lock is dependent on the underlying lock
implementation, and this type does not guarantee that any particular policy
will be used. In particular, a producer which is waiting to acquire the lock
in send
might or might not block concurrent calls to borrow
, e.g.:
Potential deadlock example
// Task 1 (on thread A) | // Task 2 (on thread B)
let _ref1 = rx1.borrow_and_update(); |
| // will block
| let _ = tx.send(());
// may deadlock |
let _ref2 = rx2.borrow_and_update(); |
sourcepub fn has_changed(&self) -> Result<bool, RecvError>
pub fn has_changed(&self) -> Result<bool, RecvError>
Checks if this channel contains a message that this receiver has not yet seen. The new value is not marked as seen.
Although this method is called has_changed
, it does not check new
messages for equality, so this call will return true even if the new
message is equal to the old message.
Returns an error if the channel has been closed.
Examples
use tokio::sync::watch;
#[tokio::main]
async fn main() {
let (tx, mut rx) = watch::channel("hello");
tx.send("goodbye").unwrap();
assert!(rx.has_changed().unwrap());
assert_eq!(*rx.borrow_and_update(), "goodbye");
// The value has been marked as seen
assert!(!rx.has_changed().unwrap());
drop(tx);
// The `tx` handle has been dropped
assert!(rx.has_changed().is_err());
}
sourcepub async fn changed(&mut self) -> impl Future<Output = Result<(), RecvError>>
pub async fn changed(&mut self) -> impl Future<Output = Result<(), RecvError>>
Waits for a change notification, then marks the newest value as seen.
If the newest value in the channel has not yet been marked seen when
this method is called, the method marks that value seen and returns
immediately. If the newest value has already been marked seen, then the
method sleeps until a new message is sent by the Sender
connected to
this Receiver
, or until the Sender
is dropped.
This method returns an error if and only if the Sender
is dropped.
Cancel safety
This method is cancel safe. If you use it as the event in a
tokio::select!
statement and some other branch
completes first, then it is guaranteed that no values have been marked
seen by this call to changed
.
Examples
use tokio::sync::watch;
#[tokio::main]
async fn main() {
let (tx, mut rx) = watch::channel("hello");
tokio::spawn(async move {
tx.send("goodbye").unwrap();
});
assert!(rx.changed().await.is_ok());
assert_eq!(*rx.borrow(), "goodbye");
// The `tx` handle has been dropped
assert!(rx.changed().await.is_err());
}
sourcepub fn same_channel(&self, other: &Receiver<T>) -> bool
pub fn same_channel(&self, other: &Receiver<T>) -> bool
Returns true
if receivers belong to the same channel.
Examples
let (tx, rx) = tokio::sync::watch::channel(true);
let rx2 = rx.clone();
assert!(rx.same_channel(&rx2));
let (tx3, rx3) = tokio::sync::watch::channel(true);
assert!(!rx3.same_channel(&rx2));
Trait Implementations
Auto Trait Implementations
impl<T> !RefUnwindSafe for Receiver<T>
impl<T> Send for Receiver<T>where
T: Send + Sync,
impl<T> Sync for Receiver<T>where
T: Send + Sync,
impl<T> Unpin for Receiver<T>
impl<T> !UnwindSafe for Receiver<T>
Blanket Implementations
impl<T> Any for Twhere
T: Any + ?Sized,
impl<T> Any for Twhere
T: Any + ?Sized,
fn type_id_compat(&self) -> TypeId
fn type_id_compat(&self) -> TypeId
impl<T> ArchivePointee for T
impl<T> ArchivePointee for T
type ArchivedMetadata = ()
type ArchivedMetadata = ()
fn pointer_metadata(
_: &<T as ArchivePointee>::ArchivedMetadata
) -> <T as Pointee>::Metadata
fn pointer_metadata(
_: &<T as ArchivePointee>::ArchivedMetadata
) -> <T as Pointee>::Metadata
sourceimpl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
const: unstable · sourcefn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
impl<F, W, T, D> Deserialize<With<T, W>, D> for Fwhere
W: DeserializeWith<F, T, D>,
D: Fallible + ?Sized,
F: ?Sized,
impl<F, W, T, D> Deserialize<With<T, W>, D> for Fwhere
W: DeserializeWith<F, T, D>,
D: Fallible + ?Sized,
F: ?Sized,
fn deserialize(
&self,
deserializer: &mut D
) -> Result<With<T, W>, <D as Fallible>::Error>
fn deserialize(
&self,
deserializer: &mut D
) -> Result<With<T, W>, <D as Fallible>::Error>
impl<T> FutureExt for T
impl<T> FutureExt for T
fn with_context(self, otel_cx: Context) -> WithContext<Self> ⓘ
fn with_context(self, otel_cx: Context) -> WithContext<Self> ⓘ
fn with_current_context(self) -> WithContext<Self> ⓘ
fn with_current_context(self) -> WithContext<Self> ⓘ
sourceimpl<T> Instrument for T
impl<T> Instrument for T
sourcefn instrument(self, span: Span) -> Instrumented<Self> ⓘ
fn instrument(self, span: Span) -> Instrumented<Self> ⓘ
sourcefn in_current_span(self) -> Instrumented<Self> ⓘ
fn in_current_span(self) -> Instrumented<Self> ⓘ
sourceimpl<T> Instrument for T
impl<T> Instrument for T
sourcefn instrument(self, span: Span) -> Instrumented<Self> ⓘ
fn instrument(self, span: Span) -> Instrumented<Self> ⓘ
sourcefn in_current_span(self) -> Instrumented<Self> ⓘ
fn in_current_span(self) -> Instrumented<Self> ⓘ
impl<T> Pointable for T
impl<T> Pointable for T
impl<SS, SP> SupersetOf<SS> for SPwhere
SS: SubsetOf<SP>,
impl<SS, SP> SupersetOf<SS> for SPwhere
SS: SubsetOf<SP>,
fn to_subset(&self) -> Option<SS>
fn to_subset(&self) -> Option<SS>
self
from the equivalent element of its
superset. Read morefn is_in_subset(&self) -> bool
fn is_in_subset(&self) -> bool
self
is actually part of its subset T
(and can be converted to it).fn to_subset_unchecked(&self) -> SS
fn to_subset_unchecked(&self) -> SS
self.to_subset
but without any property checks. Always succeeds.fn from_subset(element: &SS) -> SP
fn from_subset(element: &SS) -> SP
self
to the equivalent element of its superset.