diff options
author | Kevin Smith <git@kismith.co.uk> | 2010-05-07 10:55:02 (GMT) |
---|---|---|
committer | Kevin Smith <git@kismith.co.uk> | 2010-05-07 10:55:02 (GMT) |
commit | 48f5bf16ff9e2c8acd095bed521ff7951a8afddf (patch) | |
tree | 0969fd3323285ab8e69cd941ad8079330109f317 /Swiften | |
parent | 2dd59db4ae815e2e6e487e4c0078d3dc495e95f0 (diff) | |
download | swift-48f5bf16ff9e2c8acd095bed521ff7951a8afddf.zip swift-48f5bf16ff9e2c8acd095bed521ff7951a8afddf.tar.bz2 |
Don't segfault when someone leaves a MUC
Diffstat (limited to 'Swiften')
-rw-r--r-- | Swiften/Roster/Roster.cpp | 11 | ||||
-rw-r--r-- | Swiften/Roster/UnitTest/RosterTest.cpp | 40 |
2 files changed, 46 insertions, 5 deletions
diff --git a/Swiften/Roster/Roster.cpp b/Swiften/Roster/Roster.cpp index 9226a63..caf2b5e 100644 --- a/Swiften/Roster/Roster.cpp +++ b/Swiften/Roster/Roster.cpp @@ -82,9 +82,9 @@ struct JIDEqualsTo { }; void Roster::removeContact(const JID& jid) { - std::vector<ContactRosterItem*> items = itemMap_[jid.toBare()]; - items.erase(std::remove_if(items.begin(), items.end(), JIDEqualsTo(jid)), items.end()); - if (items.size() == 0) { + std::vector<ContactRosterItem*>* items = &itemMap_[jid.toBare()]; + items->erase(std::remove_if(items->begin(), items->end(), JIDEqualsTo(jid)), items->end()); + if (items->size() == 0) { itemMap_.erase(jid.toBare()); } //Causes the delete @@ -98,8 +98,8 @@ void Roster::removeContactFromGroup(const JID& jid, const String& groupName) { GroupRosterItem* group = dynamic_cast<GroupRosterItem*>(*it); if (group && group->getDisplayName() == groupName) { ContactRosterItem* deleted = group->removeChild(jid); - std::vector<ContactRosterItem*> items = itemMap_[jid.toBare()]; - items.erase(std::remove(items.begin(), items.end(), deleted), items.end()); + std::vector<ContactRosterItem*>* items = &itemMap_[jid.toBare()]; + items->erase(std::remove(items->begin(), items->end(), deleted), items->end()); } it++; } @@ -116,6 +116,7 @@ void Roster::applyOnItems(const RosterItemOperation& operation) { void Roster::applyOnItem(const RosterItemOperation& operation, const JID& jid) { foreach (ContactRosterItem* item, itemMap_[jid.toBare()]) { + //std::cout << "Applying on item " << item << " : " << item->getDisplayName() << std::endl; operation(item); filterContact(item, item->getParent()); } diff --git a/Swiften/Roster/UnitTest/RosterTest.cpp b/Swiften/Roster/UnitTest/RosterTest.cpp index 2697747..d170396 100644 --- a/Swiften/Roster/UnitTest/RosterTest.cpp +++ b/Swiften/Roster/UnitTest/RosterTest.cpp @@ -10,6 +10,7 @@ #include "Swiften/Roster/Roster.h" #include "Swiften/Roster/GroupRosterItem.h" +#include "Swiften/Roster/SetPresence.h" using namespace Swift; @@ -20,6 +21,7 @@ class RosterTest : public CppUnit::TestFixture CPPUNIT_TEST(testRemoveContact); CPPUNIT_TEST(testRemoveSecondContact); CPPUNIT_TEST(testRemoveSecondContactSameBare); + CPPUNIT_TEST(testApplyPresenceLikeMUC); CPPUNIT_TEST_SUITE_END(); private: @@ -84,6 +86,44 @@ class RosterTest : public CppUnit::TestFixture CPPUNIT_ASSERT_EQUAL(String("Bert"), ((GroupRosterItem*)roster_->getRoot()->getChildren()[0])->getChildren()[0]->getDisplayName()); } + void testApplyPresenceLikeMUC() { + JID jid4a("a@b/c"); + JID jid4b("a@b/d"); + JID jid4c("a@b/e"); + roster_->addContact(jid4a, "Bird", "group1"); + roster_->addContact(jid4b, "Cookie", "group1"); + roster_->removeContact(jid4b); + roster_->addContact(jid4c, "Bert", "group1"); + roster_->addContact(jid4b, "Ernie", "group1"); + boost::shared_ptr<Presence> presence(new Presence()); + presence->setShow(StatusShow::DND); + presence->setFrom(jid4a); + roster_->applyOnItems(SetPresence(presence, JID::WithResource)); + presence->setFrom(jid4b); + roster_->applyOnItems(SetPresence(presence, JID::WithResource)); + presence->setFrom(jid4c); + roster_->applyOnItems(SetPresence(presence, JID::WithResource)); + + presence = boost::shared_ptr<Presence>(new Presence()); + presence->setFrom(jid4b); + presence->setShow(StatusShow::Online); + roster_->applyOnItems(SetPresence(presence, JID::WithResource)); + std::vector<RosterItem*> children = ((GroupRosterItem*)roster_->getRoot()->getDisplayedChildren()[0])->getDisplayedChildren(); + CPPUNIT_ASSERT_EQUAL(3, (int)children.size()); + + /* Check order */ + CPPUNIT_ASSERT_EQUAL(String("Ernie"), children[0]->getDisplayName()); + CPPUNIT_ASSERT_EQUAL(String("Bert"), children[1]->getDisplayName()); + CPPUNIT_ASSERT_EQUAL(String("Bird"), children[2]->getDisplayName()); + + presence = boost::shared_ptr<Presence>(new Presence()); + presence->setFrom(jid4c); + presence->setType(Presence::Unavailable); + roster_->removeContact(jid4c); + roster_->applyOnItems(SetPresence(presence, JID::WithResource)); + + } + }; CPPUNIT_TEST_SUITE_REGISTRATION(RosterTest); |