You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@ace.apache.org by ma...@apache.org on 2012/03/23 10:41:52 UTC

svn commit: r1304246 [1/3] - in /ace/trunk: ace-client-repository-impl/src/main/java/org/apache/ace/client/repository/stateful/impl/ ace-integrationtests/src/test/java/org/apache/ace/it/repositoryadmin/ ace-launcher/ ace-webui-vaadin/src/main/java/org/...

Author: marrs
Date: Fri Mar 23 09:41:52 2012
New Revision: 1304246

URL: http://svn.apache.org/viewvc?rev=1304246&view=rev
Log:
ACE-167 applied the patches

Modified:
    ace/trunk/ace-client-repository-impl/src/main/java/org/apache/ace/client/repository/stateful/impl/StatefulTargetRepositoryImpl.java
    ace/trunk/ace-integrationtests/src/test/java/org/apache/ace/it/repositoryadmin/RepositoryAdminTest.java
    ace/trunk/ace-launcher/pom.xml
    ace/trunk/ace-webui-vaadin/src/main/java/org/apache/ace/webui/vaadin/VaadinClient.java

Modified: ace/trunk/ace-client-repository-impl/src/main/java/org/apache/ace/client/repository/stateful/impl/StatefulTargetRepositoryImpl.java
URL: http://svn.apache.org/viewvc/ace/trunk/ace-client-repository-impl/src/main/java/org/apache/ace/client/repository/stateful/impl/StatefulTargetRepositoryImpl.java?rev=1304246&r1=1304245&r2=1304246&view=diff
==============================================================================
--- ace/trunk/ace-client-repository-impl/src/main/java/org/apache/ace/client/repository/stateful/impl/StatefulTargetRepositoryImpl.java (original)
+++ ace/trunk/ace-client-repository-impl/src/main/java/org/apache/ace/client/repository/stateful/impl/StatefulTargetRepositoryImpl.java Fri Mar 23 09:41:52 2012
@@ -65,16 +65,17 @@ import org.osgi.service.log.LogService;
  * it will be used; it is assumed that the auditlog store is up to date.
  */
 public class StatefulTargetRepositoryImpl implements StatefulTargetRepository, EventHandler {
-    private BundleContext m_context; /*Injected by dependency manager*/
-    private ArtifactRepository m_artifactRepository; /*Injected by dependency manager*/
-    private TargetRepository m_targetRepository; /*Injected by dependency manager*/
-    private DeploymentVersionRepository m_deploymentRepository; /*Injected by dependency manager*/
-    private LogStore m_auditLogStore; /*Injected by dependency manager*/
-    private EventAdmin m_eventAdmin; /*Injected by dependency manager*/
-    private LogService m_log; /*Injected by dependency manager*/
-    private BundleHelper m_bundleHelper; /*Injected by dependency manager*/
-    //TODO: Make the concurrencyLevel of this concurrent hashmap settable?
-    private Map<String, StatefulTargetObjectImpl> m_repository = new ConcurrentHashMap<String, StatefulTargetObjectImpl>();
+    private BundleContext m_context; /* Injected by dependency manager */
+    private ArtifactRepository m_artifactRepository; /* Injected by dependency manager */
+    private TargetRepository m_targetRepository; /* Injected by dependency manager */
+    private DeploymentVersionRepository m_deploymentRepository; /* Injected by dependency manager */
+    private LogStore m_auditLogStore; /* Injected by dependency manager */
+    private EventAdmin m_eventAdmin; /* Injected by dependency manager */
+    private LogService m_log; /* Injected by dependency manager */
+    private BundleHelper m_bundleHelper; /* Injected by dependency manager */
+    // TODO: Make the concurrencyLevel of this concurrent hashmap settable?
+    private Map<String, StatefulTargetObjectImpl> m_repository =
+        new ConcurrentHashMap<String, StatefulTargetObjectImpl>();
     private Map<String, StatefulTargetObjectImpl> m_index = new ConcurrentHashMap<String, StatefulTargetObjectImpl>();
     private final String m_sessionID;
 
@@ -82,12 +83,13 @@ public class StatefulTargetRepositoryImp
         m_sessionID = sessionID;
     }
 
-    public StatefulTargetObject create(Map<String, String> attributes, Map<String, String> tags) throws IllegalArgumentException {
+    public StatefulTargetObject create(Map<String, String> attributes, Map<String, String> tags)
+        throws IllegalArgumentException {
         throw new UnsupportedOperationException("Creating StatefulTargetObjects is not supported.");
     }
 
     public List<StatefulTargetObject> get() {
-        synchronized(m_repository) {
+        synchronized (m_repository) {
             List<StatefulTargetObject> result = new ArrayList<StatefulTargetObject>();
             for (StatefulTargetObjectImpl sgoi : m_repository.values()) {
                 result.add(sgoi);
@@ -97,7 +99,7 @@ public class StatefulTargetRepositoryImp
     }
 
     public List<StatefulTargetObject> get(Filter filter) {
-        synchronized(m_repository) {
+        synchronized (m_repository) {
             List<StatefulTargetObject> result = new ArrayList<StatefulTargetObject>();
             for (StatefulTargetObject entry : m_repository.values()) {
                 if (filter.match(entry.getDictionary())) {
@@ -107,24 +109,30 @@ public class StatefulTargetRepositoryImp
             return result;
         }
     }
-    
+
     public StatefulTargetObject get(String definition) {
-    	return m_index.get(definition);
+        return m_index.get(definition);
     }
 
     public void remove(StatefulTargetObject entity) {
-        throw new UnsupportedOperationException("Removing StatefulTargetObjects is not supported.");
+        synchronized (m_repository) {
+            StatefulTargetObjectImpl statefulTarget = (StatefulTargetObjectImpl) entity;
+            unregister(statefulTarget.getID());
+            removeStateful(statefulTarget);
+            // Ensure the external side sees the changes we've made...
+            statefulTarget.updateTargetObject(false);
+        }
     }
 
     public StatefulTargetObject preregister(Map<String, String> attributes, Map<String, String> tags) {
-        synchronized(m_repository) {
+        synchronized (m_repository) {
             TargetObject to = m_targetRepository.create(attributes, tags);
             return createStateful(to.getID());
         }
     }
 
     public void unregister(String targetID) {
-        synchronized(m_repository) {
+        synchronized (m_repository) {
             TargetObject to = getTargetObject(targetID);
             if (to == null) {
                 throw new IllegalArgumentException(targetID + " does not represent a TargetObject.");
@@ -142,47 +150,52 @@ public class StatefulTargetRepositoryImp
 
     /**
      * Gets the <code>TargetObject</code> which is identified by the <code>targetID</code>.
+     * 
      * @param targetID A string representing a target ID.
      * @return The <code>TargetObject</code> from the <code>TargetRepository</code> which has the given
-     * ID, or <code>null</code> if none can be found.
+     *         ID, or <code>null</code> if none can be found.
      */
     TargetObject getTargetObject(String targetID) {
-//        synchronized(m_repository) {
-            try {
-                List<TargetObject> targets = m_targetRepository.get(m_context.createFilter("(" + TargetObject.KEY_ID + "=" + RepositoryUtil.escapeFilterValue(targetID) + ")"));
-                if ((targets != null) && (targets.size() == 1)) {
-                    return targets.get(0);
-                }
-                else {
-                    return null;
-                }
+// synchronized(m_repository) {
+        try {
+            List<TargetObject> targets =
+                m_targetRepository.get(m_context.createFilter("(" + TargetObject.KEY_ID + "="
+                    + RepositoryUtil.escapeFilterValue(targetID) + ")"));
+            if ((targets != null) && (targets.size() == 1)) {
+                return targets.get(0);
             }
-            catch (InvalidSyntaxException e) {
-                // The filter syntax is illegal, probably a bad target ID.
+            else {
                 return null;
             }
-//        }
+        }
+        catch (InvalidSyntaxException e) {
+            // The filter syntax is illegal, probably a bad target ID.
+            return null;
+        }
+// }
     }
 
     /**
      * Gets the stateful representation of the given target ID.
+     * 
      * @param targetID A string representing a target ID.
      * @return The <code>StatefulTargetyObjectImpl</code> which handles the given ID,
-     * or <code>null</code> if none can be found.
+     *         or <code>null</code> if none can be found.
      */
     StatefulTargetObjectImpl getStatefulTargetObject(String targetID) {
-        synchronized(m_repository) {
+        synchronized (m_repository) {
             return m_repository.get(targetID);
         }
     }
 
     /**
      * Creates and registers a new stateful target object based on the given ID.
+     * 
      * @param targetID A string representing a target ID.
      * @return The newly created and registered <code>StatefulTargetObjectImpl</code>.
      */
     private StatefulTargetObjectImpl createStateful(String targetID) {
-        synchronized(m_repository) {
+        synchronized (m_repository) {
             StatefulTargetObjectImpl result = new StatefulTargetObjectImpl(this, targetID);
             if (add(result)) {
                 return result;
@@ -196,10 +209,11 @@ public class StatefulTargetRepositoryImp
     /**
      * Removes the given entity from this object's repository, and notifies
      * interested parties of this.
+     * 
      * @param entity The StatefulTargetObjectImpl to be removed.
      */
     void removeStateful(StatefulTargetObjectImpl entity) {
-        synchronized(m_repository) {
+        synchronized (m_repository) {
             m_repository.remove(entity.getID());
             notifyChanged(entity, StatefulTargetObject.TOPIC_REMOVED);
         }
@@ -208,9 +222,10 @@ public class StatefulTargetRepositoryImp
     /**
      * Adds the given stateful object to this object's repository, and notifies
      * interested parties of this change.
+     * 
      * @param stoi A <code>StatefulTargetObjectImpl</code> to be registered.
      * @return <code>true</code> when this object has been added to the repository
-     * and listeners have been notified, <code>false</code> otherwise.
+     *         and listeners have been notified, <code>false</code> otherwise.
      */
     boolean add(StatefulTargetObjectImpl stoi) {
         if (!m_repository.containsKey(stoi)) {
@@ -235,9 +250,10 @@ public class StatefulTargetRepositoryImp
 
     /**
      * Gets all auditlog events which are related to a given target ID.
+     * 
      * @param targetID A string representing a target ID.
      * @return a list of <code>AuditEvent</code>s related to this target ID,
-     * ordered in the order they happened. If no events can be found, and empty list will be returned.
+     *         ordered in the order they happened. If no events can be found, and empty list will be returned.
      */
     List<LogEvent> getAuditEvents(String targetID) {
         return getAuditEvents(getAllDescriptors(targetID));
@@ -245,6 +261,7 @@ public class StatefulTargetRepositoryImp
 
     /**
      * Gets all auditlog descriptors which are related to a given target.
+     * 
      * @param targetID The target ID
      * @return A list of LogDescriptors, in no particular order.
      */
@@ -265,12 +282,13 @@ public class StatefulTargetRepositoryImp
 
     /**
      * Gets all audit log events for a target is has not yet 'seen'.
+     * 
      * @param all A list of all <code>LogDescriptor</code> from which to filter
-     * the new ones.
+     *        the new ones.
      * @param seen A list of <code>LogDescriptor</code> objects, which indicate
-     * the items the target has already processed.
+     *        the items the target has already processed.
      * @return All AuditLog events that are in the audit store, but are not identified
-     * by <code>oldDescriptors</code>, ordered by 'happened-before'.
+     *         by <code>oldDescriptors</code>, ordered by 'happened-before'.
      */
     List<LogEvent> getAuditEvents(List<LogDescriptor> events) {
         // Get all events from the audit log store, if possible.
@@ -318,6 +336,7 @@ public class StatefulTargetRepositoryImp
      * This function is intended to be used for targets which are not yet represented
      * in the <code>TargetRepository</code>; if they already are, an <code>IllegalArgumentException</code>
      * will be thrown.
+     * 
      * @param targetID A string representing the ID of the new target.
      */
     void register(String targetID) {
@@ -330,10 +349,11 @@ public class StatefulTargetRepositoryImp
 
     /**
      * Notifies interested parties of a change to a <code>StatefulTargetObject</code>.
+     * 
      * @param stoi The <code>StatefulTargetObject</code> which has changed.
      * @param topic A topic string for posting the event.
      * @param additionalProperties A Properties event, already containing some extra properties. If
-     * RepositoryObject.EVENT_ENTITY is used, it will be overwritten.
+     *        RepositoryObject.EVENT_ENTITY is used, it will be overwritten.
      */
     void notifyChanged(StatefulTargetObject stoi, String topic, Properties additionalProperties) {
         additionalProperties.put(RepositoryObject.EVENT_ENTITY, stoi);
@@ -343,6 +363,7 @@ public class StatefulTargetRepositoryImp
 
     /**
      * Notifies interested parties of a change to a <code>StatefulTargetObject</code>.
+     * 
      * @param stoi The <code>StatefulTargetObject</code> which has changed.
      * @param topic A topic string for posting the event.
      */
@@ -354,7 +375,7 @@ public class StatefulTargetRepositoryImp
      * Reads the information sources to generate the stateful objects.
      */
     private void populate() {
-        synchronized(m_repository) {
+        synchronized (m_repository) {
             List<StatefulTargetObjectImpl> touched = new ArrayList<StatefulTargetObjectImpl>();
             touched.addAll(parseTargetRepository());
             touched.addAll(parseAuditLog());
@@ -380,8 +401,9 @@ public class StatefulTargetRepositoryImp
     /**
      * Checks all inhabitants of the <code>TargetRepository</code> to see
      * whether we already have a stateful representation of them.
+     * 
      * @param needsVerify states whether the objects which are 'touched' by this
-     * actions should verify their existence.
+     *        actions should verify their existence.
      * @return A list of all the target objects that have been touched by this action.
      */
     private List<StatefulTargetObjectImpl> parseTargetRepository() {
@@ -402,8 +424,9 @@ public class StatefulTargetRepositoryImp
     /**
      * Checks the audit log to see whether we already have a
      * stateful object for all targets mentioned there.
+     * 
      * @param needsVerify states whether the objects which are 'touched' by this
-     * actions should verify their existence.
+     *        actions should verify their existence.
      */
     private List<StatefulTargetObjectImpl> parseAuditLog() {
         List<StatefulTargetObjectImpl> result = new ArrayList<StatefulTargetObjectImpl>();
@@ -424,11 +447,12 @@ public class StatefulTargetRepositoryImp
             targetIDs.add(l.getTargetID());
         }
 
-        /* Note: the parsing of the audit log and the creation/notification of the
+        /*
+         * Note: the parsing of the audit log and the creation/notification of the
          * stateful objects has been separated, to prevent calling updateAuditEvents()
          * multiple times on targets which have more than one log.
          */
-        synchronized(m_repository) {
+        synchronized (m_repository) {
             for (String targetID : targetIDs) {
                 StatefulTargetObjectImpl stoi = getStatefulTargetObject(targetID);
                 if (stoi == null) {
@@ -446,6 +470,7 @@ public class StatefulTargetRepositoryImp
     /**
      * Approves the changes that will happen to the target based on the
      * changes in the shop by generating a new deployment version.
+     * 
      * @param targetID A string representing a target ID.
      * @return The version identifier of the new deployment package.
      * @throws java.io.IOException When there is a problem generating the deployment version.
@@ -460,6 +485,7 @@ public class StatefulTargetRepositoryImp
      * TODO: In the future, we want to add support for multiple shops.
      * TODO: Is this prone to concurrency issues with changes distribution- and
      * feature objects?
+     * 
      * @param targetID A string representing a target.
      * @return An array of artifact URLs.
      * @throws java.io.IOException When there is a problem processing an artifact for deployment.
@@ -469,7 +495,8 @@ public class StatefulTargetRepositoryImp
 
         Map<ArtifactObject, String> bundles = new HashMap<ArtifactObject, String>();
         Map<ArtifactObject, String> artifacts = new HashMap<ArtifactObject, String>();
-        Map<ArtifactObject, Map<FeatureObject, List<DistributionObject>>> path = new HashMap<ArtifactObject, Map<FeatureObject,List<DistributionObject>>>();
+        Map<ArtifactObject, Map<FeatureObject, List<DistributionObject>>> path =
+            new HashMap<ArtifactObject, Map<FeatureObject, List<DistributionObject>>>();
 
         // First, find all basic bundles and artifacts. An while we're traversing the
         // tree of objects, build the tree of properties.
@@ -485,13 +512,13 @@ public class StatefulTargetRepositoryImp
                         }
                         Map<FeatureObject, List<DistributionObject>> featureToDistribution = path.get(artifact);
                         if (featureToDistribution == null) {
-                        	featureToDistribution = new HashMap<FeatureObject, List<DistributionObject>>();
-                        	path.put(artifact, featureToDistribution);
+                            featureToDistribution = new HashMap<FeatureObject, List<DistributionObject>>();
+                            path.put(artifact, featureToDistribution);
                         }
                         List<DistributionObject> distributions = featureToDistribution.get(feature);
                         if (distributions == null) {
-                        	distributions = new ArrayList<DistributionObject>();
-                        	featureToDistribution.put(feature, distributions);
+                            distributions = new ArrayList<DistributionObject>();
+                            featureToDistribution.put(feature, distributions);
                         }
                         distributions.add(distribution);
                     }
@@ -530,14 +557,14 @@ public class StatefulTargetRepositoryImp
             if (bundleVersion != null) {
                 directives.put(BundleHelper.KEY_VERSION, bundleVersion);
             }
-            
+
             directives.put(DeploymentArtifact.DIRECTIVE_KEY_BASEURL, bundle.getURL());
-            
+
             String repositoryPath = getRepositoryPath(bundle, path);
             if (repositoryPath != null) {
-            	directives.put(DeploymentArtifact.REPOSITORY_PATH, repositoryPath);
+                directives.put(DeploymentArtifact.REPOSITORY_PATH, repositoryPath);
             }
-            
+
             result.add(m_deploymentRepository.createDeploymentArtifact(bundle.getURL(), directives));
         }
 
@@ -548,29 +575,31 @@ public class StatefulTargetRepositoryImp
             if (artifact.getResourceId() != null) {
                 directives.put(DeploymentArtifact.DIRECTIVE_KEY_RESOURCE_ID, artifact.getResourceId());
             }
-            
+
             String repositoryPath = getRepositoryPath(artifact, path);
             if (repositoryPath != null) {
-            	directives.put(DeploymentArtifact.REPOSITORY_PATH, repositoryPath);
+                directives.put(DeploymentArtifact.REPOSITORY_PATH, repositoryPath);
             }
-            result.add(m_deploymentRepository.createDeploymentArtifact(m_artifactRepository.preprocessArtifact(artifact, to, targetID, version), directives));
+            result.add(m_deploymentRepository.createDeploymentArtifact(
+                m_artifactRepository.preprocessArtifact(artifact, to, targetID, version), directives));
         }
 
         return result.toArray(new DeploymentArtifact[result.size()]);
     }
-    
-    private String getRepositoryPath(ArtifactObject artifact, Map<ArtifactObject, Map<FeatureObject, List<DistributionObject>>> path) {
-    	StringBuilder builder = new StringBuilder();
+
+    private String getRepositoryPath(ArtifactObject artifact,
+        Map<ArtifactObject, Map<FeatureObject, List<DistributionObject>>> path) {
+        StringBuilder builder = new StringBuilder();
         Map<FeatureObject, List<DistributionObject>> featureToDistribution = path.get(artifact);
         if (featureToDistribution != null) {
-	        for (Entry<FeatureObject, List<DistributionObject>> entry : featureToDistribution.entrySet()) {
-	        	for (DistributionObject distribution : entry.getValue()) {
-	        		builder.append(entry.getKey().getName()).append(';').append(distribution.getName()).append(',');
-	        	}
-	        }
+            for (Entry<FeatureObject, List<DistributionObject>> entry : featureToDistribution.entrySet()) {
+                for (DistributionObject distribution : entry.getValue()) {
+                    builder.append(entry.getKey().getName()).append(';').append(distribution.getName()).append(',');
+                }
+            }
         }
         else {
-        	return null;
+            return null;
         }
         builder.setLength(builder.length() - 1);
         return builder.toString();
@@ -578,7 +607,7 @@ public class StatefulTargetRepositoryImp
 
     /**
      * Quick method to find all artifacts that need to be deployed to a target.
-    */
+     */
     ArtifactObject[] getNecessaryArtifacts(String targetID) {
         List<ArtifactObject> result = new ArrayList<ArtifactObject>();
         TargetObject to = getTargetObject(targetID);
@@ -613,6 +642,7 @@ public class StatefulTargetRepositoryImp
      * Generates a new deployment version for the the given target,
      * based on the artifacts it is linked to by the distributions it is
      * associated to.
+     * 
      * @param targetID A string representing a target.
      * @return A new DeploymentVersionObject, representing this new version for the target.
      * @throws java.io.IOException When there is a problem determining the artifacts to be deployed.
@@ -632,7 +662,7 @@ public class StatefulTargetRepositoryImp
         }
         attr.put(DeploymentVersionObject.KEY_VERSION, nextVersion);
 
-        synchronized(m_repository) {
+        synchronized (m_repository) {
             DeploymentVersionObject result = m_deploymentRepository.create(attr, tags, getNecessaryDeploymentArtifacts(targetID, nextVersion));
 
             StatefulTargetObjectImpl stoi = getStatefulTargetObject(targetID);
@@ -653,6 +683,7 @@ public class StatefulTargetRepositoryImp
      * 'major' version is generated. In the future, we might want to do
      * 'smarter' things here, like checking the impact of a new version
      * and use the minor and micro versions, or attach some qualifier.
+     * 
      * @param version A string representing a deployment version's version.
      * @return A string representing the next version.
      */
@@ -669,8 +700,9 @@ public class StatefulTargetRepositoryImp
     }
 
     public void handleEvent(Event event) {
-        if (event.getTopic().equals(TargetObject.TOPIC_ADDED) || event.getTopic().equals(TargetObject.TOPIC_REMOVED)) {
-            synchronized(m_repository) {
+        String topic = event.getTopic();
+        if (TargetObject.TOPIC_ADDED.equals(topic)) {
+            synchronized (m_repository) {
                 String id = ((TargetObject) event.getProperty(RepositoryObject.EVENT_ENTITY)).getID();
                 StatefulTargetObjectImpl stoi = getStatefulTargetObject(id);
                 if (stoi == null) {
@@ -681,8 +713,18 @@ public class StatefulTargetRepositoryImp
                 }
             }
         }
-        else if (event.getTopic().equals(DeploymentVersionObject.TOPIC_ADDED) || event.getTopic().equals(DeploymentVersionObject.TOPIC_REMOVED)) {
-            synchronized(m_repository) {
+        else if (TargetObject.TOPIC_REMOVED.equals(topic)) {
+            synchronized (m_repository) {
+                String id = ((TargetObject) event.getProperty(RepositoryObject.EVENT_ENTITY)).getID();
+                StatefulTargetObjectImpl stoi = getStatefulTargetObject(id);
+                // if the stateful target is already gone; we don't have to do anything...
+                if (stoi != null) {
+                    stoi.updateTargetObject(true);
+                }
+            }
+        }
+        else if (DeploymentVersionObject.TOPIC_ADDED.equals(topic) || DeploymentVersionObject.TOPIC_REMOVED.equals(topic)) {
+            synchronized (m_repository) {
                 DeploymentVersionObject deploymentVersionObject = ((DeploymentVersionObject) event.getProperty(RepositoryObject.EVENT_ENTITY));
                 String id = deploymentVersionObject.getTargetID();
                 StatefulTargetObjectImpl stoi = getStatefulTargetObject(id);
@@ -694,20 +736,15 @@ public class StatefulTargetRepositoryImp
                 }
             }
         }
-        else if (event.getTopic().equals(RepositoryAdmin.TOPIC_LOGIN)) {
-            synchronized(m_repository) {
-                populate();
-            }
-        }
-        else if (event.getTopic().equals(RepositoryAdmin.TOPIC_REFRESH)) {
-            synchronized(m_repository) {
+        else if (RepositoryAdmin.TOPIC_LOGIN.equals(topic) || RepositoryAdmin.TOPIC_REFRESH.equals(topic)) {
+            synchronized (m_repository) {
                 populate();
             }
         }
         else {
             // Something else has changed; however, the entire shop may have an influence on
             // any target, so recheck everything.
-            synchronized(m_repository) {
+            synchronized (m_repository) {
                 for (StatefulTargetObjectImpl stoi : m_repository.values()) {
                     stoi.determineStatus();
                 }