changeset 31004:3cff7a5e0351

Add a function that allows annotating a contact through a SOAP call.
author Elliott Sales de Andrade <qulogic@pidgin.im>
date Sun, 05 Dec 2010 02:40:39 +0000
parents dc996aa83f49
children b91cd8c4e6e5
files libpurple/protocols/msn/contact.c libpurple/protocols/msn/contact.h
diffstat 2 files changed, 127 insertions(+), 1 deletions(-) [+]
line wrap: on
line diff
--- a/libpurple/protocols/msn/contact.c	Fri Dec 03 04:51:48 2010 +0000
+++ b/libpurple/protocols/msn/contact.c	Sun Dec 05 02:40:39 2010 +0000
@@ -190,6 +190,8 @@
 		strcat(buf, "Renaming Group,");
 	if (action & MSN_UPDATE_INFO)
 		strcat(buf, "Updating Contact Info,");
+	if (action & MSN_ANNOTATE_USER)
+		strcat(buf, "Annotating Contact,");
 
 	return buf;
 }
@@ -1533,6 +1535,96 @@
 }
 
 static void
+msn_annotate_contact_read_cb(MsnSoapMessage *req, MsnSoapMessage *resp,
+	gpointer data)
+{
+	MsnCallbackState *state = (MsnCallbackState *)data;
+	xmlnode *fault;
+
+	/* We don't know how to respond to this faultcode, so log it */
+	fault = xmlnode_get_child(resp->xml, "Body/Fault");
+	if (fault != NULL) {
+		char *fault_str = xmlnode_to_str(fault, NULL);
+		purple_debug_error("msn", "Operation {%s} Failed, SOAP Fault was: %s\n",
+		                   msn_contact_operation_str(state->action), fault_str);
+		g_free(fault_str);
+		return;
+	}
+
+	purple_debug_info("msn", "Contact annotated successfully\n");
+}
+
+/* Update a contact's annotations */
+void
+msn_annotate_contact(MsnSession *session, const char *passport, ...)
+{
+	va_list params;
+	MsnCallbackState *state;
+	xmlnode *contact;
+	xmlnode *contact_info;
+	xmlnode *annotations;
+	MsnUser *user = NULL;
+
+	g_return_if_fail(passport != NULL);
+
+	if (strcmp(passport, "Me") != 0) {
+		user = msn_userlist_find_user(session->userlist, passport);
+		if (!user)
+			return;
+	}
+
+	contact_info = xmlnode_new("contactInfo");
+	annotations = xmlnode_new_child(contact_info, "annotations");
+
+	va_start(params, passport);
+	while (TRUE) {
+		const char *name;
+		const char *value;
+		xmlnode *a, *n, *v;
+
+		name = va_arg(params, const char *);
+		if (!name)
+			break;
+
+		value = va_arg(params, const char *);
+		if (!value)
+			break;
+
+		a = xmlnode_new_child(annotations, "Annotation");
+		n = xmlnode_new_child(a, "Name");
+		xmlnode_insert_data(n, name, -1);
+		v = xmlnode_new_child(a, "Value");
+		xmlnode_insert_data(v, value, -1);
+	}
+	va_end(params);
+
+	state = msn_callback_state_new(session);
+
+	state->body = xmlnode_from_str(MSN_CONTACT_ANNOTATE_TEMPLATE, -1);
+	state->action = MSN_ANNOTATE_USER;
+	state->post_action = MSN_CONTACT_ANNOTATE_SOAP_ACTION;
+	state->post_url = MSN_ADDRESS_BOOK_POST_URL;
+	state->cb = msn_annotate_contact_read_cb;
+
+	xmlnode_insert_data(xmlnode_get_child(state->body,
+	                                      "Header/ABApplicationHeader/PartnerScenario"),
+	                    MsnSoapPartnerScenarioText[MSN_PS_SAVE_CONTACT], -1);
+
+	contact = xmlnode_get_child(state->body, "Body/ABContactUpdate/contacts/Contact");
+
+	if (user) {
+		xmlnode *contactId = xmlnode_new_child(contact, "contactId");
+		msn_callback_state_set_uid(state, user->uid);
+		xmlnode_insert_data(contactId, state->uid, -1);
+	} else {
+		xmlnode *contactType = xmlnode_new_child(contact_info, "contactType");
+		xmlnode_insert_data(contactType, "Me", -1);
+	}
+
+	msn_contact_request(state);
+}
+
+static void
 msn_del_contact_from_list_read_cb(MsnSoapMessage *req, MsnSoapMessage *resp,
 	gpointer data)
 {
--- a/libpurple/protocols/msn/contact.h	Fri Dec 03 04:51:48 2010 +0000
+++ b/libpurple/protocols/msn/contact.h	Sun Dec 05 02:40:39 2010 +0000
@@ -36,7 +36,8 @@
 	MSN_ADD_GROUP       = 0x10,
 	MSN_DEL_GROUP       = 0x20,
 	MSN_RENAME_GROUP    = 0x40,
-	MSN_UPDATE_INFO     = 0x80
+	MSN_UPDATE_INFO     = 0x80,
+	MSN_ANNOTATE_USER   = 0x100
 } MsnCallbackAction;
 
 typedef enum
@@ -428,6 +429,37 @@
 	"</soap:Body>"\
 "</soap:Envelope>"
 
+/* Update Contact Annotations */
+#define MSN_CONTACT_ANNOTATE_SOAP_ACTION	"http://www.msn.com/webservices/AddressBook/ABContactUpdate"
+#define MSN_CONTACT_ANNOTATE_TEMPLATE	"<?xml version=\"1.0\" encoding=\"utf-8\"?>"\
+"<soap:Envelope"\
+	" xmlns:soap=\"http://schemas.xmlsoap.org/soap/envelope/\""\
+	" xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\""\
+	" xmlns:xsd=\"http://www.w3.org/2001/XMLSchema\""\
+	" xmlns:soapenc=\"http://schemas.xmlsoap.org/soap/encoding/\">"\
+	"<soap:Header>"\
+		"<ABApplicationHeader xmlns=\"http://www.msn.com/webservices/AddressBook\">"\
+			"<ApplicationId>" MSN_APPLICATION_ID "</ApplicationId>"\
+			"<IsMigration>false</IsMigration>"\
+			"<PartnerScenario></PartnerScenario>"\
+		"</ABApplicationHeader>"\
+		"<ABAuthHeader xmlns=\"http://www.msn.com/webservices/AddressBook\">"\
+			"<ManagedGroupRequest>false</ManagedGroupRequest>"\
+			"<TicketToken>EMPTY</TicketToken>"\
+		"</ABAuthHeader>"\
+	"</soap:Header>"\
+	"<soap:Body>"\
+		"<ABContactUpdate xmlns=\"http://www.msn.com/webservices/AddressBook\">"\
+			"<abId>00000000-0000-0000-0000-000000000000</abId>"\
+			"<contacts>"\
+				"<Contact xmlns=\"http://www.msn.com/webservices/AddressBook\">"\
+					"<propertiesChanged>Annotation</propertiesChanged>"\
+				"</Contact>"\
+			"</contacts>"\
+		"</ABContactUpdate>"\
+	"</soap:Body>"\
+"</soap:Envelope>"
+
 /*******************************************************
  * Add/Delete contact from lists SOAP actions
  *******************************************************/
@@ -687,6 +719,8 @@
 /* contact SOAP operations */
 void msn_update_contact(MsnSession *session, const char *passport, MsnContactUpdateType type, const char* value);
 
+void msn_annotate_contact(MsnSession *session, const char *passport, ...) G_GNUC_NULL_TERMINATED;
+
 void msn_add_contact(MsnSession *session, MsnCallbackState *state,
 		     const char *passport);
 void msn_delete_contact(MsnSession *session, MsnUser *user);