From 9f93c8ad1140617a35a2203bea01d175433db7db Mon Sep 17 00:00:00 2001 From: Svata Dedic Date: Tue, 15 Nov 2022 16:06:42 +0100 Subject: [PATCH 1/8] Do not delete "$JsCallbacks$" and similar custom-generated classes --- .../antsrc/org/netbeans/nbbuild/CustomJavac.java | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/nbbuild/antsrc/org/netbeans/nbbuild/CustomJavac.java b/nbbuild/antsrc/org/netbeans/nbbuild/CustomJavac.java index 54746445ad7f..c2f69cbe836a 100644 --- a/nbbuild/antsrc/org/netbeans/nbbuild/CustomJavac.java +++ b/nbbuild/antsrc/org/netbeans/nbbuild/CustomJavac.java @@ -226,12 +226,16 @@ private void cleanUpDependDebris() { continue; } int i = clazz.indexOf('$'); - File enclosing = new File(d, clazz.substring(0, i) + ".class"); - if (!enclosing.isFile()) { - File enclosed = new File(d, clazz); - log(clazz + " will be deleted since " + enclosing.getName() + " is missing", Project.MSG_VERBOSE); - if (!enclosed.delete()) { - throw new BuildException("could not delete " + enclosed, getLocation()); + // ignore filenames that start right with '$' (separatorChar preceded), these could not be inner classes. + if (i > 0 && clazz.charAt(i - 1) != File.separatorChar) { + File enclosing = new File(d, clazz.substring(0, i) + ".class"); + // no inner class' filename may begin directly with '$', it must be preceded by an outer class' name. + if (!enclosing.isFile()) { + File enclosed = new File(d, clazz); + log(clazz + " will be deleted since " + enclosing.getName() + " is missing", Project.MSG_VERBOSE); + if (!enclosed.delete()) { + throw new BuildException("could not delete " + enclosed, getLocation()); + } } } } From 97eba59aff634bc627f190c79b0bfafda79daa9c Mon Sep 17 00:00:00 2001 From: Svata Dedic Date: Tue, 15 Nov 2022 16:06:48 +0100 Subject: [PATCH 2/8] Additional logging --- .../java/lsp/server/protocol/Server.java | 9 ++ .../java/lsp/server/protocol/ServerTest.java | 141 ++++++++++-------- 2 files changed, 91 insertions(+), 59 deletions(-) diff --git a/java/java.lsp.server/src/org/netbeans/modules/java/lsp/server/protocol/Server.java b/java/java.lsp.server/src/org/netbeans/modules/java/lsp/server/protocol/Server.java index df866c4ccd71..6b5203f4c7f8 100644 --- a/java/java.lsp.server/src/org/netbeans/modules/java/lsp/server/protocol/Server.java +++ b/java/java.lsp.server/src/org/netbeans/modules/java/lsp/server/protocol/Server.java @@ -78,6 +78,7 @@ import org.eclipse.lsp4j.jsonrpc.Launcher; import org.eclipse.lsp4j.jsonrpc.MessageConsumer; import org.eclipse.lsp4j.jsonrpc.MessageIssueException; +import org.eclipse.lsp4j.jsonrpc.RemoteEndpoint; import org.eclipse.lsp4j.jsonrpc.messages.Either; import org.eclipse.lsp4j.jsonrpc.messages.Message; import org.eclipse.lsp4j.jsonrpc.messages.NotificationMessage; @@ -119,6 +120,7 @@ import org.netbeans.spi.project.ActionProvider; import org.openide.filesystems.FileObject; import org.openide.filesystems.FileUtil; +import org.openide.util.Exceptions; import org.openide.util.Lookup; import org.openide.util.NbBundle; import org.openide.util.NbPreferences; @@ -180,6 +182,10 @@ private static Launcher createLauncher(LanguageServerImpl } }); }) + .setExceptionHandler((t) -> { + LOG.log(Level.WARNING, "Error occurred during LSP message dispatch", t); + return RemoteEndpoint.DEFAULT_EXCEPTION_HANDLER.apply(t); + }) .create(); } @@ -255,6 +261,9 @@ public void consume(Message msg) throws MessageIssueException, JsonRpcException Lookups.executeWith(ll, () -> { try { delegate.consume(msg); + } catch (RuntimeException | Error e) { + LOG.log(Level.WARNING, "Error occurred during message dispatch", e); + throw e; } finally { // cancel while the OperationContext is still active. if (ftoCancel != null) { diff --git a/java/java.lsp.server/test/unit/src/org/netbeans/modules/java/lsp/server/protocol/ServerTest.java b/java/java.lsp.server/test/unit/src/org/netbeans/modules/java/lsp/server/protocol/ServerTest.java index 367718191951..fc8818df160c 100644 --- a/java/java.lsp.server/test/unit/src/org/netbeans/modules/java/lsp/server/protocol/ServerTest.java +++ b/java/java.lsp.server/test/unit/src/org/netbeans/modules/java/lsp/server/protocol/ServerTest.java @@ -25,7 +25,10 @@ import java.io.File; import java.io.FileWriter; import java.io.IOException; +import java.io.InputStream; +import java.io.OutputStream; import java.io.OutputStreamWriter; +import java.io.PrintWriter; import java.io.Writer; import java.lang.ref.Reference; import java.lang.ref.WeakReference; @@ -140,8 +143,14 @@ import org.eclipse.lsp4j.WorkspaceSymbol; import org.eclipse.lsp4j.WorkspaceSymbolLocation; import org.eclipse.lsp4j.WorkspaceSymbolParams; +import org.eclipse.lsp4j.jsonrpc.Endpoint; import org.eclipse.lsp4j.jsonrpc.Launcher; +import org.eclipse.lsp4j.jsonrpc.MessageConsumer; +import org.eclipse.lsp4j.jsonrpc.RemoteEndpoint; +import org.eclipse.lsp4j.jsonrpc.json.MessageJsonHandler; +import org.eclipse.lsp4j.jsonrpc.json.StreamMessageConsumer; import org.eclipse.lsp4j.jsonrpc.messages.Either; +import org.eclipse.lsp4j.jsonrpc.services.ServiceEndpoints; import org.eclipse.lsp4j.launch.LSPLauncher; import org.eclipse.lsp4j.services.LanguageClient; import org.eclipse.lsp4j.services.LanguageServer; @@ -328,7 +337,7 @@ public void testMain() throws Exception { try (Writer w = new FileWriter(src)) { w.write(code); } - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient(), client.getInputStream(), client.getOutputStream()); + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient(), client.getInputStream(), client.getOutputStream()); serverLauncher.startListening(); LanguageServer server = serverLauncher.getRemoteProxy(); InitializeResult result = server.initialize(new InitializeParams()).get(); @@ -405,7 +414,7 @@ public void testDiagnosticsRemovedForDeletedFile() throws Exception { try (Writer w = new FileWriter(src)) { w.write(code); } - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient(), client.getInputStream(), client.getOutputStream()); + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient(), client.getInputStream(), client.getOutputStream()); serverLauncher.startListening(); LanguageServer server = serverLauncher.getRemoteProxy(); InitializeResult result = server.initialize(new InitializeParams()).get(); @@ -513,7 +522,7 @@ public void testDidOpenPreservesLines() throws Exception { OpenCloseHook hook = new OpenCloseHook(); TextDocumentServiceImpl.HOOK_NOTIFICATION = hook::accept; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient(), client.getInputStream(), client.getOutputStream()); + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient(), client.getInputStream(), client.getOutputStream()); serverLauncher.startListening(); LanguageServer server = serverLauncher.getRemoteProxy(); InitializeResult result = server.initialize(new InitializeParams()).get(); @@ -589,7 +598,7 @@ public void testSimulateNewUnnamedFile() throws Exception { OpenCloseHook hook = new OpenCloseHook(); TextDocumentServiceImpl.HOOK_NOTIFICATION = hook::accept; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient(), client.getInputStream(), client.getOutputStream()); + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient(), client.getInputStream(), client.getOutputStream()); serverLauncher.startListening(); LanguageServer server = serverLauncher.getRemoteProxy(); InitializeResult result = server.initialize(new InitializeParams()).get(); @@ -625,7 +634,7 @@ public void testCodeActionWithRemoval() throws Exception { w.write(code); } List[] diags = new List[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -732,7 +741,7 @@ public void testNavigator() throws Exception { } file2SourceLevel.put(FileUtil.toFileObject(src.getParentFile()), "17"); FileUtil.refreshFor(getWorkDir()); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -875,7 +884,7 @@ public void testGoToDefinition() throws Exception { } FileUtil.refreshFor(getWorkDir()); CountDownLatch indexingComplete = new CountDownLatch(1); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -959,7 +968,7 @@ public void testGoToTypeDefinition() throws Exception { } FileUtil.refreshFor(getWorkDir()); CountDownLatch indexingComplete = new CountDownLatch(1); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -1024,7 +1033,7 @@ public void testGoToImplementations() throws Exception { } FileUtil.refreshFor(getWorkDir()); CountDownLatch indexingComplete = new CountDownLatch(1); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object params) { throw new UnsupportedOperationException("Not supported yet."); @@ -1088,7 +1097,7 @@ public void testGoToSuperImplementation() throws Exception { "}"); } FileUtil.refreshFor(getWorkDir()); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object params) { throw new UnsupportedOperationException("Not supported yet."); @@ -1131,7 +1140,7 @@ public void logMessage(MessageParams params) { } public void testFindDebugAttachConfigurations() throws Exception { - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { }, client.getInputStream(), client.getOutputStream()); serverLauncher.startListening(); LanguageServer server = serverLauncher.getRemoteProxy(); @@ -1190,7 +1199,7 @@ public void testOpenProjectOpenJDK() throws Exception { List[] diags = new List[1]; boolean[] indexingComplete = new boolean[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -1258,7 +1267,7 @@ public void testMarkOccurrences() throws Exception { w.write(code); } FileUtil.refreshFor(getWorkDir()); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -1308,7 +1317,7 @@ public void testHover() throws Exception { w.write(code); } FileUtil.refreshFor(getWorkDir()); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -1368,7 +1377,7 @@ public void testAdvancedCompletion1() throws Exception { } List[] diags = new List[1]; CountDownLatch indexingComplete = new CountDownLatch(1); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -1503,7 +1512,7 @@ public void testAutoImportOnCompletion() throws Exception { } List[] diags = new List[1]; CountDownLatch indexingComplete = new CountDownLatch(1); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -1589,14 +1598,14 @@ public void testFixImports() throws Exception { } List[] diags = new List[1]; CountDownLatch indexingComplete = new CountDownLatch(1); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new TestCodeLanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new TestCodeLanguageClient() { @Override public void showStatusBarMessage(ShowStatusMessageParams params) { if (Server.INDEXING_COMPLETED.equals(params.getMessage())) { indexingComplete.countDown(); } } - + @Override public void publishDiagnostics(PublishDiagnosticsParams params) { synchronized (diags) { @@ -1661,7 +1670,7 @@ public void testFindUsages() throws Exception { "}\n"); } CountDownLatch indexingComplete = new CountDownLatch(1); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new TestCodeLanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new TestCodeLanguageClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -1766,7 +1775,7 @@ public void testWorkspaceSymbols() throws Exception { w.write(code); } CountDownLatch indexingComplete = new CountDownLatch(1); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -1826,7 +1835,7 @@ public void testCodeActionGenerateVarFieldOrParam() throws Exception { } List[] diags = new List[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -1954,7 +1963,7 @@ public void testCodeActionGenerateMethod() throws Exception { } List[] diags = new List[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -2040,7 +2049,7 @@ public void testCodeActionGenerateClass() throws Exception { } List[] diags = new List[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -2127,7 +2136,7 @@ public void testCodeActionImplementAllAbstractMethodsInClass() throws Exception } List[] diags = new List[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -2217,7 +2226,7 @@ public void testCodeActionImplementAllAbstractMethodsInAnonymousClass() throws E } List[] diags = new List[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -2304,7 +2313,7 @@ public void testCodeActionImplementAllAbstractMethodsInEnum() throws Exception { } List[] diags = new List[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -2392,7 +2401,7 @@ public void testCodeActionIntroduceVariable() throws Exception { } List[] diags = new List[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -2501,7 +2510,7 @@ public void testCodeActionIntroduceConstant() throws Exception { } List[] diags = new List[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -2605,7 +2614,7 @@ public void testCodeActionIntroduceField() throws Exception { } List[] diags = new List[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -2709,7 +2718,7 @@ public void testCodeActionIntroduceMethod() throws Exception { } List[] diags = new List[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -2816,7 +2825,7 @@ public void testCodeActionGetterSetter() throws Exception { try (Writer w = new FileWriter(src)) { w.write(code); } - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -2893,7 +2902,7 @@ public void testCodeActionGenerateConstructor() throws Exception { w.write(code); } AtomicReference data = new AtomicReference<>(); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new TestCodeLanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new TestCodeLanguageClient() { @Override public CompletableFuture applyEdit(ApplyWorkspaceEditParams params) { throw new UnsupportedOperationException("Not supported yet."); @@ -2950,7 +2959,7 @@ public void testSourceActionGetterSetter() throws Exception { try (Writer w = new FileWriter(src)) { w.write(code); } - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -3051,7 +3060,7 @@ public void testSourceActionConstructor() throws Exception { w.write(code); } AtomicReference data = new AtomicReference<>(); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new TestCodeLanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new TestCodeLanguageClient() { @Override public CompletableFuture applyEdit(ApplyWorkspaceEditParams params) { throw new UnsupportedOperationException("Not supported yet."); @@ -3125,7 +3134,7 @@ public void testSourceActionEqualsHashCode() throws Exception { try (Writer w = new FileWriter(src)) { w.write(code); } - Launcher serverLauncher = LSPLauncher.createClientLauncher(new TestCodeLanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new TestCodeLanguageClient() { @Override public CompletableFuture> showQuickPick(ShowQuickPickParams params) { return CompletableFuture.completedFuture(params.getItems().size() > 2 ? params.getItems().subList(0, 2) : params.getItems()); @@ -3187,7 +3196,7 @@ public void testSourceActionToString() throws Exception { try (Writer w = new FileWriter(src)) { w.write(code); } - Launcher serverLauncher = LSPLauncher.createClientLauncher(new TestCodeLanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new TestCodeLanguageClient() { @Override public CompletableFuture applyEdit(ApplyWorkspaceEditParams params) { throw new UnsupportedOperationException("Not supported yet."); @@ -3246,7 +3255,7 @@ public void testSourceActionDelegateMethod() throws Exception { w.write(code); } AtomicReference data = new AtomicReference<>(); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new TestCodeLanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new TestCodeLanguageClient() { @Override public CompletableFuture applyEdit(ApplyWorkspaceEditParams params) { throw new UnsupportedOperationException("Not supported yet."); @@ -3332,7 +3341,7 @@ public void testSourceActionOverrideMethod() throws Exception { try (Writer w = new FileWriter(src)) { w.write(code); } - Launcher serverLauncher = LSPLauncher.createClientLauncher(new TestCodeLanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new TestCodeLanguageClient() { @Override public CompletableFuture applyEdit(ApplyWorkspaceEditParams params) { throw new UnsupportedOperationException("Not supported yet."); @@ -3391,7 +3400,7 @@ public void testSourceActionLogger() throws Exception { try (Writer w = new FileWriter(src)) { w.write(code); } - Launcher serverLauncher = LSPLauncher.createClientLauncher(new TestCodeLanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new TestCodeLanguageClient() { @Override public CompletableFuture applyEdit(ApplyWorkspaceEditParams params) { throw new UnsupportedOperationException("Not supported yet."); @@ -3456,7 +3465,7 @@ public void testSourceActionOrganizeImports() throws Exception { try (Writer w = new FileWriter(src)) { w.write(code); } - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -3590,7 +3599,7 @@ private void doTestRename(Consumer settings, } List[] diags = new List[1]; CountDownLatch indexingComplete = new CountDownLatch(1); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -3674,7 +3683,7 @@ public void testMoveClass() throws Exception { List[] diags = new List[1]; CountDownLatch indexingComplete = new CountDownLatch(1); WorkspaceEdit[] edit = new WorkspaceEdit[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new TestCodeLanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new TestCodeLanguageClient() { @Override public void publishDiagnostics(PublishDiagnosticsParams params) { synchronized (diags) { @@ -3789,7 +3798,7 @@ public void testMoveMethod() throws Exception { List[] diags = new List[1]; CountDownLatch indexingComplete = new CountDownLatch(1); WorkspaceEdit[] edit = new WorkspaceEdit[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new TestCodeLanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new TestCodeLanguageClient() { @Override public void publishDiagnostics(PublishDiagnosticsParams params) { synchronized (diags) { @@ -3895,7 +3904,7 @@ public void testExtractInterface() throws Exception { List[] diags = new List[1]; CountDownLatch indexingComplete = new CountDownLatch(1); WorkspaceEdit[] edit = new WorkspaceEdit[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new TestCodeLanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new TestCodeLanguageClient() { @Override public void publishDiagnostics(PublishDiagnosticsParams params) { synchronized (diags) { @@ -4016,7 +4025,7 @@ public void testExtractSuperclass() throws Exception { List[] diags = new List[1]; CountDownLatch indexingComplete = new CountDownLatch(1); WorkspaceEdit[] edit = new WorkspaceEdit[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new TestCodeLanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new TestCodeLanguageClient() { @Override public void publishDiagnostics(PublishDiagnosticsParams params) { synchronized (diags) { @@ -4153,7 +4162,7 @@ public void testPullUp() throws Exception { List[] diags = new List[1]; CountDownLatch indexingComplete = new CountDownLatch(1); WorkspaceEdit[] edit = new WorkspaceEdit[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new TestCodeLanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new TestCodeLanguageClient() { @Override public void publishDiagnostics(PublishDiagnosticsParams params) { synchronized (diags) { @@ -4251,7 +4260,7 @@ public void testPushDown() throws Exception { List[] diags = new List[1]; CountDownLatch indexingComplete = new CountDownLatch(1); WorkspaceEdit[] edit = new WorkspaceEdit[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new TestCodeLanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new TestCodeLanguageClient() { @Override public void publishDiagnostics(PublishDiagnosticsParams params) { synchronized (diags) { @@ -4334,6 +4343,20 @@ public CompletableFuture> showQuickPick(ShowQuickPickParams } } } + + private Launcher createClientLauncherWithLogging(LanguageClient client, InputStream input, OutputStream output) { + return new LSPLauncher.Builder() + .setLocalService(client) + .setExceptionHandler((t) -> { + System.err.println("Error during dispatch at client: "); + t.printStackTrace(); + return RemoteEndpoint.DEFAULT_EXCEPTION_HANDLER.apply(t); + }) + .traceMessages(new PrintWriter(System.out)) + .setRemoteInterface(LanguageServer.class) + .setInput(input) + .setOutput(output).create(); + } public void testChangeMethodParameters() throws Exception { File src = new File(getWorkDir(), "a/Foo.java"); @@ -4363,7 +4386,7 @@ public void testChangeMethodParameters() throws Exception { List[] diags = new List[1]; CountDownLatch indexingComplete = new CountDownLatch(1); WorkspaceEdit[] edit = new WorkspaceEdit[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new TestCodeLanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new TestCodeLanguageClient() { @Override public void publishDiagnostics(PublishDiagnosticsParams params) { synchronized (diags) { @@ -4461,7 +4484,7 @@ public void testSurroundWith() throws Exception { } List[] diags = new List[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -4541,7 +4564,7 @@ public void testFormatDocument() throws Exception { } List[] diags = new List[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -4625,7 +4648,7 @@ public void testFormatSelection() throws Exception { } List[] diags = new List[1]; - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -4704,7 +4727,7 @@ public void testNoErrorAndHintsFor() throws Exception { } Map> publishedDiagnostics = new HashMap<>(); FileUtil.refreshFor(getWorkDir()); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -4773,7 +4796,7 @@ public void testCodeFolding() throws Exception { try (Writer w = new FileWriter(src)) { w.write(code); } - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -4845,7 +4868,7 @@ public void testAnnotationCompletion() throws Exception { try (Writer w = new FileWriter(src)) { w.write(code); } - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient(), client.getInputStream(), client.getOutputStream()); + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient(), client.getInputStream(), client.getOutputStream()); serverLauncher.startListening(); LanguageServer server = serverLauncher.getRemoteProxy(); InitializeResult result = server.initialize(new InitializeParams()).get(); @@ -4908,7 +4931,7 @@ public void testSemanticHighlighting() throws Exception { w.write(code); } FileUtil.refreshFor(getWorkDir()); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LanguageClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -4971,7 +4994,7 @@ public void testSemanticHighlighting2() throws Exception { w.write(code); } FileUtil.refreshFor(getWorkDir()); - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LanguageClient() { + Launcher serverLauncher = createClientLauncherWithLogging(new LanguageClient() { @Override public void telemetryEvent(Object arg0) { throw new UnsupportedOperationException("Not supported yet."); @@ -5404,7 +5427,7 @@ public void showMessage(MessageParams params) { Lookup d = Lookup.getDefault(); IOProvider prov = IOProvider.getDefault(); - Launcher serverLauncher = LSPLauncher.createClientLauncher(lc, client.getInputStream(), client.getOutputStream()); + Launcher serverLauncher = createClientLauncherWithLogging(lc, client.getInputStream(), client.getOutputStream()); serverLauncher.startListening(); LanguageServer server = serverLauncher.getRemoteProxy(); InitializeParams initP = new InitializeParams(); @@ -5445,7 +5468,7 @@ public void testFileModificationDiags() throws Exception { try (Writer w = new FileWriter(src)) { w.write(code); } - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient(), client.getInputStream(), client.getOutputStream()); + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient(), client.getInputStream(), client.getOutputStream()); serverLauncher.startListening(); LanguageServer server = serverLauncher.getRemoteProxy(); InitializeResult result = server.initialize(new InitializeParams()).get(); @@ -5492,7 +5515,7 @@ public void testDeclarativeHints() throws Exception { try (Writer w = new FileWriter(src)) { w.write(code); } - Launcher serverLauncher = LSPLauncher.createClientLauncher(new LspClient(), client.getInputStream(), client.getOutputStream()); + Launcher serverLauncher = createClientLauncherWithLogging(new LspClient(), client.getInputStream(), client.getOutputStream()); serverLauncher.startListening(); LanguageServer server = serverLauncher.getRemoteProxy(); InitializeResult result = server.initialize(new InitializeParams()).get(); From 22c1fe2e61880ccefe73b625b963ae6f80a411db Mon Sep 17 00:00:00 2001 From: Svata Dedic Date: Wed, 16 Nov 2022 12:11:57 +0100 Subject: [PATCH 3/8] Conditional message tracing in tests. --- .../java/lsp/server/protocol/ServerTest.java | 17 ++++++++--------- 1 file changed, 8 insertions(+), 9 deletions(-) diff --git a/java/java.lsp.server/test/unit/src/org/netbeans/modules/java/lsp/server/protocol/ServerTest.java b/java/java.lsp.server/test/unit/src/org/netbeans/modules/java/lsp/server/protocol/ServerTest.java index fc8818df160c..99b9b6fbfdde 100644 --- a/java/java.lsp.server/test/unit/src/org/netbeans/modules/java/lsp/server/protocol/ServerTest.java +++ b/java/java.lsp.server/test/unit/src/org/netbeans/modules/java/lsp/server/protocol/ServerTest.java @@ -143,14 +143,9 @@ import org.eclipse.lsp4j.WorkspaceSymbol; import org.eclipse.lsp4j.WorkspaceSymbolLocation; import org.eclipse.lsp4j.WorkspaceSymbolParams; -import org.eclipse.lsp4j.jsonrpc.Endpoint; import org.eclipse.lsp4j.jsonrpc.Launcher; -import org.eclipse.lsp4j.jsonrpc.MessageConsumer; import org.eclipse.lsp4j.jsonrpc.RemoteEndpoint; -import org.eclipse.lsp4j.jsonrpc.json.MessageJsonHandler; -import org.eclipse.lsp4j.jsonrpc.json.StreamMessageConsumer; import org.eclipse.lsp4j.jsonrpc.messages.Either; -import org.eclipse.lsp4j.jsonrpc.services.ServiceEndpoints; import org.eclipse.lsp4j.launch.LSPLauncher; import org.eclipse.lsp4j.services.LanguageClient; import org.eclipse.lsp4j.services.LanguageServer; @@ -213,7 +208,8 @@ */ @SuppressWarnings({"unchecked", "rawtypes", "deprecation"}) public class ServerTest extends NbTestCase { - + static final boolean ENABLE_MESSAGE_LOGGING = Boolean.getBoolean(ServerTest.class.getName() + ".traceMessages"); + private final Gson gson = new Gson(); private Socket client; private Thread serverThread; @@ -4345,17 +4341,20 @@ public CompletableFuture> showQuickPick(ShowQuickPickParams } private Launcher createClientLauncherWithLogging(LanguageClient client, InputStream input, OutputStream output) { - return new LSPLauncher.Builder() + Launcher.Builder builder = new LSPLauncher.Builder() .setLocalService(client) .setExceptionHandler((t) -> { System.err.println("Error during dispatch at client: "); t.printStackTrace(); return RemoteEndpoint.DEFAULT_EXCEPTION_HANDLER.apply(t); }) - .traceMessages(new PrintWriter(System.out)) .setRemoteInterface(LanguageServer.class) .setInput(input) - .setOutput(output).create(); + .setOutput(output); + if (ENABLE_MESSAGE_LOGGING) { + builder = builder.traceMessages(new PrintWriter(System.out)); + } + return builder.create(); } public void testChangeMethodParameters() throws Exception { From 5b964b75a9d7430da8dc1f07477812ac157b16f3 Mon Sep 17 00:00:00 2001 From: Svata Dedic Date: Wed, 16 Nov 2022 12:41:29 +0100 Subject: [PATCH 4/8] Suppress groovy-not-found stacktrace in the expected situations. --- .../modules/java/lsp/server/protocol/Server.java | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/java/java.lsp.server/src/org/netbeans/modules/java/lsp/server/protocol/Server.java b/java/java.lsp.server/src/org/netbeans/modules/java/lsp/server/protocol/Server.java index 6b5203f4c7f8..cd19b1bbd38c 100644 --- a/java/java.lsp.server/src/org/netbeans/modules/java/lsp/server/protocol/Server.java +++ b/java/java.lsp.server/src/org/netbeans/modules/java/lsp/server/protocol/Server.java @@ -1088,10 +1088,17 @@ public CompletableFuture configurationUpdate(UpdateConfigParams params) { private static void hackConfigureGroovySupport(NbCodeClientCapabilities caps) { boolean b = caps != null && caps.wantsGroovySupport(); try { - Class clazz = Lookup.getDefault().lookup(ClassLoader.class).loadClass("org.netbeans.modules.groovy.editor.api.GroovyIndexer"); + Class clazz = Lookup.getDefault().lookup(ClassLoader.class).loadClass("org.netbeans.modules.groovy.editor.api.GroovyIndexer"); Method m = clazz.getDeclaredMethod("setIndexingEnabled", Boolean.TYPE); m.setAccessible(true); m.invoke(null, b); + } catch (ClassNotFoundException ex) { + // java.lang.ClassNotFoundException is expected when Groovy support is not activated / enabled. Do not log, if the + // client wants groovy disabled, which is obviuously true in this case :) + if (b && !groovyClassWarningLogged) { + groovyClassWarningLogged = true; + LOG.log(Level.WARNING, "Unable to configure Groovy indexing: Groovy support is not enabled"); + } } catch (ReflectiveOperationException ex) { if (!groovyClassWarningLogged) { groovyClassWarningLogged = true; From 82f14ec4a242a9b239ece79146930f5ae2b25860 Mon Sep 17 00:00:00 2001 From: Svata Dedic Date: Wed, 16 Nov 2022 15:23:22 +0100 Subject: [PATCH 5/8] Support for reentrancy or multiple uses: absolutize just once --- .../project/uiapi/ProjectTemplateAttributesProvider.java | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/ide/projectuiapi/src/org/netbeans/modules/project/uiapi/ProjectTemplateAttributesProvider.java b/ide/projectuiapi/src/org/netbeans/modules/project/uiapi/ProjectTemplateAttributesProvider.java index c38c31842211..0a1588397915 100644 --- a/ide/projectuiapi/src/org/netbeans/modules/project/uiapi/ProjectTemplateAttributesProvider.java +++ b/ide/projectuiapi/src/org/netbeans/modules/project/uiapi/ProjectTemplateAttributesProvider.java @@ -155,7 +155,10 @@ private static void ensureProjectAttrs(Map map, FileObject paren // in order to get through the freemarker, the path needs to "absolute" in freemarker terms - http://freemarker.sourceforge.net/docs/ref_directive_include.html // relative would mean relative to the template and we cannot be sure what the path from template to license template is.. // it used to be, ../Licenses/ or ../../Licenses but can be anything similar, just based on where the template resides. - map.put(ATTR_LICENSE_PATH, "/" + url); + // Note: ensure reentrancy, so if 'url' starts with slash, do not prepend + if (!url.startsWith("/")) { // NOI18N + map.put(ATTR_LICENSE_PATH, "/" + url); // NOI18N + } //appears to cover both the new and old default value of the include path } if (map.get(ATTR_ENCODING) == null) { From ead9e68d556b04640b2dd93b4296276d727b1cf8 Mon Sep 17 00:00:00 2001 From: Svata Dedic Date: Wed, 16 Nov 2022 16:55:58 +0100 Subject: [PATCH 6/8] Allow JDK11 test access to sun.misc.Unsafe --- nbbuild/templates/projectized.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/nbbuild/templates/projectized.xml b/nbbuild/templates/projectized.xml index 287fe6b2331f..d73a5ea0b6f8 100644 --- a/nbbuild/templates/projectized.xml +++ b/nbbuild/templates/projectized.xml @@ -123,7 +123,7 @@ - + From 49380eb05f0102140663d81973e8ab5ab32a49d2 Mon Sep 17 00:00:00 2001 From: Svata Dedic Date: Fri, 11 Nov 2022 17:56:04 +0100 Subject: [PATCH 7/8] Avoid spurious Socket Closed exceptions. --- .../java/lsp/server/ConnectionSpec.java | 31 ++++++++++++++++--- 1 file changed, 27 insertions(+), 4 deletions(-) diff --git a/java/java.lsp.server/src/org/netbeans/modules/java/lsp/server/ConnectionSpec.java b/java/java.lsp.server/src/org/netbeans/modules/java/lsp/server/ConnectionSpec.java index 98dd3ccc25a0..9ab389564cc2 100644 --- a/java/java.lsp.server/src/org/netbeans/modules/java/lsp/server/ConnectionSpec.java +++ b/java/java.lsp.server/src/org/netbeans/modules/java/lsp/server/ConnectionSpec.java @@ -25,6 +25,7 @@ import java.net.Inet4Address; import java.net.ServerSocket; import java.net.Socket; +import java.net.SocketException; import java.util.ArrayList; import java.util.List; import java.util.concurrent.ExecutionException; @@ -46,7 +47,10 @@ final class ConnectionSpec implements Closeable { private final Boolean listen; private final int port; + // @GuardedBy (this) private final List close = new ArrayList<>(); + // @GuardedBy (this) + private final List closed = new ArrayList<>(); private ConnectionSpec(Boolean listen, int port) { this.listen = listen; @@ -110,11 +114,15 @@ public void prepare( @Override public void run() { while (true) { + Socket socket = null; try { - Socket socket = server.accept(); + socket = server.accept(); close.add(socket); connectToSocket(socket, prefix, session, serverSetter, launcher); } catch (IOException ex) { + if (isClosed(server)) { + break; + } Exceptions.printStackTrace(ex); } } @@ -144,7 +152,9 @@ public void run() { serverSetter.accept(session, connectionObject); connectionObject.getRunningFuture().get(); } catch (IOException | InterruptedException | ExecutionException ex) { - Exceptions.printStackTrace(ex); + if (!isClosed(socket)) { + Exceptions.printStackTrace(ex); + } } finally { serverSetter.accept(session, null); } @@ -152,11 +162,24 @@ public void run() { }; connectedThread.start(); } + + private boolean isClosed(Closeable c) { + synchronized (this) { + return closed.contains(c); + } + } @Override public void close() throws IOException { - for (Closeable c : close) { - c.close(); + synchronized (this) { + for (Closeable c : close) { + try { + c.close(); + closed.add(c); + } catch (IOException ex) { + Exceptions.printStackTrace(ex); + } + } } } } From eb1edbd4f95b9991dfb0dc3f081eee54979d0fc5 Mon Sep 17 00:00:00 2001 From: Svata Dedic Date: Wed, 23 Nov 2022 09:32:05 +0100 Subject: [PATCH 8/8] Fixing LSP tests for JDK11 --- .../java/lsp/server/protocol/ServerTest.java | 43 ++++++++++++++----- 1 file changed, 32 insertions(+), 11 deletions(-) diff --git a/java/java.lsp.server/test/unit/src/org/netbeans/modules/java/lsp/server/protocol/ServerTest.java b/java/java.lsp.server/test/unit/src/org/netbeans/modules/java/lsp/server/protocol/ServerTest.java index 99b9b6fbfdde..5b620cb2f035 100644 --- a/java/java.lsp.server/test/unit/src/org/netbeans/modules/java/lsp/server/protocol/ServerTest.java +++ b/java/java.lsp.server/test/unit/src/org/netbeans/modules/java/lsp/server/protocol/ServerTest.java @@ -177,6 +177,7 @@ import org.netbeans.modules.java.source.BootClassPathUtil; import org.netbeans.modules.java.source.ElementHandleAccessor; import org.netbeans.modules.java.source.parsing.JavacParser; +import org.netbeans.modules.java.source.parsing.ParameterNameProviderImpl; import org.netbeans.modules.parsing.api.ResultIterator; import org.netbeans.modules.parsing.impl.indexing.implspi.CacheFolderProvider; import org.netbeans.spi.java.classpath.ClassPathProvider; @@ -221,6 +222,7 @@ public ServerTest(String name) { @Override protected void setUp() throws Exception { System.setProperty("java.awt.headless", Boolean.TRUE.toString()); + ParameterNameProviderImpl.DISABLE_PARAMETER_NAMES_LOADING = true; super.setUp(); clearWorkDir(); ServerSocket srv = new ServerSocket(0, 1, InetAddress.getLoopbackAddress()); @@ -1360,6 +1362,7 @@ public void logMessage(MessageParams arg0) { } public void testAdvancedCompletion1() throws Exception { + String javaVersion = System.getProperty("java.specification.version"); File src = new File(getWorkDir(), "Test.java"); src.getParentFile().mkdirs(); try (Writer w = new FileWriter(new File(src.getParentFile(), ".test-project"))) {} @@ -1427,7 +1430,11 @@ public void logMessage(MessageParams arg0) { Optional substringItem = completion.getRight().getItems().stream().filter(ci -> ci.getLabel().startsWith("substring(") && ci.getLabel().contains(",")).findAny(); assertTrue(substringItem.isPresent()); assertEquals(InsertTextFormat.Snippet, substringItem.get().getInsertTextFormat()); - assertEquals("substring(${1:i}, ${2:i1})$0", substringItem.get().getInsertText()); + if ("1.8".equals(javaVersion)) { + assertEquals("substring(${1:arg0}, ${2:arg1})$0", substringItem.get().getInsertText()); + } else { + assertEquals("substring(${1:beginIndex}, ${2:endIndex})$0", substringItem.get().getInsertText()); + } } { @@ -3047,6 +3054,7 @@ public CompletableFuture applyEdit(ApplyWorkspaceEdi } public void testSourceActionConstructor() throws Exception { + String javaVersion = System.getProperty("java.specification.version"); File src = new File(getWorkDir(), "Test.java"); src.getParentFile().mkdirs(); String code = "public class Test extends Exception {\n" + @@ -3098,16 +3106,29 @@ public CompletableFuture, String>>> showM assertEquals(new Range(new Position(2, 0), new Position(2, 0)), fileChanges.get(0).getRange()); - assertEquals("\n" + - " public Test(String f1) {\n" + - " this.f1 = f1;\n" + - " }\n" + - "\n" + - " public Test(String f1, String string) {\n" + - " super(string);\n" + - " this.f1 = f1;\n" + - " }\n", - fileChanges.get(0).getNewText()); + if ("1.8".equals(javaVersion)) { + assertEquals("\n" + + " public Test(String f1) {\n" + + " this.f1 = f1;\n" + + " }\n" + + "\n" + + " public Test(String f1, String arg0) {\n" + + " super(arg0);\n" + + " this.f1 = f1;\n" + + " }\n", + fileChanges.get(0).getNewText()); + } else { + assertEquals("\n" + + " public Test(String f1) {\n" + + " this.f1 = f1;\n" + + " }\n" + + "\n" + + " public Test(String f1, String message) {\n" + + " super(message);\n" + + " this.f1 = f1;\n" + + " }\n", + fileChanges.get(0).getNewText()); + } } public void testSourceActionEqualsHashCode() throws Exception {