SLING-4564 : Use a single listener registered for multiple path in JCR installer.
git-svn-id: https://svn.apache.org/repos/asf/sling/trunk@1671760 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/src/main/java/org/apache/sling/installer/provider/jcr/impl/JcrInstaller.java b/src/main/java/org/apache/sling/installer/provider/jcr/impl/JcrInstaller.java
index 6931ee1..d4b57ab 100644
--- a/src/main/java/org/apache/sling/installer/provider/jcr/impl/JcrInstaller.java
+++ b/src/main/java/org/apache/sling/installer/provider/jcr/impl/JcrInstaller.java
@@ -213,7 +213,7 @@
session = repository.loginAdministrative(repository.getDefaultWorkspace());
for (final String path : cfg.getRoots()) {
- listeners.add(new RootFolderListener(session, path, updateFoldersListTimer));
+ listeners.add(new RootFolderListener(session, path, updateFoldersListTimer, cfg));
logger.debug("Configured root folder: {}", path);
}
diff --git a/src/main/java/org/apache/sling/installer/provider/jcr/impl/RootFolderListener.java b/src/main/java/org/apache/sling/installer/provider/jcr/impl/RootFolderListener.java
index 84535fa..afce64a 100644
--- a/src/main/java/org/apache/sling/installer/provider/jcr/impl/RootFolderListener.java
+++ b/src/main/java/org/apache/sling/installer/provider/jcr/impl/RootFolderListener.java
@@ -18,6 +18,9 @@
*/
package org.apache.sling.installer.provider.jcr.impl;
+import java.util.ArrayList;
+import java.util.List;
+
import javax.jcr.RepositoryException;
import javax.jcr.Session;
import javax.jcr.observation.Event;
@@ -38,14 +41,18 @@
private final RescanTimer timer;
private final String watchedPath;
- RootFolderListener(final Session session, final String path, final RescanTimer timer)
+ private final InstallerConfig cfg;
+
+ RootFolderListener(final Session session, final String path, final RescanTimer timer, final InstallerConfig cfg)
throws RepositoryException {
this.timer = timer;
this.watchedPath = path;
+ this.cfg = cfg;
- int eventTypes = Event.NODE_ADDED | Event.NODE_REMOVED;
- boolean isDeep = true;
- boolean noLocal = true;
+ 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, watchedPath,
isDeep, null, null, noLocal);
@@ -65,14 +72,32 @@
* Schedule a scan.
*/
public void onEvent(final EventIterator it) {
- // we don't care about the events
- // they are only logged if debug log level
- if ( logger.isDebugEnabled() ) {
- while(it.hasNext()) {
- final Event e = it.nextEvent();
- logger.debug("Got event {}", e);
+ // we only do the global scan for node changes
+ boolean globalScan = false;
+ // copy watched folders
+ final List<WatchedFolder> checkFolders = new ArrayList<WatchedFolder>(cfg.getWatchedFolders());
+ while(it.hasNext()) {
+ final Event e = it.nextEvent();
+ logger.debug("Got event {}", e);
+ if ( e.getType() == Event.NODE_ADDED || e.getType() == Event.NODE_REMOVED ) {
+ globalScan = true;
+ }
+ try {
+ final String path = e.getPath();
+
+ for(final WatchedFolder folder : checkFolders) {
+ if ( path.startsWith(folder.getPathWithSlash()) ) {
+ folder.onEvent(it);
+ checkFolders.remove(folder);
+ break;
+ }
+ }
+ } catch ( final RepositoryException re ) {
+ logger.warn("Error while getting path from event", re);
}
}
- timer.scheduleScan();
+ if ( globalScan ) {
+ timer.scheduleScan();
+ }
}
}
diff --git a/src/main/java/org/apache/sling/installer/provider/jcr/impl/WatchedFolder.java b/src/main/java/org/apache/sling/installer/provider/jcr/impl/WatchedFolder.java
index b673be1..fed3bf9 100644
--- a/src/main/java/org/apache/sling/installer/provider/jcr/impl/WatchedFolder.java
+++ b/src/main/java/org/apache/sling/installer/provider/jcr/impl/WatchedFolder.java
@@ -47,6 +47,7 @@
private final Logger log = LoggerFactory.getLogger(getClass());
private final String path;
+ private final String pathWithSlash;
private final int priority;
private final Session session;
private final Collection <JcrInstaller.NodeConverter> converters;
@@ -72,6 +73,7 @@
}
this.path = path;
+ this.pathWithSlash = path.concat("/");
this.converters = converters;
this.priority = priority;
@@ -85,20 +87,20 @@
| 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);
+// session.getWorkspace().getObservationManager().addEventListener(this, eventTypes, path,
+// isDeep, null, null, noLocal);
this.needsScan = true;
log.info("Watching folder {} (priority {})", path, priority);
}
public void stop() {
- try {
+/* try {
session.getWorkspace().getObservationManager().removeEventListener(this);
} catch(RepositoryException re) {
log.warn("RepositoryException in stop()", re);
}
- }
+*/ }
@Override
public String toString() {
@@ -109,6 +111,10 @@
return path;
}
+ public String getPathWithSlash() {
+ return this.pathWithSlash;
+ }
+
/**
* Update scan flag whenever an observation event occurs.
*/