From fd72c800236f69637e0c22e9fffdd2436de43b74 Mon Sep 17 00:00:00 2001 From: Ritesh Chitlangi Date: Thu, 22 Jul 2021 18:35:20 +0800 Subject: [PATCH] added macro for serializer element name for generic objects --- .gitignore | 5 +- Cargo.toml | 29 +----- epp-client-macros/.gitignore | 2 + epp-client-macros/Cargo.toml | 13 +++ epp-client-macros/src/lib.rs | 86 +++++++++++++++++ epp-client/Cargo.toml | 26 +++++ epp-client/examples/client.rs | 57 +++++++++++ {src => epp-client/src}/config.rs | 0 {src => epp-client/src}/connection.rs | 4 +- {src => epp-client/src}/epp.rs | 1 - {src => epp-client/src}/epp/command.rs | 0 {src => epp-client/src}/epp/object.rs | 2 + epp-client/src/epp/object/data.rs | 94 +++++++++++++++++++ {src => epp-client/src}/epp/quick_xml.rs | 0 {src => epp-client/src}/epp/request.rs | 31 ++---- epp-client/src/epp/request/contact.rs | 2 + .../src/epp/request/contact/check.rs | 14 +-- epp-client/src/epp/request/contact/create.rs | 61 ++++++++++++ epp-client/src/epp/request/domain.rs | 1 + .../src/epp/request/domain/check.rs | 14 +-- {src => epp-client/src}/epp/response.rs | 19 +--- epp-client/src/epp/response/contact.rs | 1 + .../src/epp/response/contact/check.rs | 0 epp-client/src/epp/response/domain.rs | 1 + .../src/epp/response/domain/check.rs | 0 {src => epp-client/src}/epp/xml.rs | 3 + {src => epp-client/src}/error.rs | 0 {src => epp-client/src}/lib.rs | 0 examples/client.rs | 36 ------- 29 files changed, 383 insertions(+), 119 deletions(-) create mode 100644 epp-client-macros/.gitignore create mode 100644 epp-client-macros/Cargo.toml create mode 100644 epp-client-macros/src/lib.rs create mode 100644 epp-client/Cargo.toml create mode 100644 epp-client/examples/client.rs rename {src => epp-client/src}/config.rs (100%) rename {src => epp-client/src}/connection.rs (97%) rename {src => epp-client/src}/epp.rs (80%) rename {src => epp-client/src}/epp/command.rs (100%) rename {src => epp-client/src}/epp/object.rs (99%) create mode 100644 epp-client/src/epp/object/data.rs rename {src => epp-client/src}/epp/quick_xml.rs (100%) rename {src => epp-client/src}/epp/request.rs (83%) create mode 100644 epp-client/src/epp/request/contact.rs rename src/epp/request/contact.rs => epp-client/src/epp/request/contact/check.rs (83%) create mode 100644 epp-client/src/epp/request/contact/create.rs create mode 100644 epp-client/src/epp/request/domain.rs rename src/epp/request/domain.rs => epp-client/src/epp/request/domain/check.rs (83%) rename {src => epp-client/src}/epp/response.rs (91%) create mode 100644 epp-client/src/epp/response/contact.rs rename src/epp/response/contact.rs => epp-client/src/epp/response/contact/check.rs (100%) create mode 100644 epp-client/src/epp/response/domain.rs rename src/epp/response/domain.rs => epp-client/src/epp/response/domain/check.rs (100%) rename {src => epp-client/src}/epp/xml.rs (81%) rename {src => epp-client/src}/error.rs (100%) rename {src => epp-client/src}/lib.rs (100%) delete mode 100644 examples/client.rs diff --git a/.gitignore b/.gitignore index a08a4e4..7aa4d0b 100644 --- a/.gitignore +++ b/.gitignore @@ -1,3 +1,4 @@ /target -/misc -Cargo.lock \ No newline at end of file +**/target +/epp-client/misc +Cargo.lock diff --git a/Cargo.toml b/Cargo.toml index fbdd014..ad1a1d7 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,25 +1,6 @@ -[package] -name = "epp-client" -version = "0.1.0" -edition = "2018" +[workspace] -# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html - -[[example]] -name = "example-client" -path = "examples/client.rs" - -[dependencies] -bytes = "1" -confy = "0.4" -futures = "0.3" -lazy_static = "1.4" -quick-xml = { version = "0.22", features = [ "serialize" ] } -serde = { version = "1.0", features = ["derive"] } -tokio = { version = "1.0", features = [ "full" ] } -tokio-rustls = "0.22" -webpki = "0.22" -webpki-roots = "0.21" - -[dev-dependencies] -tokio-test = "*" +members = [ + 'epp-client-macros', + 'epp-client' +] diff --git a/epp-client-macros/.gitignore b/epp-client-macros/.gitignore new file mode 100644 index 0000000..96ef6c0 --- /dev/null +++ b/epp-client-macros/.gitignore @@ -0,0 +1,2 @@ +/target +Cargo.lock diff --git a/epp-client-macros/Cargo.toml b/epp-client-macros/Cargo.toml new file mode 100644 index 0000000..516397b --- /dev/null +++ b/epp-client-macros/Cargo.toml @@ -0,0 +1,13 @@ +[package] +name = "epp-client-macros" +version = "0.1.0" +edition = "2018" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[lib] +proc-macro = true + +[dependencies] +syn = { version = "1", features = ["full", "fold"] } +quote = "1" diff --git a/epp-client-macros/src/lib.rs b/epp-client-macros/src/lib.rs new file mode 100644 index 0000000..4032e48 --- /dev/null +++ b/epp-client-macros/src/lib.rs @@ -0,0 +1,86 @@ +extern crate proc_macro; + +use proc_macro::TokenStream; +use quote::quote; + +fn element_name_macro(ast: &syn::DeriveInput) -> TokenStream { + let name = &ast.ident; + let mut elem_name = ast.ident.to_string(); + let (impl_generics, type_generics, where_clause) = &ast.generics.split_for_impl(); + + if ast.attrs.len() > 0 { + let attribute = &ast.attrs[0]; + let meta = match attribute.parse_meta() { + Ok(syn::Meta::List(meta)) => { + if meta.nested.len() > 0 { + elem_name = match &meta.nested[0] { + syn::NestedMeta::Meta(syn::Meta::NameValue(v)) => match &v.lit { + syn::Lit::Str(lit) => lit.value(), + _ => panic!("Invalid element_name attribute"), + }, + _ => panic!("Invalid element_name attribute"), + }; + } else { + panic!("Invalid element_name attribute"); + } + } + _ => panic!("Invalid element_name attribute"), + }; + } + + let implement = quote! { + impl #impl_generics ElementName for #name #type_generics { + fn element_name(&self) -> &'static str { + #elem_name + } + } + }; + implement.into() +} + +#[proc_macro_derive(ElementName, attributes(element_name))] +pub fn element_name_derive(input: TokenStream) -> TokenStream { + let ast = syn::parse(input).expect("Error while parsing ElementName macro input"); + + element_name_macro(&ast) +} + +// #[proc_macro_attribute] +// pub fn epp_client_command_response(_metadat: TokenStream, input: TokenStream) -> TokenStream { +// let mut ast = parse_macro_input!(input as DeriveInput); + +// match &mut ast.data { +// syn::Data::Struct(ref mut data) => { +// match &mut data.fields { +// syn::Fields::Named(fields) => { +// fields.named.push( +// syn::Field::parse_named +// .parse2(quote! { +// pub result: EppResult +// }) +// .unwrap() +// ); +// fields.named.push( +// syn::Field::parse_named +// .parse2(quote! { +// pub tr_ids: ResponseTRID +// }) +// .unwrap() +// ); +// } +// _ => (), +// } + +// return quote! { #ast }.into(); +// } +// _ => panic!("Failed to parse CommandResponse macro input"), +// } +// } + +// #[cfg(test)] +// mod tests { +// #[test] +// fn it_works() { +// assert_eq!(2 + 2, 4); +// } +// } diff --git a/epp-client/Cargo.toml b/epp-client/Cargo.toml new file mode 100644 index 0000000..2fccefc --- /dev/null +++ b/epp-client/Cargo.toml @@ -0,0 +1,26 @@ +[package] +name = "epp-client" +version = "0.1.0" +edition = "2018" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[[example]] +name = "example-client" +path = "examples/client.rs" + +[dependencies] +epp-client-macros = { path = "../epp-client-macros" } +bytes = "1" +confy = "0.4" +futures = "0.3" +lazy_static = "1.4" +quick-xml = { version = "0.22", features = [ "serialize" ] } +serde = { version = "1.0", features = ["derive"] } +tokio = { version = "1.0", features = [ "full" ] } +tokio-rustls = "0.22" +webpki = "0.22" +webpki-roots = "0.21" + +[dev-dependencies] +tokio-test = "*" diff --git a/epp-client/examples/client.rs b/epp-client/examples/client.rs new file mode 100644 index 0000000..9a43df2 --- /dev/null +++ b/epp-client/examples/client.rs @@ -0,0 +1,57 @@ +use epp_client::{epp::request::generate_client_tr_id, connection::EppClient, connection, epp::xml::EppXml, epp::response::EppGreeting}; +use epp_client::epp::request::domain::check::EppDomainCheck; +use epp_client::epp::response::domain::check::EppDomainCheckResponse; +use epp_client::epp::request::contact::check::EppContactCheck; +use epp_client::epp::response::contact::check::EppContactCheckResponse; +use epp_client::epp::object::data::{PostalInfo, Address, Phone}; +use epp_client::epp::request::contact::create::EppContactCreate; + +async fn check_domains(client: &mut EppClient) { + let domains = vec!["eppdev.com", "hexonet.net"]; + let domain_check = EppDomainCheck::new(domains, generate_client_tr_id("eppdev").unwrap().as_str()); + + client.transact::(&domain_check).await.unwrap(); +} + +async fn check_contacts(client: &mut EppClient) { + let contacts = vec!["eppdev-contact-1", "eppdev-contact-2"]; + let contact_check = EppContactCheck::new(contacts, generate_client_tr_id("eppdev").unwrap().as_str()); + + client.transact::<_, EppContactCheckResponse>(&contact_check).await.unwrap(); +} + +async fn create_contact() { + let street = vec!["58", "Orchid Road"]; + let address = Address::new(street, "Paris", "Paris", "392374", "FR"); + let postal_info = PostalInfo::new("int", "John Doe", "Acme Widgets", address); + let mut voice = Phone::new("+47.47237942"); + voice.set_extension("123"); + let mut fax = Phone::new("+47.86698799"); + fax.set_extension("677"); + + let mut contact_create = EppContactCreate::new("eppdev-contact-1", "contact@eppdev.net", postal_info, voice, "eppdev-387323", generate_client_tr_id("eppdev").unwrap().as_str()); + contact_create.set_fax(fax); + + println!("xml: {}", contact_create.serialize().unwrap()); + + //client.transact::(&contact_check).await.unwrap(); +} + +#[tokio::main] +async fn main() { + let mut client = match connection::connect("hexonet").await { + Ok(client) => { + let greeting = client.greeting(); + let greeting_object = EppGreeting::deserialize(&greeting).unwrap(); + println!("{:?}", greeting_object); + client + }, + Err(e) => panic!("Error: {}", e) + }; + + // check_domains(&mut client).await; + + check_contacts(&mut client).await; + + // create_contact().await; +} diff --git a/src/config.rs b/epp-client/src/config.rs similarity index 100% rename from src/config.rs rename to epp-client/src/config.rs diff --git a/src/connection.rs b/epp-client/src/connection.rs similarity index 97% rename from src/connection.rs rename to epp-client/src/connection.rs index e54ee5e..a0c7c93 100644 --- a/src/connection.rs +++ b/epp-client/src/connection.rs @@ -10,7 +10,7 @@ use tokio::{net::TcpStream, io::AsyncWriteExt, io::AsyncReadExt, io::split, io:: use crate::config::{CONFIG, EppClientConnection}; use crate::error; -use crate::epp::request::{generate_client_tr_id, Login, EppLogin, Logout, EppLogout}; +use crate::epp::request::{generate_client_tr_id, EppLogin, EppLogout}; use crate::epp::response::EppCommandResponse; use crate::epp::xml::EppXml; @@ -160,6 +160,8 @@ impl EppClient { println!("Response:\r\n{}", response); + // let result_object = EppCommandResponse::deserialize(&response); + let response_obj = E::deserialize(&response)?; println!("Response:\r\n{:?}", response_obj); diff --git a/src/epp.rs b/epp-client/src/epp.rs similarity index 80% rename from src/epp.rs rename to epp-client/src/epp.rs index 8821ffc..697297c 100644 --- a/src/epp.rs +++ b/epp-client/src/epp.rs @@ -4,4 +4,3 @@ pub mod quick_xml; pub mod request; pub mod response; pub mod xml; -pub use request::domain; diff --git a/src/epp/command.rs b/epp-client/src/epp/command.rs similarity index 100% rename from src/epp/command.rs rename to epp-client/src/epp/command.rs diff --git a/src/epp/object.rs b/epp-client/src/epp/object.rs similarity index 99% rename from src/epp/object.rs rename to epp-client/src/epp/object.rs index 9eb347a..e6ae298 100644 --- a/src/epp/object.rs +++ b/epp-client/src/epp/object.rs @@ -1,3 +1,5 @@ +pub mod data; + use serde::{ser::SerializeStruct, Deserialize, Serialize, Serializer}; use crate::epp::xml::{EPP_XMLNS, EPP_XMLNS_XSI, EPP_XSI_SCHEMA_LOCATION}; diff --git a/epp-client/src/epp/object/data.rs b/epp-client/src/epp/object/data.rs new file mode 100644 index 0000000..aff677c --- /dev/null +++ b/epp-client/src/epp/object/data.rs @@ -0,0 +1,94 @@ +use crate::epp::object::{StringValue, StringValueTrait}; +use serde::{Deserialize, Serialize}; + +#[derive(Serialize, Deserialize, Debug)] +pub struct Phone { + #[serde(rename = "$value")] + pub number: String, + #[serde(rename = "x")] + extension: Option, +} + +#[derive(Serialize, Deserialize, Debug)] +pub struct Address { + street: Vec, + city: StringValue, + #[serde(rename = "sp")] + province: StringValue, + #[serde(rename = "pc")] + postal_code: StringValue, + #[serde(rename = "cc")] + country_code: StringValue, +} + +#[derive(Serialize, Deserialize, Debug)] +pub struct PostalInfo { + #[serde(rename = "type")] + info_type: String, + name: StringValue, + #[serde(rename = "org")] + organization: StringValue, + #[serde(rename = "addr")] + address: Address, +} + +#[derive(Serialize, Deserialize, Debug)] +pub struct AuthInfo { + #[serde(rename = "pw")] + password: StringValue, +} + +impl Phone { + pub fn new(number: &str) -> Phone { + Phone { + extension: None, + number: number.to_string(), + } + } + + pub fn set_extension(&mut self, ext: &str) { + self.extension = Some(ext.to_string()); + } +} + +impl AuthInfo { + pub fn new(password: &str) -> AuthInfo { + AuthInfo { + password: password.to_string_value(), + } + } +} + +impl Address { + pub fn new( + street: Vec<&str>, + city: &str, + province: &str, + postal_code: &str, + country_code: &str, + ) -> Address { + let street = street + .iter() + .filter_map(|s| Some(s.to_string_value())) + .collect::>(); + + Address { + street: street, + city: city.to_string_value(), + province: province.to_string_value(), + postal_code: postal_code.to_string_value(), + country_code: country_code.to_string_value(), + } + } +} + +impl PostalInfo { + pub fn new(info_type: &str, name: &str, organization: &str, address: Address) -> PostalInfo { + PostalInfo { + info_type: info_type.to_string(), + name: name.to_string_value(), + organization: organization.to_string_value(), + address: address, + } + } +} diff --git a/src/epp/quick_xml.rs b/epp-client/src/epp/quick_xml.rs similarity index 100% rename from src/epp/quick_xml.rs rename to epp-client/src/epp/quick_xml.rs diff --git a/src/epp/request.rs b/epp-client/src/epp/request.rs similarity index 83% rename from src/epp/request.rs rename to epp-client/src/epp/request.rs index b500692..e1f1108 100644 --- a/src/epp/request.rs +++ b/epp-client/src/epp/request.rs @@ -5,11 +5,12 @@ use serde::{Deserialize, Serialize}; use std::error::Error; use std::time::SystemTime; -pub use crate::epp::command::Command; +use crate::epp::command::Command; use crate::epp::object::{ ElementName, EppObject, Options, ServiceExtension, Services, StringValue, StringValueTrait, }; use crate::epp::xml::{EPP_LANG, EPP_VERSION}; +use epp_client_macros::*; pub type EppHello = EppObject; pub type EppLogin = EppObject>; @@ -20,24 +21,20 @@ pub fn generate_client_tr_id(username: &str) -> Result> { Ok(format!("{}:{}", username, timestamp.as_secs())) } -#[derive(Serialize, Deserialize, Debug, PartialEq)] +#[derive(Serialize, Deserialize, Debug, PartialEq, ElementName)] #[serde(rename = "hello")] +#[element_name(name = "hello")] pub struct Hello; -impl ElementName for Hello { - fn element_name(&self) -> &'static str { - "hello" - } -} - impl EppHello { pub fn new() -> EppHello { EppObject::build(Hello {}) } } -#[derive(Serialize, Deserialize, Debug, PartialEq)] +#[derive(Serialize, Deserialize, Debug, PartialEq, ElementName)] #[serde(rename = "login")] +#[element_name(name = "login")] pub struct Login { #[serde(rename(serialize = "clID", deserialize = "clID"))] username: StringValue, @@ -48,12 +45,6 @@ pub struct Login { services: Services, } -impl ElementName for Login { - fn element_name(&self) -> &'static str { - "login" - } -} - impl EppLogin { pub fn new(username: &str, password: &str, client_tr_id: &str) -> EppLogin { let login = Login { @@ -92,8 +83,8 @@ impl EppLogin { } } -#[derive(Serialize, Deserialize, Debug, PartialEq)] -#[serde(rename_all = "lowercase")] +#[derive(Serialize, Deserialize, Debug, PartialEq, ElementName)] +#[element_name(name = "logout")] pub struct Logout; impl EppLogout { @@ -104,9 +95,3 @@ impl EppLogout { }) } } - -impl ElementName for Logout { - fn element_name(&self) -> &'static str { - "logout" - } -} diff --git a/epp-client/src/epp/request/contact.rs b/epp-client/src/epp/request/contact.rs new file mode 100644 index 0000000..3aa3078 --- /dev/null +++ b/epp-client/src/epp/request/contact.rs @@ -0,0 +1,2 @@ +pub mod check; +pub mod create; diff --git a/src/epp/request/contact.rs b/epp-client/src/epp/request/contact/check.rs similarity index 83% rename from src/epp/request/contact.rs rename to epp-client/src/epp/request/contact/check.rs index 4ce8d02..f7dd0d8 100644 --- a/src/epp/request/contact.rs +++ b/epp-client/src/epp/request/contact/check.rs @@ -1,9 +1,10 @@ +use epp_client_macros::*; + use crate::epp::command::Command; use crate::epp::object::{ElementName, EppObject, StringValue, StringValueTrait}; +use crate::epp::xml::EPP_CONTACT_XMLNS; use serde::{Deserialize, Serialize}; -const EPP_CONTACT_XMLNS: &str = "urn:ietf:params:xml:ns:contact-1.0"; - pub type EppContactCheck = EppObject>; #[derive(Serialize, Deserialize, Debug)] @@ -13,18 +14,13 @@ pub struct ContactList { pub contact_ids: Vec, } -#[derive(Serialize, Deserialize, Debug)] +#[derive(Serialize, Deserialize, Debug, ElementName)] +#[element_name(name = "check")] pub struct ContactCheck { #[serde(rename = "check")] list: ContactList, } -impl ElementName for ContactCheck { - fn element_name(&self) -> &'static str { - "check" - } -} - impl EppContactCheck { pub fn new(contact_ids: Vec<&str>, client_tr_id: &str) -> EppContactCheck { let contact_ids = contact_ids diff --git a/epp-client/src/epp/request/contact/create.rs b/epp-client/src/epp/request/contact/create.rs new file mode 100644 index 0000000..117cd65 --- /dev/null +++ b/epp-client/src/epp/request/contact/create.rs @@ -0,0 +1,61 @@ +use epp_client_macros::*; + +use crate::epp::command::Command; +use crate::epp::object::data; +use crate::epp::object::{ElementName, EppObject, StringValue, StringValueTrait}; +use crate::epp::xml::EPP_CONTACT_XMLNS; +use serde::{Deserialize, Serialize}; + +pub type EppContactCreate = EppObject>; + +#[derive(Serialize, Deserialize, Debug)] +pub struct Contact { + xmlns: String, + id: StringValue, + #[serde(rename = "postalInfo")] + postal_info: data::PostalInfo, + voice: data::Phone, + fax: Option, + email: StringValue, + #[serde(rename = "authInfo")] + auth_info: data::AuthInfo, +} + +#[derive(Serialize, Deserialize, Debug, ElementName)] +#[element_name(name = "create")] +pub struct ContactCreate { + #[serde(rename = "create")] + pub contact: Contact, +} + +impl EppContactCreate { + pub fn new( + id: &str, + email: &str, + postal_info: data::PostalInfo, + voice: data::Phone, + auth_password: &str, + client_tr_id: &str, + ) -> EppContactCreate { + let contact_create = ContactCreate { + contact: Contact { + xmlns: EPP_CONTACT_XMLNS.to_string(), + id: id.to_string_value(), + postal_info: postal_info, + voice: voice, + fax: None, + email: email.to_string_value(), + auth_info: data::AuthInfo::new(auth_password), + }, + }; + + EppObject::build(Command:: { + command: contact_create, + client_tr_id: client_tr_id.to_string_value(), + }) + } + + pub fn set_fax(&mut self, fax: data::Phone) { + self.data.command.contact.fax = Some(fax); + } +} diff --git a/epp-client/src/epp/request/domain.rs b/epp-client/src/epp/request/domain.rs new file mode 100644 index 0000000..3e8ff0f --- /dev/null +++ b/epp-client/src/epp/request/domain.rs @@ -0,0 +1 @@ +pub mod check; diff --git a/src/epp/request/domain.rs b/epp-client/src/epp/request/domain/check.rs similarity index 83% rename from src/epp/request/domain.rs rename to epp-client/src/epp/request/domain/check.rs index b0123b0..28ea9e7 100644 --- a/src/epp/request/domain.rs +++ b/epp-client/src/epp/request/domain/check.rs @@ -1,9 +1,10 @@ +use epp_client_macros::*; + use crate::epp::command::Command; use crate::epp::object::{ElementName, EppObject, StringValue, StringValueTrait}; +use crate::epp::xml::EPP_DOMAIN_XMLNS; use serde::{Deserialize, Serialize}; -const EPP_DOMAIN_XMLNS: &str = "urn:ietf:params:xml:ns:domain-1.0"; - pub type EppDomainCheck = EppObject>; #[derive(Serialize, Deserialize, Debug)] @@ -13,18 +14,13 @@ pub struct DomainList { pub domains: Vec, } -#[derive(Serialize, Deserialize, Debug)] +#[derive(Serialize, Deserialize, Debug, ElementName)] +#[element_name(name = "check")] pub struct DomainCheck { #[serde(rename = "check")] list: DomainList, } -impl ElementName for DomainCheck { - fn element_name(&self) -> &'static str { - "check" - } -} - impl EppDomainCheck { pub fn new(domains: Vec<&str>, client_tr_id: &str) -> EppDomainCheck { let domains = domains diff --git a/src/epp/response.rs b/epp-client/src/epp/response.rs similarity index 91% rename from src/epp/response.rs rename to epp-client/src/epp/response.rs index f260544..b028226 100644 --- a/src/epp/response.rs +++ b/epp-client/src/epp/response.rs @@ -1,6 +1,7 @@ pub mod contact; pub mod domain; +use epp_client_macros::*; use serde::{Deserialize, Deserializer, Serialize}; use crate::epp::object::{ @@ -101,8 +102,9 @@ pub struct Dcp { statement: Statement, } -#[derive(Serialize, Deserialize, Debug, PartialEq)] +#[derive(Serialize, Deserialize, Debug, PartialEq, ElementName)] #[serde(rename_all = "lowercase")] +#[element_name(name = "greeting")] pub struct Greeting { #[serde(rename = "svID")] service_id: String, @@ -128,8 +130,9 @@ pub struct ResponseTRID { pub server_tr_id: StringValue, } -#[derive(Serialize, Deserialize, Debug, PartialEq)] +#[derive(Serialize, Deserialize, Debug, PartialEq, ElementName)] #[serde(rename_all = "lowercase")] +#[element_name(name = "response")] pub struct CommandResponse { pub result: EppResult, #[serde(rename = "resData")] @@ -137,15 +140,3 @@ pub struct CommandResponse { #[serde(rename = "trID")] pub tr_ids: ResponseTRID, } - -impl ElementName for Greeting { - fn element_name(&self) -> &'static str { - "greeting" - } -} - -impl ElementName for CommandResponse { - fn element_name(&self) -> &'static str { - "command" - } -} diff --git a/epp-client/src/epp/response/contact.rs b/epp-client/src/epp/response/contact.rs new file mode 100644 index 0000000..3e8ff0f --- /dev/null +++ b/epp-client/src/epp/response/contact.rs @@ -0,0 +1 @@ +pub mod check; diff --git a/src/epp/response/contact.rs b/epp-client/src/epp/response/contact/check.rs similarity index 100% rename from src/epp/response/contact.rs rename to epp-client/src/epp/response/contact/check.rs diff --git a/epp-client/src/epp/response/domain.rs b/epp-client/src/epp/response/domain.rs new file mode 100644 index 0000000..3e8ff0f --- /dev/null +++ b/epp-client/src/epp/response/domain.rs @@ -0,0 +1 @@ +pub mod check; diff --git a/src/epp/response/domain.rs b/epp-client/src/epp/response/domain/check.rs similarity index 100% rename from src/epp/response/domain.rs rename to epp-client/src/epp/response/domain/check.rs diff --git a/src/epp/xml.rs b/epp-client/src/epp/xml.rs similarity index 81% rename from src/epp/xml.rs rename to epp-client/src/epp/xml.rs index 6d748d2..a192614 100644 --- a/src/epp/xml.rs +++ b/epp-client/src/epp/xml.rs @@ -7,6 +7,9 @@ pub const EPP_XMLNS: &str = "urn:ietf:params:xml:ns:epp-1.0"; pub const EPP_XMLNS_XSI: &str = "http://www.w3.org/2001/XMLSchema-instance"; pub const EPP_XSI_SCHEMA_LOCATION: &str = "urn:ietf:params:xml:ns:epp-1.0 epp-1.0.xsd"; +pub const EPP_DOMAIN_XMLNS: &str = "urn:ietf:params:xml:ns:domain-1.0"; +pub const EPP_CONTACT_XMLNS: &str = "urn:ietf:params:xml:ns:contact-1.0"; + pub const EPP_VERSION: &str = "1.0"; pub const EPP_LANG: &str = "en"; diff --git a/src/error.rs b/epp-client/src/error.rs similarity index 100% rename from src/error.rs rename to epp-client/src/error.rs diff --git a/src/lib.rs b/epp-client/src/lib.rs similarity index 100% rename from src/lib.rs rename to epp-client/src/lib.rs diff --git a/examples/client.rs b/examples/client.rs deleted file mode 100644 index 956b767..0000000 --- a/examples/client.rs +++ /dev/null @@ -1,36 +0,0 @@ -use epp_client::{epp::request::generate_client_tr_id, connection::EppClient, connection, epp::xml::EppXml, epp::response::EppGreeting}; -use epp_client::epp::request::domain::EppDomainCheck; -use epp_client::epp::response::domain::EppDomainCheckResponse; -use epp_client::epp::request::contact::EppContactCheck; -use epp_client::epp::response::contact::EppContactCheckResponse; - -async fn check_domains(client: &mut EppClient) { - let domains = vec!["eppdev.com", "hexonet.net"]; - let domain_check = EppDomainCheck::new(domains, generate_client_tr_id("eppdev").unwrap().as_str()); - - client.transact::(&domain_check).await.unwrap(); -} - -async fn check_contacts(client: &mut EppClient) { - let contacts = vec!["eppdev-contact-1", "eppdev-contact-2"]; - let contact_check = EppContactCheck::new(contacts, generate_client_tr_id("eppdev").unwrap().as_str()); - - client.transact::(&contact_check).await.unwrap(); -} - -#[tokio::main] -async fn main() { - let mut client = match connection::connect("hexonet").await { - Ok(client) => { - let greeting = client.greeting(); - let greeting_object = EppGreeting::deserialize(&greeting).unwrap(); - println!("{:?}", greeting_object); - client - }, - Err(e) => panic!("Error: {}", e) - }; - - check_domains(&mut client).await; - - check_contacts(&mut client).await; -}