instant_epp/contact/
update.rs1use instant_xml::ToXml;
4
5use super::{ContactAuthInfo, Fax, PostalInfo, Status, Voice, XMLNS};
6use crate::common::{NoExtension, EPP_XMLNS};
7use crate::request::{Command, Transaction};
8
9impl<'a> Transaction<NoExtension> for ContactUpdate<'a> {}
10
11impl<'a> Command for ContactUpdate<'a> {
12 type Response = ();
13 const COMMAND: &'static str = "update";
14}
15
16impl<'a> ContactUpdate<'a> {
17 pub fn new(id: &'a str) -> ContactUpdate {
18 Self {
19 contact: ContactUpdateRequest {
20 id,
21 add_statuses: None,
22 remove_statuses: None,
23 change_info: None,
24 },
25 }
26 }
27
28 pub fn set_info(
30 &mut self,
31 email: &'a str,
32 postal_info: PostalInfo<'a>,
33 voice: Voice<'a>,
34 auth_password: &'a str,
35 ) {
36 self.contact.change_info = Some(ContactChangeInfo {
37 email: Some(email),
38 postal_info: Some(postal_info),
39 voice: Some(voice),
40 auth_info: Some(ContactAuthInfo::new(auth_password)),
41 fax: None,
42 });
43 }
44
45 pub fn set_fax(&mut self, fax: Fax<'a>) {
47 if let Some(info) = &mut self.contact.change_info {
48 info.fax = Some(fax)
49 }
50 }
51
52 pub fn add(&mut self, statuses: &'a [Status]) {
54 self.contact.add_statuses = Some(AddStatuses { statuses });
55 }
56
57 pub fn remove(&mut self, statuses: &'a [Status]) {
59 self.contact.remove_statuses = Some(RemoveStatuses { statuses });
60 }
61}
62
63#[derive(Debug, ToXml)]
65#[xml(rename = "chg", ns(XMLNS))]
66pub struct ContactChangeInfo<'a> {
67 postal_info: Option<PostalInfo<'a>>,
68 voice: Option<Voice<'a>>,
69 fax: Option<Fax<'a>>,
70 email: Option<&'a str>,
71 auth_info: Option<ContactAuthInfo<'a>>,
72}
73
74#[derive(Debug, ToXml)]
76pub struct StatusList<'a> {
77 status: &'a [Status],
78}
79
80#[derive(Debug, ToXml)]
81#[xml(rename = "add", ns(XMLNS))]
82struct AddStatuses<'a> {
83 statuses: &'a [Status],
84}
85
86#[derive(Debug, ToXml)]
87#[xml(rename = "rem", ns(XMLNS))]
88struct RemoveStatuses<'a> {
89 statuses: &'a [Status],
90}
91
92#[derive(Debug, ToXml)]
94#[xml(rename = "update", ns(XMLNS))]
95pub struct ContactUpdateRequest<'a> {
96 id: &'a str,
97 add_statuses: Option<AddStatuses<'a>>,
98 #[xml(rename = "rem")]
99 remove_statuses: Option<RemoveStatuses<'a>>,
100 change_info: Option<ContactChangeInfo<'a>>,
101}
102
103#[derive(Debug, ToXml)]
105#[xml(rename = "update", ns(EPP_XMLNS))]
106pub struct ContactUpdate<'a> {
107 contact: ContactUpdateRequest<'a>,
109}
110
111#[cfg(test)]
112mod tests {
113 use super::{ContactUpdate, PostalInfo, Status, Voice};
114 use crate::contact::Address;
115 use crate::response::ResultCode;
116 use crate::tests::{assert_serialized, response_from_file, CLTRID, SUCCESS_MSG, SVTRID};
117
118 #[test]
119 fn command() {
120 let mut object = ContactUpdate::new("eppdev-contact-3");
121
122 let street = &["58", "Orchid Road"];
123 let address = Address::new(
124 street,
125 "Paris",
126 Some("Paris"),
127 Some("392374"),
128 "FR".parse().unwrap(),
129 );
130 let postal_info = PostalInfo::new("loc", "John Doe", Some("Acme Widgets"), address);
131 let voice = Voice::new("+33.47237942");
132
133 object.set_info("newemail@eppdev.net", postal_info, voice, "eppdev-387323");
134 object.add(&[Status::ClientTransferProhibited]);
135 object.remove(&[Status::ClientDeleteProhibited]);
136
137 assert_serialized("request/contact/update.xml", &object);
138 }
139
140 #[test]
141 fn contact_update() {
142 let object = response_from_file::<ContactUpdate>("response/contact/update.xml");
143 assert_eq!(object.result.code, ResultCode::CommandCompletedSuccessfully);
144 assert_eq!(object.result.message, SUCCESS_MSG);
145 assert_eq!(object.tr_ids.client_tr_id.unwrap(), CLTRID);
146 assert_eq!(object.tr_ids.server_tr_id, SVTRID);
147 }
148}