1use core_crypto::MlsTransport;
2use core_crypto::prelude::MlsCommitBundle;
3use core_crypto_ffi::CommitBundle;
4use openmls::prelude::MlsMessageOut;
5use spinoff::Spinner;
6use tokio::sync::RwLock;
7
8pub(crate) struct RunningProcess {
9 spinner: Option<Spinner>,
10 is_task: bool,
11}
12
13impl std::fmt::Debug for RunningProcess {
14 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
15 f.debug_struct("RunningProcess")
16 .field("is_task", &self.is_task)
17 .finish()
18 }
19}
20
21impl RunningProcess {
22 pub(crate) fn new(msg: impl AsRef<str> + std::fmt::Display, is_task: bool) -> Self {
23 let spinner = if std::env::var("CI").is_err() {
24 Some(Spinner::new(
25 spinoff::spinners::Aesthetic,
26 msg.as_ref().to_owned(),
27 if is_task {
28 spinoff::Color::Green
29 } else {
30 spinoff::Color::Blue
31 },
32 ))
33 } else {
34 if is_task {
35 log::info!("{msg}");
36 } else {
37 log::debug!("{msg}");
38 }
39
40 None
41 };
42
43 Self { spinner, is_task }
44 }
45
46 pub(crate) fn update(&mut self, msg: impl AsRef<str> + std::fmt::Display) {
47 if let Some(spinner) = &mut self.spinner {
48 spinner.update_text(msg.as_ref().to_owned());
49 } else if self.is_task {
50 log::info!("{msg}");
51 } else {
52 log::debug!("{msg}");
53 }
54 }
55
56 pub(crate) fn success(self, msg: impl AsRef<str> + std::fmt::Display) {
57 if let Some(mut spinner) = self.spinner {
58 spinner.success(msg.as_ref());
59 } else {
60 log::info!("{msg}");
61 }
62 }
63}
64
65#[async_trait::async_trait]
66pub trait MlsTransportTestExt: MlsTransport {
67 async fn latest_commit_bundle(&self) -> MlsCommitBundle;
68 async fn latest_welcome_message(&self) -> MlsMessageOut {
69 self.latest_commit_bundle().await.welcome.unwrap().clone()
70 }
71}
72
73#[derive(Debug, Default)]
74pub struct MlsTransportSuccessProvider {
75 latest_commit_bundle: RwLock<Option<MlsCommitBundle>>,
76 latest_message: RwLock<Option<Vec<u8>>>,
77}
78
79#[async_trait::async_trait]
80impl MlsTransport for MlsTransportSuccessProvider {
81 async fn send_commit_bundle(
82 &self,
83 commit_bundle: MlsCommitBundle,
84 ) -> core_crypto::Result<core_crypto::MlsTransportResponse> {
85 self.latest_commit_bundle.write().await.replace(commit_bundle);
86 Ok(core_crypto::MlsTransportResponse::Success)
87 }
88
89 async fn send_message(&self, mls_message: Vec<u8>) -> core_crypto::Result<core_crypto::MlsTransportResponse> {
90 self.latest_message.write().await.replace(mls_message);
91 Ok(core_crypto::MlsTransportResponse::Success)
92 }
93}
94
95#[async_trait::async_trait]
96impl MlsTransportTestExt for MlsTransportSuccessProvider {
97 async fn latest_commit_bundle(&self) -> MlsCommitBundle {
98 self.latest_commit_bundle
99 .read()
100 .await
101 .clone()
102 .expect("latest_commit_bundle")
103 }
104}
105
106#[async_trait::async_trait]
107impl core_crypto_ffi::MlsTransport for MlsTransportSuccessProvider {
108 async fn send_commit_bundle(&self, _commit_bundle: CommitBundle) -> core_crypto_ffi::MlsTransportResponse {
109 core_crypto_ffi::MlsTransportResponse::Success
110 }
111
112 async fn send_message(&self, mls_message: Vec<u8>) -> core_crypto_ffi::MlsTransportResponse {
113 self.latest_message.write().await.replace(mls_message);
114 core_crypto_ffi::MlsTransportResponse::Success
115 }
116}