comparison mcabber/mcabber/xmpp.c @ 1691:b2e0083891cc

Replace JEP with XEP
author Mikael Berthe <mikael@lilotux.net>
date Sat, 06 Feb 2010 18:16:06 +0100
parents b8f9481dd0fe
children 32c6d81bd1ef
comparison
equal deleted inserted replaced
1690:46f1cf3b6373 1691:b2e0083891cc
298 LmMessage *x; 298 LmMessage *x;
299 LmMessageSubType subtype; 299 LmMessageSubType subtype;
300 #ifdef HAVE_LIBOTR 300 #ifdef HAVE_LIBOTR
301 int otr_msg = 0; 301 int otr_msg = 0;
302 #endif 302 #endif
303 #if defined HAVE_GPGME || defined JEP0022 || defined JEP0085 303 #if defined HAVE_GPGME || defined XEP0022 || defined XEP0085
304 char *rname, *barejid; 304 char *rname, *barejid;
305 GSList *sl_buddy; 305 GSList *sl_buddy;
306 #endif 306 #endif
307 #if defined JEP0022 || defined JEP0085 307 #if defined XEP0022 || defined XEP0085
308 LmMessageNode *event; 308 LmMessageNode *event;
309 guint use_jep85 = 0; 309 guint use_jep85 = 0;
310 struct jep0085 *jep85 = NULL; 310 struct jep0085 *jep85 = NULL;
311 #endif 311 #endif
312 gchar *enc = NULL; 312 gchar *enc = NULL;
328 else 328 else
329 subtype = LM_MESSAGE_SUB_TYPE_CHAT; 329 subtype = LM_MESSAGE_SUB_TYPE_CHAT;
330 } 330 }
331 331
332 #if defined HAVE_GPGME || defined HAVE_LIBOTR || \ 332 #if defined HAVE_GPGME || defined HAVE_LIBOTR || \
333 defined JEP0022 || defined JEP0085 333 defined XEP0022 || defined XEP0085
334 rname = strchr(fjid, JID_RESOURCE_SEPARATOR); 334 rname = strchr(fjid, JID_RESOURCE_SEPARATOR);
335 barejid = jidtodisp(fjid); 335 barejid = jidtodisp(fjid);
336 sl_buddy = roster_find(barejid, jidsearch, ROSTER_TYPE_USER); 336 sl_buddy = roster_find(barejid, jidsearch, ROSTER_TYPE_USER);
337 337
338 // If we can get a resource name, we use it. Else we use NULL, 338 // If we can get a resource name, we use it. Else we use NULL,
385 } 385 }
386 } 386 }
387 #endif // HAVE_GPGME 387 #endif // HAVE_GPGME
388 388
389 g_free(barejid); 389 g_free(barejid);
390 #endif // HAVE_GPGME || defined JEP0022 || defined JEP0085 390 #endif // HAVE_GPGME || defined XEP0022 || defined XEP0085
391 391
392 x = lm_message_new_with_sub_type(fjid, LM_MESSAGE_TYPE_MESSAGE, subtype); 392 x = lm_message_new_with_sub_type(fjid, LM_MESSAGE_TYPE_MESSAGE, subtype);
393 lm_message_node_add_child(x->node, "body", 393 lm_message_node_add_child(x->node, "body",
394 enc ? "This message is PGP-encrypted." : text); 394 enc ? "This message is PGP-encrypted." : text);
395 395
413 (lm_message_node_add_child(x->node, "request", NULL), 413 (lm_message_node_add_child(x->node, "request", NULL),
414 "xmlns", NS_RECEIPTS); 414 "xmlns", NS_RECEIPTS);
415 *xep184 = lm_message_handler_new(cb_xep184, NULL, NULL); 415 *xep184 = lm_message_handler_new(cb_xep184, NULL, NULL);
416 } 416 }
417 417
418 #if defined JEP0022 || defined JEP0085 418 #if defined XEP0022 || defined XEP0085
419 // If typing notifications are disabled, we can skip all this stuff... 419 // If typing notifications are disabled, we can skip all this stuff...
420 if (chatstates_disabled || type == ROSTER_TYPE_ROOM) 420 if (chatstates_disabled || type == ROSTER_TYPE_ROOM)
421 goto xmpp_send_msg_no_chatstates; 421 goto xmpp_send_msg_no_chatstates;
422 422
423 if (sl_buddy) 423 if (sl_buddy)
424 jep85 = buddy_resource_jep85(sl_buddy->data, rname); 424 jep85 = buddy_resource_jep85(sl_buddy->data, rname);
425 #endif 425 #endif
426 426
427 #ifdef JEP0085 427 #ifdef XEP0085
428 /* JEP-0085 5.1 428 /* XEP-0085 5.1
429 * "Until receiving a reply to the initial content message (or a standalone 429 * "Until receiving a reply to the initial content message (or a standalone
430 * notification) from the Contact, the User MUST NOT send subsequent chat 430 * notification) from the Contact, the User MUST NOT send subsequent chat
431 * state notifications to the Contact." 431 * state notifications to the Contact."
432 * In our implementation support is initially "unknown", then it's "probed" 432 * In our implementation support is initially "unknown", then it's "probed"
433 * and can become "ok". 433 * and can become "ok".
441 else 441 else
442 use_jep85 = 1; 442 use_jep85 = 1;
443 jep85->last_state_sent = ROSTER_EVENT_ACTIVE; 443 jep85->last_state_sent = ROSTER_EVENT_ACTIVE;
444 } 444 }
445 #endif 445 #endif
446 #ifdef JEP0022 446 #ifdef XEP0022
447 /* JEP-22 447 /* XEP-22
448 * If the Contact supports JEP-0085, we do not use JEP-0022. 448 * If the Contact supports XEP-0085, we do not use XEP-0022.
449 * If not, we try to fall back to JEP-0022. 449 * If not, we try to fall back to XEP-0022.
450 */ 450 */
451 if (!use_jep85) { 451 if (!use_jep85) {
452 struct jep0022 *jep22 = NULL; 452 struct jep0022 *jep22 = NULL;
453 event = lm_message_node_add_child(x->node, "x", NULL); 453 event = lm_message_node_add_child(x->node, "x", NULL);
454 lm_message_node_set_attribute(event, "xmlns", NS_EVENT); 454 lm_message_node_set_attribute(event, "xmlns", NS_EVENT);
457 if (sl_buddy) 457 if (sl_buddy)
458 jep22 = buddy_resource_jep22(sl_buddy->data, rname); 458 jep22 = buddy_resource_jep22(sl_buddy->data, rname);
459 if (jep22) 459 if (jep22)
460 jep22->last_state_sent = ROSTER_EVENT_ACTIVE; 460 jep22->last_state_sent = ROSTER_EVENT_ACTIVE;
461 461
462 // An id is mandatory when using JEP-0022. 462 // An id is mandatory when using XEP-0022.
463 if (text || subject) { 463 if (text || subject) {
464 const gchar *msgid = lm_message_get_id(x); 464 const gchar *msgid = lm_message_get_id(x);
465 // Let's update last_msgid_sent 465 // Let's update last_msgid_sent
466 if (jep22) { 466 if (jep22) {
467 g_free(jep22->last_msgid_sent); 467 g_free(jep22->last_msgid_sent);
480 } else 480 } else
481 lm_connection_send(lconnection, x, NULL); 481 lm_connection_send(lconnection, x, NULL);
482 lm_message_unref(x); 482 lm_message_unref(x);
483 } 483 }
484 484
485 #ifdef JEP0085 485 #ifdef XEP0085
486 // xmpp_send_jep85_chatstate() 486 // xmpp_send_jep85_chatstate()
487 // Send a JEP-85 chatstate. 487 // Send a XEP-85 chatstate.
488 static void xmpp_send_jep85_chatstate(const char *bjid, const char *resname, 488 static void xmpp_send_jep85_chatstate(const char *bjid, const char *resname,
489 guint state) 489 guint state)
490 { 490 {
491 LmMessage *m; 491 LmMessage *m;
492 LmMessageNode *event; 492 LmMessageNode *event;
516 else if (state == ROSTER_EVENT_COMPOSING) 516 else if (state == ROSTER_EVENT_COMPOSING)
517 chattag = "composing"; 517 chattag = "composing";
518 else if (state == ROSTER_EVENT_PAUSED) 518 else if (state == ROSTER_EVENT_PAUSED)
519 chattag = "paused"; 519 chattag = "paused";
520 else { 520 else {
521 scr_LogPrint(LPRINT_LOGNORM, "Error: unsupported JEP-85 state (%d)", state); 521 scr_LogPrint(LPRINT_LOGNORM, "Error: unsupported XEP-85 state (%d)", state);
522 return; 522 return;
523 } 523 }
524 524
525 jep85->last_state_sent = state; 525 jep85->last_state_sent = state;
526 526
539 539
540 g_free(fjid); 540 g_free(fjid);
541 } 541 }
542 #endif 542 #endif
543 543
544 #ifdef JEP0022 544 #ifdef XEP0022
545 // xmpp_send_jep22_event() 545 // xmpp_send_jep22_event()
546 // Send a JEP-22 message event (delivered, composing...). 546 // Send a XEP-22 message event (delivered, composing...).
547 static void xmpp_send_jep22_event(const char *fjid, guint type) 547 static void xmpp_send_jep22_event(const char *fjid, guint type)
548 { 548 {
549 LmMessage *x; 549 LmMessage *x;
550 LmMessageNode *event; 550 LmMessageNode *event;
551 const char *msgid; 551 const char *msgid;
573 return; // XXX Maybe we could try harder (other resources?) 573 return; // XXX Maybe we could try harder (other resources?)
574 574
575 msgid = jep22->last_msgid_rcvd; 575 msgid = jep22->last_msgid_rcvd;
576 576
577 // For composing events (composing, active, inactive, paused...), 577 // For composing events (composing, active, inactive, paused...),
578 // JEP22 only has 2 states; we'll use composing and active. 578 // XEP22 only has 2 states; we'll use composing and active.
579 if (type == ROSTER_EVENT_COMPOSING) 579 if (type == ROSTER_EVENT_COMPOSING)
580 jep22_state = ROSTER_EVENT_COMPOSING; 580 jep22_state = ROSTER_EVENT_COMPOSING;
581 else if (type == ROSTER_EVENT_ACTIVE || 581 else if (type == ROSTER_EVENT_ACTIVE ||
582 type == ROSTER_EVENT_PAUSED) 582 type == ROSTER_EVENT_PAUSED)
583 jep22_state = ROSTER_EVENT_ACTIVE; 583 jep22_state = ROSTER_EVENT_ACTIVE;
606 lm_message_unref(x); 606 lm_message_unref(x);
607 } 607 }
608 #endif 608 #endif
609 609
610 // xmpp_send_chatstate(buddy, state) 610 // xmpp_send_chatstate(buddy, state)
611 // Send a chatstate or event (JEP-22/85) according to the buddy's capabilities. 611 // Send a chatstate or event (XEP-22/85) according to the buddy's capabilities.
612 // The message is sent to one of the resources with the highest priority. 612 // The message is sent to one of the resources with the highest priority.
613 #if defined JEP0022 || defined JEP0085 613 #if defined XEP0022 || defined XEP0085
614 void xmpp_send_chatstate(gpointer buddy, guint chatstate) 614 void xmpp_send_chatstate(gpointer buddy, guint chatstate)
615 { 615 {
616 const char *bjid; 616 const char *bjid;
617 #ifdef JEP0085 617 #ifdef XEP0085
618 GSList *resources, *p_res, *p_next; 618 GSList *resources, *p_res, *p_next;
619 struct jep0085 *jep85 = NULL; 619 struct jep0085 *jep85 = NULL;
620 #endif 620 #endif
621 #ifdef JEP0022 621 #ifdef XEP0022
622 struct jep0022 *jep22; 622 struct jep0022 *jep22;
623 #endif 623 #endif
624 624
625 bjid = buddy_getjid(buddy); 625 bjid = buddy_getjid(buddy);
626 if (!bjid) return; 626 if (!bjid) return;
627 627
628 #ifdef JEP0085 628 #ifdef XEP0085
629 /* Send the chatstate to the last resource (which should have the highest 629 /* Send the chatstate to the last resource (which should have the highest
630 priority). 630 priority).
631 If chatstate is "active", send an "active" state to all resources 631 If chatstate is "active", send an "active" state to all resources
632 which do not curently have this state. 632 which do not curently have this state.
633 */ 633 */
644 } 644 }
645 g_free(p_res->data); 645 g_free(p_res->data);
646 } 646 }
647 g_slist_free(resources); 647 g_slist_free(resources);
648 // If the last resource had chatstates support when can return now, 648 // If the last resource had chatstates support when can return now,
649 // we don't want to send a JEP22 event. 649 // we don't want to send a XEP22 event.
650 if (jep85 && jep85->support == CHATSTATES_SUPPORT_OK) 650 if (jep85 && jep85->support == CHATSTATES_SUPPORT_OK)
651 return; 651 return;
652 #endif 652 #endif
653 #ifdef JEP0022 653 #ifdef XEP0022
654 jep22 = buddy_resource_jep22(buddy, NULL); 654 jep22 = buddy_resource_jep22(buddy, NULL);
655 if (jep22 && jep22->support == CHATSTATES_SUPPORT_OK) { 655 if (jep22 && jep22->support == CHATSTATES_SUPPORT_OK) {
656 xmpp_send_jep22_event(bjid, chatstate); 656 xmpp_send_jep22_event(bjid, chatstate);
657 } 657 }
658 #endif 658 #endif
659 } 659 }
660 #endif 660 #endif
661 661
662 662
663 // chatstates_reset_probed(fulljid) 663 // chatstates_reset_probed(fulljid)
664 // If the JEP has been probed for this contact, set it back to unknown so 664 // If the XEP has been probed for this contact, set it back to unknown so
665 // that we probe it again. The parameter must be a full jid (w/ resource). 665 // that we probe it again. The parameter must be a full jid (w/ resource).
666 #if defined JEP0022 || defined JEP0085 666 #if defined XEP0022 || defined XEP0085
667 static void chatstates_reset_probed(const char *fulljid) 667 static void chatstates_reset_probed(const char *fulljid)
668 { 668 {
669 char *rname, *barejid; 669 char *rname, *barejid;
670 GSList *sl_buddy; 670 GSList *sl_buddy;
671 struct jep0085 *jep85; 671 struct jep0085 *jep85;
938 scr_LogPrint(LPRINT_NORMAL, "Disconnected, reason:%d->'%s'\n", reason, str); 938 scr_LogPrint(LPRINT_NORMAL, "Disconnected, reason:%d->'%s'\n", reason, str);
939 } 939 }
940 940
941 static void handle_state_events(const char *from, LmMessageNode *node) 941 static void handle_state_events(const char *from, LmMessageNode *node)
942 { 942 {
943 #if defined JEP0022 || defined JEP0085 943 #if defined XEP0022 || defined XEP0085
944 LmMessageNode *state_ns = NULL; 944 LmMessageNode *state_ns = NULL;
945 const char *body; 945 const char *body;
946 char *rname, *bjid; 946 char *rname, *bjid;
947 GSList *sl_buddy; 947 GSList *sl_buddy;
948 guint events; 948 guint events;
949 struct jep0022 *jep22 = NULL; 949 struct jep0022 *jep22 = NULL;
950 struct jep0085 *jep85 = NULL; 950 struct jep0085 *jep85 = NULL;
951 enum { 951 enum {
952 JEP_none, 952 XEP_none,
953 JEP_85, 953 XEP_85,
954 JEP_22 954 XEP_22
955 } which_jep = JEP_none; 955 } which_jep = XEP_none;
956 956
957 rname = strchr(from, JID_RESOURCE_SEPARATOR); 957 rname = strchr(from, JID_RESOURCE_SEPARATOR);
958 if (rname) 958 if (rname)
959 ++rname; 959 ++rname;
960 else 960 else
962 bjid = jidtodisp(from); 962 bjid = jidtodisp(from);
963 sl_buddy = roster_find(bjid, jidsearch, ROSTER_TYPE_USER); 963 sl_buddy = roster_find(bjid, jidsearch, ROSTER_TYPE_USER);
964 g_free(bjid); 964 g_free(bjid);
965 965
966 /* XXX Actually that's wrong, since it filters out server "offline" 966 /* XXX Actually that's wrong, since it filters out server "offline"
967 messages (for JEP-0022). This JEP is (almost) deprecated so 967 messages (for XEP-0022). This XEP is (almost) deprecated so
968 we don't really care. */ 968 we don't really care. */
969 if (!sl_buddy) { 969 if (!sl_buddy) {
970 return; 970 return;
971 } 971 }
972 972
973 /* Let's see chich JEP the contact uses. If possible, we'll use 973 /* Let's see chich XEP the contact uses. If possible, we'll use
974 JEP-85, if not we'll look for JEP-22 support. */ 974 XEP-85, if not we'll look for XEP-22 support. */
975 events = buddy_resource_getevents(sl_buddy->data, rname); 975 events = buddy_resource_getevents(sl_buddy->data, rname);
976 976
977 jep85 = buddy_resource_jep85(sl_buddy->data, rname); 977 jep85 = buddy_resource_jep85(sl_buddy->data, rname);
978 if (jep85) { 978 if (jep85) {
979 state_ns = lm_message_node_find_xmlns(node, NS_CHATSTATES); 979 state_ns = lm_message_node_find_xmlns(node, NS_CHATSTATES);
980 if (state_ns) 980 if (state_ns)
981 which_jep = JEP_85; 981 which_jep = XEP_85;
982 } 982 }
983 983
984 if (which_jep != JEP_85) { /* Fall back to JEP-0022 */ 984 if (which_jep != XEP_85) { /* Fall back to XEP-0022 */
985 jep22 = buddy_resource_jep22(sl_buddy->data, rname); 985 jep22 = buddy_resource_jep22(sl_buddy->data, rname);
986 if (jep22) { 986 if (jep22) {
987 state_ns = lm_message_node_find_xmlns(node, NS_EVENT); 987 state_ns = lm_message_node_find_xmlns(node, NS_EVENT);
988 if (state_ns) 988 if (state_ns)
989 which_jep = JEP_22; 989 which_jep = XEP_22;
990 } 990 }
991 } 991 }
992 992
993 if (!which_jep) { /* Sender does not use chat states */ 993 if (!which_jep) { /* Sender does not use chat states */
994 return; 994 return;
995 } 995 }
996 996
997 body = lm_message_node_get_child_value(node, "body"); 997 body = lm_message_node_get_child_value(node, "body");
998 998
999 if (which_jep == JEP_85) { /* JEP-0085 */ 999 if (which_jep == XEP_85) { /* XEP-0085 */
1000 jep85->support = CHATSTATES_SUPPORT_OK; 1000 jep85->support = CHATSTATES_SUPPORT_OK;
1001 1001
1002 if (!strcmp(state_ns->name, "composing")) { 1002 if (!strcmp(state_ns->name, "composing")) {
1003 jep85->last_state_rcvd = ROSTER_EVENT_COMPOSING; 1003 jep85->last_state_rcvd = ROSTER_EVENT_COMPOSING;
1004 } else if (!strcmp(state_ns->name, "active")) { 1004 } else if (!strcmp(state_ns->name, "active")) {
1009 jep85->last_state_rcvd = ROSTER_EVENT_INACTIVE; 1009 jep85->last_state_rcvd = ROSTER_EVENT_INACTIVE;
1010 } else if (!strcmp(state_ns->name, "gone")) { 1010 } else if (!strcmp(state_ns->name, "gone")) {
1011 jep85->last_state_rcvd = ROSTER_EVENT_GONE; 1011 jep85->last_state_rcvd = ROSTER_EVENT_GONE;
1012 } 1012 }
1013 events = jep85->last_state_rcvd; 1013 events = jep85->last_state_rcvd;
1014 } else { /* JEP-0022 */ 1014 } else { /* XEP-0022 */
1015 #ifdef JEP0022 1015 #ifdef XEP0022
1016 const char *msgid; 1016 const char *msgid;
1017 jep22->support = CHATSTATES_SUPPORT_OK; 1017 jep22->support = CHATSTATES_SUPPORT_OK;
1018 jep22->last_state_rcvd = ROSTER_EVENT_NONE; 1018 jep22->last_state_rcvd = ROSTER_EVENT_NONE;
1019 1019
1020 msgid = lm_message_node_get_attribute(node, "id"); 1020 msgid = lm_message_node_get_attribute(node, "id");
1231 timestamp = lm_message_node_get_timestamp(m->node); 1231 timestamp = lm_message_node_get_timestamp(m->node);
1232 1232
1233 if (mstype == LM_MESSAGE_SUB_TYPE_ERROR) { 1233 if (mstype == LM_MESSAGE_SUB_TYPE_ERROR) {
1234 x = lm_message_node_get_child(m->node, "error"); 1234 x = lm_message_node_get_child(m->node, "error");
1235 display_server_error(x); 1235 display_server_error(x);
1236 #if defined JEP0022 || defined JEP0085 1236 #if defined XEP0022 || defined XEP0085
1237 // If the JEP85/22 support is probed, set it back to unknown so that 1237 // If the XEP85/22 support is probed, set it back to unknown so that
1238 // we probe it again. 1238 // we probe it again.
1239 chatstates_reset_probed(from); 1239 chatstates_reset_probed(from);
1240 #endif 1240 #endif
1241 } else { 1241 } else {
1242 handle_state_events(from, m->node); 1242 handle_state_events(from, m->node);