Mercurial > pidgin
diff libpurple/protocols/yahoo/yahoo.c @ 15623:71af5b6209d5
uri-handler support for AIM/ICQ, Yahoo and MSN
author | Daniel Atallah <daniel.atallah@gmail.com> |
---|---|
date | Sun, 11 Feb 2007 21:58:50 +0000 |
parents | 2193394fd427 |
children | 12778e2f7282 |
line wrap: on
line diff
--- a/libpurple/protocols/yahoo/yahoo.c Sun Feb 11 19:34:43 2007 +0000 +++ b/libpurple/protocols/yahoo/yahoo.c Sun Feb 11 21:58:50 2007 +0000 @@ -28,6 +28,7 @@ #include "blist.h" #include "cipher.h" #include "cmds.h" +#include "core.h" #include "debug.h" #include "notify.h" #include "privacy.h" @@ -3794,6 +3795,107 @@ _("doodle: Request user to start a Doodle session"), NULL); } +static GaimAccount *find_acct(const char *prpl, const char *acct_id) +{ + GaimAccount *acct = NULL; + + /* If we have a specific acct, use it */ + if (acct_id) { + acct = gaim_accounts_find(acct_id, prpl); + if (acct && !gaim_account_is_connected(acct)) + acct = NULL; + } else { /* Otherwise find an active account for the protocol */ + GList *l = gaim_accounts_get_all(); + while (l) { + if (!strcmp(prpl, gaim_account_get_protocol_id(l->data)) + && gaim_account_is_connected(l->data)) { + acct = l->data; + break; + } + l = l->next; + } + } + + return acct; +} + +/* This may not be the best way to do this, but we find the first key w/o a value + * and assume it is the screenname */ +static void yahoo_find_uri_novalue_param(gpointer key, gpointer value, gpointer user_data) +{ + char **retval = user_data; + + if (value == NULL && *retval == NULL) { + *retval = key; + } +} + +static gboolean yahoo_uri_handler(const char *proto, const char *cmd, GHashTable *params) +{ + char *acct_id = g_hash_table_lookup(params, "account"); + GaimAccount *acct; + + if (g_ascii_strcasecmp(proto, "ymsgr")) + return FALSE; + + acct = find_acct(gaim_plugin_get_id(my_protocol), acct_id); + + if (!acct) + return FALSE; + + /* ymsgr:SendIM?screename&m=The+Message */ + if (!g_ascii_strcasecmp(cmd, "SendIM")) { + char *sname = NULL; + g_hash_table_foreach(params, yahoo_find_uri_novalue_param, &sname); + if (sname) { + char *message = g_hash_table_lookup(params, "m"); + + GaimConversation *conv = gaim_find_conversation_with_account( + GAIM_CONV_TYPE_IM, sname, acct); + if (conv == NULL) + conv = gaim_conversation_new(GAIM_CONV_TYPE_IM, acct, sname); + gaim_conversation_present(conv); + + if (message) { + /* Spaces are encoded as '+' */ + g_strdelimit(message, "+", ' '); + gaim_conv_im_send(GAIM_CONV_IM(conv), message); + } + } + /*else + **If pidgindialogs_im() was in the core, we could use it here. + * It is all gaim_request_* based, but I'm not sure it really belongs in the core + pidgindialogs_im();*/ + + return TRUE; + } + /* ymsgr:Chat?roomname */ + else if (!g_ascii_strcasecmp(cmd, "Chat")) { + char *rname = NULL; + g_hash_table_foreach(params, yahoo_find_uri_novalue_param, &rname); + if (rname) { + /* This is somewhat hacky, but the params aren't useful after this command */ + g_hash_table_insert(params, g_strdup("room"), g_strdup(rname)); + g_hash_table_insert(params, g_strdup("type"), g_strdup("Chat")); + serv_join_chat(gaim_account_get_connection(acct), params); + } + /*else + ** Same as above (except that this would have to be re-written using gaim_request_*) + pidgin_blist_joinchat_show(); */ + + return TRUE; + } + /* ymsgr:AddFriend?name */ + else if (!g_ascii_strcasecmp(cmd, "AddFriend")) { + char *name = NULL; + g_hash_table_foreach(params, yahoo_find_uri_novalue_param, &name); + gaim_blist_request_add_buddy(acct, name, NULL, NULL); + return TRUE; + } + + return FALSE; +} + static GaimWhiteboardPrplOps yahoo_whiteboard_prpl_ops = { yahoo_doodle_start, @@ -3950,6 +4052,9 @@ my_protocol = plugin; yahoogaim_register_commands(); yahoo_init_colorht(); + + gaim_signal_connect(gaim_get_core(), "uri-handler", plugin, + GAIM_CALLBACK(yahoo_uri_handler), NULL); } GAIM_INIT_PLUGIN(yahoo, init_plugin, info);