Skip to main content

moq_native/
error.rs

1use std::sync::Arc;
2
3/// Errors produced while configuring or establishing native MoQ connections.
4///
5/// Backend-specific failures live in per-backend error types ([`crate::tls::Error`],
6/// [`crate::quinn::Error`], etc.). They're wrapped in `Arc` here so the aggregate
7/// stays `Clone` even though the underlying transport/IO errors are not.
8#[derive(Debug, Clone, thiserror::Error)]
9#[non_exhaustive]
10pub enum Error {
11	#[error(transparent)]
12	Io(Arc<std::io::Error>),
13
14	#[error(transparent)]
15	MoqNet(#[from] moq_net::Error),
16
17	#[error("invalid log directive")]
18	Directive(#[source] Arc<tracing_subscriber::filter::ParseError>),
19
20	#[error("failed to set global tracing subscriber")]
21	SetSubscriber(#[source] Arc<tracing_subscriber::util::TryInitError>),
22
23	#[error("failed to initialize Android logcat layer")]
24	Logcat(#[source] Arc<std::io::Error>),
25
26	#[error("{0}")]
27	NoBackend(&'static str),
28
29	#[error("failed to connect to server")]
30	ConnectFailed,
31
32	#[cfg(feature = "iroh")]
33	#[error("Iroh support is not enabled")]
34	IrohDisabled,
35
36	#[error("tls.root (mTLS) is only supported by the quinn backend")]
37	MtlsQuinnOnly,
38
39	#[error("invalid status code")]
40	InvalidStatusCode,
41
42	#[error("{0}")]
43	Reconnect(String),
44
45	#[error(transparent)]
46	Tls(Arc<crate::tls::Error>),
47
48	#[cfg(feature = "quinn")]
49	#[error(transparent)]
50	Quinn(Arc<crate::quinn::Error>),
51
52	#[cfg(feature = "noq")]
53	#[error(transparent)]
54	Noq(Arc<crate::noq::Error>),
55
56	#[cfg(feature = "quiche")]
57	#[error(transparent)]
58	Quiche(Arc<crate::quiche::Error>),
59
60	#[cfg(feature = "iroh")]
61	#[error(transparent)]
62	Iroh(Arc<crate::iroh::Error>),
63
64	#[cfg(feature = "websocket")]
65	#[error(transparent)]
66	WebSocket(Arc<crate::websocket::Error>),
67}
68
69// The wrapped sources aren't `Clone`, so `#[from]` can't store them behind `Arc`
70// directly. These hand-written conversions keep `?` ergonomic at the call sites.
71impl From<std::io::Error> for Error {
72	fn from(err: std::io::Error) -> Self {
73		Self::Io(Arc::new(err))
74	}
75}
76
77impl From<tracing_subscriber::filter::ParseError> for Error {
78	fn from(err: tracing_subscriber::filter::ParseError) -> Self {
79		Self::Directive(Arc::new(err))
80	}
81}
82
83impl From<crate::tls::Error> for Error {
84	fn from(err: crate::tls::Error) -> Self {
85		Self::Tls(Arc::new(err))
86	}
87}
88
89#[cfg(feature = "quinn")]
90impl From<crate::quinn::Error> for Error {
91	fn from(err: crate::quinn::Error) -> Self {
92		Self::Quinn(Arc::new(err))
93	}
94}
95
96#[cfg(feature = "noq")]
97impl From<crate::noq::Error> for Error {
98	fn from(err: crate::noq::Error) -> Self {
99		Self::Noq(Arc::new(err))
100	}
101}
102
103#[cfg(feature = "quiche")]
104impl From<crate::quiche::Error> for Error {
105	fn from(err: crate::quiche::Error) -> Self {
106		Self::Quiche(Arc::new(err))
107	}
108}
109
110#[cfg(feature = "iroh")]
111impl From<crate::iroh::Error> for Error {
112	fn from(err: crate::iroh::Error) -> Self {
113		Self::Iroh(Arc::new(err))
114	}
115}
116
117#[cfg(feature = "websocket")]
118impl From<crate::websocket::Error> for Error {
119	fn from(err: crate::websocket::Error) -> Self {
120		Self::WebSocket(Arc::new(err))
121	}
122}
123
124/// Convenience alias for results produced by this crate.
125pub type Result<T> = std::result::Result<T, Error>;