You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@labs.apache.org by be...@apache.org on 2008/04/08 18:16:26 UTC
svn commit: r645987 - in /labs/vysper/src:
main/java/org/apache/vysper/xmpp/resourcebinding/ResourceRegistry.java
test/java/org/apache/vysper/xmpp/resourcebinding/
test/java/org/apache/vysper/xmpp/resourcebinding/ResourceRegistryTestCase.java
Author: berndf
Date: Tue Apr 8 09:16:24 2008
New Revision: 645987
URL: http://svn.apache.org/viewvc?rev=645987&view=rev
Log:
[vysper] have a registry where we can identify sessions and bound resources (LABS-111)
Added:
labs/vysper/src/test/java/org/apache/vysper/xmpp/resourcebinding/
labs/vysper/src/test/java/org/apache/vysper/xmpp/resourcebinding/ResourceRegistryTestCase.java
Modified:
labs/vysper/src/main/java/org/apache/vysper/xmpp/resourcebinding/ResourceRegistry.java
Modified: labs/vysper/src/main/java/org/apache/vysper/xmpp/resourcebinding/ResourceRegistry.java
URL: http://svn.apache.org/viewvc/labs/vysper/src/main/java/org/apache/vysper/xmpp/resourcebinding/ResourceRegistry.java?rev=645987&r1=645986&r2=645987&view=diff
==============================================================================
--- labs/vysper/src/main/java/org/apache/vysper/xmpp/resourcebinding/ResourceRegistry.java (original)
+++ labs/vysper/src/main/java/org/apache/vysper/xmpp/resourcebinding/ResourceRegistry.java Tue Apr 8 09:16:24 2008
@@ -19,27 +19,144 @@
import org.apache.vysper.xmpp.server.SessionContext;
import org.apache.vysper.xmpp.uuid.JVMBuiltinUUIDGenerator;
import org.apache.vysper.xmpp.uuid.UUIDGenerator;
+import org.apache.vysper.xmpp.addressing.Entity;
+import org.apache.vysper.xmpp.addressing.EntityImpl;
import java.util.List;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.Collections;
+import java.util.Map;
+import java.util.HashMap;
/**
- * assigns and holds resource ids
+ * assigns and holds resource ids and their related session
*/
public class ResourceRegistry {
private UUIDGenerator resourceIdGenerator = new JVMBuiltinUUIDGenerator();
- protected final List<String> boundResources = new ArrayList<String>();
+
+ protected final Map<String, SessionContext> boundResources = new HashMap<String, SessionContext>();
+ protected final Map<Entity, List<String>> entityResources = new HashMap<Entity, List<String>>();
public String bindSession(SessionContext sessionContext) {
+ if (sessionContext == null) throw new IllegalArgumentException("session context cannot be NULL");
+ if (sessionContext.getInitiatingEntity() == null) throw new IllegalStateException("session context must have a initiating entity set");
String resourceId = resourceIdGenerator.create();
- boundResources.add(resourceId);
+
+ synchronized (boundResources) {
+ synchronized (entityResources) {
+ boundResources.put(resourceId, sessionContext);
+
+ Entity initiatingEntity = sessionContext.getInitiatingEntity();
+ List<String> resourceList = getResourceList(initiatingEntity);
+ if (resourceList == null) {
+ resourceList = new ArrayList<String>();
+ entityResources.put(getBareEntity(initiatingEntity), resourceList);
+ }
+ resourceList.add(resourceId);
+ }
+ }
+
return resourceId;
}
public Iterator<String> boundResources() {
- return Collections.unmodifiableList(boundResources).iterator();
+ return Collections.unmodifiableSet(boundResources.keySet()).iterator();
+ }
+
+ public void unbindResource(String resourceId) {
+ boundResources.remove(resourceId);
+ }
+
+ public void unbindSession(SessionContext unbindingSessionContext) {
+ if (unbindingSessionContext == null) return;
+
+ synchronized (boundResources) {
+ synchronized (entityResources) {
+ // collect all remove candidates
+ List<String> removeResourceIds = getResourcesForSession(unbindingSessionContext);
+
+ // actually remove from bound resources
+ for (String removeResourceId : removeResourceIds) {
+ unbindResource(removeResourceId);
+ }
+
+ // actually remove from entity map
+ List<String> resourceList = getResourceList(unbindingSessionContext.getInitiatingEntity());
+ if (resourceList != null) {
+ resourceList.remove(removeResourceIds);
+ }
+ }
+ }
+ }
+
+ protected List<String> getResourcesForSession(SessionContext sessionContext) {
+ if (sessionContext == null) return null;
+
+ List<String> resourceIds = new ArrayList<String>();
+ for (String resourceId : boundResources.keySet()) {
+ SessionContext visitedSessionContext = boundResources.get(resourceId);
+ if (visitedSessionContext != null && visitedSessionContext.getSessionId().equals(sessionContext.getSessionId())) {
+ resourceIds.add(resourceId);
+ // indeed continue iteration, session might have more than one resource bound.
+ }
+ }
+ return resourceIds;
+ }
+
+ public SessionContext getSessionContext(String resourceId) {
+ return boundResources.get(resourceId);
+ }
+
+ private Entity getBareEntity(Entity entity) {
+ if (entity.getResource() == null) return entity; // bare already
+ return new EntityImpl(entity.getNode(), entity.getDomain(), null);
+ }
+
+ /**
+ * @param entity
+ * @return all resources bound to this entity modulo the entity's resource (if given)
+ */
+ private List<String> getResourceList(Entity entity) {
+ return entityResources.get(getBareEntity(entity));
+ }
+
+ /**
+ * retrieve IDs of all bound resources for this entity
+ */
+ public List<String> getBoundResources(Entity entity) {
+ return getBoundResources(entity, true);
+ }
+
+ /**
+ * retrieve IDs of all bound resources for this entity
+ */
+ public List<String> getBoundResources(Entity entity, boolean considerBareID) {
+ // all resources for the entity
+ List<String> resourceList = Collections.unmodifiableList(getResourceList(entity));
+
+ // if resource should not be considered, return all resources
+ if (considerBareID || entity.getResource() == null) return resourceList;
+ // resource not contained, result is empty
+ if (!resourceList.contains(entity.getResource())) {
+ return Collections.emptyList();
+ }
+ // do we have a bound entity and want only their resource returned?
+ List<String> singleResult = new ArrayList<String>();
+ singleResult.add(entity.getResource());
+ return singleResult;
+ }
+
+
+ public List<SessionContext> getSessions(Entity entity) {
+ List<SessionContext> sessionContexts = new ArrayList<SessionContext>();
+
+ List<String> boundResources = getBoundResources(entity, false);
+ for (String resourceId : boundResources) {
+ sessionContexts.add(getSessionContext(resourceId));
+ }
+
+ return sessionContexts;
}
}
Added: labs/vysper/src/test/java/org/apache/vysper/xmpp/resourcebinding/ResourceRegistryTestCase.java
URL: http://svn.apache.org/viewvc/labs/vysper/src/test/java/org/apache/vysper/xmpp/resourcebinding/ResourceRegistryTestCase.java?rev=645987&view=auto
==============================================================================
--- labs/vysper/src/test/java/org/apache/vysper/xmpp/resourcebinding/ResourceRegistryTestCase.java (added)
+++ labs/vysper/src/test/java/org/apache/vysper/xmpp/resourcebinding/ResourceRegistryTestCase.java Tue Apr 8 09:16:24 2008
@@ -0,0 +1,151 @@
+/***********************************************************************
+ * Copyright (c) 2006-2007 The Apache Software Foundation. *
+ * All rights reserved. *
+ * ------------------------------------------------------------------- *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you *
+ * may not use this file except in compliance with the License. You *
+ * may obtain a copy of the License at: *
+ * *
+ * http://www.apache.org/licenses/LICENSE-2.0 *
+ * *
+ * Unless required by applicable law or agreed to in writing, software *
+ * distributed under the License is distributed on an "AS IS" BASIS, *
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or *
+ * implied. See the License for the specific language governing *
+ * permissions and limitations under the License. *
+ ***********************************************************************/
+package org.apache.vysper.xmpp.resourcebinding;
+
+import junit.framework.TestCase;
+import org.apache.vysper.xmpp.server.TestSessionContext;
+import org.apache.vysper.xmpp.server.SessionContext;
+import org.apache.vysper.xmpp.protocol.SessionStateHolder;
+import org.apache.vysper.xmpp.addressing.Entity;
+import org.apache.vysper.xmpp.addressing.EntityImpl;
+import org.apache.vysper.xmpp.addressing.EntityFormatException;
+
+import java.util.List;
+
+/**
+ */
+public class ResourceRegistryTestCase extends TestCase {
+
+ protected ResourceRegistry resourceRegistry = new ResourceRegistry();
+
+ private TestSessionContext createSessionContext(Entity entity) {
+ SessionStateHolder sessionStateHolder = new SessionStateHolder();
+ TestSessionContext sessionContext = new TestSessionContext(sessionStateHolder);
+ sessionContext.setInitiatingEntity(entity);
+ return sessionContext;
+ }
+
+ public void testSessionNotWellDefinedForResourceBinding() {
+ TestSessionContext sessionContext = createSessionContext(null);
+ assertNull(sessionContext.getInitiatingEntity());
+ try {
+ resourceRegistry.bindSession(sessionContext);
+ fail("do not accept sessions with no initiating entity");
+ } catch (IllegalStateException _) {
+ // test succeeded
+ }
+ }
+
+ public void testAddSession() throws EntityFormatException {
+ TestSessionContext sessionContext = createSessionContext(EntityImpl.parse("me@test"));
+ String resourceId = resourceRegistry.bindSession(sessionContext);
+ assertNotNull(resourceId);
+ List<String> resourceList = resourceRegistry.getResourcesForSession(sessionContext);
+ assertEquals(1, resourceList.size());
+ assertTrue(resourceList.contains(resourceId));
+ }
+
+ public void testAddMultipleSession() throws EntityFormatException {
+ TestSessionContext sessionContext1 = createSessionContext(EntityImpl.parse("me1@test"));
+ String resourceId1 = resourceRegistry.bindSession(sessionContext1);
+ TestSessionContext sessionContext2 = createSessionContext(EntityImpl.parse("me2@test"));
+ String resourceId2 = resourceRegistry.bindSession(sessionContext2);
+ assertNotNull(resourceId2);
+ List<String> resourceList = resourceRegistry.getResourcesForSession(sessionContext1);
+ assertEquals(1, resourceList.size());
+ assertTrue(resourceList.contains(resourceId1));
+ resourceList = resourceRegistry.getResourcesForSession(sessionContext2);
+ assertEquals(1, resourceList.size());
+ assertTrue(resourceList.contains(resourceId2));
+
+ assertEquals(resourceRegistry.getSessionContext(resourceId1), sessionContext1);
+ assertEquals(resourceRegistry.getSessionContext(resourceId2), sessionContext2);
+ }
+
+ public void testAddOneEntityMultipleResources() throws EntityFormatException {
+ EntityImpl entity = EntityImpl.parse("me@test");
+
+ TestSessionContext sessionContext1 = createSessionContext(entity);
+ String resourceId1 = resourceRegistry.bindSession(sessionContext1);
+
+ TestSessionContext sessionContext2 = createSessionContext(entity);
+ String resourceId2 = resourceRegistry.bindSession(sessionContext2);
+
+ assertNotNull(resourceId1);
+ assertNotNull(resourceId2);
+
+ List<String> resourceList = resourceRegistry.getBoundResources(entity);
+ assertEquals(2, resourceList.size());
+ assertTrue(resourceList.contains(resourceId1));
+ assertTrue(resourceList.contains(resourceId2));
+
+ List<SessionContext> sessionList = resourceRegistry.getSessions(entity);
+ assertEquals(2, resourceList.size());
+ assertTrue(sessionList.contains(sessionContext1));
+ assertTrue(sessionList.contains(sessionContext2));
+ }
+
+ public void testAddOneEntityMultipleResources_TolerateResourceIds() throws EntityFormatException {
+ EntityImpl entity = EntityImpl.parse("me@test");
+
+ TestSessionContext sessionContext1 = createSessionContext(EntityImpl.parse("me@test/xy"));
+ String resourceId1 = resourceRegistry.bindSession(sessionContext1);
+
+ TestSessionContext sessionContext2 = createSessionContext(EntityImpl.parse("me@test/ab"));
+ String resourceId2 = resourceRegistry.bindSession(sessionContext2);
+
+ assertNotNull(resourceId1);
+ assertNotNull(resourceId2);
+
+ List<String> resourceList = resourceRegistry.getBoundResources(entity);
+ assertEquals(2, resourceList.size());
+ assertTrue(resourceList.contains(resourceId1));
+ assertTrue(resourceList.contains(resourceId2));
+
+ List<SessionContext> sessionList = resourceRegistry.getSessions(entity);
+ assertEquals(2, resourceList.size());
+ assertTrue(sessionList.contains(sessionContext1));
+ assertTrue(sessionList.contains(sessionContext2));
+ }
+
+ public void testSameEntityMultipleResources() throws EntityFormatException {
+ EntityImpl entity = EntityImpl.parse("me@test");
+
+ TestSessionContext sessionContext1 = createSessionContext(entity);
+ String resourceId1 = resourceRegistry.bindSession(sessionContext1);
+
+ TestSessionContext sessionContext2 = createSessionContext(entity);
+ String resourceId2 = resourceRegistry.bindSession(sessionContext2);
+
+ // resource ids are different
+ assertFalse(resourceId1.equals(resourceId2));
+ }
+
+ public void testUnbindSimple() throws EntityFormatException {
+ EntityImpl entity = EntityImpl.parse("me@test");
+
+ TestSessionContext sessionContext1 = createSessionContext(entity);
+ String resourceId1 = resourceRegistry.bindSession(sessionContext1);
+ assertEquals(sessionContext1, resourceRegistry.getSessionContext(resourceId1));
+
+ resourceRegistry.unbindResource(resourceId1);
+
+ assertNull(resourceRegistry.getSessionContext(resourceId1));
+ assertEquals(0, resourceRegistry.getBoundResources(entity).size());
+ }
+
+}
---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@labs.apache.org
For additional commands, e-mail: commits-help@labs.apache.org