This is an automated email from the ASF dual-hosted git repository.
jlahoda pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/netbeans.git
The following commit(s) were added to refs/heads/master by this push:
new 18524270fd [NETBEANS-6881][NETBEANS-6880][NETBEANS-6921] Additional
fixes for the multi-file launcher: - checking for null return result for
getClassPath(COMPILE) - filtering out directories that belong to a project from
the multi-file launcher source path - more thoroughly prevent creating of the
multi-file launcher source ClassPath for files under projects - never touch
read-only filesystems (i.e. typically jars/zip) - do not register the source CP
into GlobalPathRegistry by de [...]
new 7fc8a87c21 Merge pull request #6912 from
lahodaj/multi-file-launcher-fixes
18524270fd is described below
commit 18524270fd822604724ca07acf3b578663d64f40
Author: Jan Lahoda <[email protected]>
AuthorDate: Wed Jan 3 11:12:35 2024 +0100
[NETBEANS-6881][NETBEANS-6880][NETBEANS-6921] Additional fixes for the
multi-file launcher:
- checking for null return result for getClassPath(COMPILE)
- filtering out directories that belong to a project from the multi-file
launcher source path
- more thoroughly prevent creating of the multi-file launcher source
ClassPath for files under projects
- never touch read-only filesystems (i.e. typically jars/zip)
- do not register the source CP into GlobalPathRegistry by default in the
IDE - the behavior can either be overriden using a localization bundle
---
.../lsp/client/bindings/CustomIndexerImpl.java | 7 ++-
java/java.file.launcher/nbproject/project.xml | 18 ++++++
.../launcher/AttributeBasedSingleFileOptions.java | 6 +-
.../modules/java/file/launcher/SharedRootData.java | 10 +--
.../java/file/launcher/SingleSourceFileUtil.java | 13 +++-
.../launcher/indexer/CompilerOptionsIndexer.java | 14 ++++-
.../launcher/queries/MultiSourceRootProvider.java | 72 +++++++++++++++++++++-
.../java/file/launcher/queries/Bundle.properties | 18 ++++++
.../modules/java/source/indexing/APTUtils.java | 8 ++-
9 files changed, 141 insertions(+), 25 deletions(-)
diff --git
a/ide/lsp.client/src/org/netbeans/modules/lsp/client/bindings/CustomIndexerImpl.java
b/ide/lsp.client/src/org/netbeans/modules/lsp/client/bindings/CustomIndexerImpl.java
index c46c3d4095..9e97e8c736 100644
---
a/ide/lsp.client/src/org/netbeans/modules/lsp/client/bindings/CustomIndexerImpl.java
+++
b/ide/lsp.client/src/org/netbeans/modules/lsp/client/bindings/CustomIndexerImpl.java
@@ -51,8 +51,13 @@ public class CustomIndexerImpl extends CustomIndexer {
@Override
protected void index(Iterable<? extends Indexable> files, Context context)
{
+ FileObject root = context.getRoot();
+
+ if (root == null) {
+ return ; //ignore
+ }
+
handleStoredFiles(context, props -> {
- FileObject root = context.getRoot();
for (Indexable i : files) {
FileObject file = root.getFileObject(i.getRelativePath());
if (file != null) {
diff --git a/java/java.file.launcher/nbproject/project.xml
b/java/java.file.launcher/nbproject/project.xml
index d5520075de..195981d25e 100644
--- a/java/java.file.launcher/nbproject/project.xml
+++ b/java/java.file.launcher/nbproject/project.xml
@@ -140,6 +140,15 @@
<specification-version>1.84</specification-version>
</run-dependency>
</dependency>
+ <dependency>
+
<code-name-base>org.netbeans.modules.parsing.api</code-name-base>
+ <build-prerequisite/>
+ <compile-dependency/>
+ <run-dependency>
+ <release-version>1</release-version>
+ <specification-version>9.30</specification-version>
+ </run-dependency>
+ </dependency>
<dependency>
<code-name-base>org.netbeans.modules.parsing.indexing</code-name-base>
<build-prerequisite/>
@@ -166,6 +175,15 @@
<specification-version>1.63</specification-version>
</run-dependency>
</dependency>
+ <dependency>
+
<code-name-base>org.netbeans.spi.editor.hints</code-name-base>
+ <build-prerequisite/>
+ <compile-dependency/>
+ <run-dependency>
+ <release-version>0</release-version>
+ <specification-version>1.65</specification-version>
+ </run-dependency>
+ </dependency>
<dependency>
<code-name-base>org.openide.filesystems</code-name-base>
<build-prerequisite/>
diff --git
a/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/AttributeBasedSingleFileOptions.java
b/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/AttributeBasedSingleFileOptions.java
index 586415f3c4..cfa6c4d209 100644
---
a/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/AttributeBasedSingleFileOptions.java
+++
b/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/AttributeBasedSingleFileOptions.java
@@ -19,8 +19,6 @@
package org.netbeans.modules.java.file.launcher;
import javax.swing.event.ChangeListener;
-import org.netbeans.api.project.FileOwnerQuery;
-import org.netbeans.api.project.Project;
import org.netbeans.modules.java.file.launcher.queries.MultiSourceRootProvider;
import
org.netbeans.modules.java.file.launcher.spi.SingleFileOptionsQueryImplementation;
import org.openide.filesystems.FileAttributeEvent;
@@ -38,9 +36,7 @@ public class AttributeBasedSingleFileOptions implements
SingleFileOptionsQueryIm
@Override
public Result optionsFor(FileObject file) {
- Project p = FileOwnerQuery.getOwner(file);
-
- if (p != null) {
+ if (!SingleSourceFileUtil.isSupportedFile(file)) {
return null;
}
diff --git
a/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/SharedRootData.java
b/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/SharedRootData.java
index 3c9d909922..98530378dd 100644
---
a/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/SharedRootData.java
+++
b/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/SharedRootData.java
@@ -18,16 +18,13 @@
*/
package org.netbeans.modules.java.file.launcher;
-import java.io.File;
import java.io.IOException;
import java.util.Enumeration;
import java.util.HashMap;
-import java.util.List;
import java.util.Map;
import java.util.TreeMap;
import java.util.logging.Level;
import java.util.logging.Logger;
-import java.util.stream.Collectors;
import org.netbeans.api.annotations.common.CheckForNull;
import org.netbeans.modules.java.file.launcher.api.SourceLauncher;
import org.openide.filesystems.FileAttributeEvent;
@@ -36,8 +33,6 @@ import org.openide.filesystems.FileChangeListener;
import org.openide.filesystems.FileEvent;
import org.openide.filesystems.FileObject;
import org.openide.filesystems.FileUtil;
-import org.openide.modules.SpecificationVersion;
-import org.openide.util.Exceptions;
/**
*
@@ -108,10 +103,7 @@ public class SharedRootData {
}
String joinedCommandLine =
SourceLauncher.joinCommandLines(options.values());
try {
- if (
- !root.getFileSystem().isReadOnly() // Skip read-only FSes
(like JarFileSystem)
- &&
!joinedCommandLine.equals(root.getAttribute(SingleSourceFileUtil.FILE_VM_OPTIONS))
- ) {
+ if
(!joinedCommandLine.equals(root.getAttribute(SingleSourceFileUtil.FILE_VM_OPTIONS)))
{
root.setAttribute(SingleSourceFileUtil.FILE_VM_OPTIONS,
joinedCommandLine);
}
} catch (IOException ex) {
diff --git
a/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/SingleSourceFileUtil.java
b/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/SingleSourceFileUtil.java
index 65b6fc08fd..0d18a7b12c 100644
---
a/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/SingleSourceFileUtil.java
+++
b/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/SingleSourceFileUtil.java
@@ -34,6 +34,7 @@ import
org.netbeans.modules.java.file.launcher.spi.SingleFileOptionsQueryImpleme
import
org.netbeans.modules.java.file.launcher.spi.SingleFileOptionsQueryImplementation.Result;
import org.netbeans.spi.java.queries.CompilerOptionsQueryImplementation;
import org.openide.filesystems.FileObject;
+import org.openide.filesystems.FileStateInvalidException;
import org.openide.filesystems.FileUtil;
import org.openide.loaders.DataObject;
import org.openide.util.Lookup;
@@ -74,13 +75,21 @@ public final class SingleSourceFileUtil {
}
public static boolean isSingleSourceFile(FileObject fObj) {
- Project p = FileOwnerQuery.getOwner(fObj);
- if (p != null || !fObj.getExt().equalsIgnoreCase("java")) { //NOI18N
+ if (!isSupportedFile(fObj) || !fObj.getExt().equalsIgnoreCase("java"))
{ //NOI18N
return false;
}
return true;
}
+ public static boolean isSupportedFile(FileObject file) {
+ try {
+ return !MultiSourceRootProvider.DISABLE_MULTI_SOURCE_ROOT &&
+ FileOwnerQuery.getOwner(file) == null &&
+ !file.getFileSystem().isReadOnly();
+ } catch (FileStateInvalidException ex) {
+ return false;
+ }
+ }
public static Process compileJavaSource(FileObject fileObject) {
FileObject javac =
JavaPlatformManager.getDefault().getDefaultPlatform().findTool("javac");
//NOI18N
File javacFile = FileUtil.toFile(javac);
diff --git
a/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/indexer/CompilerOptionsIndexer.java
b/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/indexer/CompilerOptionsIndexer.java
index d541b4c776..b8fe279be4 100644
---
a/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/indexer/CompilerOptionsIndexer.java
+++
b/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/indexer/CompilerOptionsIndexer.java
@@ -20,11 +20,12 @@ package org.netbeans.modules.java.file.launcher.indexer;
import org.netbeans.modules.java.file.launcher.SharedRootData;
import org.netbeans.api.editor.mimelookup.MimeRegistration;
-import org.netbeans.api.project.FileOwnerQuery;
+import org.netbeans.modules.java.file.launcher.SingleSourceFileUtil;
import org.netbeans.modules.parsing.spi.indexing.Context;
import org.netbeans.modules.parsing.spi.indexing.CustomIndexer;
import org.netbeans.modules.parsing.spi.indexing.CustomIndexerFactory;
import org.netbeans.modules.parsing.spi.indexing.Indexable;
+import org.openide.filesystems.FileObject;
/**
*
@@ -35,10 +36,17 @@ public class CompilerOptionsIndexer extends CustomIndexer {
@Override
protected void index(Iterable<? extends Indexable> files, Context context)
{
- if (FileOwnerQuery.getOwner(context.getRoot()) != null) {
+ FileObject root = context.getRoot();
+
+ if (root == null) {
+ return ; //ignore
+ }
+
+ if (!SingleSourceFileUtil.isSupportedFile(root)) {
return ; //ignore roots under projects
}
- SharedRootData.ensureRootRegistered(context.getRoot());
+
+ SharedRootData.ensureRootRegistered(root);
}
diff --git
a/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/queries/MultiSourceRootProvider.java
b/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/queries/MultiSourceRootProvider.java
index 7f5061d3fa..ad76218b3e 100644
---
a/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/queries/MultiSourceRootProvider.java
+++
b/java/java.file.launcher/src/org/netbeans/modules/java/file/launcher/queries/MultiSourceRootProvider.java
@@ -21,6 +21,8 @@ package org.netbeans.modules.java.file.launcher.queries;
import java.beans.PropertyChangeListener;
import java.beans.PropertyChangeSupport;
import java.io.IOException;
+import java.lang.ref.Reference;
+import java.lang.ref.WeakReference;
import java.net.URL;
import java.util.ArrayList;
import java.util.Arrays;
@@ -32,6 +34,7 @@ import java.util.Map;
import java.util.Objects;
import java.util.Set;
import java.util.WeakHashMap;
+import java.util.concurrent.atomic.AtomicReference;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
import org.netbeans.api.java.classpath.ClassPath;
@@ -41,6 +44,7 @@ import org.netbeans.api.java.lexer.JavaTokenId;
import org.netbeans.api.java.platform.JavaPlatformManager;
import org.netbeans.api.lexer.TokenHierarchy;
import org.netbeans.api.lexer.TokenSequence;
+import org.netbeans.api.project.FileOwnerQuery;
import org.netbeans.api.queries.FileEncodingQuery;
import org.netbeans.modules.java.file.launcher.SingleSourceFileUtil;
import
org.netbeans.modules.java.file.launcher.spi.SingleFileOptionsQueryImplementation;
@@ -48,11 +52,14 @@ import org.netbeans.spi.java.classpath.ClassPathFactory;
import org.netbeans.spi.java.classpath.ClassPathImplementation;
import static
org.netbeans.spi.java.classpath.ClassPathImplementation.PROP_RESOURCES;
import org.netbeans.spi.java.classpath.ClassPathProvider;
+import org.netbeans.spi.java.classpath.FilteringPathResourceImplementation;
import org.netbeans.spi.java.classpath.PathResourceImplementation;
import org.netbeans.spi.java.classpath.support.ClassPathSupport;
import org.openide.filesystems.FileObject;
import org.openide.filesystems.FileUtil;
+import org.openide.filesystems.URLMapper;
import org.openide.util.Exceptions;
+import org.openide.util.NbBundle.Messages;
import org.openide.util.lookup.ServiceProvider;
import org.openide.util.lookup.ServiceProviders;
@@ -89,7 +96,7 @@ public class MultiSourceRootProvider implements
ClassPathProvider {
}
private ClassPath getSourcePath(FileObject file) {
- if (DISABLE_MULTI_SOURCE_ROOT) return null;
+ if (!SingleSourceFileUtil.isSupportedFile(file)) return null;
synchronized (this) {
//XXX: what happens if there's a Java file in user's home???
if (file.isValid() && file.isData() &&
"text/x-java".equals(file.getMIMEType())) {
@@ -116,8 +123,10 @@ public class MultiSourceRootProvider implements
ClassPathProvider {
}
return root2SourceCP.computeIfAbsent(root, r -> {
- ClassPath srcCP =
ClassPathSupport.createClassPath(r);
-
GlobalPathRegistry.getDefault().register(ClassPath.SOURCE, new ClassPath[]
{srcCP});
+ ClassPath srcCP =
ClassPathSupport.createClassPath(Arrays.asList(new
RootPathResourceImplementation(r)));
+ if (registerRoot(r)) {
+
GlobalPathRegistry.getDefault().register(ClassPath.SOURCE, new ClassPath[]
{srcCP});
+ }
return srcCP;
});
} catch (IOException ex) {
@@ -234,6 +243,13 @@ public class MultiSourceRootProvider implements
ClassPathProvider {
}
}
+ @Messages({
+ "SETTING_AutoRegisterAsRoot=false"
+ })
+ private static boolean registerRoot(FileObject root) {
+ return "true".equals(Bundle.SETTING_AutoRegisterAsRoot());
+ }
+
private static final class AttributeBasedClassPathImplementation
implements ChangeListener, ClassPathImplementation {
private final PropertyChangeSupport pcs = new
PropertyChangeSupport(this);
private final SingleFileOptionsQueryImplementation.Result delegate;
@@ -299,4 +315,54 @@ public class MultiSourceRootProvider implements
ClassPathProvider {
}
+ private static final class RootPathResourceImplementation implements
FilteringPathResourceImplementation {
+
+ private final URL root;
+ private final URL[] roots;
+ private final AtomicReference<String> lastCheckedAsIncluded = new
AtomicReference<>();
+
+ public RootPathResourceImplementation(FileObject root) {
+ this.root = root.toURL();
+ this.roots = new URL[] {this.root};
+ }
+
+ @Override
+ public boolean includes(URL root, String resource) {
+ if (!resource.endsWith("/")) {
+ int lastSlash = resource.lastIndexOf('/');
+ if (lastSlash != (-1)) {
+ resource = resource.substring(0, lastSlash + 1);
+ }
+ }
+ if (resource.equals(lastCheckedAsIncluded.get())) {
+ return true;
+ }
+ FileObject fo = URLMapper.findFileObject(root);
+ fo = fo != null ? fo.getFileObject(resource) : null;
+ boolean included = fo == null || FileOwnerQuery.getOwner(fo) ==
null;
+ if (included) {
+ lastCheckedAsIncluded.set(resource);
+ }
+ return included;
+ }
+
+ @Override
+ public URL[] getRoots() {
+ return roots;
+ }
+
+ @Override
+ public ClassPathImplementation getContent() {
+ return null;
+ }
+
+ @Override
+ public void addPropertyChangeListener(PropertyChangeListener listener)
{
+ }
+
+ @Override
+ public void removePropertyChangeListener(PropertyChangeListener
listener) {
+ }
+
+ }
}
diff --git
a/java/java.lsp.server/nbcode/branding/modules/org-netbeans-modules-java-file-launcher.jar/org/netbeans/modules/java/file/launcher/queries/Bundle.properties
b/java/java.lsp.server/nbcode/branding/modules/org-netbeans-modules-java-file-launcher.jar/org/netbeans/modules/java/file/launcher/queries/Bundle.properties
new file mode 100644
index 0000000000..684c2d3a5f
--- /dev/null
+++
b/java/java.lsp.server/nbcode/branding/modules/org-netbeans-modules-java-file-launcher.jar/org/netbeans/modules/java/file/launcher/queries/Bundle.properties
@@ -0,0 +1,18 @@
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you 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.
+
+SETTING_AutoRegisterAsRoot=true
diff --git
a/java/java.source.base/src/org/netbeans/modules/java/source/indexing/APTUtils.java
b/java/java.source.base/src/org/netbeans/modules/java/source/indexing/APTUtils.java
index 5f47ca7cd4..58f01106fc 100644
---
a/java/java.source.base/src/org/netbeans/modules/java/source/indexing/APTUtils.java
+++
b/java/java.source.base/src/org/netbeans/modules/java/source/indexing/APTUtils.java
@@ -135,7 +135,9 @@ public class APTUtils implements ChangeListener,
PropertyChangeListener {
this.root = root;
bootPath = ClassPath.getClassPath(root, ClassPath.BOOT);
compilePath = ClassPath.getClassPath(root, ClassPath.COMPILE);
- compilePath.addPropertyChangeListener(this);
+ if (compilePath != null) {
+ compilePath.addPropertyChangeListener(this);
+ }
processorPath = new AtomicReference<>(ClassPath.getClassPath(root,
JavaClassPathConstants.PROCESSOR_PATH));
processorModulePath = new
AtomicReference<>(ClassPath.getClassPath(root,
JavaClassPathConstants.MODULE_PROCESSOR_PATH));
aptOptions =
AnnotationProcessingQuery.getAnnotationProcessingOptions(root);
@@ -360,7 +362,9 @@ public class APTUtils implements ChangeListener,
PropertyChangeListener {
compilePath.removePropertyChangeListener(this);
}
compilePath = ClassPath.getClassPath(root, ClassPath.COMPILE);
- compilePath.addPropertyChangeListener(this);
+ if (compilePath != null) {
+ compilePath.addPropertyChangeListener(this);
+ }
listenOnProcessorPath(pp, this);
classLoaderCache = null;
}
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]
For further information about the NetBeans mailing lists, visit:
https://cwiki.apache.org/confluence/display/NETBEANS/Mailing+lists