From 3fbab3b40dfc31da46924f13984415b18087a8d4 Mon Sep 17 00:00:00 2001 From: Kevin Smith <git@kismith.co.uk> Date: Thu, 5 Nov 2009 22:05:15 +0000 Subject: A block of the work for roster pushes. Still needs unit testing diff --git a/Swift/Controllers/RosterController.cpp b/Swift/Controllers/RosterController.cpp index 07edcf3..063d2a7 100644 --- a/Swift/Controllers/RosterController.cpp +++ b/Swift/Controllers/RosterController.cpp @@ -35,6 +35,8 @@ RosterController::RosterController(const JID& jid, boost::shared_ptr<XMPPRoster> mainWindow_->onSignOutRequest.connect(boost::bind(boost::ref(onSignOutRequest))); roster_->onUserAction.connect(boost::bind(&RosterController::handleUserAction, this, _1)); xmppRoster_->onJIDAdded.connect(boost::bind(&RosterController::handleOnJIDAdded, this, _1)); + xmppRoster_->onJIDUpdated.connect(boost::bind(&RosterController::handleOnJIDUpdated, this, _1, _2, _3)); + xmppRoster_->onJIDRemoved.connect(boost::bind(&RosterController::handleOnJIDRemoved, this, _1)); avatarManager_ = NULL; setAvatarManager(avatarManager); setNickResolver(nickResolver); @@ -103,6 +105,34 @@ void RosterController::handleOnJIDAdded(const JID& jid) { } } +void RosterController::handleOnJIDRemoved(const JID& jid) { + roster_->removeContact(jid); +} + +void RosterController::handleOnJIDUpdated(const JID& jid, const String& oldName, const std::vector<String> oldGroups) { + if (oldName != xmppRoster_->getNameForJID(jid)) { + handleOnJIDAdded(jid); + return; + } + std::vector<String> groups = xmppRoster_->getGroupsForJID(jid); + String name = xmppRoster_->getNameForJID(jid); + String contactsGroup = "Contacts"; + if (groups.empty()) { + groups.push_back(contactsGroup); + } + foreach(const String& group, groups) { + if (std::find(oldGroups.begin(), oldGroups.end(), jid) == oldGroups.end()) { + roster_->addContact(jid, xmppRoster_->getNameForJID(jid), group); + } + } + foreach(const String& group, oldGroups) { + if (std::find(groups.begin(), groups.end(), group) == groups.end()) { + roster_->removeContactFromGroup(jid, group); + } + } + +} + void RosterController::handleIncomingPresence(boost::shared_ptr<Presence> presence) { roster_->applyOnItems(SetPresence(presence)); } diff --git a/Swift/Controllers/RosterController.h b/Swift/Controllers/RosterController.h index 0da00ac..f3d96e1 100644 --- a/Swift/Controllers/RosterController.h +++ b/Swift/Controllers/RosterController.h @@ -37,6 +37,8 @@ namespace Swift { void setEnabled(bool enabled); private: void handleOnJIDAdded(const JID &jid); + void handleOnJIDRemoved(const JID &jid); + void handleOnJIDUpdated(const JID &jid, const String& oldName, const std::vector<String> oldGroups); void handleStartChatRequest(const JID& contact); void handleJoinMUCRequest(const JID &muc, const String &nick); void handleUserAction(boost::shared_ptr<UserRosterAction> action); diff --git a/Swift/Controllers/XMPPRosterController.cpp b/Swift/Controllers/XMPPRosterController.cpp index e1716e6..d089cff 100644 --- a/Swift/Controllers/XMPPRosterController.cpp +++ b/Swift/Controllers/XMPPRosterController.cpp @@ -33,6 +33,7 @@ void XMPPRosterController::requestRoster() { void XMPPRosterController::handleRosterReceived(boost::shared_ptr<RosterPayload> rosterPayload) { foreach(const RosterItemPayload& item, rosterPayload->getItems()) { + //Don't worry about the updated case, the XMPPRoster sorts that out. if (item.getSubscription() == RosterItemPayload::Remove) { xmppRoster_->removeContact(item.getJID()); } else { diff --git a/Swiften/Roster/Roster.cpp b/Swiften/Roster/Roster.cpp index b09964c..28245af 100644 --- a/Swiften/Roster/Roster.cpp +++ b/Swiften/Roster/Roster.cpp @@ -72,6 +72,18 @@ void Roster::removeContact(const JID& jid) { } } +void Roster::removeContactFromGroup(const JID& jid, const String& groupName) { + std::vector<RosterItem*>::iterator it = children_.begin(); + while (it != children_.end()) { + GroupRosterItem* group = dynamic_cast<GroupRosterItem*>(*it); + if (group && group->getName() == groupName) { + group->removeChild(jid); + } + it++; + } +} + + void Roster::applyOnItems(const RosterItemOperation& operation) { std::deque<RosterItem*> queue(children_.begin(), children_.end()); while (!queue.empty()) { diff --git a/Swiften/Roster/Roster.h b/Swiften/Roster/Roster.h index cdd1407..6010832 100644 --- a/Swiften/Roster/Roster.h +++ b/Swiften/Roster/Roster.h @@ -27,6 +27,7 @@ class Roster { GroupRosterItem* getGroup(const String& groupName); void addContact(const JID& jid, const String& name, const String& group); void removeContact(const JID& jid); + void removeContactFromGroup(const JID& jid, const String& group); void applyOnItems(const RosterItemOperation& operation); boost::signal<void (boost::shared_ptr<UserRosterAction>)> onUserAction; void addFilter(RosterFilter *filter) {filters_.push_back(filter);filterAll();} diff --git a/Swiften/Roster/XMPPRoster.cpp b/Swiften/Roster/XMPPRoster.cpp index 9661171..a5cccaf 100644 --- a/Swiften/Roster/XMPPRoster.cpp +++ b/Swiften/Roster/XMPPRoster.cpp @@ -8,9 +8,12 @@ void XMPPRoster::addContact(const JID& jid, const String& name, const std::vecto if (exists) { entries_.erase(bareJID); } + String oldName = getNameForJID(bareJID); + std::vector<String> oldGroups = entries_[bareJID].second; entries_[bareJID] = std::pair<String, std::vector<String> >(name, groups); if (exists) { - onJIDUpdated(bareJID); + + onJIDUpdated(bareJID, oldName, oldGroups); } else { onJIDAdded(bareJID); } diff --git a/Swiften/Roster/XMPPRoster.h b/Swiften/Roster/XMPPRoster.h index f2afbb3..7a72e00 100644 --- a/Swiften/Roster/XMPPRoster.h +++ b/Swiften/Roster/XMPPRoster.h @@ -23,7 +23,7 @@ class XMPPRoster { boost::signal<void (const JID&)> onJIDAdded; boost::signal<void (const JID&)> onJIDRemoved; - boost::signal<void (const JID&)> onJIDUpdated; + boost::signal<void (const JID&, const String&, const std::vector<String>&)> onJIDUpdated; private: std::map<JID, std::pair<String, std::vector<String> > > entries_; -- cgit v0.10.2-6-g49f6