use anyhow::Result;
use serde::{Deserialize, Serialize};
#[derive(Debug, Clone, PartialEq, Eq, Hash, Default, Serialize, Deserialize)]
pub struct Root {
org: Org,
}
#[derive(Debug, Clone, PartialEq, Eq, Hash, Default, Serialize, Deserialize)]
pub struct Org {
pub opencontainers: OpenContainers,
}
#[derive(Debug, Clone, PartialEq, Eq, Hash, Default, Serialize, Deserialize)]
pub struct OpenContainers {
pub image: Annotations,
}
#[derive(Debug, Clone, PartialEq, Eq, Hash, Default, Serialize, Deserialize)]
pub struct Annotations {
#[serde(skip_serializing_if = "Option::is_none")]
pub created: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub authors: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub url: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub documentation: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub source: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub version: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub revision: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub vendor: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub licenses: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub title: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub description: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub r#ref: Option<Ref>,
#[serde(skip_serializing_if = "Option::is_none")]
pub base: Option<Base>,
}
#[derive(Debug, Clone, PartialEq, Eq, Hash, Default, Serialize, Deserialize)]
pub struct Base {
#[serde(skip_serializing_if = "Option::is_none")]
pub digest: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub name: Option<String>,
}
#[derive(Debug, Clone, PartialEq, Eq, Hash, Default, Serialize, Deserialize)]
pub struct Ref {
#[serde(skip_serializing_if = "Option::is_none")]
pub name: Option<String>,
}
impl Annotations {
pub fn from_toml(input: &str) -> Result<Self> {
let root: Root = toml::from_str(input)?;
Ok(root.org.opencontainers.image)
}
pub fn to_toml(&self) -> String {
let root = Root {
org: Org {
opencontainers: OpenContainers {
image: self.clone(),
},
},
};
toml::to_string_pretty(&root).unwrap()
}
}
impl From<super::flat::Annotations> for Annotations {
fn from(flat: super::flat::Annotations) -> Self {
let base = if flat.base_name.is_none() && flat.base_digest.is_none() {
None
} else {
Some(Base {
name: flat.base_name,
digest: flat.base_digest,
})
};
let r#ref = flat.ref_name.map(|name| Ref { name: Some(name) });
Annotations {
created: flat.created,
authors: flat.authors,
url: flat.url,
documentation: flat.documentation,
description: flat.description,
title: flat.title,
source: flat.source,
version: flat.version,
revision: flat.revision,
vendor: flat.vendor,
licenses: flat.licenses,
r#ref,
base,
}
}
}