You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@sling.apache.org by cz...@apache.org on 2015/04/07 11:17:12 UTC

svn commit: r1671768 - in /sling/trunk/installer/providers/jcr/src: main/java/org/apache/sling/installer/provider/jcr/impl/ test/java/org/apache/sling/installer/provider/jcr/impl/

Author: cziegeler
Date: Tue Apr  7 09:17:11 2015
New Revision: 1671768

URL: http://svn.apache.org/r1671768
Log:
SLING-4564 : Use a single listener registered for multiple path in JCR installer. 

Modified:
    sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/InstallerConfig.java
    sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/JcrInstaller.java
    sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/RootFolderListener.java
    sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/WatchedFolder.java
    sling/trunk/installer/providers/jcr/src/test/java/org/apache/sling/installer/provider/jcr/impl/FindPathsToWatchTest.java
    sling/trunk/installer/providers/jcr/src/test/java/org/apache/sling/installer/provider/jcr/impl/MiscUtil.java

Modified: sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/InstallerConfig.java
URL: http://svn.apache.org/viewvc/sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/InstallerConfig.java?rev=1671768&r1=1671767&r2=1671768&view=diff
==============================================================================
--- sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/InstallerConfig.java (original)
+++ sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/InstallerConfig.java Tue Apr  7 09:17:11 2015
@@ -21,10 +21,15 @@ package org.apache.sling.installer.provi
 import java.util.ArrayList;
 import java.util.Collection;
 import java.util.Dictionary;
+import java.util.Iterator;
 import java.util.LinkedList;
 import java.util.List;
 
+import javax.jcr.RepositoryException;
+import javax.jcr.Session;
+
 import org.apache.sling.commons.osgi.PropertiesUtil;
+import org.apache.sling.installer.api.InstallableResource;
 import org.apache.sling.installer.provider.jcr.impl.JcrInstaller.NodeConverter;
 import org.apache.sling.settings.SlingSettingsService;
 import org.osgi.framework.Constants;
@@ -56,11 +61,14 @@ public class InstallerConfig {
     /** List of watched folders */
     private final List<WatchedFolder> watchedFolders = new LinkedList<WatchedFolder>();
 
+    private final Logger logger;
+
     public InstallerConfig(
             final Logger logger,
             final ComponentContext ctx,
             final Dictionary<?, ?> cfg,
             final SlingSettingsService settings) {
+        this.logger = logger;
         this.writeBack = PropertiesUtil.toBoolean(getPropertyValue(logger, ctx, cfg, JcrInstaller.PROP_ENABLE_WRITEBACK), JcrInstaller.DEFAULT_ENABLE_WRITEBACK);
 
         // Setup converters
@@ -156,7 +164,76 @@ public class InstallerConfig {
         return this.newConfigPath;
     }
 
-    public List<WatchedFolder> getWatchedFolders() {
-        return this.watchedFolders;
+    public List<WatchedFolder> cloneWatchedFolders() {
+        synchronized ( this.watchedFolders ) {
+            return new ArrayList<WatchedFolder>(this.watchedFolders);
+        }
+    }
+
+    /**
+     * Scan watchedFolders and get installable resources
+     */
+    public List<InstallableResource> scanWatchedFolders() throws RepositoryException {
+        final List<InstallableResource> resources = new LinkedList<InstallableResource>();
+        synchronized ( this.watchedFolders ) {
+            for(final WatchedFolder f : this.watchedFolders) {
+                final WatchedFolder.ScanResult r = f.scan();
+                logger.debug("Startup: {} provides resources {}", f, r.toAdd);
+                resources.addAll(r.toAdd);
+            }
+        }
+        return resources;
+    }
+
+    /**
+     * Check all WatchedFolder, in case some were deleted
+     */
+
+    public List<String> checkForRemovedWatchedFolders(final Session session) throws RepositoryException {
+        final List<String> removedResources = new LinkedList<String>();
+        synchronized ( this.watchedFolders ) {
+            final Iterator<WatchedFolder> i = this.watchedFolders.iterator();
+            while ( i.hasNext() ) {
+                final WatchedFolder wf = i.next();
+
+                logger.debug("Item {} exists? {}", wf.getPath(), session.itemExists(wf.getPath()));
+                if (!session.itemExists(wf.getPath())) {
+                    logger.info("Deleting {}, path does not exist anymore", wf);
+                    removedResources.addAll(wf.scan().toRemove);
+                    i.remove();
+                }
+            }
+        }
+        return removedResources;
+    }
+
+    /**
+     * Add WatchedFolder to our list if it doesn't exist yet.
+     */
+    public void addWatchedFolder(final WatchedFolder toAdd) {
+        synchronized ( this.watchedFolders ) {
+            WatchedFolder existing = null;
+            for(WatchedFolder wf : this.watchedFolders) {
+                if (wf.getPath().equals(toAdd.getPath())) {
+                    existing = wf;
+                    break;
+                }
+            }
+            if (existing == null) {
+                this.watchedFolders.add(toAdd);
+                toAdd.start();
+            }
+        }
+    }
+
+    public boolean anyWatchFolderNeedsScan() {
+        synchronized ( this.watchedFolders ) {
+            for (final WatchedFolder wf : this.watchedFolders) {
+                if (wf.needsScan()) {
+                    return true;
+                }
+            }
+        }
+        return false;
     }
 }

Modified: sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/JcrInstaller.java
URL: http://svn.apache.org/viewvc/sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/JcrInstaller.java?rev=1671768&r1=1671767&r2=1671768&view=diff
==============================================================================
--- sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/JcrInstaller.java (original)
+++ sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/JcrInstaller.java Tue Apr  7 09:17:11 2015
@@ -26,7 +26,6 @@ import java.util.ArrayList;
 import java.util.Calendar;
 import java.util.Dictionary;
 import java.util.Hashtable;
-import java.util.Iterator;
 import java.util.LinkedList;
 import java.util.List;
 import java.util.Map;
@@ -261,13 +260,7 @@ public class JcrInstaller implements Upd
                 }
 
                 // Scan watchedFolders and register resources with installer
-                final List<InstallableResource> resources = new LinkedList<InstallableResource>();
-                for(final WatchedFolder f : cfg.getWatchedFolders()) {
-                    f.start();
-                    final WatchedFolder.ScanResult r = f.scan();
-                    logger.debug("Startup: {} provides resources {}", f, r.toAdd);
-                    resources.addAll(r.toAdd);
-                }
+                final List<InstallableResource> resources = cfg.scanWatchedFolders();
                 logger.debug("Registering {} resources with OSGi installer: {}", resources.size(), resources);
                 installer.registerResources(URL_SCHEME, resources.toArray(new InstallableResource[resources.size()]));
                 this.active.set(true);
@@ -470,7 +463,7 @@ public class JcrInstaller implements Upd
         final String path = n.getPath();
         final int priority = cfg.getFolderNameFilter().getPriority(path);
         if (priority > 0) {
-            addWatchedFolder(cfg, new WatchedFolder(session, path, priority, cfg.getConverters()));
+            cfg.addWatchedFolder(new WatchedFolder(session, path, priority, cfg.getConverters()));
         }
         final int depth = path.split("/").length;
         if(depth > cfg.getMaxWatchedFolderDepth()) {
@@ -484,24 +477,6 @@ public class JcrInstaller implements Upd
     }
 
     /**
-     * Add WatchedFolder to our list if it doesn't exist yet.
-     */
-    private void addWatchedFolder(final InstallerConfig cfg, final WatchedFolder toAdd)
-    throws RepositoryException {
-        WatchedFolder existing = null;
-        for(WatchedFolder wf : cfg.getWatchedFolders()) {
-            if (wf.getPath().equals(toAdd.getPath())) {
-                existing = wf;
-                break;
-            }
-        }
-        if (existing == null) {
-            toAdd.start();
-            cfg.getWatchedFolders().add(toAdd);
-        }
-    }
-
-    /**
      * Add new folders to watch if any have been detected
      * @return a list of InstallableResource that must be unregistered,
      *  	for folders that have been removed
@@ -509,25 +484,12 @@ public class JcrInstaller implements Upd
     private List<String> updateFoldersList(final InstallerConfig cfg, final Session session) throws Exception {
         logger.debug("Updating folder list.");
 
-	    for(String root : cfg.getRoots()) {
+	    for(final String root : cfg.getRoots()) {
 	        findPathsToWatch(cfg, session, root);
 	    }
 
         // Check all WatchedFolder, in case some were deleted
-        final List<String> removedResources = new LinkedList<String>();
-
-        final Iterator<WatchedFolder> i = cfg.getWatchedFolders().iterator();
-        while ( i.hasNext() ) {
-            final WatchedFolder wf = i.next();
-
-            logger.debug("Item {} exists? {}", wf.getPath(), session.itemExists(wf.getPath()));
-            if (!session.itemExists(wf.getPath())) {
-                logger.info("Deleting {}, path does not exist anymore", wf);
-                removedResources.addAll(wf.scan().toRemove);
-                wf.stop();
-                i.remove();
-            }
-        }
+        final List<String> removedResources = cfg.checkForRemovedWatchedFolders(session);
 
         return removedResources;
     }
@@ -554,7 +516,7 @@ public class JcrInstaller implements Upd
         try {
             boolean didRefresh = false;
 
-            if (anyWatchFolderNeedsScan(cfg)) {
+            if (cfg.anyWatchFolderNeedsScan()) {
                 session.refresh(false);
                 didRefresh = true;
                 if (scanningIsPaused(cfg, session)) {
@@ -572,7 +534,7 @@ public class JcrInstaller implements Upd
 
             // Rescan WatchedFolders if needed
             boolean scanWf = false;
-            for(final WatchedFolder wf : cfg.getWatchedFolders()) {
+            for(final WatchedFolder wf : cfg.cloneWatchedFolders()) {
                 if (!wf.needsScan()) {
                     continue;
                 }
@@ -648,15 +610,6 @@ public class JcrInstaller implements Upd
         }
         return false;
     }
-
-    private boolean anyWatchFolderNeedsScan(final InstallerConfig cfg) {
-        for (WatchedFolder wf : cfg.getWatchedFolders()) {
-            if (wf.needsScan()) {
-                return true;
-            }
-        }
-        return false;
-    }
 
     long [] getCounters() {
         return counters;

Modified: sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/RootFolderListener.java
URL: http://svn.apache.org/viewvc/sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/RootFolderListener.java?rev=1671768&r1=1671767&r2=1671768&view=diff
==============================================================================
--- sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/RootFolderListener.java (original)
+++ sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/RootFolderListener.java Tue Apr  7 09:17:11 2015
@@ -18,7 +18,6 @@
  */
 package org.apache.sling.installer.provider.jcr.impl;
 
-import java.util.ArrayList;
 import java.util.List;
 
 import javax.jcr.RepositoryException;
@@ -75,7 +74,7 @@ class RootFolderListener implements Even
         // we only do the global scan for node changes
         boolean globalScan = false;
         // copy watched folders
-        final List<WatchedFolder> checkFolders = new ArrayList<WatchedFolder>(cfg.getWatchedFolders());
+        final List<WatchedFolder> checkFolders = cfg.cloneWatchedFolders();
         while(it.hasNext()) {
             final Event e = it.nextEvent();
             logger.debug("Got event {}", e);
@@ -87,7 +86,7 @@ class RootFolderListener implements Even
 
                 for(final WatchedFolder folder : checkFolders) {
                     if ( path.startsWith(folder.getPathWithSlash()) ) {
-                        folder.onEvent(it);
+                        folder.markForScan();
                         checkFolders.remove(folder);
                         break;
                     }

Modified: sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/WatchedFolder.java
URL: http://svn.apache.org/viewvc/sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/WatchedFolder.java?rev=1671768&r1=1671767&r2=1671768&view=diff
==============================================================================
--- sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/WatchedFolder.java (original)
+++ sling/trunk/installer/providers/jcr/src/main/java/org/apache/sling/installer/provider/jcr/impl/WatchedFolder.java Tue Apr  7 09:17:11 2015
@@ -31,9 +31,6 @@ import javax.jcr.Node;
 import javax.jcr.NodeIterator;
 import javax.jcr.RepositoryException;
 import javax.jcr.Session;
-import javax.jcr.observation.Event;
-import javax.jcr.observation.EventIterator;
-import javax.jcr.observation.EventListener;
 
 import org.apache.sling.installer.api.InstallableResource;
 import org.slf4j.Logger;
@@ -42,9 +39,9 @@ import org.slf4j.LoggerFactory;
 /** Watch a single folder in the JCR Repository, detecting changes
  *  to it and providing InstallableData for its contents.
  */
-class WatchedFolder implements EventListener{
+class WatchedFolder {
 
-    private final Logger log = LoggerFactory.getLogger(getClass());
+    private final Logger logger = LoggerFactory.getLogger(getClass());
 
     private final String path;
     private final String pathWithSlash;
@@ -76,32 +73,14 @@ class WatchedFolder implements EventList
         this.pathWithSlash = path.concat("/");
         this.converters = converters;
         this.priority = priority;
-
         this.session = session;
     }
 
-    public void start() throws RepositoryException {
-        // observe any changes in our folder (and under it, as changes to properties
-        // might be lower in the hierarchy)
-        final int eventTypes = Event.NODE_ADDED | Event.NODE_REMOVED
-                | Event.PROPERTY_ADDED | Event.PROPERTY_CHANGED | Event.PROPERTY_REMOVED;
-        final boolean isDeep = true;
-        final boolean noLocal = true;
-//        session.getWorkspace().getObservationManager().addEventListener(this, eventTypes, path,
-//                isDeep, null, null, noLocal);
+    public void start() {
+        logger.info("Watching folder {} (priority {})", path, priority);
         this.needsScan = true;
-
-        log.info("Watching folder {} (priority {})", path, priority);
     }
 
-    public void stop() {
-/*    	try {
-	    	session.getWorkspace().getObservationManager().removeEventListener(this);
-    	} catch(RepositoryException re) {
-    		log.warn("RepositoryException in stop()", re);
-    	}
-*/    }
-
     @Override
     public String toString() {
     	return getClass().getSimpleName() + ":" + path;
@@ -118,8 +97,8 @@ class WatchedFolder implements EventList
     /**
      * Update scan flag whenever an observation event occurs.
      */
-    public void onEvent(final EventIterator it) {
-        log.debug("JCR events received for path {}", path);
+    public void markForScan() {
+        logger.debug("JCR events received for path {}", path);
         needsScan = true;
     }
 
@@ -135,7 +114,7 @@ class WatchedFolder implements EventList
      * <code>ScanResult</code> containing the <code>InstallableResource</code>s.
      */
     public ScanResult scan() throws RepositoryException {
-        log.debug("Scanning {}", path);
+        logger.debug("Scanning {}", path);
         needsScan = false;
 
         Node folder = null;
@@ -186,8 +165,8 @@ class WatchedFolder implements EventList
                     processed = true;
                     resourcesSeen.add(r.getId());
                     final String oldDigest = digests.get(r.getId());
-                    if(r.getDigest().equals(oldDigest)) {
-                        log.debug("Digest didn't change, ignoring " + r);
+                    if (r.getDigest().equals(oldDigest)) {
+                        logger.debug("Digest didn't change, ignoring " + r);
                     } else {
                         result.toAdd.add(r);
                     }

Modified: sling/trunk/installer/providers/jcr/src/test/java/org/apache/sling/installer/provider/jcr/impl/FindPathsToWatchTest.java
URL: http://svn.apache.org/viewvc/sling/trunk/installer/providers/jcr/src/test/java/org/apache/sling/installer/provider/jcr/impl/FindPathsToWatchTest.java?rev=1671768&r1=1671767&r2=1671768&view=diff
==============================================================================
--- sling/trunk/installer/providers/jcr/src/test/java/org/apache/sling/installer/provider/jcr/impl/FindPathsToWatchTest.java (original)
+++ sling/trunk/installer/providers/jcr/src/test/java/org/apache/sling/installer/provider/jcr/impl/FindPathsToWatchTest.java Tue Apr  7 09:17:11 2015
@@ -24,8 +24,6 @@ import javax.jcr.Session;
 
 import org.apache.sling.commons.testing.jcr.EventHelper;
 import org.apache.sling.commons.testing.jcr.RepositoryTestBase;
-import org.apache.sling.installer.provider.jcr.impl.JcrInstaller;
-import org.apache.sling.installer.provider.jcr.impl.WatchedFolder;
 import org.apache.sling.jcr.api.SlingRepository;
 
 /** Verify that the JcrInstaller finds all folders that must
@@ -125,10 +123,9 @@ public class FindPathsToWatchTest extend
     }
 
     public void testDeleteWatchedFolders() throws Exception {
-        final Collection<WatchedFolder> wf = MiscUtil.getWatchedFolders(installer);
-        assertEquals("activate() must find all watched folders", contentHelper.WATCHED_FOLDERS.length, wf.size());
+        assertEquals("activate() must find all watched folders", contentHelper.WATCHED_FOLDERS.length, MiscUtil.getWatchedFolders(installer).size());
         contentHelper.cleanupContent();
         MiscUtil.waitAfterContentChanges(eventHelper, installer);
-        assertEquals("After deleting content, no more folders must be watched", 0, wf.size());
+        assertEquals("After deleting content, no more folders must be watched", 0, MiscUtil.getWatchedFolders(installer).size());
     }
 }
\ No newline at end of file

Modified: sling/trunk/installer/providers/jcr/src/test/java/org/apache/sling/installer/provider/jcr/impl/MiscUtil.java
URL: http://svn.apache.org/viewvc/sling/trunk/installer/providers/jcr/src/test/java/org/apache/sling/installer/provider/jcr/impl/MiscUtil.java?rev=1671768&r1=1671767&r2=1671768&view=diff
==============================================================================
--- sling/trunk/installer/providers/jcr/src/test/java/org/apache/sling/installer/provider/jcr/impl/MiscUtil.java (original)
+++ sling/trunk/installer/providers/jcr/src/test/java/org/apache/sling/installer/provider/jcr/impl/MiscUtil.java Tue Apr  7 09:17:11 2015
@@ -96,11 +96,10 @@ class MiscUtil {
     }
 
     /** Get the WatchedFolders of supplied JcrInstaller */
-    @SuppressWarnings({ "unchecked"})
-    static Collection<WatchedFolder> getWatchedFolders(JcrInstaller installer) throws Exception {
+    static Collection<WatchedFolder> getWatchedFolders(final JcrInstaller installer) {
         final InstallerConfig cfg = installer.getConfiguration();
 
-        return cfg.getWatchedFolders();
+        return cfg.cloneWatchedFolders();
     }
 
     /** Wait long enough for all changes in content to be processed by JcrInstaller */