soc.2009.transport: 6d81c0a3: Better order in User::receivedPresence a...
hanzz at soc.pidgin.im
hanzz at soc.pidgin.im
Tue Jul 14 13:05:48 EDT 2009
-----------------------------------------------------------------
Revision: 6d81c0a370fe09bfb2ac55f406691e29ea7cc7ae
Ancestor: 9b79ee59b6c40b373c609d487979d63fd22307f0
Author: hanzz at soc.pidgin.im
Date: 2009-07-14T10:17:34
Branch: im.pidgin.soc.2009.transport
URL: http://d.pidgin.im/viewmtn/revision/info/6d81c0a370fe09bfb2ac55f406691e29ea7cc7ae
Modified files:
protocols/irc.cpp user.cpp user.h
ChangeLog:
Better order in User::receivedPresence and independent receivedPresence handler for IRC
-------------- next part --------------
============================================================
--- protocols/irc.cpp f95d3d8e4f56dced0ce40fe439c16ee9ed7997c6
+++ protocols/irc.cpp d3d011c5e921d54c5b2ec67256ad7f876601fdc3
@@ -21,6 +21,7 @@
#include "irc.h"
#include "../main.h"
#include "../muchandler.h"
+#include "../usermanager.h"
IRCProtocol::IRCProtocol(GlooxMessageHandler *main){
m_main = main;
@@ -93,6 +94,7 @@ bool IRCProtocol::onPresenceReceived(Use
}
bool IRCProtocol::onPresenceReceived(User *user, const Presence &stanza) {
+ Tag *stanzaTag = stanza.tag();
if (stanza.to().username()!="") {
IRCProtocolData *data = (IRCProtocolData *) user->protocolData();
GHashTable *m_mucs = user->mucs();
@@ -120,11 +122,121 @@ bool IRCProtocol::onPresenceReceived(Use
}
}
}
- return false;
+
+ // this presence is for the transport
+ if ( !tempAccountsAllowed() || isMUC(NULL, stanza.to().bare()) ){
+ if(stanza.presence() == Presence::Unavailable) {
+ // disconnect from legacy network if we are connected
+ if (user->isConnected()) {
+ if (g_hash_table_size(user->mucs()) == 0) {
+ Log().Get(user->jid()) << "disconecting";
+ purple_account_disconnect(user->account());
+ m_main->userManager()->removeUserTimer(user);
+ }
+// else {
+// iter = m_resources.begin();
+// m_resource=(*iter).first;
+// }
+ }
+ else {
+ if (!user->resources().empty() && int(time(NULL))>int(user->connectionStart())+10){
+ std::map<std::string,Resource> ::iterator iter = user->resources().begin();
+ iter = user->resources().begin();
+ std::string res = (*iter).first;
+ user->setActiveResource(res);
+ }
+ else if (user->account()){
+ Log().Get(user->jid()) << "disconecting2";
+ purple_account_disconnect(user->account());
+ }
+ }
+ } else {
+ std::string resource = stanza.from().resource();
+ std::map<std::string,Resource> ::iterator iter = user->resources().begin();
+ iter = user->resources().find(resource);
+ if(iter == user->resources().end()){
+ user->resources()[resource].priority = stanza.priority();
+ Tag *c = stanzaTag->findChildWithAttrib("xmlns","http://jabber.org/protocol/caps");
+ // presence has caps
+ if (c!=NULL){
+ if (m_main->hasCaps(c->findAttribute("ver"))){
+ user->resources()[resource].capsVersion = c->findAttribute("ver");
+ }
+ }
+ if (user->resources()[resource].priority > user->resources()[user->resource()].priority)
+ user->setActiveResource(resource);
+ }
+
+ Log().Get(user->jid()) << "resource: " << user->resource();
+ if (!user->isConnected()) {
+ // we are not connected to legacy network, so we should do it when disco#info arrive :)
+ Log().Get(user->jid()) << "connecting: resource=" << user->resource();
+ if (user->readyForConnect()==false){
+ user->setReadyForConnect(true);
+ if (user->getResource().capsVersion.empty()){
+ // caps not arrived yet, so we can't connect just now and we have to wait for caps
+ }
+ else{
+ user->connect();
+ }
+ }
+ }
+ else {
+ Log().Get(user->jid()) << "mirroring presence to legacy network";
+ // we are already connected so we have to change status
+ PurpleSavedStatus *status;
+ int PurplePresenceType;
+ std::string statusMessage;
+
+ // mirror presence types
+ switch(stanza.presence()) {
+ case Presence::Available: {
+ PurplePresenceType=PURPLE_STATUS_AVAILABLE;
+ break;
+ }
+ case Presence::Chat: {
+ PurplePresenceType=PURPLE_STATUS_AVAILABLE;
+ break;
+ }
+ case Presence::Away: {
+ PurplePresenceType=PURPLE_STATUS_AWAY;
+ break;
+ }
+ case Presence::DND: {
+ PurplePresenceType=PURPLE_STATUS_UNAVAILABLE;
+ break;
+ }
+ case Presence::XA: {
+ PurplePresenceType=PURPLE_STATUS_EXTENDED_AWAY;
+ break;
+ }
+ default: break;
+ }
+ // send presence to our legacy network
+ status = purple_savedstatus_new(NULL, (PurpleStatusPrimitive)PurplePresenceType);
+
+ statusMessage.clear();
+
+ if (user->hasTransportFeature(TRANSPORT_MANGLE_STATUS)) {
+ m_main->sql()->getRandomStatus(statusMessage);
+ statusMessage.append(" - ");
+ }
+
+ statusMessage.append(stanza.status());
+
+ if (!statusMessage.empty())
+ purple_savedstatus_set_message(status,statusMessage.c_str());
+ purple_savedstatus_activate_for_account(status,user->account());
+ }
+ }
+ }
+ delete stanzaTag;
+ return true;
}
void IRCProtocol::onDestroy(User *user) {
- delete user->protocolData();
+ IRCProtocolData *data = (IRCProtocolData *) user->protocolData();
+ delete data;
}
============================================================
--- user.cpp c9338d2e560bd740805757911c09b82be3f05dde
+++ user.cpp b75f2979ddcc65d9d120b712d8df4e28d5f4f4e9
@@ -1053,8 +1053,18 @@ void User::receivedPresence(const Presen
*/
void User::receivedPresence(const Presence &stanza){
- if (p->protocol()->onPresenceReceived(this, stanza))
+
+ Tag *stanzaTag = stanza.tag();
+ if (!stanzaTag)
return;
+ if (m_lang == NULL) {
+ std::string lang = stanzaTag->findAttribute("xml:lang");
+ if (lang == "")
+ lang = "en";
+ setLang(lang.c_str());
+ localization.loadLocale(getLang());
+ Log().Get("LANG") << lang << " " << lang.c_str();
+ }
if (m_connected){
@@ -1082,16 +1092,9 @@ void User::receivedPresence(const Presen
}
}
- Tag *stanzaTag = stanza.tag();
- if (!stanzaTag)
+ if (p->protocol()->onPresenceReceived(this, stanza)) {
+ delete stanzaTag;
return;
- if (m_lang == NULL) {
- std::string lang = stanzaTag->findAttribute("xml:lang");
- if (lang == "")
- lang = "en";
- setLang(lang.c_str());
- localization.loadLocale(getLang());
- Log().Get("LANG") << lang << " " << lang.c_str();
}
// this presence is for the transport
============================================================
--- user.h 9b3bb92926f4d285cadb3dad89ed59f0701509a4
+++ user.h b38e79524dc7c25b1e5ab66cf829d89e75b185b4
@@ -142,14 +142,16 @@ class User {
if (priority != -256) m_resources[resource].priority = priority;
if (!caps.empty()) m_resources[resource].capsVersion = caps;
}
+ void setActiveResource(std::string resource) { m_resource = resource; }
bool hasResource(const std::string r) {return m_resources.find(r) != m_resources.end(); }
- Resource & getResource(const std::string r) { return m_resources[r];}
+ Resource & getResource(const std::string r = "") { if (r.empty()) return m_resources[m_resource]; else return m_resources[r];}
PurpleAccount *account() { return m_account; }
std::map<std::string,Resource> & resources() { return m_resources; }
int reconnectCount() { return m_reconnectCount; }
bool isVIP() { return m_vip; }
bool readyForConnect() { return m_readyForConnect; }
+ void setReadyForConnect(bool ready) { m_readyForConnect = ready; }
std::string & username() { return m_username; }
std::string & jid() { return m_jid; }
std::string & resource() { return m_resource; }
More information about the Commits
mailing list