use base64_serde::base64_serde_type;
use serde::{Deserialize, Serialize};
pub const ENDPOINT_V1: &str = "/v1/dnclient";
pub const CHECK_FOR_UPDATE: &str = "CheckForUpdate";
pub const DO_UPDATE: &str = "DoUpdate";
base64_serde_type!(Base64Standard, base64::engine::general_purpose::STANDARD);
#[derive(Serialize, Deserialize, Debug)]
pub struct RequestV1 {
pub version: i32,
#[serde(rename = "hostID")]
pub host_id: String,
pub counter: u32,
pub message: String,
#[serde(with = "Base64Standard")]
pub signature: Vec<u8>,
}
#[derive(Serialize, Deserialize, Debug)]
pub struct RequestWrapper {
#[serde(rename = "type")]
pub message_type: String,
#[serde(with = "b64_as")]
pub value: Vec<u8>,
pub timestamp: String,
}
#[derive(Serialize, Deserialize, Debug)]
pub struct SignedResponseWrapper {
pub data: SignedResponse,
}
#[derive(Serialize, Deserialize, Debug)]
pub struct SignedResponse {
pub version: i32,
#[serde(with = "Base64Standard")]
pub message: Vec<u8>,
#[serde(with = "Base64Standard")]
pub signature: Vec<u8>,
}
#[derive(Serialize, Deserialize, Debug)]
pub struct CheckForUpdateResponseWrapper {
pub data: CheckForUpdateResponse,
}
#[derive(Serialize, Deserialize, Debug)]
pub struct CheckForUpdateResponse {
#[serde(rename = "updateAvailable")]
pub update_available: bool,
}
#[derive(Serialize, Deserialize, Debug)]
pub struct DoUpdateRequest {
#[serde(rename = "edPubkeyPEM")]
#[serde(with = "Base64Standard")]
pub ed_pubkey_pem: Vec<u8>,
#[serde(rename = "dhPubkeyPEM")]
#[serde(with = "Base64Standard")]
pub dh_pubkey_pem: Vec<u8>,
#[serde(with = "Base64Standard")]
pub nonce: Vec<u8>,
}
#[derive(Serialize, Deserialize, Debug)]
pub struct DoUpdateResponse {
#[serde(with = "Base64Standard")]
pub config: Vec<u8>,
pub counter: u32,
#[serde(with = "Base64Standard")]
pub nonce: Vec<u8>,
#[serde(rename = "trustedKeys")]
#[serde(with = "Base64Standard")]
pub trusted_keys: Vec<u8>,
}
pub const ENROLL_ENDPOINT: &str = "/v2/enroll";
#[derive(Serialize, Deserialize, Debug)]
pub struct EnrollRequest {
pub code: String,
#[serde(rename = "dhPubkey")]
#[serde(with = "Base64Standard")]
pub dh_pubkey: Vec<u8>,
#[serde(rename = "edPubkey")]
#[serde(with = "Base64Standard")]
pub ed_pubkey: Vec<u8>,
pub timestamp: String,
}
#[derive(Serialize, Deserialize, Debug)]
#[serde(untagged)]
pub enum EnrollResponse {
Success {
data: EnrollResponseData,
},
Error {
errors: APIErrors,
},
}
#[derive(Serialize, Deserialize, Debug)]
pub struct EnrollResponseData {
#[serde(with = "Base64Standard")]
pub config: Vec<u8>,
#[serde(rename = "hostID")]
pub host_id: String,
pub counter: u32,
#[serde(rename = "trustedKeys")]
#[serde(with = "Base64Standard")]
pub trusted_keys: Vec<u8>,
pub organization: EnrollResponseDataOrg,
}
#[derive(Serialize, Deserialize, Debug)]
pub struct EnrollResponseDataOrg {
pub id: String,
pub name: String,
}
#[derive(Serialize, Deserialize, Debug)]
pub struct APIError {
pub code: String,
pub message: String,
pub path: Option<String>,
}
pub type APIErrors = Vec<APIError>;
mod b64_as {
use base64::Engine;
use serde::{Deserialize, Serialize};
use serde::{Deserializer, Serializer};
pub fn serialize<S: Serializer>(v: &Vec<u8>, s: S) -> Result<S::Ok, S::Error> {
let base64 = base64::engine::general_purpose::STANDARD.encode(v);
<String>::serialize(&base64, s)
}
pub fn deserialize<'de, D: Deserializer<'de>>(d: D) -> Result<Vec<u8>, D::Error> {
let base64 = <Option<String>>::deserialize(d)?;
base64.map_or_else(
|| Ok(vec![]),
|v| {
base64::engine::general_purpose::STANDARD
.decode(v.as_bytes())
.map_err(serde::de::Error::custom)
},
)
}
}