Improve check request API types by redirecting serialization

This commit is contained in:
Dirkjan Ochtman 2022-01-27 12:58:05 +01:00 committed by masalachai
parent fdec3f29fc
commit 5fb32978bd
7 changed files with 85 additions and 53 deletions

View File

@ -26,7 +26,7 @@
//! println!("{:?}", greeting); //! println!("{:?}", greeting);
//! //!
//! // Execute an EPP Command against the registry with distinct request and response objects //! // Execute an EPP Command against the registry with distinct request and response objects
//! let domain_check = DomainCheck::new(vec!["eppdev.com", "eppdev.net"]); //! let domain_check = DomainCheck { domains: &["eppdev.com", "eppdev.net"] };
//! let response = client.transact(&domain_check, "transaction-id").await.unwrap(); //! let response = client.transact(&domain_check, "transaction-id").await.unwrap();
//! println!("{:?}", response); //! println!("{:?}", response);
//! //!

View File

@ -17,34 +17,41 @@ impl<'a> Command for ContactCheck<'a> {
/// Type that represents the &lt;check&gt; command for contact transactions /// Type that represents the &lt;check&gt; command for contact transactions
#[derive(Serialize, Debug)] #[derive(Serialize, Debug)]
pub struct ContactList<'a> { struct ContactList<'a> {
/// The XML namespace for the contact &lt;check&gt; /// The XML namespace for the contact &lt;check&gt;
#[serde(rename = "xmlns:contact")] #[serde(rename = "xmlns:contact")]
xmlns: &'a str, xmlns: &'a str,
/// The list of contact ids to check for availability /// The list of contact ids to check for availability
#[serde(rename = "contact:id")] #[serde(rename = "contact:id")]
pub contact_ids: Vec<StringValue<'a>>, contact_ids: Vec<StringValue<'a>>,
} }
#[derive(Serialize, Debug)] #[derive(Serialize, Debug)]
/// The &lt;command&gt; type for contact check command struct SerializeContactCheck<'a> {
pub struct ContactCheck<'a> {
/// The &lt;check&gt; tag for the contact check command /// The &lt;check&gt; tag for the contact check command
#[serde(rename = "contact:check")] #[serde(rename = "contact:check")]
list: ContactList<'a>, list: ContactList<'a>,
} }
impl<'a> ContactCheck<'a> { impl<'a> From<ContactCheck<'a>> for SerializeContactCheck<'a> {
pub fn new(contact_ids: &'a [&'a str]) -> Self { fn from(check: ContactCheck<'a>) -> Self {
Self { Self {
list: ContactList { list: ContactList {
xmlns: XMLNS, xmlns: XMLNS,
contact_ids: contact_ids.iter().map(|&id| id.into()).collect(), contact_ids: check.contact_ids.iter().map(|&id| id.into()).collect(),
}, },
} }
} }
} }
/// The EPP `check` command for contacts
#[derive(Clone, Debug, Serialize)]
#[serde(into = "SerializeContactCheck")]
pub struct ContactCheck<'a> {
/// The list of contact IDs to be checked
pub contact_ids: &'a [&'a str],
}
#[cfg(test)] #[cfg(test)]
mod tests { mod tests {
use super::ContactCheck; use super::ContactCheck;
@ -56,7 +63,9 @@ mod tests {
#[test] #[test]
fn command() { fn command() {
let xml = get_xml("request/contact/check.xml").unwrap(); let xml = get_xml("request/contact/check.xml").unwrap();
let object = ContactCheck::new(&["eppdev-contact-1", "eppdev-contact-2"]); let object = ContactCheck {
contact_ids: &["eppdev-contact-1", "eppdev-contact-2"],
};
let serialized = let serialized =
<ContactCheck as Transaction<NoExtension>>::serialize_request(&object, None, CLTRID) <ContactCheck as Transaction<NoExtension>>::serialize_request(&object, None, CLTRID)
.unwrap(); .unwrap();

View File

@ -12,36 +12,42 @@ impl<'a> Command for DomainCheck<'a> {
const COMMAND: &'static str = "check"; const COMMAND: &'static str = "check";
} }
impl<'a> DomainCheck<'a> { // Request
pub fn new(domains: Vec<&'a str>) -> Self {
/// Type for &lt;name&gt; elements under the domain &lt;check&gt; tag
#[derive(Serialize, Debug)]
struct DomainList<'a> {
#[serde(rename = "xmlns:domain")]
/// XML namespace for domain commands
xmlns: &'a str,
#[serde(rename = "domain:name")]
/// List of domains to be checked for availability
domains: Vec<StringValue<'a>>,
}
#[derive(Serialize, Debug)]
struct SerializeDomainCheck<'a> {
#[serde(rename = "domain:check")]
list: DomainList<'a>,
}
impl<'a> From<DomainCheck<'a>> for SerializeDomainCheck<'a> {
fn from(check: DomainCheck<'a>) -> Self {
Self { Self {
list: DomainList { list: DomainList {
xmlns: XMLNS, xmlns: XMLNS,
domains: domains.into_iter().map(|d| d.into()).collect(), domains: check.domains.iter().map(|&d| d.into()).collect(),
}, },
} }
} }
} }
// Request /// The EPP `check` command for domains
#[derive(Clone, Debug, Serialize)]
/// Type for &lt;name&gt; elements under the domain &lt;check&gt; tag #[serde(into = "SerializeDomainCheck")]
#[derive(Serialize, Debug)]
pub struct DomainList<'a> {
#[serde(rename = "xmlns:domain")]
/// XML namespace for domain commands
pub xmlns: &'a str,
#[serde(rename = "domain:name")]
/// List of domains to be checked for availability
pub domains: Vec<StringValue<'a>>,
}
#[derive(Serialize, Debug)]
/// Type for EPP XML &lt;check&gt; command for domains
pub struct DomainCheck<'a> { pub struct DomainCheck<'a> {
/// The object holding the list of domains to be checked /// The list of domains to be checked
#[serde(rename = "domain:check")] pub domains: &'a [&'a str],
list: DomainList<'a>,
} }
#[cfg(test)] #[cfg(test)]
@ -56,7 +62,9 @@ mod tests {
fn command() { fn command() {
let xml = get_xml("request/domain/check.xml").unwrap(); let xml = get_xml("request/domain/check.xml").unwrap();
let object = DomainCheck::new(vec!["eppdev.com", "eppdev.net"]); let object = DomainCheck {
domains: &["eppdev.com", "eppdev.net"],
};
let serialized = let serialized =
<DomainCheck as Transaction<NoExtension>>::serialize_request(&object, None, CLTRID) <DomainCheck as Transaction<NoExtension>>::serialize_request(&object, None, CLTRID)

View File

@ -106,7 +106,9 @@ mod tests {
let namestore_ext = NameStore::new("com"); let namestore_ext = NameStore::new("com");
let object = DomainCheck::new(vec!["example1.com", "example2.com", "example3.com"]); let object = DomainCheck {
domains: &["example1.com", "example2.com", "example3.com"],
};
let serialized = <DomainCheck as Transaction<NameStore>>::serialize_request( let serialized = <DomainCheck as Transaction<NameStore>>::serialize_request(
&object, &object,

View File

@ -14,40 +14,46 @@ impl<'a> Command for HostCheck<'a> {
const COMMAND: &'static str = "check"; const COMMAND: &'static str = "check";
} }
impl<'a> HostCheck<'a> {
pub fn new(hosts: &[&'a str]) -> Self {
let hosts = hosts.iter().map(|&d| d.into()).collect();
Self {
list: HostList {
xmlns: XMLNS,
hosts,
},
}
}
}
// Request // Request
/// Type for data under the host &lt;check&gt; tag /// Type for data under the host &lt;check&gt; tag
#[derive(Serialize, Debug)] #[derive(Serialize, Debug)]
pub struct HostList<'a> { struct HostList<'a> {
/// XML namespace for host commands /// XML namespace for host commands
#[serde(rename = "xmlns:host")] #[serde(rename = "xmlns:host")]
xmlns: &'a str, xmlns: &'a str,
/// List of hosts to be checked for availability /// List of hosts to be checked for availability
#[serde(rename = "host:name")] #[serde(rename = "host:name")]
pub hosts: Vec<StringValue<'a>>, hosts: Vec<StringValue<'a>>,
} }
#[derive(Serialize, Debug)] #[derive(Serialize, Debug)]
/// Type for EPP XML &lt;check&gt; command for hosts /// Type for EPP XML &lt;check&gt; command for hosts
pub struct HostCheck<'a> { struct SerializeHostCheck<'a> {
/// The instance holding the list of hosts to be checked /// The instance holding the list of hosts to be checked
#[serde(rename = "host:check")] #[serde(rename = "host:check")]
list: HostList<'a>, list: HostList<'a>,
} }
impl<'a> From<HostCheck<'a>> for SerializeHostCheck<'a> {
fn from(check: HostCheck<'a>) -> Self {
Self {
list: HostList {
xmlns: XMLNS,
hosts: check.hosts.iter().map(|&id| id.into()).collect(),
},
}
}
}
/// The EPP `check` command for hosts
#[derive(Clone, Debug, Serialize)]
#[serde(into = "SerializeHostCheck")]
pub struct HostCheck<'a> {
/// The list of hosts to be checked
pub hosts: &'a [&'a str],
}
#[cfg(test)] #[cfg(test)]
mod tests { mod tests {
use super::HostCheck; use super::HostCheck;
@ -60,7 +66,9 @@ mod tests {
fn command() { fn command() {
let xml = get_xml("request/host/check.xml").unwrap(); let xml = get_xml("request/host/check.xml").unwrap();
let object = HostCheck::new(&["ns1.eppdev-1.com", "host1.eppdev-1.com"]); let object = HostCheck {
hosts: &["ns1.eppdev-1.com", "host1.eppdev-1.com"],
};
let serialized = let serialized =
<HostCheck as Transaction<NoExtension>>::serialize_request(&object, None, CLTRID) <HostCheck as Transaction<NoExtension>>::serialize_request(&object, None, CLTRID)

View File

@ -64,9 +64,9 @@
//! //!
//! // Make a domain check call, which returns an object of type EppDomainCheckResponse //! // Make a domain check call, which returns an object of type EppDomainCheckResponse
//! // that contains the result of the call //! // that contains the result of the call
//! let domain_check = DomainCheck::new( //! let domain_check = DomainCheck {
//! vec!["eppdev.com", "eppdev.net"], //! domains: &["eppdev.com", "eppdev.net"],
//! ); //! };
//! //!
//! let response = client.transact(&domain_check, "transaction-id").await.unwrap(); //! let response = client.transact(&domain_check, "transaction-id").await.unwrap();
//! //!

View File

@ -101,7 +101,12 @@ async fn client() {
.unwrap(); .unwrap();
let rsp = client let rsp = client
.transact(&DomainCheck::new(vec!["eppdev.com", "eppdev.net"]), CLTRID) .transact(
&DomainCheck {
domains: &["eppdev.com", "eppdev.net"],
},
CLTRID,
)
.await .await
.unwrap(); .unwrap();
assert_eq!(rsp.result.code, ResultCode::CommandCompletedSuccessfully); assert_eq!(rsp.result.code, ResultCode::CommandCompletedSuccessfully);