aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorWilmer van der Gaast <wilmer@gaast.net>2010-08-14 22:33:33 +0100
committerWilmer van der Gaast <wilmer@gaast.net>2010-08-14 22:33:33 +0100
commit4fc95c57361193c5338d9916fd37cc8a939067cd (patch)
tree5c080dcc780c7a6aba80fe4a26f0d12f8ee76c06
parent6ddb2236943384d45cacd08e02cb4ef9ed03bba3 (diff)
Add/Remove support.
-rw-r--r--protocols/msn/msn_util.c15
-rw-r--r--protocols/msn/soap.c86
-rw-r--r--protocols/msn/soap.h37
-rw-r--r--protocols/msn/tables.c2
4 files changed, 135 insertions, 5 deletions
diff --git a/protocols/msn/msn_util.c b/protocols/msn/msn_util.c
index b7fdda28..84d68b8c 100644
--- a/protocols/msn/msn_util.c
+++ b/protocols/msn/msn_util.c
@@ -73,7 +73,7 @@ static char *adlrml_entry( const char *handle_, msn_buddy_flags_t list )
domain, handle, list );
}
-int msn_buddy_list_add( struct im_connection *ic, msn_buddy_flags_t list, const char *who, const char *realname_, const char *group )
+int msn_buddy_list_add( struct im_connection *ic, msn_buddy_flags_t list, const char *who, const char *realname, const char *group )
{
struct msn_data *md = ic->proto_data;
char buf[1024], groupid[8];
@@ -130,13 +130,17 @@ int msn_buddy_list_add( struct im_connection *ic, msn_buddy_flags_t list, const
}
#endif
- if( !( bu = bee_user_by_handle( ic->bee, ic, who ) ) ||
+ if( !( ( bu = bee_user_by_handle( ic->bee, ic, who ) ) ||
+ ( bu = bee_user_new( ic->bee, ic, who, 0 ) ) ) ||
!( bd = bu->data ) || bd->flags & list )
return 1;
bd->flags |= list;
- msn_soap_memlist_edit( ic, who, TRUE, list );
+ if( list == MSN_BUDDY_FL )
+ msn_soap_ab_contact_add( ic, bu );
+ else
+ msn_soap_memlist_edit( ic, who, TRUE, list );
if( ( adl = adlrml_entry( who, list ) ) )
{
@@ -178,7 +182,10 @@ int msn_buddy_list_remove( struct im_connection *ic, msn_buddy_flags_t list, con
bd->flags &= ~list;
- msn_soap_memlist_edit( ic, who, FALSE, list );
+ if( list == MSN_BUDDY_FL )
+ msn_soap_ab_contact_del( ic, bu );
+ else
+ msn_soap_memlist_edit( ic, who, FALSE, list );
if( ( adl = adlrml_entry( who, list ) ) )
{
diff --git a/protocols/msn/soap.c b/protocols/msn/soap.c
index 130df840..13ef7e37 100644
--- a/protocols/msn/soap.c
+++ b/protocols/msn/soap.c
@@ -749,3 +749,89 @@ int msn_soap_addressbook_set_display_name( struct im_connection *ic, const char
msn_soap_ab_namechange_handle_response,
msn_soap_ab_namechange_free_data );
}
+
+/* Add a contact. */
+static int msn_soap_ab_contact_add_build_request( struct msn_soap_req_data *soap_req )
+{
+ struct msn_data *md = soap_req->ic->proto_data;
+ bee_user_t *bu = soap_req->data;
+
+ soap_req->url = g_strdup( SOAP_ADDRESSBOOK_URL );
+ soap_req->action = g_strdup( SOAP_AB_CONTACT_ADD_ACTION );
+ soap_req->payload = msn_soap_abservice_build( SOAP_AB_CONTACT_ADD_PAYLOAD,
+ "ContactSave", md->tokens[1], bu->handle, bu->fullname ? bu->fullname : bu->handle );
+
+ return 1;
+}
+
+static xt_status msn_soap_ab_contact_add_cid( struct xt_node *node, gpointer data )
+{
+ struct msn_soap_req_data *soap_req = data;
+ bee_user_t *bu = soap_req->data;
+ struct msn_buddy_data *bd = bu->data;
+
+ g_free( bd->cid );
+ bd->cid = g_strdup( node->text );
+
+ return XT_HANDLED;
+}
+
+static const struct xt_handler_entry msn_soap_ab_contact_add_parser[] = {
+ { "guid", "ABContactAddResult", msn_soap_ab_contact_add_cid },
+ { NULL, NULL, NULL }
+};
+
+static int msn_soap_ab_contact_add_handle_response( struct msn_soap_req_data *soap_req )
+{
+ /* TODO: Ack the change? Not sure what the NAKs look like.. */
+ return MSN_SOAP_OK;
+}
+
+static int msn_soap_ab_contact_add_free_data( struct msn_soap_req_data *soap_req )
+{
+ return 0;
+}
+
+int msn_soap_ab_contact_add( struct im_connection *ic, bee_user_t *bu )
+{
+ return msn_soap_start( ic, bu,
+ msn_soap_ab_contact_add_build_request,
+ msn_soap_ab_contact_add_parser,
+ msn_soap_ab_contact_add_handle_response,
+ msn_soap_ab_contact_add_free_data );
+}
+
+/* Remove a contact. */
+static int msn_soap_ab_contact_del_build_request( struct msn_soap_req_data *soap_req )
+{
+ struct msn_data *md = soap_req->ic->proto_data;
+ bee_user_t *bu = soap_req->data;
+ struct msn_buddy_data *bd = bu->data;
+
+ soap_req->url = g_strdup( SOAP_ADDRESSBOOK_URL );
+ soap_req->action = g_strdup( SOAP_AB_CONTACT_DEL_ACTION );
+ soap_req->payload = msn_soap_abservice_build( SOAP_AB_CONTACT_DEL_PAYLOAD,
+ "Timer", md->tokens[1], bd->cid );
+
+ return 1;
+}
+
+static int msn_soap_ab_contact_del_handle_response( struct msn_soap_req_data *soap_req )
+{
+ /* TODO: Ack the change? Not sure what the NAKs look like.. */
+ return MSN_SOAP_OK;
+}
+
+static int msn_soap_ab_contact_del_free_data( struct msn_soap_req_data *soap_req )
+{
+ return 0;
+}
+
+int msn_soap_ab_contact_del( struct im_connection *ic, bee_user_t *bu )
+{
+ return msn_soap_start( ic, bu,
+ msn_soap_ab_contact_del_build_request,
+ NULL,
+ msn_soap_ab_contact_del_handle_response,
+ msn_soap_ab_contact_del_free_data );
+}
diff --git a/protocols/msn/soap.h b/protocols/msn/soap.h
index 8ce893df..19a5c6ae 100644
--- a/protocols/msn/soap.h
+++ b/protocols/msn/soap.h
@@ -247,8 +247,43 @@ int msn_soap_memlist_edit( struct im_connection *ic, const char *handle, gboolea
"</contacts>" \
"</ABContactUpdate>"
+#define SOAP_AB_CONTACT_ADD_ACTION "http://www.msn.com/webservices/AddressBook/ABContactAdd"
+
+#define SOAP_AB_CONTACT_ADD_PAYLOAD \
+ "<ABContactAdd xmlns=\"http://www.msn.com/webservices/AddressBook\">" \
+ "<abId>00000000-0000-0000-0000-000000000000</abId>" \
+ "<contacts>" \
+ "<Contact xmlns=\"http://www.msn.com/webservices/AddressBook\">" \
+ "<contactInfo>" \
+ "<contactType>LivePending</contactType>" \
+ "<passportName>%s</passportName>" \
+ "<isMessengerUser>true</isMessengerUser>" \
+ "<MessengerMemberInfo>" \
+ "<DisplayName>%s</DisplayName>" \
+ "</MessengerMemberInfo>" \
+ "</contactInfo>" \
+ "</Contact>" \
+ "</contacts>" \
+ "<options>" \
+ "<EnableAllowListManagement>true</EnableAllowListManagement>" \
+ "</options>" \
+ "</ABContactAdd>"
+
+#define SOAP_AB_CONTACT_DEL_ACTION "http://www.msn.com/webservices/AddressBook/ABContactDelete"
+
+#define SOAP_AB_CONTACT_DEL_PAYLOAD \
+ "<ABContactDelete xmlns=\"http://www.msn.com/webservices/AddressBook\">" \
+ "<abId>00000000-0000-0000-0000-000000000000</abId>" \
+ "<contacts>" \
+ "<Contact xmlns=\"http://www.msn.com/webservices/AddressBook\">" \
+ "<contactId>%s</contactId>" \
+ "</Contact>" \
+ "</contacts>" \
+ "</ABContactDelete>"
+
int msn_soap_addressbook_request( struct im_connection *ic );
int msn_soap_addressbook_set_display_name( struct im_connection *ic, const char *new );
-
+int msn_soap_ab_contact_add( struct im_connection *ic, bee_user_t *bu );
+int msn_soap_ab_contact_del( struct im_connection *ic, bee_user_t *bu );
#endif /* __SOAP_H__ */
diff --git a/protocols/msn/tables.c b/protocols/msn/tables.c
index fd7eca41..191abe43 100644
--- a/protocols/msn/tables.c
+++ b/protocols/msn/tables.c
@@ -82,6 +82,8 @@ const struct msn_status_code msn_status_code_list[] =
{ 229, "Group name too long", 0 },
{ 230, "Cannot remove that group", 0 },
{ 231, "Invalid group", 0 },
+ { 240, "ADL/RML command with corrupted payload", STATUS_FATAL },
+ { 241, "ADL/RML command with invalid modification", STATUS_FATAL },
{ 280, "Switchboard failed", STATUS_SB_FATAL },
{ 281, "Transfer to switchboard failed", 0 },