Skip to main content

wire_framework/resource/
unique.rs

1use std::sync::{Arc, Mutex};
2
3/// Wrapper for resources that only support one consumer.
4///
5/// Normally, all the resources should support sharing between several tasks,
6/// but there are some cases where a resource should only be consumed by a single task.
7#[derive(Debug)]
8pub struct Unique<T: 'static + Send> {
9    inner: Arc<Mutex<Option<T>>>,
10}
11
12impl<T> Clone for Unique<T>
13where
14    T: 'static + Send,
15{
16    fn clone(&self) -> Self {
17        Self {
18            inner: self.inner.clone(),
19        }
20    }
21}
22
23impl<T: 'static + Send> Unique<T> {
24    /// Creates a new unique resource.
25    pub fn new(inner: T) -> Self {
26        Self {
27            inner: Arc::new(Mutex::new(Some(inner))),
28        }
29    }
30
31    /// Takes the resource from the container.
32    /// Will return `None` if the resource was already taken.
33    pub fn take(&self) -> Option<T> {
34        let result = self.inner.lock().unwrap().take();
35
36        if result.is_some() {
37            tracing::info!(
38                "Resource {} has been taken",
39                std::any::type_name::<Unique<T>>()
40            );
41        }
42
43        result
44    }
45}