[hg] main-silver: #223269:The indexing reacts on VisibilityChang...

  • From: Tomas Zezula < >
  • To:
  • Subject: [hg] main-silver: #223269:The indexing reacts on VisibilityChang...
  • Date: Tue, 04 Dec 2012 14:39:11 -0800

changeset 8dd5618a3d2d in main-silver ((none))
details: http://hg.netbeans.org/main-silver/rev/8dd5618a3d2d
description:
        #223269:The indexing reacts on VisibilityChanges even after IDE is 
stoped

diffstat:

 
parsing.api/src/org/netbeans/modules/parsing/impl/indexing/RepositoryUpdater.java
              |   93 +----
 
parsing.api/src/org/netbeans/modules/parsing/impl/indexing/VisibilitySupport.java
              |  174 ++++++++++
 
parsing.api/test/unit/src/org/netbeans/modules/parsing/impl/indexing/VisibilityChangeTest.java
 |   42 ++
 3 files changed, 227 insertions(+), 82 deletions(-)

diffs (423 lines):

diff --git 
a/parsing.api/src/org/netbeans/modules/parsing/impl/indexing/RepositoryUpdater.java
 
b/parsing.api/src/org/netbeans/modules/parsing/impl/indexing/RepositoryUpdater.java
--- 
a/parsing.api/src/org/netbeans/modules/parsing/impl/indexing/RepositoryUpdater.java
+++ 
b/parsing.api/src/org/netbeans/modules/parsing/impl/indexing/RepositoryUpdater.java
@@ -138,7 +138,7 @@
  * @author Tomas Zezula
  */
 @SuppressWarnings("ClassWithMultipleLoggers")
-public final class RepositoryUpdater implements PathRegistryListener, 
ChangeListener, PropertyChangeListener, DocumentListener, AtomicLockListener {
+public final class RepositoryUpdater implements PathRegistryListener, 
PropertyChangeListener, DocumentListener, AtomicLockListener {
     /**
      * If the task is delayed longer than this constant from its schedule to 
execution, the previous task's info
      * will be chained to it. If the user cancels the task, the log will 
also contain the long-blocking predecessor.
@@ -175,7 +175,7 @@
                 EditorRegistry.addPropertyChangeListener(this);
                 IndexerCache.getCifCache().addPropertyChangeListener(this);
                 IndexerCache.getEifCache().addPropertyChangeListener(this);
-                VisibilityQuery.getDefault().addChangeListener(this);
+                visibilitySupport.start();
                 if (force) {
                     work = new InitialRootsWork(
                         scannedRoots2Dependencies,
@@ -206,7 +206,7 @@
                 PathRegistry.getDefault().removePathRegistryListener(this);
                 rootsListeners.setListener(null, null);
                 EditorRegistry.removePropertyChangeListener(this);
-
+                visibilitySupport.stop();
                 cancel = true;
             }
         }
@@ -581,73 +581,11 @@
         }
     }
 
-    @Override
-    public void stateChanged (@NonNull final ChangeEvent event) {
-        visibilityCache.clear();
-        if (Crawler.listenOnVisibility()) {
-            if (visibilityLogCtx.get()==null) {
-                visibilityLogCtx.compareAndSet(null, 
LogContext.create(LogContext.EventType.FILE, null));
-            }
-            visibilityChanged.schedule(VISIBILITY_CHANGE_WINDOW);
-        }
-    }
-
     // 
-----------------------------------------------------------------------
     // FileChangeListener implementation
     // 
-----------------------------------------------------------------------
     
     private final FileEventLog eventQueue = new FileEventLog();
-    //@GuardedBy("visibilityCache")
-    private final Map<FileObject,Boolean> visibilityCache = 
Collections.synchronizedMap(new WeakHashMap<FileObject, Boolean>());
-
-    private boolean isVisible(
-        @NonNull FileObject file,
-        @NullAllowed final FileObject root) {
-        long st = 0L;
-        if (PERF_LOGGER.isLoggable(Level.FINE)) {
-            st = System.currentTimeMillis();
-        }
-        try {
-            final VisibilityQuery vq = VisibilityQuery.getDefault();
-            final Deque<FileObject> fta = new ArrayDeque<FileObject>();
-            Boolean vote = null;
-            boolean folder = false;
-            while (root != null && !root.equals(file)) {
-                vote = visibilityCache.get(file);
-                if (vote != null) {
-                    break;
-                }
-                if (folder || file.isFolder()) {
-                    fta.offer(file);
-                }
-                if (!vq.isVisible(file)) {
-                    vote = Boolean.FALSE;
-                    break;
-                }
-                file = file.getParent();
-                folder = true;
-            }
-            if (vote == null) {
-                vote = vq.isVisible(file);
-                fta.offer(file);
-            }
-            if (!fta.isEmpty()) {
-                synchronized(visibilityCache) {
-                    for (FileObject nf : fta) {
-                        visibilityCache.put(nf, vote);
-                    }
-                }
-            }
-            return vote;
-        } finally {
-            if (PERF_LOGGER.isLoggable(Level.FINE)) {
-                PERF_LOGGER.log(
-                    Level.FINE,
-                    "reportVisibilityOverhead: {0}",    //NOI18N
-                    (System.currentTimeMillis() - st));
-            }
-        }
-    }
 
     private void fileFolderCreatedImpl(FileEvent fe, Boolean source) {
         FileObject fo = fe.getFile();
@@ -668,7 +606,7 @@
         if (fo != null && fo.isValid()) {
             if (source == null || source.booleanValue()) {
                 root = getOwningSourceRoot(fo);
-                if (root != null && isVisible(fo, root.second)) {
+                if (root != null && visibilitySupport.isVisible(fo, 
root.second)) {
                     if (root.second == null) {
                         LOGGER.log(
                             Level.INFO,
@@ -741,7 +679,7 @@
 
             if (!processed && (source == null || !source.booleanValue())) {
                 root = getOwningBinaryRoot(fo);
-                if (root != null && isVisible(fo, root.second)) {
+                if (root != null && visibilitySupport.isVisible(fo, 
root.second)) {
                     final Work wrk = new BinaryWork(
                         root.first,
                         suspendSupport.getSuspendStatus(),
@@ -776,7 +714,7 @@
         if (fo != null && fo.isValid()) {
             if (source == null || source.booleanValue()) {
                 root = getOwningSourceRoot (fo);
-                if (root != null && isVisible(fo,root.second)) {
+                if (root != null && 
visibilitySupport.isVisible(fo,root.second)) {
                     if (root.second == null) {
                         LOGGER.log(
                             Level.INFO,
@@ -808,7 +746,7 @@
 
             if (!processed && (source == null || !source.booleanValue())) {
                 root = getOwningBinaryRoot(fo);
-                if (root != null && isVisible(fo,root.second)) {
+                if (root != null && 
visibilitySupport.isVisible(fo,root.second)) {
                     final Work wrk = new BinaryWork(
                         root.first,
                         suspendSupport.getSuspendStatus(),
@@ -849,7 +787,7 @@
         if (fo != null) {
             if (source == null || source.booleanValue()) {
                 root = getOwningSourceRoot (fo);
-                if (root != null && fo.isData() && isVisible(fo, 
root.second)) {
+                if (root != null && fo.isData() && 
visibilitySupport.isVisible(fo, root.second)) {
                     String relativePath = null;
                     try {
                     //Root may be deleted -> no root.second available
@@ -878,7 +816,7 @@
 
             if (!processed && (source == null || !source.booleanValue())) {
                 root = getOwningBinaryRoot(fo);
-                if (root != null && isVisible(fo, root.second)) {
+                if (root != null && visibilitySupport.isVisible(fo, 
root.second)) {
                     final Work wrk = new BinaryWork(
                         root.first,
                         suspendSupport.getSuspendStatus(),
@@ -959,7 +897,7 @@
                         }
                     }
 
-                    if (isVisible(newFile,root.second)) {
+                    if (visibilitySupport.isVisible(newFile,root.second)) {
                         final boolean sourceForBinaryRoot = 
sourcesForBinaryRoots.contains(root.first);
                         ClassPath.Entry entry = sourceForBinaryRoot ? null : 
getClassPathEntry(rootFo);
                         if (entry == null || entry.includes(newFile)) {
@@ -1259,7 +1197,6 @@
     private static final String PROP_OWNING_SOURCE_ROOT_URL = 
RepositoryUpdater.class.getName() + "-owning-source-root-url"; //NOI18N
     private static final String PROP_OWNING_SOURCE_ROOT = 
RepositoryUpdater.class.getName() + "-owning-source-root"; //NOI18N
     private static final String PROP_OWNING_SOURCE_UNKNOWN_IN = 
RepositoryUpdater.class.getName() + "-owning-source-root-unknown-in"; //NOI18N
-    private static final int VISIBILITY_CHANGE_WINDOW = 500;
     private static final String INDEX_DOWNLOAD_FOLDER = "index-download";   
//NOI18N
 
     /* test */ static final List<URL> EMPTY_DEPS = 
Collections.unmodifiableList(new LinkedList<URL>());
@@ -1304,15 +1241,7 @@
     private final FileChangeListener binaryRootsListener = new 
FCL(Boolean.FALSE);
     private final ThreadLocal<Boolean> inIndexer = new 
ThreadLocal<Boolean>();
 
-    //Todo: Separate visibility to new class
-    private final AtomicReference<LogContext> visibilityLogCtx = new 
AtomicReference<LogContext>();
-    private final RequestProcessor.Task visibilityChanged = RP.create(new 
Runnable() {
-        @Override
-        public void run() {
-            LOGGER.fine ("VisibilityQuery changed, reindexing");    //NOI18N
-            refreshAll(false, false, true, visibilityLogCtx.getAndSet(null));
-        }
-    });
+   private final VisibilitySupport visibilitySupport = 
VisibilitySupport.create(this, RP);
    private final SuspendSupport suspendSupport = new SuspendSupport(WORKER);
    private final AtomicLong scannedRoots2DependenciesLamport = new 
AtomicLong();
 
diff --git 
a/parsing.api/src/org/netbeans/modules/parsing/impl/indexing/VisibilitySupport.java
 
b/parsing.api/src/org/netbeans/modules/parsing/impl/indexing/VisibilitySupport.java
new file mode 100644
--- /dev/null
+++ 
b/parsing.api/src/org/netbeans/modules/parsing/impl/indexing/VisibilitySupport.java
@@ -0,0 +1,174 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright 2012 Oracle and/or its affiliates. All rights reserved.
+ *
+ * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
+ * Other names may be trademarks of their respective owners.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common
+ * Development and Distribution License("CDDL") (collectively, the
+ * "License"). You may not use this file except in compliance with the
+ * License. You can obtain a copy of the License at
+ * http://www.netbeans.org/cddl-gplv2.html
+ * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
+ * specific language governing permissions and limitations under the
+ * License.  When distributing the software, include this License Header
+ * Notice in each file and include the License file at
+ * nbbuild/licenses/CDDL-GPL-2-CP.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the GPL Version 2 section of the License file that
+ * accompanied this code. If applicable, add the following below the
+ * License Header, with the fields enclosed by brackets [] replaced by
+ * your own identifying information:
+ * "Portions Copyrighted [year] [name of copyright owner]"
+ *
+ * If you wish your version of this file to be governed by only the CDDL
+ * or only the GPL Version 2, indicate your decision by adding
+ * "[Contributor] elects to include this software in this distribution
+ * under the [CDDL or GPL Version 2] license." If you do not indicate a
+ * single choice of license, a recipient has the option to distribute
+ * your version of this file under either the CDDL, the GPL Version 2 or
+ * to extend the choice of license to its licensees as provided above.
+ * However, if you add GPL Version 2 code and therefore, elected the GPL
+ * Version 2 license, then the option applies only if the new code is
+ * made subject to such option by the copyright holder.
+ *
+ * Contributor(s):
+ *
+ * Portions Copyrighted 2012 Sun Microsystems, Inc.
+ */
+package org.netbeans.modules.parsing.impl.indexing;
+
+import java.util.ArrayDeque;
+import java.util.Collections;
+import java.util.Deque;
+import java.util.Map;
+import java.util.WeakHashMap;
+import java.util.concurrent.atomic.AtomicReference;
+import java.util.logging.Level;
+import java.util.logging.Logger;
+import javax.swing.event.ChangeEvent;
+import javax.swing.event.ChangeListener;
+import org.netbeans.api.annotations.common.NonNull;
+import org.netbeans.api.annotations.common.NullAllowed;
+import org.netbeans.api.queries.VisibilityQuery;
+import org.openide.filesystems.FileObject;
+import org.openide.util.Parameters;
+import org.openide.util.RequestProcessor;
+
+/**
+ *
+ * @author Tomas Zezula
+ */
+class VisibilitySupport implements ChangeListener {
+
+    private static final int VISIBILITY_CHANGE_WINDOW = 500;
+    private static final Logger LOGGER = 
Logger.getLogger(VisibilitySupport.class.getName());
+    
+    //@GuardedBy("visibilityCache")
+    private final Map<FileObject,Boolean> visibilityCache = 
Collections.synchronizedMap(new WeakHashMap<FileObject, Boolean>());    
+    private final AtomicReference<LogContext> visibilityLogCtx = new 
AtomicReference<LogContext>();
+    private final RequestProcessor.Task visibilityChanged;
+    
+    private VisibilitySupport(
+            @NonNull final RepositoryUpdater ru,
+            @NonNull final RequestProcessor worker) {
+        this.visibilityChanged = worker.create(new SlidingTask(ru));
+    }
+
+    void start() {
+        VisibilityQuery.getDefault().addChangeListener(this);
+    }
+    
+    void stop() {
+        VisibilityQuery.getDefault().removeChangeListener(this);
+    }
+    
+    boolean isVisible(
+        @NonNull FileObject file,
+        @NullAllowed final FileObject root) {
+        long st = 0L;
+        if (LOGGER.isLoggable(Level.FINER)) {
+            st = System.currentTimeMillis();
+        }
+        try {
+            final VisibilityQuery vq = VisibilityQuery.getDefault();
+            final Deque<FileObject> fta = new ArrayDeque<FileObject>();
+            Boolean vote = null;
+            boolean folder = false;
+            while (root != null && !root.equals(file)) {
+                vote = visibilityCache.get(file);
+                if (vote != null) {
+                    break;
+                }
+                if (folder || file.isFolder()) {
+                    fta.offer(file);
+                }
+                if (!vq.isVisible(file)) {
+                    vote = Boolean.FALSE;
+                    break;
+                }
+                file = file.getParent();
+                folder = true;
+            }
+            if (vote == null) {
+                vote = vq.isVisible(file);
+                fta.offer(file);
+            }
+            if (!fta.isEmpty()) {
+                synchronized(visibilityCache) {
+                    for (FileObject nf : fta) {
+                        visibilityCache.put(nf, vote);
+                    }
+                }
+            }
+            return vote;
+        } finally {
+            if (LOGGER.isLoggable(Level.FINER)) {
+                LOGGER.log(
+                    Level.FINER,
+                    "reportVisibilityOverhead: {0}",    //NOI18N
+                    (System.currentTimeMillis() - st));
+            }
+        }
+    }
+
+    @Override
+    public void stateChanged(ChangeEvent e) {
+        visibilityCache.clear();
+        if (Crawler.listenOnVisibility()) {
+            if (visibilityLogCtx.get()==null) {
+                visibilityLogCtx.compareAndSet(null, 
LogContext.create(LogContext.EventType.FILE, null));
+            }
+            visibilityChanged.schedule(VISIBILITY_CHANGE_WINDOW);
+        }
+    }
+
+    private class SlidingTask implements Runnable {
+
+        private final RepositoryUpdater ru;
+
+        SlidingTask(@NonNull final RepositoryUpdater ru) {
+            this.ru = ru;
+        }
+
+        @Override
+        public void run() {
+            LOGGER.fine ("VisibilityQuery changed, reindexing");    //NOI18N
+            ru.refreshAll(false, false, true, 
visibilityLogCtx.getAndSet(null));
+        }
+    }
+
+    @NonNull
+    static VisibilitySupport create(
+        @NonNull final RepositoryUpdater ru,
+        @NonNull final RequestProcessor worker) {
+        Parameters.notNull("ru", ru);   //NOI18N
+        Parameters.notNull("worker", worker);   //NOI18N
+        return new VisibilitySupport(ru, worker);
+    }
+
+
+}
diff --git 
a/parsing.api/test/unit/src/org/netbeans/modules/parsing/impl/indexing/VisibilityChangeTest.java
 
b/parsing.api/test/unit/src/org/netbeans/modules/parsing/impl/indexing/VisibilityChangeTest.java
--- 
a/parsing.api/test/unit/src/org/netbeans/modules/parsing/impl/indexing/VisibilityChangeTest.java
+++ 
b/parsing.api/test/unit/src/org/netbeans/modules/parsing/impl/indexing/VisibilityChangeTest.java
@@ -263,6 +263,48 @@
 
     }
     
+    public void testVisibilityChangeInSingleRoot() throws 
InterruptedException, IOException {
+
+        
assertTrue(GlobalPathRegistry.getDefault().getPaths(FOO_SOURCES).isEmpty());
+        final RepositoryUpdaterTest.TestHandler handler = new 
RepositoryUpdaterTest.TestHandler();
+        final Logger logger = 
Logger.getLogger(RepositoryUpdater.class.getName()+".tests"); //NOI18N
+        logger.setLevel (Level.FINEST);
+        logger.addHandler(handler);
+
+        globalPathRegistry_register(FOO_SOURCES,new ClassPath[]{cp1});
+        assertTrue (handler.await());
+        assertEquals(0, handler.getBinaries().size());
+        assertEquals(4, handler.getSources().size());
+        assertEquals(
+            new URI[] {
+                src1file1.toURI(),
+                src1file2.toURI(),
+                src2file1.toURI(),
+                src2file2.toURI(),
+                src3file1.toURI(),
+                src3file2.toURI(),
+                src4file1.toURI(),
+                src4file2.toURI()
+            },
+            
MimeLookup.getLookup(MimePath.get(FOO_MIME)).lookup(FooIndexerFactory.class).clearIndexedFiles());
+        assertEquals(
+            new URI[0],
+            
MimeLookup.getLookup(MimePath.get(FOO_MIME)).lookup(FooIndexerFactory.class).clearRemovedFiles());
+        handler.reset();
+//        
Lookup.getDefault().lookup(MockVisibilityQuery.class).change(src1file1);
+//        assertTrue (handler.await());
+//        assertEquals(0, handler.getBinaries().size());
+//        assertEquals(1, handler.getSources().size());
+//        assertEquals(
+//            new URI[0],
+//            
MimeLookup.getLookup(MimePath.get(FOO_MIME)).lookup(FooIndexerFactory.class).clearIndexedFiles());
+//        assertEquals(
+//            new URI[]{
+//                src1file1.toURI()
+//            },
+//            
MimeLookup.getLookup(MimePath.get(FOO_MIME)).lookup(FooIndexerFactory.class).clearRemovedFiles());
+    }
+    
     private void assertEquals(URI[] expected, URI[] result) {
         final Set<URI> es = new HashSet<URI>(Arrays.asList(expected));
         final Set<URI> rs = new HashSet<URI>(Arrays.asList(result));

[hg] main-silver: #223269:The indexing reacts on VisibilityChang...

Tomas Zezula 12/04/2012

Project Features

About this Project

Editor was started in November 2009, is owned by Martin Ryzl, and has 147 members.
By use of this website, you agree to the NetBeans Policies and Terms of Use (revision 20131025.e7cbc9d). © 2013, Oracle Corporation and/or its affiliates. Sponsored by Oracle logo
 
 
Close
loading
Please Confirm
Close