summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/com/isode/stroke/client/Client.java4
-rw-r--r--src/com/isode/stroke/presence/PresenceOracle.java58
-rw-r--r--test/com/isode/stroke/presence/PresenceOracleTest.java11
3 files changed, 54 insertions, 19 deletions
diff --git a/src/com/isode/stroke/client/Client.java b/src/com/isode/stroke/client/Client.java
index 07ac885..88022e3 100644
--- a/src/com/isode/stroke/client/Client.java
+++ b/src/com/isode/stroke/client/Client.java
@@ -1,8 +1,8 @@
/*
- * Copyright (c) 2010-2015, Isode Limited, London, England.
+ * Copyright (c) 2010-2016, Isode Limited, London, England.
* All rights reserved.
*/
package com.isode.stroke.client;
import com.isode.stroke.avatars.AvatarManager;
import com.isode.stroke.avatars.AvatarManagerImpl;
@@ -98,13 +98,13 @@ public class Client extends CoreClient {
roster = new XMPPRosterImpl();
rosterController = new XMPPRosterController(getIQRouter(), roster, getStorages().getRosterStorage());
subscriptionManager = new SubscriptionManager(getStanzaChannel());
- presenceOracle = new PresenceOracle(getStanzaChannel());
+ presenceOracle = new PresenceOracle(getStanzaChannel(),roster);
presenceOracle.onPresenceChange.connect(onPresenceChange);
stanzaChannelPresenceSender = new StanzaChannelPresenceSender(getStanzaChannel());
directedPresenceSender = new DirectedPresenceSender(stanzaChannelPresenceSender);
discoManager = new ClientDiscoManager(getIQRouter(), directedPresenceSender, networkFactories.getCryptoProvider());
diff --git a/src/com/isode/stroke/presence/PresenceOracle.java b/src/com/isode/stroke/presence/PresenceOracle.java
index e3e68cb..7ac5b9d 100644
--- a/src/com/isode/stroke/presence/PresenceOracle.java
+++ b/src/com/isode/stroke/presence/PresenceOracle.java
@@ -1,8 +1,8 @@
/*
- * Copyright (c) 2010-2015, Isode Limited, London, England.
+ * Copyright (c) 2010-2016, Isode Limited, London, England.
* All rights reserved.
*/
package com.isode.stroke.presence;
import java.util.ArrayList;
import java.util.Collection;
@@ -10,44 +10,57 @@ import java.util.HashMap;
import java.util.Map;
import com.isode.stroke.client.StanzaChannel;
import com.isode.stroke.elements.Presence;
import com.isode.stroke.elements.StatusShow;
import com.isode.stroke.jid.JID;
+import com.isode.stroke.roster.XMPPRoster;
import com.isode.stroke.signals.Signal1;
import com.isode.stroke.signals.SignalConnection;
import com.isode.stroke.signals.Slot1;
public class PresenceOracle {
private final Map<JID,Map<JID,Presence>> entries_ = new HashMap<JID,Map<JID,Presence>>();
private final StanzaChannel stanzaChannel_;
private final SignalConnection onPresenceReceivedSignal;
private final SignalConnection onAvailableChangedSignal;
+ private final XMPPRoster xmppRoster_;
public final Signal1<Presence> onPresenceChange = new Signal1<Presence>();
+ private final SignalConnection onJIDRemovedConnection;
- public PresenceOracle(StanzaChannel stanzaChannel) {
- stanzaChannel_ = stanzaChannel;
- onPresenceReceivedSignal = stanzaChannel_.onPresenceReceived.connect(new Slot1<Presence>() {
- @Override
- public void call(Presence p1) {
- handleIncomingPresence(p1);
- }
- });
- onAvailableChangedSignal = stanzaChannel_.onAvailableChanged.connect(new Slot1<Boolean>() {
- @Override
- public void call(Boolean p1) {
- handleStanzaChannelAvailableChanged(p1);
- }
- });
+ public PresenceOracle(StanzaChannel stanzaChannel, XMPPRoster xmppRoster) {
+ stanzaChannel_ = stanzaChannel;
+ xmppRoster_ = xmppRoster;
+ onPresenceReceivedSignal = stanzaChannel_.onPresenceReceived.connect(new Slot1<Presence>() {
+ @Override
+ public void call(Presence p1) {
+ handleIncomingPresence(p1);
+ }
+ });
+ onAvailableChangedSignal = stanzaChannel_.onAvailableChanged.connect(new Slot1<Boolean>() {
+ @Override
+ public void call(Boolean p1) {
+ handleStanzaChannelAvailableChanged(p1);
+ }
+ });
+ onJIDRemovedConnection = xmppRoster_.onJIDRemoved.connect(new Slot1<JID>() {
+
+ @Override
+ public void call(JID removedJID) {
+ handleJIDRemoved(removedJID);
+ }
+
+ });
}
void delete() {
onPresenceReceivedSignal.disconnect();
onAvailableChangedSignal.disconnect();
+ onJIDRemovedConnection.disconnect();
}
void handleStanzaChannelAvailableChanged(boolean available) {
if (available) {
entries_.clear();
}
@@ -82,12 +95,27 @@ public class PresenceOracle {
jidMap.put(passedPresence.getFrom(), passedPresence);
}
entries_.put(bareJID, jidMap);
onPresenceChange.emit(passedPresence);
}
}
+
+ private void handleJIDRemoved(JID removedJID) {
+ // 3921bis says that we don't follow up with an unavailable, so simulate this ourselves
+ Presence unavailablePresence = new Presence();
+ unavailablePresence.setType(Presence.Type.Unavailable);
+ unavailablePresence.setFrom(removedJID);
+
+ if (entries_.containsKey(removedJID.toBare())) {
+ Map<JID,Presence> presenceMap = entries_.get(removedJID.toBare());
+ presenceMap.clear();
+ presenceMap.put(removedJID, unavailablePresence);
+ }
+
+ onPresenceChange.emit(unavailablePresence);
+ }
public Presence getLastPresence(final JID jid) {
Map<JID,Presence> presenceMap = entries_.get(jid.toBare());
if (presenceMap == null) return null;
Presence i = presenceMap.get(jid);
diff --git a/test/com/isode/stroke/presence/PresenceOracleTest.java b/test/com/isode/stroke/presence/PresenceOracleTest.java
index 03aea04..ac82045 100644
--- a/test/com/isode/stroke/presence/PresenceOracleTest.java
+++ b/test/com/isode/stroke/presence/PresenceOracleTest.java
@@ -1,8 +1,8 @@
/*
- * Copyright (c) 2010 Isode Limited.
+ * Copyright (c) 2010-2016 Isode Limited.
* All rights reserved.
* See the COPYING file for more information.
*/
/*
* Copyright (c) 2015 Tarun Gupta.
* Licensed under the simplified BSD license.
@@ -13,27 +13,32 @@ package com.isode.stroke.presence;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
+
import org.junit.Test;
import org.junit.Before;
+
import com.isode.stroke.elements.Presence;
import com.isode.stroke.elements.Payload;
import com.isode.stroke.client.DummyStanzaChannel;
import com.isode.stroke.presence.DirectedPresenceSender;
import com.isode.stroke.presence.StanzaChannelPresenceSender;
import com.isode.stroke.presence.PayloadAddingPresenceSender;
import com.isode.stroke.presence.PresenceOracle;
import com.isode.stroke.presence.SubscriptionManager;
import com.isode.stroke.jid.JID;
+import com.isode.stroke.roster.XMPPRoster;
+import com.isode.stroke.roster.XMPPRosterImpl;
import com.isode.stroke.signals.SignalConnection;
import com.isode.stroke.signals.Slot2;
import com.isode.stroke.signals.Slot3;
import com.isode.stroke.signals.Slot1;
+
import java.util.Collection;
import java.util.Vector;
public class PresenceOracleTest {
private class SubscriptionRequestInfo {
@@ -46,12 +51,13 @@ public class PresenceOracleTest {
}
};
private PresenceOracle oracle_;
private SubscriptionManager subscriptionManager_;
private DummyStanzaChannel stanzaChannel_;
+ private XMPPRoster xmppRoster_;
private Collection<Presence> changes = new Vector<Presence>();
private Collection<SubscriptionRequestInfo> subscriptionRequests = new Vector<SubscriptionRequestInfo>();
private JID user1;
private JID user1alt;
private JID user2;
@@ -86,13 +92,14 @@ public class PresenceOracleTest {
return sentPresence;
}
@Before
public void setUp() {
stanzaChannel_ = new DummyStanzaChannel();
- oracle_ = new PresenceOracle(stanzaChannel_);
+ xmppRoster_ = new XMPPRosterImpl();
+ oracle_ = new PresenceOracle(stanzaChannel_,xmppRoster_);
oracle_.onPresenceChange.connect(new Slot1<Presence>() {
@Override
public void call(Presence p) {
handlePresenceChange(p);
}
});