use crate::{Client, Error};
use reqwest::StatusCode;
use serde::{Deserialize, Serialize};
pub struct DomainClient<'a> {
pub(crate) client: &'a crate::Client,
}
impl<'a> Client {
pub fn domain(&'a self) -> DomainClient<'a> {
DomainClient { client: self }
}
}
#[derive(Serialize, Deserialize, Debug, Clone, Default)]
pub struct Domain {
pub created: String,
pub keys: Option<Vec<DNSSECKeyInfo>>,
pub minimum_ttl: u16,
pub name: String,
pub published: Option<String>,
pub touched: String,
pub zonefile: Option<String>,
}
#[derive(Serialize, Deserialize, Debug, Clone, Default)]
pub struct DNSSECKeyInfo {
pub dnskey: String,
pub ds: Vec<String>,
#[serde(rename = "flags")]
pub keyflags: u16,
pub keytype: String,
pub managed: bool,
}
impl<'a> DomainClient<'a> {
pub async fn create_domain(&self, domain: &str) -> Result<Domain, Error> {
let response = self
.client
.post("/domains/", Some(format!("{{\"name\": \"{domain}\"}}")))
.await?;
match response.status() {
StatusCode::CREATED => {
let response_text = response.text().await.map_err(Error::Reqwest)?;
serde_json::from_str(&response_text)
.map_err(|error| Error::InvalidAPIResponse(error.to_string(), response_text))
}
_ => Err(Error::UnexpectedStatusCode(
response.status().into(),
response.text().await.unwrap_or_default(),
)),
}
}
pub async fn get_domains(&self) -> Result<Vec<Domain>, Error> {
let response = self.client.get("/domains/").await?;
match response.status() {
StatusCode::OK => {
let response_text = response.text().await.map_err(Error::Reqwest)?;
serde_json::from_str(&response_text)
.map_err(|error| Error::InvalidAPIResponse(error.to_string(), response_text))
}
_ => Err(Error::UnexpectedStatusCode(
response.status().into(),
response.text().await.unwrap_or_default(),
)),
}
}
pub async fn get_domain(&self, domain: &str) -> Result<Domain, Error> {
let response = self
.client
.get(format!("/domains/{domain}/").as_str())
.await?;
match response.status() {
StatusCode::OK => {
let response_text = response.text().await.map_err(Error::Reqwest)?;
serde_json::from_str(&response_text)
.map_err(|error| Error::InvalidAPIResponse(error.to_string(), response_text))
}
_ => Err(Error::UnexpectedStatusCode(
response.status().into(),
response.text().await.unwrap_or_default(),
)),
}
}
pub async fn delete_domain(&self, domain: &str) -> Result<(), Error> {
let response = self
.client
.delete(format!("/domains/{domain}/").as_str())
.await?;
match response.status() {
StatusCode::NO_CONTENT => Ok(()),
_ => Err(Error::UnexpectedStatusCode(
response.status().into(),
response.text().await.unwrap_or_default(),
)),
}
}
pub async fn get_owning_domain(&self, qname: &str) -> Result<Vec<Domain>, Error> {
let response = self
.client
.get(format!("/domains/?owns_qname={qname}").as_str())
.await?;
match response.status() {
StatusCode::OK => {
let response_text = response.text().await.map_err(Error::Reqwest)?;
serde_json::from_str(&response_text)
.map_err(|error| Error::InvalidAPIResponse(error.to_string(), response_text))
}
_ => Err(Error::UnexpectedStatusCode(
response.status().into(),
response.text().await.unwrap_or_default(),
)),
}
}
pub async fn get_zonefile(&self, domain: &str) -> Result<String, Error> {
let response = self
.client
.get(format!("/domains/{domain}/zonefile/").as_str())
.await?;
match response.status() {
StatusCode::OK => response.text().await.map_err(Error::Reqwest),
_ => Err(Error::UnexpectedStatusCode(
response.status().into(),
response.text().await.unwrap_or_default(),
)),
}
}
}