Skip to main content

relay_knowledge/ports/
release_metadata.rs

1use std::{error::Error, fmt, future::Future, pin::Pin};
2
3/// One release-metadata endpoint requested by the update workflow.
4#[derive(Debug, Clone, PartialEq, Eq)]
5pub struct ReleaseMetadataRequest {
6    pub url: String,
7}
8
9/// Stable failure categories exposed by release-metadata adapters.
10#[derive(Debug, Clone, Copy, PartialEq, Eq)]
11pub enum ReleaseMetadataErrorKind {
12    ClientBuild,
13    NetworkTimeout,
14    Network,
15    Transport,
16    HttpStatus,
17    ResponseTooLarge,
18}
19
20impl ReleaseMetadataErrorKind {
21    /// Returns the low-cardinality diagnostic code used by application responses.
22    pub const fn diagnostic_code(self) -> &'static str {
23        match self {
24            Self::ClientBuild => "client_build_failed",
25            Self::NetworkTimeout => "network_timeout",
26            Self::Network => "network_error",
27            Self::Transport => "transport_failed",
28            Self::HttpStatus => "http_status",
29            Self::ResponseTooLarge => "response_body_too_large",
30        }
31    }
32}
33
34/// Adapter-neutral release-metadata failure.
35#[derive(Debug, Clone, PartialEq, Eq)]
36pub struct ReleaseMetadataError {
37    pub kind: ReleaseMetadataErrorKind,
38    pub message: String,
39    pub retryable: bool,
40}
41
42impl fmt::Display for ReleaseMetadataError {
43    fn fmt(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result {
44        write!(formatter, "{}", self.message)
45    }
46}
47
48impl Error for ReleaseMetadataError {}
49
50/// Future returned by one bounded metadata request.
51pub type ReleaseMetadataFuture<'a> =
52    Pin<Box<dyn Future<Output = Result<Vec<u8>, ReleaseMetadataError>> + Send + 'a>>;
53
54/// Prepared release-metadata session that may reuse one client across sources.
55pub trait ReleaseMetadataSession: Send + Sync {
56    fn fetch(&self, request: ReleaseMetadataRequest) -> ReleaseMetadataFuture<'_>;
57}
58
59/// Port that prepares a release-metadata session from current runtime policy.
60pub trait ReleaseMetadataPort: Send + Sync {
61    fn open(&self) -> Result<Box<dyn ReleaseMetadataSession>, ReleaseMetadataError>;
62}
63
64#[cfg(test)]
65#[path = "release_metadata_tests.rs"]
66mod tests;