Adds the ability to handle multiple presences of a user

git-svn-id: http://svn.igniterealtime.org/svn/repos/smack/trunk@2175 b35dd754-fafc-0310-a699-88a17e54d16e
This commit is contained in:
Gaston Dombiak 2003-11-28 21:49:25 +00:00 committed by gdombiak
parent d92bb4f40a
commit b73060d000
1 changed files with 91 additions and 10 deletions

View File

@ -436,7 +436,10 @@ public class Roster {
/** /**
* Returns the presence info for a particular user, or <tt>null</tt> if the user * Returns the presence info for a particular user, or <tt>null</tt> if the user
* is unavailable (offline) or if no presence information is available, such as * is unavailable (offline) or if no presence information is available, such as
* when you are not subscribed to the user's presence updates. * when you are not subscribed to the user's presence updates.<p>
*
* If the user has several presences (one for each resource) then answer the presence
* with the highest priority.
* *
* @param user a fully qualified xmpp ID, e.g. jdoe@example.com * @param user a fully qualified xmpp ID, e.g. jdoe@example.com
* @return the user's current presence, or <tt>null</tt> if the user is unavailable * @return the user's current presence, or <tt>null</tt> if the user is unavailable
@ -444,7 +447,72 @@ public class Roster {
*/ */
public Presence getPresence(String user) { public Presence getPresence(String user) {
String key = StringUtils.parseName(user) + "@" + StringUtils.parseServer(user); String key = StringUtils.parseName(user) + "@" + StringUtils.parseServer(user);
return (Presence)presenceMap.get(key); Map userPresences = (Map) presenceMap.get(key);
if (userPresences == null) {
return null;
}
else {
// Find the resource with the highest priority
// Might be changed to use the resource with the highest availability instead.
Iterator it = userPresences.keySet().iterator();
Presence p;
Presence presence = null;
while (it.hasNext()) {
p = (Presence) userPresences.get(it.next());
if (presence == null) {
presence = p;
}
else {
if (p.getPriority() > presence.getPriority()) {
presence = p;
}
}
}
return presence;
}
}
/**
* Returns the presence info for a particular user's resource, or <tt>null</tt> if the user
* is unavailable (offline) or if no presence information is available, such as
* when you are not subscribed to the user's presence updates.
*
* @param user a fully qualified xmpp ID including a resource, e.g. jdoe@example.com/Home
* @return the user's current presence, or <tt>null</tt> if the user is unavailable
* or if no presence information is available.
*/
public Presence getPresenceResource(String userResource) {
String key =
StringUtils.parseName(userResource) + "@" + StringUtils.parseServer(userResource);
String resource = StringUtils.parseResource(userResource);
Map userPresences = (Map) presenceMap.get(key);
if (userPresences == null) {
return null;
}
else {
return (Presence) userPresences.get(resource);
}
}
/**
* Returns an iterator for all the user's current presences or <tt>null</tt> if the user
* is unavailable (offline) or if no presence information is available, such as
* when you are not subscribed to the user's presence updates.
*
* @param user a fully qualified xmpp ID, e.g. jdoe@example.com
* @return an iterator for all the user's current presences, or <tt>null</tt> if the user is
* unavailable or if no presence information is available.
*/
public Iterator getPresences(String user) {
String key = StringUtils.parseName(user) + "@" + StringUtils.parseServer(user);
Map userPresences = (Map) presenceMap.get(key);
if (userPresences == null) {
return null;
}
else {
return userPresences.entrySet().iterator();
}
} }
/** /**
@ -483,16 +551,23 @@ public class Roster {
Presence presence = (Presence)packet; Presence presence = (Presence)packet;
String from = presence.getFrom(); String from = presence.getFrom();
String key = StringUtils.parseBareAddress(from); String key = StringUtils.parseBareAddress(from);
// If an "available" packet, add it to the presence map. This means that for // If an "available" packet, add it to the presence map. Each presence map will hold
// a particular user, we'll only ever have a single presence packet saved. // for a particular user a map with the presence packets saved for each resource.
// Because this ignores resources, this is not an ideal solution, so will
// have to be revisited.
if (presence.getType() == Presence.Type.AVAILABLE) { if (presence.getType() == Presence.Type.AVAILABLE) {
presenceMap.put(key, presence); Map userPresences;
// Get the user presence map
if (presenceMap.get(key) == null) {
userPresences = new HashMap();
presenceMap.put(key, userPresences);
} else {
userPresences = (Map) presenceMap.get(key);
}
// Add the new presence taking in consideration the presence´s resource
userPresences.put(StringUtils.parseResource(from), presence);
// If the user is in the roster, fire an event. // If the user is in the roster, fire an event.
synchronized (entries) { synchronized (entries) {
for (Iterator i=entries.iterator(); i.hasNext(); ) { for (Iterator i = entries.iterator(); i.hasNext();) {
RosterEntry entry = (RosterEntry)i.next(); RosterEntry entry = (RosterEntry) i.next();
if (entry.getUser().equals(key)) { if (entry.getUser().equals(key)) {
fireRosterPresenceEvent(key); fireRosterPresenceEvent(key);
} }
@ -501,7 +576,13 @@ public class Roster {
} }
// If an "unavailable" packet, remove any entries in the presence map. // If an "unavailable" packet, remove any entries in the presence map.
else if (presence.getType() == Presence.Type.UNAVAILABLE) { else if (presence.getType() == Presence.Type.UNAVAILABLE) {
presenceMap.remove(key); if (presenceMap.get(key) != null) {
Map userPresences = (Map) presenceMap.get(key);
userPresences.remove(StringUtils.parseResource(from));
if (userPresences.isEmpty()) {
presenceMap.remove(key);
}
}
// If the user is in the roster, fire an event. // If the user is in the roster, fire an event.
synchronized (entries) { synchronized (entries) {
for (Iterator i=entries.iterator(); i.hasNext(); ) { for (Iterator i=entries.iterator(); i.hasNext(); ) {