comparison libpurple/protocols/msn/contact.c @ 21107:ca624eda4267

merge of '3380c786d272dcd9ab1360f49c3e4e51227af663' and 'c0e79d15a4fe4c5b0129fcae5060754b25f72a56'
author Ka-Hing Cheung <khc@hxbc.us>
date Wed, 24 Oct 2007 06:45:26 +0000
parents c8f99cb61dc9 90fd0826c6ce
children cc43e75a1da7
comparison
equal deleted inserted replaced
21102:f387e8c671a4 21107:ca624eda4267
26 26
27 #include "msn.h" 27 #include "msn.h"
28 #include "contact.h" 28 #include "contact.h"
29 #include "xmlnode.h" 29 #include "xmlnode.h"
30 #include "group.h" 30 #include "group.h"
31 #include "soap2.h"
31 32
32 const char *MsnSoapPartnerScenarioText[] = 33 const char *MsnSoapPartnerScenarioText[] =
33 { 34 {
34 "Initial", 35 "Initial",
35 "ContactSave", 36 "ContactSave",
45 "Block", 46 "Block",
46 "Reverse", 47 "Reverse",
47 "Pending" 48 "Pending"
48 }; 49 };
49 50
51 typedef struct {
52 MsnContact *contact;
53 MsnSoapPartnerScenario which;
54 } GetContactListCbData;
55
50 /* new a contact */ 56 /* new a contact */
51 MsnContact * 57 MsnContact *
52 msn_contact_new(MsnSession *session) 58 msn_contact_new(MsnSession *session)
53 { 59 {
54 MsnContact *contact; 60 MsnContact *contact;
55 61
56 contact = g_new0(MsnContact, 1); 62 contact = g_new0(MsnContact, 1);
57 contact->session = session; 63 contact->session = session;
58 contact->soapconn = msn_soap_new(session,contact,1);
59 64
60 return contact; 65 return contact;
61 } 66 }
62 67
63 /* destroy the contact */ 68 /* destroy the contact */
64 void 69 void
65 msn_contact_destroy(MsnContact *contact) 70 msn_contact_destroy(MsnContact *contact)
66 { 71 {
67 msn_soap_destroy(contact->soapconn);
68 g_free(contact); 72 g_free(contact);
69 } 73 }
70 74
71 MsnCallbackState * 75 MsnCallbackState *
72 msn_callback_state_new(void) 76 msn_callback_state_new(MsnSession *session)
73 { 77 {
74 return g_new0(MsnCallbackState, 1); 78 MsnCallbackState *state = g_new0(MsnCallbackState, 1);
75 } 79
80 state->session = session;
81
82 return state;
83 }
76 84
77 void 85 void
78 msn_callback_state_free(MsnCallbackState *state) 86 msn_callback_state_free(MsnCallbackState *state)
79 { 87 {
80 if (state == NULL) 88 if (state == NULL)
236 // msn_soap_free_read_buf(soapconn); 244 // msn_soap_free_read_buf(soapconn);
237 return TRUE; 245 return TRUE;
238 } 246 }
239 247
240 static void 248 static void
241 msn_create_address_written_cb(MsnSoapConn *soapconn) 249 msn_create_address_cb(MsnSoapMessage *req, MsnSoapMessage *resp, gpointer data)
242 { 250 {
243 purple_debug_info("MSN AddressBook","AddressBookAdd written\n"); 251 if (resp && msn_soap_xml_get(resp->xml, "Body/Fault") == NULL) {
244 soapconn->read_cb = msn_create_address_cb; 252 purple_debug_info("msnab", "Address Book successfully created!\n");
245 253 msn_get_address_book((MsnContact *)data, MSN_PS_INITIAL, NULL, NULL);
246 return; 254 } else {
255 purple_debug_info("msnab", "Address Book creation failed!\n");
256 }
247 } 257 }
248 258
249 static void 259 static void
250 msn_create_address_book(MsnContact * contact) 260 msn_create_address_book(MsnContact * contact)
251 { 261 {
252 MsnSoapReq *soap_request;
253 gchar *body; 262 gchar *body;
254 263
255 g_return_if_fail(contact != NULL); 264 g_return_if_fail(contact != NULL);
256 g_return_if_fail(contact->session != NULL); 265 g_return_if_fail(contact->session != NULL);
257 g_return_if_fail(contact->session->user != NULL); 266 g_return_if_fail(contact->session->user != NULL);
258 g_return_if_fail(contact->session->user->passport != NULL); 267 g_return_if_fail(contact->session->user->passport != NULL);
259 268
260 purple_debug_info("MSN AddressBook","Creating an Address Book.\n"); 269 purple_debug_info("msnab","Creating an Address Book.\n");
261 270
262 body = g_strdup_printf(MSN_ADD_ADDRESSBOOK_TEMPLATE, contact->session->user->passport); 271 body = g_strdup_printf(MSN_ADD_ADDRESSBOOK_TEMPLATE, contact->session->user->passport);
263 272
264 soap_request = msn_soap_request_new(MSN_CONTACT_SERVER, 273 msn_soap_message_send(contact->session,
265 MSN_ADDRESS_BOOK_POST_URL,MSN_ADD_ADDRESSBOOK_SOAP_ACTION, 274 msn_soap_message_new(MSN_ADD_ADDRESSBOOK_SOAP_ACTION,
266 body, 275 xmlnode_from_str(body, -1)),
267 NULL, 276 MSN_CONTACT_SERVER, MSN_ADDRESS_BOOK_POST_URL, msn_create_address_cb,
268 msn_create_address_cb, 277 contact);
269 msn_create_address_written_cb,
270 msn_contact_connect_init);
271 msn_soap_post(contact->soapconn, soap_request);
272 278
273 g_free(body); 279 g_free(body);
274 280 }
275 return; 281
282 static void
283 msn_parse_each_member(MsnSession *session, xmlnode *member, const char *node,
284 MsnListId list)
285 {
286 char *passport = xmlnode_get_data(xmlnode_get_child(member, node));
287 char *type = xmlnode_get_data(xmlnode_get_child(member, "type"));
288 char *member_id = xmlnode_get_data(xmlnode_get_child(member, "MembershipId"));
289 MsnUser *user = msn_userlist_find_add_user(session->userlist, passport, NULL);
290
291 purple_debug_info("msncl","%s name: %s, Type: %s\n", node, passport, type);
292
293 if (member_id) {
294 user->membership_id[list] = atoi(member_id);
295 }
296
297 msn_got_lst_user(session, user, 1 << list, NULL);
298
299 g_free(passport);
300 g_free(type);
301 g_free(member_id);
302 }
303
304 static void
305 msn_parse_each_service(MsnSession *session, xmlnode *service)
306 {
307 xmlnode *type;
308
309 if ((type = msn_soap_xml_get(service, "Info/Handle/Type"))) {
310 char *type_str = xmlnode_get_data(type);
311
312 if (g_str_equal(type_str, "Profile")) {
313 /* Process Windows Live 'Messenger Roaming Identity' */
314 } else if (g_str_equal(type_str, "Messenger")) {
315 xmlnode *lastchange = xmlnode_get_child(service, "LastChange");
316 char *lastchange_str = xmlnode_get_data(lastchange);
317 xmlnode *membership;
318
319 purple_debug_info("msncl","last change: %s\n", lastchange_str);
320 purple_account_set_string(session->account, "CLLastChange",
321 lastchange_str);
322
323 for (membership = msn_soap_xml_get(service,
324 "Memberships/Membership");
325 membership; membership = xmlnode_get_next_twin(membership)) {
326
327 xmlnode *role = xmlnode_get_child(membership, "MemberRole");
328 char *role_str = xmlnode_get_data(role);
329 MsnListId list = msn_get_memberrole(role_str);
330 xmlnode *member;
331
332 purple_debug_info("msncl", "MemberRole role: %s, list: %d\n",
333 role, list);
334
335 for (member = msn_soap_xml_get(membership, "Members/Member");
336 member; member = xmlnode_get_next_twin(member)) {
337 const char *member_type = xmlnode_get_attrib(member, "type");
338 if (g_str_equal(member_type, "PassportMember")) {
339 msn_parse_each_member(session, member, "PassportName",
340 list);
341 } else if (g_str_equal(member_type, "PhoneMember")) {
342
343 } else if (g_str_equal(member_type, "EmailMember")) {
344 msn_parse_each_member(session, member, "Email", list);
345 }
346 }
347
348 g_free(role_str);
349 }
350
351 g_free(lastchange_str);
352 }
353
354 g_free(type_str);
355 }
276 } 356 }
277 357
278 /*parse contact list*/ 358 /*parse contact list*/
279 static void 359 static void
280 msn_parse_contact_list(MsnContact * contact) 360 msn_parse_contact_list(MsnContact *contact, xmlnode *node)
281 { 361 {
282 MsnSession * session; 362 xmlnode *fault, *faultnode;
283 MsnListOp list_op = 0; 363
284 MsnListId list; 364 /* we may get a response if our cache data is too old:
285 char * passport, *typedata; 365 *
286 xmlnode *fault, *faultstringnode, *faultdetail, *errorcode; 366 * <faultstring>Need to do full sync. Can't sync deltas Client
287 xmlnode *node, *body, *response, *result, *services; 367 * has too old a copy for us to do a delta sync</faultstring>
288 xmlnode *service, *memberships, *info, *handle, *handletype; 368 *
289 xmlnode *membershipnode, *members, *member, *passportNode; 369 * this is not handled yet
290 370 */
291 session = contact->session; 371 if ((fault = msn_soap_xml_get(node, "Body/Fault"))) {
292 node = xmlnode_from_str(contact->soapconn->body, contact->soapconn->body_len); 372 if ((faultnode = xmlnode_get_child(fault, "faultstring"))) {
293 373 char *faultstring = xmlnode_get_data(faultnode);
294 if (node == NULL) { 374 purple_debug_info("msncl", "Retrieving contact list failed: %s\n",
295 purple_debug_error("MSNCL","Unable to parse SOAP data!\n"); 375 faultstring);
296 return;
297 }
298
299 purple_debug_misc("MSNCL","Parsing contact list with size %d\n", contact->soapconn->body_len);
300
301 purple_debug_misc("MSNCL","Root node @ %p: Name: '%s', child: '%s', lastchild: '%s'\n", node,
302 node->name ? node->name : "(null)",
303 (node->child && node->child->name) ? node->child->name : "(null)",
304 (node->lastchild && node->lastchild->name) ? node->lastchild->name : "(null)");
305
306 body = xmlnode_get_child(node, "Body");
307
308 if (body == NULL) {
309 purple_debug_warning("MSNCL", "Failed to parse contact list Body node\n");
310 xmlnode_free(node);
311 return;
312 }
313 purple_debug_info("MSNCL","Body @ %p: Name: '%s'\n",body,body->name);
314
315 /* Did we receive a <Fault> ? */
316 if ( (fault = xmlnode_get_child(body, "Fault")) != NULL) {
317 purple_debug_info("MSNCL","Fault received from SOAP server!\n");
318
319 if ( (faultstringnode = xmlnode_get_child(fault, "faultstring")) != NULL ) {
320 gchar * faultstring = xmlnode_get_data(faultstringnode);
321 purple_debug_info("MSNCL", "Faultstring: %s\n", faultstring ? faultstring : "(null)");
322 g_free(faultstring); 376 g_free(faultstring);
323 } 377 }
324 if ( (faultdetail = xmlnode_get_child(fault, "detail")) != NULL ) { 378 if ((faultnode = msn_soap_xml_get(fault, "detail/errorcode"))) {
325 purple_debug_info("MSNCL","detail @ %p, name: %s\n",faultdetail, faultdetail->name); 379 char *errorcode = xmlnode_get_data(faultnode);
326 380
327 if ( (errorcode = xmlnode_get_child(faultdetail, "errorcode")) != NULL ) { 381 if (g_str_equal(errorcode, "ABDoesNotExist")) {
328 purple_debug_info("MSNCL","errorcode @ %p, name: %s\n", errorcode, errorcode->name); 382 msn_create_address_book(contact);
329 383 g_free(errorcode);
330 if (errorcode->child != NULL) {
331 gchar *errorcodestring = xmlnode_get_data(errorcode);
332 purple_debug_info("MSNCL", "Error Code: %s\n", errorcodestring ? errorcodestring : "(null)");
333
334 if (errorcodestring && !strncmp(errorcodestring, "ABDoesNotExist", 14) ) {
335 xmlnode_free(node);
336 g_free(errorcodestring);
337 msn_create_address_book(contact);
338 return;
339 }
340 g_free(errorcodestring);
341 }
342 }
343 }
344 xmlnode_free(node);
345 msn_get_contact_list(contact, MSN_PS_INITIAL, NULL);
346 return;
347 }
348
349 response = xmlnode_get_child(body,"FindMembershipResponse");
350
351 if (response == NULL) {
352 /* we may get a response if our cache data is too old:
353 *
354 * <faultstring>Need to do full sync. Can't sync deltas Client
355 * has too old a copy for us to do a delta sync</faultstring>
356 */
357 xmlnode_free(node);
358 msn_get_contact_list(contact, MSN_PS_INITIAL, NULL);
359 return;
360 }
361 purple_debug_info("MSNCL","FindMembershipResponse @ %p: Name: '%s'\n",response,response->name);
362
363 result = xmlnode_get_child(response,"FindMembershipResult");
364 if (result == NULL) {
365 purple_debug_warning("MSNCL","Received No Update!\n");
366 xmlnode_free(node);
367 return;
368 }
369 purple_debug_info("MSNCL","Result @ %p: Name: '%s'\n", result, result->name);
370
371 if ( (services = xmlnode_get_child(result,"Services")) == NULL) {
372 purple_debug_misc("MSNCL","No <Services> received.\n");
373 xmlnode_free(node);
374 return;
375 }
376
377 purple_debug_info("MSNCL","Services @ %p\n",services);
378
379 for (service = xmlnode_get_child(services, "Service"); service;
380 service = xmlnode_get_next_twin(service)) {
381 purple_debug_info("MSNCL","Service @ %p\n",service);
382
383 if ( (info = xmlnode_get_child(service,"Info")) == NULL ) {
384 purple_debug_error("MSNCL","Error getting 'Info' child node\n");
385 continue;
386 }
387 if ( (handle = xmlnode_get_child(info,"Handle")) == NULL ) {
388 purple_debug_error("MSNCL","Error getting 'Handle' child node\n");
389 continue;
390 }
391 if ( (handletype = xmlnode_get_child(handle,"Type")) == NULL ) {
392 purple_debug_error("MSNCL","Error getting 'Type' child node\n");
393 continue;
394 }
395
396 if ( (typedata = xmlnode_get_data(handletype)) == NULL) {
397 purple_debug_error("MSNCL","Error retrieving data from 'Type' child node\n");
398 continue;
399 }
400
401 purple_debug_info("MSNCL","processing '%s' Service\n", typedata);
402
403 if ( !g_strcasecmp(typedata, "Profile") ) {
404 /* Process Windows Live 'Messenger Roaming Identity' */
405 g_free(typedata);
406 continue;
407 }
408
409 if ( !g_strcasecmp(typedata, "Messenger") ) {
410 char *LastChangeStr = NULL;
411 xmlnode *LastChangeNode;
412
413 /*Last Change Node*/
414 if ((LastChangeNode = xmlnode_get_child(service, "LastChange")))
415 LastChangeStr = xmlnode_get_data(LastChangeNode);
416 purple_debug_info("MSNCL","LastChangeNode: '%s'\n",LastChangeStr ? LastChangeStr : "(null)");
417 purple_account_set_string(session->account, "CLLastChange", LastChangeStr);
418 g_free(LastChangeStr);
419
420 memberships = xmlnode_get_child(service,"Memberships");
421 if (memberships == NULL) {
422 purple_debug_warning("MSNCL","Memberships = NULL, cleaning up and returning.\n");
423 g_free(typedata);
424 xmlnode_free(node);
425 return; 384 return;
426 } 385 }
427 purple_debug_info("MSNCL","Memberships @ %p: Name: '%s'\n",memberships,memberships->name); 386
428 for (membershipnode = xmlnode_get_child(memberships, "Membership"); membershipnode; 387 g_free(errorcode);
429 membershipnode = xmlnode_get_next_twin(membershipnode)){ 388 }
430 xmlnode *roleNode; 389
431 char *role = NULL; 390 msn_get_contact_list(contact, MSN_PS_INITIAL, NULL);
432 list = 0; 391 } else {
433 392 xmlnode *service;
434 if ((roleNode = xmlnode_get_child(membershipnode,"MemberRole"))) { 393
435 role = xmlnode_get_data(roleNode); 394 for (service = msn_soap_xml_get(node, "Body/FindMembershipResponse/"
436 list = msn_get_memberrole(role); 395 "FindMembershipResult/Services/Service");
437 } 396 service; service = xmlnode_get_next_twin(service)) {
438 list_op = 1 << list; 397 msn_parse_each_service(contact->session, service);
439
440 purple_debug_info("MSNCL","MemberRole role: %s, list_op: %d\n", role ? role : "(null)", list_op);
441
442 g_free(role);
443
444 members = xmlnode_get_child(membershipnode, "Members");
445 for (member = xmlnode_get_child(members, "Member"); member;
446 member = xmlnode_get_next_twin(member)){
447 MsnUser *user = NULL;
448 xmlnode *typeNode, *membershipIdNode = NULL;
449 gchar *type, *membershipId = NULL;
450 const char *member_type = xmlnode_get_attrib(member, "type");
451
452 if (!member_type) {
453 purple_debug_error("msn", "No Member Type specified for Member.\n");
454 continue;
455 }
456
457 if(!g_strcasecmp(member_type, "PassportMember") ) {
458 passport = type = NULL;
459 if ((passportNode = xmlnode_get_child(member, "PassportName")))
460 passport = xmlnode_get_data(passportNode);
461 if ((typeNode = xmlnode_get_child(member, "Type")))
462 type = xmlnode_get_data(typeNode);
463 purple_debug_info("MSNCL","Passport name: '%s', Type: %s\n", passport ? passport : "(null)", type ? type : "(null)");
464 /* Why do we even bother parsing it just to free it??? */
465 g_free(type);
466
467 user = msn_userlist_find_add_user(session->userlist,passport,NULL);
468 g_free(passport);
469
470 membershipIdNode = xmlnode_get_child(member,"MembershipId");
471 if (membershipIdNode != NULL) {
472 membershipId = xmlnode_get_data(membershipIdNode);
473 if (membershipId != NULL) {
474 user->membership_id[list] = atoi(membershipId);
475 g_free(membershipId);
476 }
477 }
478
479 msn_got_lst_user(session, user, list_op, NULL);
480 }
481 else if (!g_strcasecmp(member_type, "PhoneMember")) {
482 purple_debug_info("msn", "Recieved Phone Member; ignoring.\n");
483 }
484 else if (!g_strcasecmp(member_type, "EmailMember")) {
485 xmlnode *emailNode;
486 passport = NULL;
487
488 if ((emailNode = xmlnode_get_child(member, "Email")))
489 passport = xmlnode_get_data(emailNode);
490 purple_debug_info("MSNCL","Email Member: Name: '%s', list_op: %d\n", passport ? passport : "(null)", list_op);
491
492 user = msn_userlist_find_add_user(session->userlist, passport, NULL);
493 g_free(passport);
494
495 membershipIdNode = xmlnode_get_child(member,"MembershipId");
496 if (membershipIdNode != NULL) {
497 membershipId = xmlnode_get_data(membershipIdNode);
498 if (membershipId != NULL) {
499 user->membership_id[list] = atoi(membershipId);
500 g_free(membershipId);
501 }
502 }
503
504 msn_got_lst_user(session, user, list_op, NULL);
505 } else {
506 purple_debug_info("msn", "Unknown Member type: %s\n", member_type);
507 }
508 }
509 }
510 } 398 }
511 g_free(typedata); 399 g_free(typedata);
512 } 400 }
513 401 }
514 xmlnode_free(node); /* Free the whole XML tree */ 402
515 } 403 static void
516 404 msn_get_contact_list_cb(MsnSoapMessage *req, MsnSoapMessage *resp,
517 static gboolean 405 gpointer data)
518 msn_get_contact_list_cb(MsnSoapConn *soapconn) 406 {
519 { 407 GetContactListCbData *cb_data = data;
520 MsnContact *contact; 408 MsnContact *contact = cb_data->contact;
521 MsnSession *session; 409 MsnSession *session = contact->session;
522 const char *abLastChange; 410
523 const char *dynamicItemLastChange; 411 g_return_if_fail(session != NULL);
524 gchar *partner_scenario; 412
525 413 if (resp != NULL) {
526 if (soapconn->body == NULL) 414 const char *abLastChange;
527 return TRUE; 415 const char *dynamicItemLastChange;
528 416
529 purple_debug_misc("MSNCL","Got the contact list!\n"); 417 purple_debug_misc("msncl","Got the contact list!\n");
530 418
531 contact = soapconn->parent; 419 msn_parse_contact_list(cb_data->contact, resp->xml);
532 g_return_val_if_fail(contact != NULL, TRUE); 420 abLastChange = purple_account_get_string(session->account,
533 session = soapconn->session; 421 "ablastChange", NULL);
534 g_return_val_if_fail(session != NULL, FALSE); 422 dynamicItemLastChange = purple_account_get_string(session->account,
535 g_return_val_if_fail(soapconn->data_cb != NULL, TRUE); 423 "dynamicItemLastChange", NULL);
536 424
537 partner_scenario = soapconn->data_cb; 425 if (cb_data->which == MSN_PS_INITIAL) {
538
539 msn_parse_contact_list(contact);
540 /*free the read buffer*/
541 msn_soap_free_read_buf(soapconn);
542
543 abLastChange = purple_account_get_string(session->account, "ablastChange", NULL);
544 dynamicItemLastChange = purple_account_get_string(session->account, "dynamicItemLastChange", NULL);
545
546 if (!strcmp(partner_scenario, MsnSoapPartnerScenarioText[MSN_PS_INITIAL])) {
547
548 #ifdef MSN_PARTIAL_LISTS 426 #ifdef MSN_PARTIAL_LISTS
549 /* XXX: this should be enabled when we can correctly do partial 427 /* XXX: this should be enabled when we can correctly do partial
550 syncs with the server. Currently we need to retrieve the whole 428 syncs with the server. Currently we need to retrieve the whole
551 list to detect sync issues */ 429 list to detect sync issues */
552 msn_get_address_book(contact, MSN_PS_INITIAL, abLastChange, dynamicItemLastChange); 430 msn_get_address_book(contact, MSN_PS_INITIAL, abLastChange, dynamicItemLastChange);
553 #else 431 #else
554 msn_get_address_book(contact, MSN_PS_INITIAL, NULL, NULL); 432 msn_get_address_book(contact, MSN_PS_INITIAL, NULL, NULL);
555 #endif 433 #endif
556 } else { 434 }
557 msn_soap_free_read_buf(soapconn); 435 }
558 } 436
559 437 g_free(cb_data);
560 return TRUE;
561 }
562
563 static void
564 msn_get_contact_written_cb(MsnSoapConn *soapconn)
565 {
566 purple_debug_misc("MSNCL","Sent SOAP request for the contact list.\n");
567 soapconn->read_cb = msn_get_contact_list_cb;
568 } 438 }
569 439
570 /* SOAP get contact list*/ 440 /* SOAP get contact list*/
571 void 441 void
572 msn_get_contact_list(MsnContact * contact, const MsnSoapPartnerScenario partner_scenario, const char *update_time) 442 msn_get_contact_list(MsnContact * contact,
573 { 443 const MsnSoapPartnerScenario partner_scenario, const char *update_time)
574 MsnSoapReq *soap_request; 444 {
575 gchar *body; 445 gchar *body = NULL;
576 gchar *update_str = NULL; 446 gchar * update_str;
447 GetContactListCbData cb_data = { contact, partner_scenario };
577 const gchar *partner_scenario_str = MsnSoapPartnerScenarioText[partner_scenario]; 448 const gchar *partner_scenario_str = MsnSoapPartnerScenarioText[partner_scenario];
578 449
579 purple_debug_misc("MSNCL","Getting Contact List.\n"); 450 purple_debug_misc("MSNCL","Getting Contact List.\n");
580 451
581 if ( update_time != NULL ) { 452 if ( update_time != NULL ) {
582 purple_debug_info("MSNCL","Last update time: %s\n",update_time); 453 purple_debug_info("MSNCL","Last update time: %s\n",update_time);
583 update_str = g_strdup_printf(MSN_GET_CONTACT_UPDATE_XML,update_time); 454 update_str = g_strdup_printf(MSN_GET_CONTACT_UPDATE_XML,update_time);
584 } 455 }
585 456
586 body = g_strdup_printf(MSN_GET_CONTACT_TEMPLATE, partner_scenario_str, update_str ? update_str : ""); 457 body = g_strdup_printf(MSN_GET_CONTACT_TEMPLATE, partner_scenario_str,
458 update_str);
459
460 msn_soap_message_send(contact->session,
461 msn_soap_message_new(MSN_GET_CONTACT_SOAP_ACTION,
462 xmlnode_from_str(body, -1)),
463 MSN_CONTACT_SERVER, MSN_GET_CONTACT_POST_URL,
464 msn_get_contact_list_cb, g_memdup(&cb_data, sizeof(cb_data)));
465
587 g_free(update_str); 466 g_free(update_str);
588
589 soap_request = msn_soap_request_new(MSN_CONTACT_SERVER,
590 MSN_GET_CONTACT_POST_URL,
591 MSN_GET_CONTACT_SOAP_ACTION,
592 body,
593 (gpointer) partner_scenario_str,
594 msn_get_contact_list_cb,
595 msn_get_contact_written_cb,
596 msn_contact_connect_init);
597 msn_soap_post(contact->soapconn,soap_request);
598 g_free(body); 467 g_free(body);
599 } 468 }
600 469
601 static void 470 static void
602 msn_parse_addressbook_groups(MsnContact *contact, xmlnode *node) 471 msn_parse_addressbook_groups(MsnContact *contact, xmlnode *node)
603 { 472 {
604 MsnSession *session = contact->session; 473 MsnSession *session = contact->session;
605 xmlnode *group; 474 xmlnode *group;
606 475
607 purple_debug_info("MsnAb","msn_parse_addressbook_groups()\n"); 476 purple_debug_info("MSNAB","msn_parse_addressbook_groups()\n");
608 477
609 for(group = xmlnode_get_child(node, "Group"); group; 478 for(group = xmlnode_get_child(node, "Group"); group;
610 group = xmlnode_get_next_twin(group)){ 479 group = xmlnode_get_next_twin(group)){
611 xmlnode *groupId, *groupInfo, *groupname; 480 xmlnode *groupId, *groupInfo, *groupname;
612 char *group_id = NULL, *group_name = NULL; 481 char *group_id = NULL, *group_name = NULL;
754 g_free(uid); 623 g_free(uid);
755 g_free(type); 624 g_free(type);
756 } 625 }
757 626
758 static gboolean 627 static gboolean
759 msn_parse_addressbook(MsnContact * contact) 628 msn_parse_addressbook(MsnContact * contact, xmlnode *node)
760 { 629 {
761 MsnSession *session; 630 MsnSession * session;
762 xmlnode * node,*body,*response,*result; 631 xmlnode *result;
763 xmlnode *groups; 632 xmlnode *groups;
764 xmlnode *contacts; 633 xmlnode *contacts;
765 xmlnode *abNode; 634 xmlnode *abNode;
766 xmlnode *fault, *faultstringnode, *faultdetail, *errorcode; 635 xmlnode *fault;
767 636
768 session = contact->session; 637 session = contact->session;
769 638
770 node = xmlnode_from_str(contact->soapconn->body, contact->soapconn->body_len); 639 if ((fault = msn_soap_xml_get(node, "Body/Fault"))) {
771 if ( node == NULL ) { 640 xmlnode *faultnode;
772 purple_debug_error("MSN AddressBook","Error parsing Address Book with size %d\n", contact->soapconn->body_len); 641
642 if ((faultnode = xmlnode_get_child(fault, "faultstring"))) {
643 gchar *faultstring = xmlnode_get_data(faultnode);
644 purple_debug_info("MSNAB","Faultstring: %s\n", faultstring);
645 g_free(faultstring);
646 }
647
648 if ((faultnode = msn_soap_xml_get(fault, "detail/errorcode"))) {
649 gchar *errorcode = xmlnode_get_data(faultnode);
650
651 purple_debug_info("MSNAB", "Error Code: %s\n", errorcode);
652
653 if (g_str_equal(errorcode, "ABDoesNotExist")) {
654 g_free(errorcode);
655 return TRUE;
656 }
657 }
658
773 return FALSE; 659 return FALSE;
774 } 660 }
775 661
776 purple_debug_misc("MSN AddressBook", "Parsing Address Book with size %d\n", contact->soapconn->body_len); 662 result = msn_soap_xml_get(node, "Body/ABFindAllResponse/ABFindAllResult");
777
778 purple_debug_misc("MSN AddressBook","node{%p},name:%s,child:%s,last:%s\n", node,
779 node->name ? node->name : "(null)",
780 (node->child && node->child->name) ? node->child->name : "(null)",
781 (node->lastchild && node->lastchild->name) ? node->lastchild->name : "(null)");
782
783 body = xmlnode_get_child(node,"Body");
784 purple_debug_misc("MSN AddressBook","body{%p},name:%s\n",body,body->name);
785
786 /* TODO: This appears to be used in a number of places and should be de-duplicated */
787 if ( (fault = xmlnode_get_child(body, "Fault")) != NULL) {
788 purple_debug_info("MSN AddressBook","Fault received from SOAP server!\n");
789
790 if ( (faultstringnode = xmlnode_get_child(fault, "faultstring")) != NULL ) {
791 gchar *faultstring = xmlnode_get_data(faultstringnode);
792 purple_debug_info("MSN AddressBook","Faultstring: %s\n", faultstring ? faultstring : "(null)");
793 g_free(faultstring);
794 }
795 if ( (faultdetail = xmlnode_get_child(fault, "detail")) != NULL ) {
796 purple_debug_info("MSN AddressBook","detail @ %p, name: %s\n",faultdetail, faultdetail->name);
797
798 if ( (errorcode = xmlnode_get_child(faultdetail, "errorcode")) != NULL ) {
799 gchar *errorcodestring;
800 purple_debug_info("MSN AddressBook","errorcode @ %p, name: %s\n",errorcode, errorcode->name);
801
802 errorcodestring = xmlnode_get_data(errorcode);
803 purple_debug_info("MSN AddressBook", "Error Code: %s\n", errorcodestring ? errorcodestring : "(null)");
804
805 if (errorcodestring && !strncmp(errorcodestring, "ABDoesNotExist", 14) ) {
806 g_free(errorcodestring);
807 xmlnode_free(node);
808 return TRUE;
809 }
810 g_free(errorcodestring);
811 }
812 }
813 xmlnode_free(node);
814 return FALSE;
815 }
816
817
818 response = xmlnode_get_child(body,"ABFindAllResponse");
819
820 if (response == NULL) {
821 xmlnode_free(node);
822 return FALSE;
823 }
824
825 purple_debug_misc("MSN SOAP","response{%p},name:%s\n",response,response->name);
826 result = xmlnode_get_child(response,"ABFindAllResult");
827 if(result == NULL){ 663 if(result == NULL){
828 purple_debug_misc("MSNAB","receive no address book update\n"); 664 purple_debug_misc("MSNAB","receive no address book update\n");
829 xmlnode_free(node);
830 return TRUE; 665 return TRUE;
831 } 666 }
832 purple_debug_info("MSN SOAP","result{%p},name:%s\n",result,result->name); 667
833 668 /* I don't see this "groups" tag documented on msnpiki, need to find out
669 if they are really there, and update msnpiki */
834 /*Process Group List*/ 670 /*Process Group List*/
835 groups = xmlnode_get_child(result,"groups"); 671 groups = xmlnode_get_child(result,"groups");
836 if (groups != NULL) { 672 if (groups != NULL) {
837 msn_parse_addressbook_groups(contact, groups); 673 msn_parse_addressbook_groups(contact, groups);
838 } 674 }
839 675
840 /*add a default No group to set up the no group Membership*/ 676 /*add a default No group to set up the no group Membership*/
841 msn_group_new(session->userlist, MSN_INDIVIDUALS_GROUP_ID, 677 msn_group_new(session->userlist, MSN_INDIVIDUALS_GROUP_ID,
842 MSN_INDIVIDUALS_GROUP_NAME); 678 MSN_INDIVIDUALS_GROUP_NAME);
843 purple_debug_misc("MsnAB","group_id:%s name:%s\n", 679 purple_debug_misc("MSNAB","group_id:%s name:%s\n",
844 MSN_INDIVIDUALS_GROUP_ID, MSN_INDIVIDUALS_GROUP_NAME); 680 MSN_INDIVIDUALS_GROUP_ID, MSN_INDIVIDUALS_GROUP_NAME);
845 if ((purple_find_group(MSN_INDIVIDUALS_GROUP_NAME)) == NULL){ 681 if ((purple_find_group(MSN_INDIVIDUALS_GROUP_NAME)) == NULL){
846 PurpleGroup *g = purple_group_new(MSN_INDIVIDUALS_GROUP_NAME); 682 PurpleGroup *g = purple_group_new(MSN_INDIVIDUALS_GROUP_NAME);
847 purple_blist_add_group(g, NULL); 683 purple_blist_add_group(g, NULL);
848 } 684 }
849 685
850 /*add a default No group to set up the no group Membership*/ 686 /*add a default No group to set up the no group Membership*/
851 msn_group_new(session->userlist, MSN_NON_IM_GROUP_ID, MSN_NON_IM_GROUP_NAME); 687 msn_group_new(session->userlist, MSN_NON_IM_GROUP_ID, MSN_NON_IM_GROUP_NAME);
852 purple_debug_misc("MsnAB","group_id:%s name:%s\n", MSN_NON_IM_GROUP_ID, MSN_NON_IM_GROUP_NAME); 688 purple_debug_misc("MSNAB","group_id:%s name:%s\n", MSN_NON_IM_GROUP_ID, MSN_NON_IM_GROUP_NAME);
853 if ((purple_find_group(MSN_NON_IM_GROUP_NAME)) == NULL){ 689 if ((purple_find_group(MSN_NON_IM_GROUP_NAME)) == NULL){
854 PurpleGroup *g = purple_group_new(MSN_NON_IM_GROUP_NAME); 690 PurpleGroup *g = purple_group_new(MSN_NON_IM_GROUP_NAME);
855 purple_blist_add_group(g, NULL); 691 purple_blist_add_group(g, NULL);
856 } 692 }
857 693
865 abNode =xmlnode_get_child(result,"ab"); 701 abNode =xmlnode_get_child(result,"ab");
866 if(abNode != NULL){ 702 if(abNode != NULL){
867 xmlnode *node2; 703 xmlnode *node2;
868 char *tmp = NULL; 704 char *tmp = NULL;
869 705
870 if ((node2 = xmlnode_get_child(abNode, "lastChange"))) 706 LastChangeNode = xmlnode_get_child(abNode,"lastChange");
871 tmp = xmlnode_get_data(node2); 707 lastchange = xmlnode_get_data(LastChangeNode);
872 purple_debug_info("MsnAB"," lastchanged Time:{%s}\n", tmp ? tmp : "(null)"); 708 purple_debug_info("MSNAB"," lastchanged Time:{%s}\n",lastchange);
873 purple_account_set_string(session->account, "ablastChange", tmp); 709 purple_account_set_string(session->account, "ablastChange", lastchange);
874 710
875 g_free(tmp); tmp = NULL; 711 DynamicItemLastChangedNode = xmlnode_get_child(abNode,"DynamicItemLastChanged");
876 if ((node2 = xmlnode_get_child(abNode, "DynamicItemLastChanged"))) 712 dynamicChange = xmlnode_get_data(DynamicItemLastChangedNode);
877 tmp = xmlnode_get_data(node2); 713 purple_debug_info("MSNAB"," DynamicItemLastChanged :{%s}\n",dynamicChange);
878 purple_debug_info("MsnAB"," DynamicItemLastChanged :{%s}\n", tmp ? tmp : "(null)"); 714 purple_account_set_string(session->account, "DynamicItemLastChanged", lastchange);
879 purple_account_set_string(session->account, "DynamicItemLastChanged", tmp); 715 g_free(dynamicChange);
880 g_free(tmp); 716 g_free(lastchange);
881 } 717 }
882 718
883 xmlnode_free(node);
884 msn_soap_free_read_buf(contact->soapconn);
885 return TRUE; 719 return TRUE;
886 } 720 }
887 721
888 static gboolean 722 static void
889 msn_get_address_cb(MsnSoapConn *soapconn) 723 msn_get_address_cb(MsnSoapMessage *req, MsnSoapMessage *resp, gpointer data)
890 { 724 {
891 MsnContact *contact; 725 MsnContact *contact = data;
892 MsnSession *session; 726 MsnSession *session;
893 727
894 if (soapconn->body == NULL) 728 if (resp == NULL)
895 return TRUE; 729 return;
896 730
897 contact = soapconn->parent; 731 g_return_if_fail(contact != NULL);
898 g_return_val_if_fail(contact != NULL, TRUE); 732 session = contact->session;
899 session = soapconn->session; 733 g_return_if_fail(session != NULL);
900 g_return_val_if_fail(session != NULL, FALSE); 734
901 735 purple_debug_misc("MSNAB", "Got the Address Book!\n");
902 purple_debug_misc("MSN AddressBook", "Got the Address Book!\n"); 736
903 737 if (msn_parse_addressbook(contact, resp->xml)) {
904 if ( msn_parse_addressbook(contact) ) {
905 //msn_soap_free_read_buf(soapconn);
906
907 if (!session->logged_in) { 738 if (!session->logged_in) {
908 msn_send_privacy(session->account->gc); 739 msn_send_privacy(session->account->gc);
909 msn_notification_dump_contact(session); 740 msn_notification_dump_contact(session);
910 } 741 }
911 742
912 /*free the read buffer*/ 743 /*free the read buffer*/
913 msn_soap_free_read_buf(soapconn); 744 msn_soap_free_read_buf(soapconn);
914 return TRUE; 745 return TRUE;
915 } else { 746 } else {
916 /* This is making us loop infinitely when we fail to parse the address book, 747 /* This is making us loop infinitely when we fail to parse the
917 disable for now (we should re-enable when we send timestamps) 748 address book, disable for now (we should re-enable when we
749 send timestamps)
918 */ 750 */
919 /* 751 /*
920 msn_get_address_book(contact, NULL, NULL); 752 msn_get_address_book(contact, NULL, NULL);
921 */ 753 */
922 msn_session_disconnect(session); 754 msn_session_disconnect(session);
933 soapconn->read_cb = msn_get_address_cb; 765 soapconn->read_cb = msn_get_address_cb;
934 } 766 }
935 767
936 /*get the address book*/ 768 /*get the address book*/
937 void 769 void
938 msn_get_address_book(MsnContact *contact, const MsnSoapPartnerScenario partner_scenario, const char *LastChanged, const char *dynamicItemLastChange) 770 msn_get_address_book(MsnContact *contact,
939 { 771 MsnSoapPartnerScenario partner_scenario, const char *LastChanged,
940 MsnSoapReq *soap_request; 772 const char *dynamicItemLastChange)
941 char *body; 773 {
942 char *update_str = NULL; 774 char *body = NULL;
943 775 char *ab_update_str,*update_str;
944 purple_debug_misc("MSN AddressBook","Getting Address Book\n"); 776
777 purple_debug_misc("MSNAB","Getting Address Book\n");
945 778
946 /*build SOAP and POST it*/ 779 /*build SOAP and POST it*/
947 if (dynamicItemLastChange != NULL) 780 if ( LastChanged != NULL ) {
948 update_str = g_strdup_printf(MSN_GET_ADDRESS_UPDATE_XML, dynamicItemLastChange); 781 ab_update_str = g_strdup_printf(MSN_GET_ADDRESS_UPDATE_XML,LastChanged);
949 else if (LastChanged != NULL) 782 } else {
950 update_str = g_strdup_printf(MSN_GET_ADDRESS_UPDATE_XML, LastChanged); 783 ab_update_str = g_strdup("");
951 784 }
952 785 if ( dynamicItemLastChange != NULL ) {
953 body = g_strdup_printf(MSN_GET_ADDRESS_TEMPLATE, MsnSoapPartnerScenarioText[partner_scenario], update_str ? update_str : ""); 786 update_str = g_strdup_printf(MSN_GET_ADDRESS_UPDATE_XML,
787 dynamicItemLastChange);
788 } else {
789 update_str = g_strdup(ab_update_str);
790 }
791
792 body = g_strdup_printf(MSN_GET_ADDRESS_TEMPLATE, MsnSoapPartnerScenarioText[partner_scenario], update_str);
954 g_free(update_str); 793 g_free(update_str);
955 794
956 soap_request = msn_soap_request_new(MSN_CONTACT_SERVER, 795 msn_soap_message_send(contact->session,
957 MSN_ADDRESS_BOOK_POST_URL,MSN_GET_ADDRESS_SOAP_ACTION, 796 msn_soap_message_new(MSN_GET_ADDRESS_SOAP_ACTION,
958 body, 797 xmlnode_from_str(body, -1)),
959 NULL, 798 MSN_CONTACT_SERVER, MSN_ADDRESS_BOOK_POST_URL, msn_get_address_cb,
960 msn_get_address_cb, 799 contact);
961 msn_address_written_cb, 800
962 msn_contact_connect_init); 801 g_free(ab_update_str);
963 msn_soap_post(contact->soapconn,soap_request);
964 g_free(body); 802 g_free(body);
965 } 803 }
966 804
967 static gboolean 805 static void
968 msn_add_contact_read_cb(MsnSoapConn *soapconn) 806 msn_add_contact_read_cb(MsnSoapMessage *req, MsnSoapMessage *resp,
969 { 807 gpointer data)
970 MsnCallbackState *state = NULL; 808 {
971 MsnUserList *userlist; 809 MsnCallbackState *state = data;
972 MsnUser *user; 810 MsnSession *session = state->session;
973 811
974 g_return_val_if_fail(soapconn->data_cb != NULL, TRUE); 812 g_return_if_fail(session != NULL);
975 g_return_val_if_fail(soapconn->session != NULL, FALSE); 813
976 g_return_val_if_fail(soapconn->session->userlist != NULL, TRUE); 814 if (resp != NULL) {
977 815 MsnUserList *userlist = session->userlist;
978 state = (MsnCallbackState *) soapconn->data_cb; 816 MsnUser *user;
979 817
980 if (soapconn->body == NULL) { 818 purple_debug_info("MSNCL","Contact added successfully\n");
981 msn_callback_state_free(state); 819
982 return TRUE; 820 // the code this block is replacing didn't send ADL for yahoo contacts,
983 } 821 // but i haven't confirmed this is WLM's behaviour wrt yahoo contacts
984 822
985 userlist = soapconn->session->userlist; 823 if ( !msn_user_is_yahoo(session->account, state->who) ) {
986
987 purple_debug_info("MSNCL","Contact added successfully\n");
988
989 // the code this block is replacing didn't send ADL for yahoo contacts,
990 // but i haven't confirmed this is WLM's behaviour wrt yahoo contacts
991
992 if ( !msn_user_is_yahoo(soapconn->session->account, state->who) ) {
993 824
994 msn_userlist_add_buddy_to_list(userlist, state->who, MSN_LIST_AL); 825 msn_userlist_add_buddy_to_list(userlist, state->who, MSN_LIST_AL);
995 msn_userlist_add_buddy_to_list(userlist, state->who, MSN_LIST_FL); 826 msn_userlist_add_buddy_to_list(userlist, state->who, MSN_LIST_FL);
996 } 827 }
997 msn_notification_send_fqy(soapconn->session, state->who); 828 msn_notification_send_fqy(session, state->who);
998 829
999 user = msn_userlist_find_add_user(userlist, state->who, state->who); 830 user = msn_userlist_find_add_user(userlist, state->who, state->who);
1000 msn_user_add_group_id(user, state->guid); 831 msn_user_add_group_id(user, state->guid);
1001 832
1002 msn_soap_free_read_buf(soapconn); 833 if (msn_userlist_user_is_in_list(user, MSN_LIST_PL)) {
834 msn_del_contact_from_list(session->contact, NULL, state->who, MSN_LIST_PL);
835 }
836 }
837
1003 msn_callback_state_free(state); 838 msn_callback_state_free(state);
1004 839
1005 return TRUE; 840 return TRUE;
1006 } 841 }
1007 842
1014 849
1015 /* add a Contact in MSN_INDIVIDUALS_GROUP */ 850 /* add a Contact in MSN_INDIVIDUALS_GROUP */
1016 void 851 void
1017 msn_add_contact(MsnContact *contact, MsnCallbackState *state, const char *passport) 852 msn_add_contact(MsnContact *contact, MsnCallbackState *state, const char *passport)
1018 { 853 {
1019 MsnSoapReq *soap_request;
1020 gchar *body = NULL; 854 gchar *body = NULL;
1021 gchar *contact_xml = NULL; 855 gchar *contact_xml = NULL;
1022 856
1023 g_return_if_fail(passport != NULL); 857 #if 0
1024 /* gchar *escaped_displayname; 858 gchar *escaped_displayname;
1025 859
1026 860
1027 if (displayname != NULL) { 861 if (displayname != NULL) {
1028 escaped_displayname = g_markup_decode_text(displayname, -1); 862 escaped_displayname = g_markup_decode_text(displayname, -1);
1029 } else { 863 } else {
1030 escaped_displayname = passport; 864 escaped_displayname = passport;
1031 } 865 }
1032 contact_xml = g_strdup_printf(MSN_XML_ADD_CONTACT, escaped_displayname, passport); 866 contact_xml = g_strdup_printf(MSN_XML_ADD_CONTACT, escaped_displayname, passport);
1033 */ 867 #endif
868
1034 purple_debug_info("MSNCL","Adding contact %s to contact list\n", passport); 869 purple_debug_info("MSNCL","Adding contact %s to contact list\n", passport);
1035 870
1036 // if ( !strcmp(state->guid, MSN_INDIVIDUALS_GROUP_ID) ) { 871 contact_xml = g_strdup_printf(MSN_CONTACT_XML, passport);
1037 contact_xml = g_strdup_printf(MSN_CONTACT_XML, passport);
1038 // }
1039 body = g_strdup_printf(MSN_ADD_CONTACT_TEMPLATE, contact_xml); 872 body = g_strdup_printf(MSN_ADD_CONTACT_TEMPLATE, contact_xml);
1040 873
874 msn_soap_message_send(contact->session,
875 msn_soap_message_new(MSN_CONTACT_ADD_SOAP_ACTION,
876 xmlnode_from_str(body, -1)),
877 MSN_CONTACT_SERVER, MSN_ADDRESS_BOOK_POST_URL,
878 msn_add_contact_read_cb, state);
879
1041 g_free(contact_xml); 880 g_free(contact_xml);
1042
1043 /*build SOAP and POST it*/
1044
1045 soap_request = msn_soap_request_new(MSN_CONTACT_SERVER,
1046 MSN_ADDRESS_BOOK_POST_URL,
1047 MSN_CONTACT_ADD_SOAP_ACTION,
1048 body,
1049 state,
1050 msn_add_contact_read_cb,
1051 msn_add_contact_written_cb,
1052 msn_contact_connect_init);
1053 msn_soap_post(contact->soapconn,soap_request);
1054
1055 g_free(body); 881 g_free(body);
1056 } 882 }
1057 883
1058 static gboolean 884 static void
1059 msn_add_contact_to_group_read_cb(MsnSoapConn *soapconn) 885 msn_add_contact_to_group_read_cb(MsnSoapMessage *req, MsnSoapMessage *resp,
1060 { 886 gpointer data)
1061 MsnCallbackState *state; 887 {
888 MsnCallbackState *state = data;
1062 MsnUserList *userlist; 889 MsnUserList *userlist;
1063 890
1064 g_return_val_if_fail(soapconn->data_cb != NULL, TRUE); 891 g_return_if_fail(data != NULL);
1065 g_return_val_if_fail(soapconn->session != NULL, FALSE); 892
1066 g_return_val_if_fail(soapconn->session->userlist != NULL, TRUE); 893 userlist = state->session->userlist;
1067 894
1068 userlist = soapconn->session->userlist; 895 if (resp != NULL) {
1069 896 if (msn_userlist_add_buddy_to_group(userlist, state->who,
1070 state = (MsnCallbackState *) soapconn->data_cb; 897 state->new_group_name)) {
1071 898 purple_debug_info("MSNCL", "Contact %s added to group %s successfully!\n", state->who, state->new_group_name);
1072 if (soapconn->body == NULL) { 899 } else {
1073 msn_callback_state_free(state); 900 purple_debug_info("MSNCL","Contact %s added to group %s successfully on server, but failed in the local list\n", state->who, state->new_group_name);
1074 return TRUE; 901 }
1075 } 902
1076 903 if (state->action & MSN_ADD_BUDDY) {
1077 if (msn_userlist_add_buddy_to_group(userlist, state->who, state->new_group_name) == TRUE) { 904 MsnUser *user = msn_userlist_find_user(userlist, state->who);
1078 purple_debug_info("MSNCL", "Contact %s added to group %s successfully!\n", state->who, state->new_group_name); 905
1079 } else { 906 if ( !msn_user_is_yahoo(state->session->account, state->who) ) {
1080 purple_debug_info("MSNCL","Contact %s added to group %s successfully on server, but failed in the local list\n", state->who, state->new_group_name); 907
1081 } 908 msn_userlist_add_buddy_to_list(userlist, state->who, MSN_LIST_AL);
1082 909 msn_userlist_add_buddy_to_list(userlist, state->who, MSN_LIST_FL);
1083 if (state->action & MSN_ADD_BUDDY) {
1084
1085 if ( !msn_user_is_yahoo(soapconn->session->account, state->who) ) {
1086
1087 msn_userlist_add_buddy_to_list(userlist, state->who, MSN_LIST_AL);
1088 msn_userlist_add_buddy_to_list(userlist, state->who, MSN_LIST_FL);
1089 } 910 }
1090 msn_notification_send_fqy(soapconn->session, state->who); 911 msn_notification_send_fqy(state->session, state->who);
1091 } 912
1092 913 if (msn_userlist_user_is_in_list(user, MSN_LIST_PL)) {
1093 if (state->action & MSN_MOVE_BUDDY) { 914 msn_del_contact_from_list(state->session->contact, NULL, state->who, MSN_LIST_PL);
1094 msn_del_contact_from_group(soapconn->session->contact, state->who, state->old_group_name); 915 msn_callback_state_free(state);
1095 } else { 916 return;
1096 msn_callback_state_free(state); 917 }
1097 msn_soap_free_read_buf(soapconn); 918 }
1098 } 919
1099 return TRUE; 920 if (state->action & MSN_MOVE_BUDDY) {
1100 } 921 msn_del_contact_from_group(state->session->contact, state->who, state->old_group_name);
1101 922 }
1102 static void 923 }
1103 msn_add_contact_to_group_written_cb(MsnSoapConn *soapconn) 924
1104 { 925 msn_callback_state_free(state);
1105 purple_debug_info("MSNCL","Add contact to group request sent!\n");
1106 soapconn->read_cb = msn_add_contact_to_group_read_cb;
1107 } 926 }
1108 927
1109 void 928 void
1110 msn_add_contact_to_group(MsnContact *contact, MsnCallbackState *state, 929 msn_add_contact_to_group(MsnContact *contact, MsnCallbackState *state,
1111 const char *passport, const char *groupId) 930 const char *passport, const char *groupId)
1112 { 931 {
1113 MsnSoapReq *soap_request;
1114 MsnUserList *userlist; 932 MsnUserList *userlist;
1115 MsnUser *user; 933 MsnUser *user;
1116 gchar *body = NULL, *contact_xml; 934 gchar *body = NULL, *contact_xml;
1117 935
1118 g_return_if_fail(passport != NULL); 936 g_return_if_fail(passport != NULL);
1141 } 959 }
1142 960
1143 return; 961 return;
1144 } 962 }
1145 963
1146
1147 purple_debug_info("MSNCL", "Adding user %s to group %s\n", passport, 964 purple_debug_info("MSNCL", "Adding user %s to group %s\n", passport,
1148 msn_userlist_find_group_name(userlist, groupId)); 965 msn_userlist_find_group_name(userlist, groupId));
1149 966
1150 user = msn_userlist_find_user(userlist, passport); 967 user = msn_userlist_find_user(userlist, passport);
1151 if (user == NULL) { 968 if (user == NULL) {
1152 purple_debug_warning("MSN CL", "Unable to retrieve user %s from the userlist!\n", passport); 969 purple_debug_warning("MSNCL", "Unable to retrieve user %s from the userlist!\n", passport);
970 msn_callback_state_free(state);
971 return; /* guess this never happened! */
1153 } 972 }
1154 973
1155 if (user != NULL && user->uid != NULL) { 974 if (user != NULL && user->uid != NULL) {
1156 contact_xml = g_strdup_printf(MSN_CONTACT_ID_XML, user->uid); 975 contact_xml = g_strdup_printf(MSN_CONTACT_ID_XML, user->uid);
1157 } else { 976 } else {
1158 contact_xml = g_strdup_printf(MSN_CONTACT_XML, passport); 977 contact_xml = g_strdup_printf(MSN_CONTACT_XML, passport);
1159 } 978 }
1160 979
1161 body = g_strdup_printf(MSN_ADD_CONTACT_GROUP_TEMPLATE, groupId, contact_xml); 980 body = g_strdup_printf(MSN_ADD_CONTACT_GROUP_TEMPLATE, groupId, contact_xml);
981
982 msn_soap_message_send(state->session,
983 msn_soap_message_new(MSN_ADD_CONTACT_GROUP_SOAP_ACTION,
984 xmlnode_from_str(body, -1)),
985 MSN_CONTACT_SERVER, MSN_ADDRESS_BOOK_POST_URL,
986 msn_add_contact_to_group_read_cb, state);
987
1162 g_free(contact_xml); 988 g_free(contact_xml);
1163
1164 /*build SOAP and POST it*/
1165
1166 soap_request = msn_soap_request_new(MSN_CONTACT_SERVER,
1167 MSN_ADDRESS_BOOK_POST_URL,
1168 MSN_ADD_CONTACT_GROUP_SOAP_ACTION,
1169 body,
1170 state,
1171 msn_add_contact_to_group_read_cb,
1172 msn_add_contact_to_group_written_cb,
1173 msn_contact_connect_init);
1174 msn_soap_post(contact->soapconn,soap_request);
1175
1176 g_free(body); 989 g_free(body);
1177 } 990 }
1178 991
1179 992 static void
1180 993 msn_delete_contact_read_cb(MsnSoapMessage *req, MsnSoapMessage *resp,
1181 static gboolean 994 gpointer data)
1182 msn_delete_contact_read_cb(MsnSoapConn *soapconn) 995 {
1183 { 996 if (resp == NULL)
1184 MsnUser *user; 997 return;
1185 MsnCallbackState *state = (MsnCallbackState *) soapconn->data_cb;
1186 MsnUserList *userlist;
1187
1188 g_return_val_if_fail(soapconn->session != NULL, FALSE);
1189 g_return_val_if_fail(soapconn->session->userlist != NULL, TRUE);
1190
1191 userlist = soapconn->session->userlist;
1192
1193 if (soapconn->body == NULL) {
1194 msn_callback_state_free(state);
1195 return TRUE;
1196 }
1197 998
1198 purple_debug_info("MSNCL","Delete contact successful\n"); 999 purple_debug_info("MSNCL","Delete contact successful\n");
1199
1200 user = msn_userlist_find_user_with_id(userlist, state->uid);
1201 if (user != NULL) {
1202 msn_userlist_remove_user(userlist, user);
1203 }
1204
1205 msn_callback_state_free(state);
1206 msn_soap_free_read_buf(soapconn);
1207
1208 return TRUE;
1209 }
1210
1211 static void
1212 msn_delete_contact_written_cb(MsnSoapConn *soapconn)
1213 {
1214 purple_debug_info("MSNCL","Delete contact request written\n");
1215 soapconn->read_cb = msn_delete_contact_read_cb;
1216 } 1000 }
1217 1001
1218 /*delete a Contact*/ 1002 /*delete a Contact*/
1219 void 1003 void
1220 msn_delete_contact(MsnContact *contact, const char *contactId) 1004 msn_delete_contact(MsnContact *contact, const char *contactId)
1221 { 1005 {
1222 gchar *body = NULL; 1006 gchar *body = NULL;
1223 gchar *contact_id_xml = NULL ; 1007 gchar *contact_id_xml = NULL ;
1224 MsnSoapReq *soap_request;
1225 MsnCallbackState *state;
1226 1008
1227 g_return_if_fail(contactId != NULL); 1009 g_return_if_fail(contactId != NULL);
1228 contact_id_xml = g_strdup_printf(MSN_CONTACT_ID_XML, contactId); 1010 contact_id_xml = g_strdup_printf(MSN_CONTACT_ID_XML, contactId);
1229 1011
1230 state = msn_callback_state_new(); 1012 state = msn_callback_state_new();
1231 msn_callback_state_set_uid(state, contactId); 1013 msn_callback_state_set_uid(state, contactId);
1232 1014
1233 /* build SOAP request */ 1015 /* build SOAP request */
1234 purple_debug_info("MSNCL","Deleting contact with contactId: %s\n", contactId); 1016 purple_debug_info("MSNCL","Deleting contact with contactId: %s\n", contactId);
1235 body = g_strdup_printf(MSN_DEL_CONTACT_TEMPLATE, contact_id_xml); 1017 body = g_strdup_printf(MSN_DEL_CONTACT_TEMPLATE, contact_id_xml);
1236 soap_request = msn_soap_request_new(MSN_CONTACT_SERVER, 1018 msn_soap_message_send(contact->session,
1237 MSN_ADDRESS_BOOK_POST_URL, 1019 msn_soap_message_new(MSN_CONTACT_DEL_SOAP_ACTION,
1238 MSN_CONTACT_DEL_SOAP_ACTION, 1020 xmlnode_from_str(body, -1)),
1239 body, 1021 MSN_CONTACT_SERVER, MSN_ADDRESS_BOOK_POST_URL,
1240 state, 1022 msn_delete_contact_read_cb, NULL);
1241 msn_delete_contact_read_cb,
1242 msn_delete_contact_written_cb,
1243 msn_contact_connect_init);
1244 1023
1245 g_free(contact_id_xml); 1024 g_free(contact_id_xml);
1246
1247 /* POST the SOAP request */
1248 msn_soap_post(contact->soapconn, soap_request);
1249
1250 g_free(body); 1025 g_free(body);
1251 } 1026 }
1252 1027
1253 static gboolean 1028 static void
1254 msn_del_contact_from_group_read_cb(MsnSoapConn *soapconn) 1029 msn_del_contact_from_group_read_cb(MsnSoapMessage *req, MsnSoapMessage *resp,
1255 { 1030 gpointer data)
1256 MsnCallbackState *state = (MsnCallbackState *) soapconn->data_cb; 1031 {
1257 1032 MsnCallbackState *state = data;
1258 if (soapconn->body == NULL) { 1033
1259 msn_callback_state_free(state); 1034 if (resp != NULL) {
1260 return TRUE; 1035 if (msn_userlist_rem_buddy_from_group(state->session->userlist,
1261 } 1036 state->who, state->old_group_name)) {
1262 1037 purple_debug_info("MSNCL", "Contact %s deleted successfully from group %s\n", state->who, state->old_group_name);
1263 if (msn_userlist_rem_buddy_from_group(soapconn->session->userlist, state->who, state->old_group_name)) { 1038 } else {
1264 purple_debug_info("MSN CL", "Contact %s deleted successfully from group %s\n", state->who, state->old_group_name); 1039 purple_debug_info("MSNCL", "Contact %s deleted successfully from group %s in the server, but failed in the local list\n", state->who, state->old_group_name);
1265 } else { 1040 }
1266 purple_debug_info("MSN CL", "Contact %s deleted successfully from group %s in the server, but failed in the local list\n", state->who, state->old_group_name);
1267 } 1041 }
1268 1042
1269 msn_callback_state_free(state); 1043 msn_callback_state_free(state);
1270 msn_soap_free_read_buf(soapconn);
1271
1272 return TRUE;
1273 }
1274
1275 static void
1276 msn_del_contact_from_group_written_cb(MsnSoapConn *soapconn)
1277 {
1278 purple_debug_info("MSN CL","Del contact from group request sent!\n");
1279 soapconn->read_cb = msn_del_contact_from_group_read_cb;
1280 } 1044 }
1281 1045
1282 void 1046 void
1283 msn_del_contact_from_group(MsnContact *contact, const char *passport, const char *group_name) 1047 msn_del_contact_from_group(MsnContact *contact, const char *passport, const char *group_name)
1284 { 1048 {
1285 MsnSoapReq *soap_request;
1286 MsnUserList * userlist; 1049 MsnUserList * userlist;
1287 MsnUser *user; 1050 MsnUser *user;
1288 MsnCallbackState *state; 1051 MsnCallbackState *state;
1289 gchar *body = NULL, *contact_id_xml; 1052 gchar *body, *contact_id_xml;
1290 const gchar *groupId; 1053 const gchar *groupId;
1291 1054
1292 g_return_if_fail(passport != NULL); 1055 g_return_if_fail(passport != NULL);
1293 g_return_if_fail(group_name != NULL); 1056 g_return_if_fail(group_name != NULL);
1294 g_return_if_fail(contact != NULL); 1057 g_return_if_fail(contact != NULL);
1297 1060
1298 userlist = contact->session->userlist; 1061 userlist = contact->session->userlist;
1299 1062
1300 groupId = msn_userlist_find_group_id(userlist, group_name); 1063 groupId = msn_userlist_find_group_id(userlist, group_name);
1301 if (groupId != NULL) { 1064 if (groupId != NULL) {
1302 purple_debug_info("MSN CL", "Deleting user %s from group %s\n", passport, group_name); 1065 purple_debug_info("MSNCL", "Deleting user %s from group %s\n", passport, group_name);
1303 } else { 1066 } else {
1304 purple_debug_warning("MSN CL", "Unable to retrieve group id from group %s !\n", group_name); 1067 purple_debug_warning("MSNCL", "Unable to retrieve group id from group %s !\n", group_name);
1305 return; 1068 return;
1306 } 1069 }
1307 1070
1308 user = msn_userlist_find_user(userlist, passport); 1071 user = msn_userlist_find_user(userlist, passport);
1309 1072
1310 if (user == NULL) { 1073 if (user == NULL) {
1311 purple_debug_warning("MSN CL", "Unable to retrieve user from passport %s!\n", passport); 1074 purple_debug_warning("MSNCL", "Unable to retrieve user from passport %s!\n", passport);
1312 return; 1075 return;
1313 } 1076 }
1314 1077
1315 if ( !strcmp(groupId, MSN_INDIVIDUALS_GROUP_ID) || !strcmp(groupId, MSN_NON_IM_GROUP_ID)) { 1078 if ( !strcmp(groupId, MSN_INDIVIDUALS_GROUP_ID) || !strcmp(groupId, MSN_NON_IM_GROUP_ID)) {
1316 msn_user_remove_group_id(user, groupId); 1079 msn_user_remove_group_id(user, groupId);
1317 return; 1080 return;
1318 } 1081 }
1319 1082
1320 state = msn_callback_state_new(); 1083 state = msn_callback_state_new(contact->session);
1321 msn_callback_state_set_who(state, passport); 1084 msn_callback_state_set_who(state, passport);
1322 msn_callback_state_set_guid(state, groupId); 1085 msn_callback_state_set_guid(state, groupId);
1323 msn_callback_state_set_old_group_name(state, group_name); 1086 msn_callback_state_set_old_group_name(state, group_name);
1324 1087
1325 contact_id_xml = g_strdup_printf(MSN_CONTACT_ID_XML, user->uid); 1088 contact_id_xml = g_strdup_printf(MSN_CONTACT_ID_XML, user->uid);
1326 body = g_strdup_printf(MSN_CONTACT_DEL_GROUP_TEMPLATE, contact_id_xml, groupId); 1089 body = g_strdup_printf(MSN_CONTACT_DEL_GROUP_TEMPLATE, contact_id_xml, groupId);
1090
1091 msn_soap_message_send(contact->session,
1092 msn_soap_message_new(MSN_CONTACT_DEL_GROUP_SOAP_ACTION,
1093 xmlnode_from_str(body, -1)),
1094 MSN_CONTACT_SERVER, MSN_ADDRESS_BOOK_POST_URL,
1095 msn_del_contact_from_group_read_cb, state);
1096
1327 g_free(contact_id_xml); 1097 g_free(contact_id_xml);
1328
1329 /*build SOAP and POST it*/
1330 soap_request = msn_soap_request_new(MSN_CONTACT_SERVER,
1331 MSN_ADDRESS_BOOK_POST_URL,
1332 MSN_CONTACT_DEL_GROUP_SOAP_ACTION,
1333 body,
1334 state,
1335 msn_del_contact_from_group_read_cb,
1336 msn_del_contact_from_group_written_cb,
1337 msn_contact_connect_init);
1338 msn_soap_post(contact->soapconn,soap_request);
1339
1340 g_free(body); 1098 g_free(body);
1341 } 1099 }
1342 1100
1343 1101
1344 static gboolean 1102 static gboolean
1351 1109
1352 return TRUE; 1110 return TRUE;
1353 } 1111 }
1354 1112
1355 static void 1113 static void
1356 msn_update_contact_written_cb(MsnSoapConn *soapconn) 1114 msn_update_contact_read_cb(MsnSoapMessage *req, MsnSoapMessage *resp,
1357 { 1115 gpointer data)
1358 purple_debug_info("MSN CL","Update contact information request sent\n"); 1116 {
1359 soapconn->read_cb = msn_update_contact_read_cb; 1117 if (resp)
1118 purple_debug_info("MSN CL","Contact updated successfully\n");
1119 else
1120 purple_debug_info("MSN CL","Contact updated successfully\n");
1360 } 1121 }
1361 1122
1362 /* Update a contact's nickname */ 1123 /* Update a contact's nickname */
1363
1364 void 1124 void
1365 msn_update_contact(MsnContact *contact, const char* nickname) 1125 msn_update_contact(MsnContact *contact, const char* nickname)
1366 { 1126 {
1367 MsnSoapReq *soap_request; 1127 gchar *body = NULL, *escaped_nickname;
1368 gchar *body, *escaped_nickname;
1369
1370 /* I'm not sure this is right, but if it isn't, the rest of this function will need to be fixed */
1371 g_return_if_fail(nickname != NULL);
1372 1128
1373 purple_debug_info("MSN CL","Update contact information with new friendly name: %s\n", nickname); 1129 purple_debug_info("MSN CL","Update contact information with new friendly name: %s\n", nickname);
1374 1130
1375 escaped_nickname = g_markup_escape_text(nickname, -1); 1131 escaped_nickname = g_markup_escape_text(nickname, -1);
1376 1132
1377 body = g_strdup_printf(MSN_CONTACT_UPDATE_TEMPLATE, escaped_nickname); 1133 body = g_strdup_printf(MSN_CONTACT_UPDATE_TEMPLATE, escaped_nickname);
1378 1134
1135 msn_soap_message_send(contact->session,
1136 msn_soap_message_new(MSN_CONTACT_UPDATE_SOAP_ACTION,
1137 xmlnode_from_str(body, -1)),
1138 MSN_CONTACT_SERVER, MSN_ADDRESS_BOOK_POST_URL,
1139 msn_update_contact_read_cb, NULL);
1140
1379 g_free(escaped_nickname); 1141 g_free(escaped_nickname);
1380 /*build SOAP and POST it*/
1381 soap_request = msn_soap_request_new(MSN_CONTACT_SERVER,
1382 MSN_ADDRESS_BOOK_POST_URL,
1383 MSN_CONTACT_UPDATE_SOAP_ACTION,
1384 body,
1385 NULL,
1386 msn_update_contact_read_cb,
1387 msn_update_contact_written_cb,
1388 msn_contact_connect_init);
1389 msn_soap_post(contact->soapconn, soap_request);
1390
1391 g_free(body); 1142 g_free(body);
1392 } 1143 }
1393 1144
1394 1145 static void
1395 static gboolean 1146 msn_del_contact_from_list_read_cb(MsnSoapMessage *req, MsnSoapMessage *resp,
1396 msn_del_contact_from_list_read_cb(MsnSoapConn *soapconn) 1147 gpointer data)
1397 { 1148 {
1398 MsnCallbackState *state = NULL; 1149 MsnCallbackState *state = data;
1399 1150 MsnSession *session = state->session;
1400 g_return_val_if_fail(soapconn->data_cb != NULL, TRUE); 1151
1401 g_return_val_if_fail(soapconn->session != NULL, FALSE); 1152 if (resp != NULL) {
1402 g_return_val_if_fail(soapconn->session->contact != NULL, FALSE); 1153 purple_debug_info("MSN CL", "Contact %s deleted successfully from %s list on server!\n", state->who, MsnMemberRole[state->list_id]);
1403 g_return_val_if_fail(soapconn->session->userlist != NULL, FALSE); 1154
1404 1155 if (state->list_id == MSN_LIST_PL) {
1405 state = (MsnCallbackState *) soapconn->data_cb; 1156 msn_add_contact_to_list(session->contact, state, state->who, MSN_LIST_RL);
1406 1157 } else if (state->list_id == MSN_LIST_AL) {
1407 if (soapconn->body == NULL) { 1158 purple_privacy_permit_remove(session->account, state->who, TRUE);
1408 msn_callback_state_free(state); 1159 msn_add_contact_to_list(session->contact, NULL, state->who, MSN_LIST_BL);
1409 return TRUE; 1160 } else if (state->list_id == MSN_LIST_BL) {
1410 } 1161 purple_privacy_deny_remove(session->account, state->who, TRUE);
1411 1162 msn_add_contact_to_list(session->contact, NULL, state->who, MSN_LIST_AL);
1412 purple_debug_info("MSN CL", "Contact %s deleted successfully from %s list on server!\n", state->who, MsnMemberRole[state->list_id]); 1163 }
1413
1414 if (state->list_id == MSN_LIST_PL) {
1415 MsnUser *user = msn_userlist_find_user(soapconn->session->userlist, state->who);
1416
1417 if (user != NULL)
1418 msn_user_unset_op(user, MSN_LIST_PL_OP);
1419
1420 msn_add_contact_to_list(soapconn->session->contact, state, state->who, MSN_LIST_RL);
1421 return TRUE;
1422 }
1423
1424 if (state->list_id == MSN_LIST_AL) {
1425 purple_privacy_permit_remove(soapconn->session->account, state->who, TRUE);
1426 msn_add_contact_to_list(soapconn->session->contact, NULL, state->who, MSN_LIST_BL);
1427 msn_callback_state_free(state);
1428 return TRUE;
1429 }
1430
1431 if (state->list_id == MSN_LIST_BL) {
1432 purple_privacy_deny_remove(soapconn->session->account, state->who, TRUE);
1433 msn_add_contact_to_list(soapconn->session->contact, NULL, state->who, MSN_LIST_AL);
1434 msn_callback_state_free(state);
1435 return TRUE;
1436 } 1164 }
1437 1165
1438 msn_callback_state_free(state); 1166 msn_callback_state_free(state);
1439 msn_soap_free_read_buf(soapconn);
1440
1441 return TRUE;
1442 }
1443
1444 static void
1445 msn_del_contact_from_list_written_cb(MsnSoapConn *soapconn)
1446 {
1447 purple_debug_info("MSN CL","Delete contact from list SOAP request sent!\n");
1448 soapconn->read_cb = msn_del_contact_from_list_read_cb;
1449 } 1167 }
1450 1168
1451 void 1169 void
1452 msn_del_contact_from_list(MsnContact *contact, MsnCallbackState *state, 1170 msn_del_contact_from_list(MsnContact *contact, MsnCallbackState *state,
1453 const gchar *passport, const MsnListId list) 1171 const gchar *passport, const MsnListId list)
1454 { 1172 {
1455 MsnSoapReq *soap_request;
1456 gchar *body = NULL, *member = NULL; 1173 gchar *body = NULL, *member = NULL;
1457 MsnSoapPartnerScenario partner_scenario; 1174 MsnSoapPartnerScenario partner_scenario;
1458 MsnUser *user; 1175 MsnUser *user;
1459 1176
1460 g_return_if_fail(contact != NULL); 1177 g_return_if_fail(contact != NULL);
1462 g_return_if_fail(list < 5); 1179 g_return_if_fail(list < 5);
1463 1180
1464 purple_debug_info("MSN CL", "Deleting contact %s from %s list\n", passport, MsnMemberRole[list]); 1181 purple_debug_info("MSN CL", "Deleting contact %s from %s list\n", passport, MsnMemberRole[list]);
1465 1182
1466 if (state == NULL) { 1183 if (state == NULL) {
1467 state = msn_callback_state_new(); 1184 state = msn_callback_state_new(contact->session);
1468 } 1185 }
1469 msn_callback_state_set_list_id(state, list); 1186 msn_callback_state_set_list_id(state, list);
1470 msn_callback_state_set_who(state, passport); 1187 msn_callback_state_set_who(state, passport);
1471 1188
1472 if (list == MSN_LIST_PL) { 1189 if (list == MSN_LIST_PL) {
1486 1203
1487 body = g_strdup_printf( MSN_CONTACT_DELECT_FROM_LIST_TEMPLATE, 1204 body = g_strdup_printf( MSN_CONTACT_DELECT_FROM_LIST_TEMPLATE,
1488 MsnSoapPartnerScenarioText[partner_scenario], 1205 MsnSoapPartnerScenarioText[partner_scenario],
1489 MsnMemberRole[list], 1206 MsnMemberRole[list],
1490 member); 1207 member);
1208
1209 msn_soap_message_send(contact->session,
1210 msn_soap_message_new(MSN_DELETE_MEMBER_FROM_LIST_SOAP_ACTION,
1211 xmlnode_from_str(body, -1)),
1212 MSN_CONTACT_SERVER, MSN_SHARE_POST_URL,
1213 msn_del_contact_from_list_read_cb, state);
1214
1491 g_free(member); 1215 g_free(member);
1492
1493 soap_request = msn_soap_request_new( MSN_CONTACT_SERVER,
1494 MSN_SHARE_POST_URL,
1495 MSN_DELETE_MEMBER_FROM_LIST_SOAP_ACTION,
1496 body,
1497 state,
1498 msn_del_contact_from_list_read_cb,
1499 msn_del_contact_from_list_written_cb,
1500 msn_contact_connect_init);
1501
1502 msn_soap_post(contact->soapconn,soap_request);
1503
1504 g_free(body); 1216 g_free(body);
1505 } 1217 }
1506 1218
1507 static gboolean 1219 static void
1508 msn_add_contact_to_list_read_cb(MsnSoapConn *soapconn) 1220 msn_add_contact_to_list_read_cb(MsnSoapMessage *req, MsnSoapMessage *resp,
1509 { 1221 gpointer data)
1510 MsnCallbackState *state = NULL; 1222 {
1511 1223 MsnCallbackState *state = data;
1512 g_return_val_if_fail(soapconn->data_cb != NULL, TRUE); 1224
1513 g_return_val_if_fail(soapconn->session != NULL, FALSE); 1225 g_return_if_fail(state != NULL);
1514 g_return_val_if_fail(soapconn->session->userlist != NULL, FALSE); 1226 g_return_if_fail(state->session != NULL);
1515 1227 g_return_if_fail(state->session->contact != NULL);
1516 state = (MsnCallbackState *) soapconn->data_cb; 1228
1517 1229 if (resp != NULL) {
1518 if (soapconn->body == NULL) { 1230 purple_debug_info("MSN CL", "Contact %s added successfully to %s list on server!\n", state->who, MsnMemberRole[state->list_id]);
1519 msn_callback_state_free(state); 1231
1520 return TRUE; 1232 if (state->list_id == MSN_LIST_RL &&
1521 } 1233 (state->action & MSN_DENIED_BUDDY)) {
1522 1234
1523 purple_debug_info("MSN CL", "Contact %s added successfully to %s list on server!\n", state->who, MsnMemberRole[state->list_id]); 1235 msn_add_contact_to_list(state->session->contact, NULL, state->who, MSN_LIST_BL);
1524 1236 } else if (state->list_id == MSN_LIST_AL) {
1525 if (state->list_id == MSN_LIST_RL) { 1237 purple_privacy_permit_add(state->session->account, state->who, TRUE);
1526 MsnUser *user = msn_userlist_find_user(soapconn->session->userlist, state->who); 1238 } else if (state->list_id == MSN_LIST_BL) {
1527 1239 purple_privacy_deny_add(state->session->account, state->who, TRUE);
1528 if (user != NULL) {
1529 msn_user_set_op(user, MSN_LIST_RL_OP);
1530 }
1531
1532 if (state->action & MSN_DENIED_BUDDY) {
1533 g_return_val_if_fail(soapconn->session->contact != NULL, FALSE);
1534
1535 msn_add_contact_to_list(soapconn->session->contact, NULL, state->who, MSN_LIST_BL);
1536 return TRUE;
1537 } 1240 }
1538 } 1241 }
1539 1242
1540 if (state->list_id == MSN_LIST_AL) { 1243 if (state->list_id == MSN_LIST_AL) {
1541 purple_privacy_permit_add(soapconn->session->account, state->who, TRUE); 1244 purple_privacy_permit_add(soapconn->session->account, state->who, TRUE);
1542 } else if (state->list_id == MSN_LIST_BL) { 1245 } else if (state->list_id == MSN_LIST_BL) {
1543 purple_privacy_deny_add(soapconn->session->account, state->who, TRUE); 1246 purple_privacy_deny_add(soapconn->session->account, state->who, TRUE);
1544 } 1247 }
1545 1248
1546 msn_callback_state_free(state); 1249 msn_callback_state_free(state);
1547 msn_soap_free_read_buf(soapconn);
1548 return TRUE;
1549 }
1550
1551
1552 static void
1553 msn_add_contact_to_list_written_cb(MsnSoapConn *soapconn)
1554 {
1555 purple_debug_info("MSN CL","Add contact to list SOAP request sent!\n");
1556 soapconn->read_cb = msn_add_contact_to_list_read_cb;
1557 } 1250 }
1558 1251
1559 void 1252 void
1560 msn_add_contact_to_list(MsnContact *contact, MsnCallbackState *state, 1253 msn_add_contact_to_list(MsnContact *contact, MsnCallbackState *state,
1561 const gchar *passport, const MsnListId list) 1254 const gchar *passport, const MsnListId list)
1562 { 1255 {
1563 MsnSoapReq *soap_request;
1564 gchar *body = NULL, *member = NULL; 1256 gchar *body = NULL, *member = NULL;
1565 MsnSoapPartnerScenario partner_scenario; 1257 MsnSoapPartnerScenario partner_scenario;
1566 1258
1567 g_return_if_fail(contact != NULL); 1259 g_return_if_fail(contact != NULL);
1568 g_return_if_fail(passport != NULL); 1260 g_return_if_fail(passport != NULL);
1569 g_return_if_fail(list < 5); 1261 g_return_if_fail(list < 5);
1570 1262
1571 purple_debug_info("MSN CL", "Adding contact %s to %s list\n", passport, MsnMemberRole[list]); 1263 purple_debug_info("MSN CL", "Adding contact %s to %s list\n", passport, MsnMemberRole[list]);
1572 1264
1573 if (state == NULL) { 1265 if (state == NULL) {
1574 state = msn_callback_state_new(); 1266 state = msn_callback_state_new(contact->session);
1575 } 1267 }
1576 msn_callback_state_set_list_id(state, list); 1268 msn_callback_state_set_list_id(state, list);
1577 msn_callback_state_set_who(state, passport); 1269 msn_callback_state_set_who(state, passport);
1578 1270
1579 partner_scenario = (list == MSN_LIST_RL) ? MSN_PS_CONTACT_API : MSN_PS_BLOCK_UNBLOCK; 1271 partner_scenario = (list == MSN_LIST_RL) ? MSN_PS_CONTACT_API : MSN_PS_BLOCK_UNBLOCK;
1583 body = g_strdup_printf(MSN_CONTACT_ADD_TO_LIST_TEMPLATE, 1275 body = g_strdup_printf(MSN_CONTACT_ADD_TO_LIST_TEMPLATE,
1584 MsnSoapPartnerScenarioText[partner_scenario], 1276 MsnSoapPartnerScenarioText[partner_scenario],
1585 MsnMemberRole[list], 1277 MsnMemberRole[list],
1586 member); 1278 member);
1587 1279
1280 msn_soap_message_send(contact->session,
1281 msn_soap_message_new(MSN_ADD_MEMBER_TO_LIST_SOAP_ACTION,
1282 xmlnode_from_str(body, -1)),
1283 MSN_CONTACT_SERVER, MSN_SHARE_POST_URL,
1284 msn_add_contact_to_list_read_cb, state);
1285
1588 g_free(member); 1286 g_free(member);
1589
1590 soap_request = msn_soap_request_new( MSN_CONTACT_SERVER,
1591 MSN_SHARE_POST_URL,
1592 MSN_ADD_MEMBER_TO_LIST_SOAP_ACTION,
1593 body,
1594 state,
1595 msn_add_contact_to_list_read_cb,
1596 msn_add_contact_to_list_written_cb,
1597 msn_contact_connect_init);
1598
1599 msn_soap_post(contact->soapconn, soap_request);
1600
1601 g_free(body); 1287 g_free(body);
1602 } 1288 }
1603
1604 1289
1605 #if 0 1290 #if 0
1606 static gboolean 1291 static gboolean
1607 msn_gleams_read_cb(MsnSoapConn * soapconn) 1292 msn_gleams_read_cb(MsnSoapConn * soapconn)
1608 { 1293 {
1609 purple_debug_info("MSN CL","Gleams read done\n"); 1294 purple_debug_info("MSN CL","Gleams read done\n");
1610 return TRUE; 1295 return TRUE;
1611 } 1296 }
1612 1297
1613 static void 1298 static void
1614 msn_gleams_written_cb(MsnSoapConn * soapconn) 1299 msn_gleams_read_cb(MsnSoapMessage *req, MsnSoapMessage *resp, gpointer data)
1615 { 1300 {
1616 purple_debug_info("MSNP14","finish Group written\n"); 1301 if (resp != NULL)
1617 soapconn->read_cb = msn_gleams_read_cb; 1302 purple_debug_info("MSNP14","Gleams read done\n");
1618 // msn_soap_read_cb(data,source,cond); 1303 else
1304 purple_debug_info("MSNP14","Gleams read failed\n");
1619 } 1305 }
1620 1306
1621 /*get the gleams info*/ 1307 /*get the gleams info*/
1622 void 1308 void
1623 msn_get_gleams(MsnContact *contact) 1309 msn_get_gleams(MsnContact *contact)
1624 { 1310 {
1625 MsnSoapReq *soap_request; 1311 MsnSoapReq *soap_request;
1626 1312
1627 purple_debug_info("MSNP14","msn get gleams info...\n"); 1313 purple_debug_info("MSNP14","msn get gleams info...\n");
1628 /*build SOAP and POST it*/ 1314 msn_soap_message_send(contact->session,
1629 soap_request = msn_soap_request_new(MSN_CONTACT_SERVER, 1315 msn_soap_message_new(MSN_GET_GLEAMS_SOAP_ACTION,
1630 MSN_ADDRESS_BOOK_POST_URL, 1316 xmlnode_from_str(MSN_GLEAMS_TEMPLATE, -1)),
1631 MSN_GET_GLEAMS_SOAP_ACTION, 1317 MSN_CONTACT_SERVER, MSN_ADDRESS_BOOK_POST_URL,
1632 MSN_GLEAMS_TEMPLATE, 1318 msn_gleams_read_cb, NULL);
1633 NULL,
1634 msn_gleams_read_cb,
1635 msn_gleams_written_cb,
1636 msn_contact_connect_init);
1637 msn_soap_post(contact->soapconn,soap_request);
1638 } 1319 }
1639 #endif 1320 #endif
1640 1321
1641 1322
1642 /*************************************************************** 1323 /***************************************************************
1643 * Group Operations 1324 * Group Operations
1644 ***************************************************************/ 1325 ***************************************************************/
1645 1326
1646 static gboolean 1327 static void
1647 msn_group_read_cb(MsnSoapConn *soapconn) 1328 msn_group_read_cb(MsnSoapMessage *req, MsnSoapMessage *resp, gpointer data)
1648 { 1329 {
1649 MsnUserList *userlist; 1330 MsnCallbackState *state = data;
1650 MsnCallbackState *state = NULL; 1331
1651 1332 purple_debug_info("MSNCL", "Group request successful.\n");
1652 purple_debug_info("MSN CL", "Group request successful.\n"); 1333
1653 1334 g_return_if_fail(state->session != NULL);
1654 g_return_val_if_fail(soapconn->session != NULL, FALSE); 1335 g_return_if_fail(state->session->userlist != NULL);
1655 g_return_val_if_fail(soapconn->session->userlist != NULL, TRUE); 1336 g_return_if_fail(state->session->contact != NULL);
1656 g_return_val_if_fail(soapconn->session->contact != NULL, FALSE); 1337
1657 1338 if (resp == NULL) {
1658 state = (MsnCallbackState *) soapconn->data_cb;
1659
1660 if (soapconn->body == NULL) {
1661 msn_callback_state_free(state); 1339 msn_callback_state_free(state);
1662 return TRUE; 1340 return TRUE;
1663 } 1341 }
1664 1342
1665 if (state) { 1343 if (state) {
1666 userlist = soapconn->session->userlist; 1344 MsnSession *session = state->session;
1345 MsnUserList *userlist = session->userlist;
1667 1346
1668 if (state->action & MSN_RENAME_GROUP) { 1347 if (state->action & MSN_RENAME_GROUP) {
1669 msn_userlist_rename_group_id(soapconn->session->userlist, 1348 msn_userlist_rename_group_id(session->userlist,
1670 state->guid, 1349 state->guid,
1671 state->new_group_name); 1350 state->new_group_name);
1672 } 1351 }
1673 1352
1674 if (state->action & MSN_ADD_GROUP) { 1353 if (state->action & MSN_ADD_GROUP) {
1675 gchar *guid, *endguid; 1354 /* the response is taken from
1676 1355 http://telepathy.freedesktop.org/wiki/Pymsn/MSNP/ContactListActions
1677 guid = g_strstr_len(soapconn->read_buf, soapconn->read_len, "<guid>"); 1356 should copy it to msnpiki some day */
1678 guid += 6; 1357 xmlnode *guid_node = msn_soap_xml_get(resp->xml,
1679 endguid = g_strstr_len(soapconn->read_buf, soapconn->read_len, "</guid>"); 1358 "Body/ABGroupAddResponse/ABGroupAddResult/guid");
1680 *endguid = '\0'; 1359
1681 /* create and add the new group to the userlist */ 1360 if (guid_node) {
1682 purple_debug_info("MSN CL", "Adding group %s with guid = %s to the userlist\n", state->new_group_name, guid); 1361 char *guid = xmlnode_get_data(guid_node);
1683 msn_group_new(soapconn->session->userlist, guid, state->new_group_name); 1362
1684 1363 /* create and add the new group to the userlist */
1685 if (state->action & MSN_ADD_BUDDY) { 1364 purple_debug_info("MSNCL", "Adding group %s with guid = %s to the userlist\n", state->new_group_name, guid);
1686 msn_userlist_add_buddy(soapconn->session->userlist, 1365 msn_group_new(session->userlist, guid, state->new_group_name);
1687 state->who, 1366
1688 state->new_group_name); 1367 if (state->action & MSN_ADD_BUDDY) {
1689 msn_callback_state_free(state); 1368 msn_userlist_add_buddy(session->userlist,
1690 return TRUE; 1369 state->who,
1691 } 1370 state->new_group_name);
1692 1371 msn_callback_state_free(state);
1693 if (state->action & MSN_MOVE_BUDDY) { 1372 } else if (state->action & MSN_MOVE_BUDDY) {
1694 msn_add_contact_to_group(soapconn->session->contact, state, state->who, guid); 1373 msn_add_contact_to_group(session->contact, state, state->who, guid);
1695 return TRUE; 1374 }
1375
1376 g_free(guid);
1377 } else {
1378 purple_debug_info("MSNCL", "Adding group %s failed\n",
1379 state->new_group_name);
1696 } 1380 }
1697 } 1381 }
1698 1382
1699 if (state->action & MSN_DEL_GROUP) { 1383 if (state->action & MSN_DEL_GROUP) {
1700 GList *l; 1384 GList *l;
1701 1385
1702 msn_userlist_remove_group_id(soapconn->session->userlist, state->guid); 1386 msn_userlist_remove_group_id(session->userlist, state->guid);
1703 for (l = userlist->users; l != NULL; l = l->next) { 1387 for (l = userlist->users; l != NULL; l = l->next) {
1704 msn_user_remove_group_id( (MsnUser *)l->data, state->guid); 1388 msn_user_remove_group_id( (MsnUser *)l->data, state->guid);
1705 } 1389 }
1706
1707 } 1390 }
1708 1391
1709 msn_callback_state_free(state); 1392 msn_callback_state_free(state);
1710 } 1393 }
1711
1712 msn_soap_free_read_buf(soapconn);
1713 return TRUE;
1714 }
1715
1716 static void
1717 msn_group_written_cb(MsnSoapConn *soapconn)
1718 {
1719 purple_debug_info("MSN CL","Sent group request.\n");
1720 soapconn->read_cb = msn_group_read_cb;
1721 } 1394 }
1722 1395
1723 /* add group */ 1396 /* add group */
1724 void 1397 void
1725 msn_add_group(MsnSession *session, MsnCallbackState *state, const char* group_name) 1398 msn_add_group(MsnSession *session, MsnCallbackState *state, const char* group_name)
1726 { 1399 {
1727 MsnSoapReq *soap_request;
1728 MsnContact *contact;
1729 char *body = NULL; 1400 char *body = NULL;
1730 gchar *escaped_group_name;
1731 1401
1732 g_return_if_fail(session != NULL); 1402 g_return_if_fail(session != NULL);
1733 g_return_if_fail(group_name != NULL); 1403 g_return_if_fail(group_name != NULL);
1734 1404
1735 contact = session->contact; 1405 purple_debug_info("MSNCL","Adding group %s to contact list.\n", group_name);
1736 purple_debug_info("MSN CL","Adding group %s to contact list.\n", group_name);
1737 1406
1738 if (state == NULL) { 1407 if (state == NULL) {
1739 state = msn_callback_state_new(); 1408 state = msn_callback_state_new(session);
1740 } 1409 }
1741 1410
1742 msn_callback_state_set_action(state, MSN_ADD_GROUP); 1411 msn_callback_state_set_action(state, MSN_ADD_GROUP);
1743 msn_callback_state_set_new_group_name(state, group_name); 1412 msn_callback_state_set_new_group_name(state, group_name);
1744 1413
1745 /* escape group name's html special chars so it can safely be sent 1414 /* escape group name's html special chars so it can safely be sent
1746 * in a XML SOAP request 1415 * in a XML SOAP request
1747 */ 1416 */
1748 escaped_group_name = g_markup_escape_text(group_name, -1); 1417 body = g_markup_printf_escaped(MSN_GROUP_ADD_TEMPLATE, group_name);
1749 body = g_strdup_printf(MSN_GROUP_ADD_TEMPLATE, escaped_group_name); 1418
1750 g_free(escaped_group_name); 1419 msn_soap_message_send(session,
1751 1420 msn_soap_message_new(MSN_GROUP_ADD_SOAP_ACTION,
1752 /*build SOAP and POST it*/ 1421 xmlnode_from_str(body, -1)),
1753 soap_request = msn_soap_request_new(MSN_CONTACT_SERVER, 1422 MSN_CONTACT_SERVER, MSN_ADDRESS_BOOK_POST_URL,
1754 MSN_ADDRESS_BOOK_POST_URL, 1423 msn_group_read_cb, state);
1755 MSN_GROUP_ADD_SOAP_ACTION, 1424
1756 body,
1757 state,
1758 msn_group_read_cb,
1759 msn_group_written_cb,
1760 msn_contact_connect_init);
1761 msn_soap_post(contact->soapconn,soap_request);
1762
1763 g_free(body); 1425 g_free(body);
1764 } 1426 }
1765 1427
1766 /* delete group */ 1428 /* delete group */
1767 void 1429 void
1768 msn_del_group(MsnSession *session, const gchar *group_name) 1430 msn_del_group(MsnSession *session, const gchar *group_name)
1769 { 1431 {
1770 MsnSoapReq *soap_request;
1771 MsnContact *contact;
1772 MsnCallbackState *state; 1432 MsnCallbackState *state;
1773 char *body = NULL; 1433 char *body = NULL;
1774 const gchar *guid; 1434 const gchar *guid;
1775 1435
1776 g_return_if_fail(session != NULL); 1436 g_return_if_fail(session != NULL);
1777 1437
1778 g_return_if_fail(group_name != NULL); 1438 g_return_if_fail(group_name != NULL);
1779 contact = session->contact; 1439 purple_debug_info("MSNCL","Deleting group %s from contact list\n", group_name);
1780 purple_debug_info("MSN CL","Deleting group %s from contact list\n", group_name);
1781 1440
1782 guid = msn_userlist_find_group_id(session->userlist, group_name); 1441 guid = msn_userlist_find_group_id(session->userlist, group_name);
1783 1442
1784 /* if group uid we need to del is NULL, 1443 /* if group uid we need to del is NULL,
1785 * we need to delete nothing 1444 * we need to delete nothing
1786 */ 1445 */
1787 if (guid == NULL) { 1446 if (guid == NULL) {
1788 purple_debug_info("MSN CL", "Group %s guid not found, returning.\n", group_name); 1447 purple_debug_info("MSNCL", "Group %s guid not found, returning.\n", group_name);
1789 return; 1448 return;
1790 } 1449 }
1791 1450
1792 if ( !strcmp(guid, MSN_INDIVIDUALS_GROUP_ID) || !strcmp(guid, MSN_NON_IM_GROUP_ID) ) { 1451 if ( !strcmp(guid, MSN_INDIVIDUALS_GROUP_ID) || !strcmp(guid, MSN_NON_IM_GROUP_ID) ) {
1793 // XXX add back PurpleGroup since it isn't really removed in the server? 1452 // XXX add back PurpleGroup since it isn't really removed in the server?
1794 return; 1453 return;
1795 } 1454 }
1796 1455
1797 state = msn_callback_state_new(); 1456 state = msn_callback_state_new(session);
1798 msn_callback_state_set_action(state, MSN_DEL_GROUP); 1457 msn_callback_state_set_action(state, MSN_DEL_GROUP);
1799 msn_callback_state_set_guid(state, guid); 1458 msn_callback_state_set_guid(state, guid);
1800 1459
1801 body = g_strdup_printf(MSN_GROUP_DEL_TEMPLATE, guid); 1460 body = g_strdup_printf(MSN_GROUP_DEL_TEMPLATE, guid);
1802 /*build SOAP and POST it*/ 1461
1803 soap_request = msn_soap_request_new(MSN_CONTACT_SERVER, 1462 msn_soap_message_send(session,
1804 MSN_ADDRESS_BOOK_POST_URL, 1463 msn_soap_message_new(MSN_GROUP_DEL_SOAP_ACTION,
1805 MSN_GROUP_DEL_SOAP_ACTION, 1464 xmlnode_from_str(body, -1)),
1806 body, 1465 MSN_CONTACT_SERVER, MSN_ADDRESS_BOOK_POST_URL,
1807 state, 1466 msn_group_read_cb, state);
1808 msn_group_read_cb,
1809 msn_group_written_cb,
1810 msn_contact_connect_init);
1811 msn_soap_post(contact->soapconn, soap_request);
1812 1467
1813 g_free(body); 1468 g_free(body);
1814 } 1469 }
1815 1470
1816 /* rename group */ 1471 /* rename group */
1817 void 1472 void
1818 msn_contact_rename_group(MsnSession *session, const char *old_group_name, const char *new_group_name) 1473 msn_contact_rename_group(MsnSession *session, const char *old_group_name, const char *new_group_name)
1819 { 1474 {
1820 MsnSoapReq *soap_request; 1475 gchar *body = NULL;
1821 MsnContact *contact;
1822 gchar * escaped_group_name, *body = NULL;
1823 const gchar * guid; 1476 const gchar * guid;
1824 MsnCallbackState *state = msn_callback_state_new(); 1477 MsnCallbackState *state;
1825 1478
1826 g_return_if_fail(session != NULL); 1479 g_return_if_fail(session != NULL);
1827 g_return_if_fail(session->userlist != NULL); 1480 g_return_if_fail(session->userlist != NULL);
1828 g_return_if_fail(old_group_name != NULL); 1481 g_return_if_fail(old_group_name != NULL);
1829 g_return_if_fail(new_group_name != NULL); 1482 g_return_if_fail(new_group_name != NULL);
1830 1483
1831 contact = session->contact;
1832 purple_debug_info("MSN CL", "Renaming group %s to %s.\n", old_group_name, new_group_name); 1484 purple_debug_info("MSN CL", "Renaming group %s to %s.\n", old_group_name, new_group_name);
1833 1485
1834 guid = msn_userlist_find_group_id(session->userlist, old_group_name); 1486 guid = msn_userlist_find_group_id(session->userlist, old_group_name);
1835 if (guid == NULL) 1487 if (guid == NULL)
1836 return; 1488 return;
1837 1489
1490 state = msn_callback_state_new(session);
1838 msn_callback_state_set_guid(state, guid); 1491 msn_callback_state_set_guid(state, guid);
1839 msn_callback_state_set_new_group_name(state, new_group_name); 1492 msn_callback_state_set_new_group_name(state, new_group_name);
1840 1493
1841 if ( !strcmp(guid, MSN_INDIVIDUALS_GROUP_ID) || !strcmp(guid, MSN_NON_IM_GROUP_ID) ) { 1494 if ( !strcmp(guid, MSN_INDIVIDUALS_GROUP_ID) || !strcmp(guid, MSN_NON_IM_GROUP_ID) ) {
1842 msn_add_group(session, state, new_group_name); 1495 msn_add_group(session, state, new_group_name);
1843 // XXX move every buddy there (we probably need to fix concurrent SOAP reqs first) 1496 // XXX move every buddy there (we probably need to fix concurrent SOAP reqs first)
1844 } 1497 }
1845 1498
1846 msn_callback_state_set_action(state, MSN_RENAME_GROUP); 1499 msn_callback_state_set_action(state, MSN_RENAME_GROUP);
1847 1500
1848 /* escape group name's html special chars so it can safely be sent 1501 body = g_markup_printf_escaped(MSN_GROUP_RENAME_TEMPLATE,
1849 * in a XML SOAP request 1502 guid, new_group_name);
1850 */ 1503
1851 escaped_group_name = g_markup_escape_text(new_group_name, -1); 1504 msn_soap_message_send(session,
1852 1505 msn_soap_message_new(MSN_GROUP_RENAME_SOAP_ACTION,
1853 body = g_strdup_printf(MSN_GROUP_RENAME_TEMPLATE, guid, escaped_group_name); 1506 xmlnode_from_str(body, -1)),
1854 1507 MSN_CONTACT_SERVER, MSN_ADDRESS_BOOK_POST_URL,
1855 soap_request = msn_soap_request_new(MSN_CONTACT_SERVER, 1508 msn_group_read_cb, state);
1856 MSN_ADDRESS_BOOK_POST_URL, 1509
1857 MSN_GROUP_RENAME_SOAP_ACTION,
1858 body,
1859 state,
1860 msn_group_read_cb,
1861 msn_group_written_cb,
1862 msn_contact_connect_init);
1863 msn_soap_post(contact->soapconn, soap_request);
1864
1865 g_free(escaped_group_name);
1866 g_free(body); 1510 g_free(body);
1867 } 1511 }
1868
1869 void
1870 msn_contact_connect_init(MsnSoapConn *soapconn)
1871 {
1872 msn_soap_init(soapconn, MSN_CONTACT_SERVER, TRUE,
1873 msn_contact_login_connect_cb,
1874 msn_contact_login_error_cb);
1875 }