From 8ebbdc1158c096d503576c6d758fae149d4e93cf Mon Sep 17 00:00:00 2001 From: nsingh Date: Tue, 31 Jan 2017 19:45:34 -0800 Subject: [PATCH 1/5] Simplify connection error handling to show only one message for now --- .../client/cftarget/CFCallableContext.java | 42 +++++++++---------- .../client/cftarget/CFTargetCache.java | 17 ++++---- .../cftarget/CfCliProviderMessages.java | 5 +-- .../cftarget/UnauthorizedException.java | 23 ---------- .../client/v2/CloudFoundryClientCache.java | 4 +- .../cloudfoundry/client/CFClientTest.java | 36 ---------------- .../yaml/AbstractCFHintsProvider.java | 5 +-- 7 files changed, 34 insertions(+), 98 deletions(-) delete mode 100644 vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/cftarget/UnauthorizedException.java diff --git a/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/cftarget/CFCallableContext.java b/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/cftarget/CFCallableContext.java index a6d565fea..969ac867e 100644 --- a/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/cftarget/CFCallableContext.java +++ b/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/cftarget/CFCallableContext.java @@ -10,6 +10,7 @@ *******************************************************************************/ package org.springframework.ide.vscode.commons.cloudfoundry.client.cftarget; +import java.net.SocketException; import java.net.UnknownHostException; import java.util.concurrent.Callable; @@ -20,10 +21,8 @@ import reactor.ipc.netty.channel.AbortedException; public class CFCallableContext { - public static final String UNAUTHORIZED_ERROR = "unauthorized"; - private final CFParamsProviderMessages paramsProviderMessages; - private Throwable lastConnectionError; + private Exception lastConnectionError; public CFCallableContext(CFParamsProviderMessages paramsProviderMessages) { this.paramsProviderMessages = paramsProviderMessages; @@ -38,29 +37,26 @@ public class CFCallableContext { } } - private Exception convertToCfVscodeError(Exception e) { - Throwable deepestCause = ExceptionUtil.getDeepestCause(e); - if (deepestCause instanceof UaaException) { - String error = ((UaaException) deepestCause).getError(); - if (error != null && error.contains(UNAUTHORIZED_ERROR)) { - this.lastConnectionError = deepestCause; - return new UnauthorizedException(this.paramsProviderMessages.unauthorised()); - } - } else if (deepestCause instanceof AbortedException) { - // This one is odd. It is thrown when a wrong token is specified, but - // instead of getting an expected UaaException, this AbortedException is thrown instead by reactor netty. - this.lastConnectionError = deepestCause; - return new UnauthorizedException(this.paramsProviderMessages.unauthorised()); - } else if (deepestCause instanceof UnknownHostException) { - this.lastConnectionError = deepestCause; - String message = ExceptionUtil.getMessage(deepestCause); - return new ConnectionException(this.paramsProviderMessages.noNetworkConnection() + " " + message); - } + protected Exception convertToCfVscodeError(Exception e) { + this.lastConnectionError = getConnectionError(e); + // return the "converted" error if it is available + if (this.lastConnectionError != null) { + return this.lastConnectionError; + } return e; } + protected Exception getConnectionError(Exception e) { + Throwable deepestCause = ExceptionUtil.getDeepestCause(e); + + if (deepestCause instanceof UaaException || deepestCause instanceof AbortedException + || deepestCause instanceof SocketException || deepestCause instanceof UnknownHostException) { + return new ConnectionException(this.paramsProviderMessages.noNetworkConnection()); + } + return null; + } + public boolean hasConnectionError() { return this.lastConnectionError != null; } - -} +} \ No newline at end of file diff --git a/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/cftarget/CFTargetCache.java b/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/cftarget/CFTargetCache.java index 5225dff64..65db645d9 100644 --- a/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/cftarget/CFTargetCache.java +++ b/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/cftarget/CFTargetCache.java @@ -28,11 +28,10 @@ public class CFTargetCache { private final CloudFoundryClientFactory clientFactory; private final ClientTimeouts timeouts; private final LoadingCache cache; - private final CFCallableContext callableContext; + private final CFCallableContext cacheCallableContext; public static final long SERVICES_EXPIRATION = 10; public static final long TARGET_EXPIRATION = 1; - public CFTargetCache(ClientParamsProvider paramsProvider, CloudFoundryClientFactory clientFactory, ClientTimeouts timeouts) { @@ -41,7 +40,7 @@ public class CFTargetCache { this.paramsProvider = paramsProvider; this.clientFactory = clientFactory; this.timeouts = timeouts; - this.callableContext = new CFCallableContext(paramsProvider.getMessages()); + this.cacheCallableContext = new CFCallableContext(paramsProvider.getMessages()); CacheLoader loader = new CacheLoader() { @Override @@ -50,7 +49,8 @@ public class CFTargetCache { } }; - cache = CacheBuilder.newBuilder().maximumSize(1).expireAfterAccess(TARGET_EXPIRATION, TimeUnit.HOURS).build(loader); + cache = CacheBuilder.newBuilder().maximumSize(1).expireAfterAccess(TARGET_EXPIRATION, TimeUnit.HOURS) + .build(loader); } /** @@ -61,9 +61,9 @@ public class CFTargetCache { * for any other error encountered */ public synchronized List getOrCreate() throws NoTargetsException, Exception { - return callableContext.checkConnection(() -> doGetOrCreate()); + return cacheCallableContext.checkConnection(() -> doGetOrCreate()); } - + protected synchronized List doGetOrCreate() throws NoTargetsException, Exception { List allParams = paramsProvider.getParams(); @@ -87,7 +87,8 @@ public class CFTargetCache { } protected CFTarget create(CFClientParams params) throws Exception { - return new CFTarget(getTargetName(params), params, clientFactory.getClient(params, timeouts), callableContext); + return new CFTarget(getTargetName(params), params, clientFactory.getClient(params, timeouts), + new CFCallableContext(paramsProvider.getMessages())); } protected static String getTargetName(CFClientParams params) { @@ -103,6 +104,4 @@ public class CFTargetCache { return cfApiUrl; } } - - } diff --git a/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/cftarget/CfCliProviderMessages.java b/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/cftarget/CfCliProviderMessages.java index a27da45d3..644eea102 100644 --- a/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/cftarget/CfCliProviderMessages.java +++ b/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/cftarget/CfCliProviderMessages.java @@ -19,8 +19,7 @@ public final class CfCliProviderMessages implements CFParamsProviderMessages { * longer */ public static final String NO_CLI_TARGETS_FOUND_MESSAGE = "No Cloud Foundry targets found: Use cf CLI to login"; - public static final String UNAUTHORISED_MESSAGE = "Unauthorized access: Use cf CLI to login"; - public static final String NO_NETWORK_CONNECTION = "Unable to connect to network: Verify network connection"; + public static final String NO_NETWORK_CONNECTION = "No connection to Cloud Foundry: Use cf CLI to login or verify network connection"; @Override public String noTargetsFound() { @@ -29,7 +28,7 @@ public final class CfCliProviderMessages implements CFParamsProviderMessages { @Override public String unauthorised() { - return UNAUTHORISED_MESSAGE; + return NO_NETWORK_CONNECTION; } @Override diff --git a/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/cftarget/UnauthorizedException.java b/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/cftarget/UnauthorizedException.java deleted file mode 100644 index 7488edebb..000000000 --- a/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/cftarget/UnauthorizedException.java +++ /dev/null @@ -1,23 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2017 Pivotal, Inc. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Eclipse Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/epl-v10.html - * - * Contributors: - * Pivotal, Inc. - initial API and implementation - *******************************************************************************/ -package org.springframework.ide.vscode.commons.cloudfoundry.client.cftarget; - -public class UnauthorizedException extends Exception { - - /** - * - */ - private static final long serialVersionUID = 1L; - - public UnauthorizedException(String message) { - super(message); - } -} diff --git a/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/v2/CloudFoundryClientCache.java b/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/v2/CloudFoundryClientCache.java index e39c25607..5cbfdd472 100644 --- a/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/v2/CloudFoundryClientCache.java +++ b/vscode-extensions/commons/commons-cf/src/main/java/org/springframework/ide/vscode/commons/cloudfoundry/client/v2/CloudFoundryClientCache.java @@ -66,7 +66,9 @@ public class CloudFoundryClientCache { } public synchronized CFClientProvider getOrCreate(CFClientParams params) throws Exception { - return cache.get(ClientParamsCacheKey.from(params)); + return create(params); + // Disable cache as corrupted clients may be kept due to connection or auth errors +// return cache.get(ClientParamsCacheKey.from(params)); } protected CFClientProvider create(CFClientParams params) { diff --git a/vscode-extensions/commons/commons-cf/src/test/java/org/springframework/ide/vscode/commons/cloudfoundry/client/CFClientTest.java b/vscode-extensions/commons/commons-cf/src/test/java/org/springframework/ide/vscode/commons/cloudfoundry/client/CFClientTest.java index 9dad69f27..32d6a8a65 100644 --- a/vscode-extensions/commons/commons-cf/src/test/java/org/springframework/ide/vscode/commons/cloudfoundry/client/CFClientTest.java +++ b/vscode-extensions/commons/commons-cf/src/test/java/org/springframework/ide/vscode/commons/cloudfoundry/client/CFClientTest.java @@ -18,7 +18,6 @@ import static org.mockito.Mockito.when; import java.net.UnknownHostException; import java.util.concurrent.Callable; -import org.cloudfoundry.uaa.UaaException; import org.junit.Before; import org.junit.Test; import org.springframework.ide.vscode.commons.cloudfoundry.client.cftarget.CFParamsProviderMessages; @@ -27,11 +26,8 @@ import org.springframework.ide.vscode.commons.cloudfoundry.client.cftarget.CFTar import org.springframework.ide.vscode.commons.cloudfoundry.client.cftarget.CfCliProviderMessages; import org.springframework.ide.vscode.commons.cloudfoundry.client.cftarget.ConnectionException; import org.springframework.ide.vscode.commons.cloudfoundry.client.cftarget.NoTargetsException; -import org.springframework.ide.vscode.commons.cloudfoundry.client.cftarget.UnauthorizedException; import org.springframework.ide.vscode.commons.util.ExceptionUtil; -import reactor.ipc.netty.channel.AbortedException; - public class CFClientTest { MockCfCli cloudfoundry = new MockCfCli(); @@ -75,38 +71,6 @@ public class CFClientTest { assertError(() -> target.getBuildpacks(), ConnectionException.class, expectedMessages.noNetworkConnection()); } - @Test - public void testAbortedExceptionServices() throws Exception { - ClientRequests client = cloudfoundry.client; - when(client.getServices()).thenThrow(new AbortedException("connection aborted")); - CFTarget target = targetCache.getOrCreate().get(0); - assertError(() -> target.getServices(), UnauthorizedException.class, expectedMessages.unauthorised()); - } - - @Test - public void testAbortedExceptionBuildpacks() throws Exception { - ClientRequests client = cloudfoundry.client; - when(client.getBuildpacks()).thenThrow(new AbortedException("connection aborted")); - CFTarget target = targetCache.getOrCreate().get(0); - assertError(() -> target.getBuildpacks(), UnauthorizedException.class, expectedMessages.unauthorised()); - } - - @Test - public void testUaaExceptionServices() throws Exception { - ClientRequests client = cloudfoundry.client; - when(client.getServices()).thenThrow(new UaaException(401, "unauthorized", "Bad credentials")); - CFTarget target = targetCache.getOrCreate().get(0); - assertError(() -> target.getServices(), UnauthorizedException.class, expectedMessages.unauthorised()); - } - - @Test - public void testUaaExceptionBuildpacks() throws Exception { - ClientRequests client = cloudfoundry.client; - when(client.getBuildpacks()).thenThrow(new UaaException(401, "unauthorized", "Bad credentials")); - CFTarget target = targetCache.getOrCreate().get(0); - assertError(() -> target.getBuildpacks(), UnauthorizedException.class, expectedMessages.unauthorised()); - } - protected void assertError(Callable callable, Class expected, String expectedMessage) throws Exception { Throwable error = null; diff --git a/vscode-extensions/vscode-manifest-yaml/src/main/java/org/springframework/ide/vscode/manifest/yaml/AbstractCFHintsProvider.java b/vscode-extensions/vscode-manifest-yaml/src/main/java/org/springframework/ide/vscode/manifest/yaml/AbstractCFHintsProvider.java index b26ca6c88..82f3a9a64 100644 --- a/vscode-extensions/vscode-manifest-yaml/src/main/java/org/springframework/ide/vscode/manifest/yaml/AbstractCFHintsProvider.java +++ b/vscode-extensions/vscode-manifest-yaml/src/main/java/org/springframework/ide/vscode/manifest/yaml/AbstractCFHintsProvider.java @@ -18,9 +18,8 @@ import java.util.logging.Logger; import org.springframework.ide.vscode.commons.cloudfoundry.client.cftarget.CFTarget; import org.springframework.ide.vscode.commons.cloudfoundry.client.cftarget.CFTargetCache; -import org.springframework.ide.vscode.commons.cloudfoundry.client.cftarget.NoTargetsException; -import org.springframework.ide.vscode.commons.cloudfoundry.client.cftarget.UnauthorizedException; import org.springframework.ide.vscode.commons.cloudfoundry.client.cftarget.ConnectionException; +import org.springframework.ide.vscode.commons.cloudfoundry.client.cftarget.NoTargetsException; import org.springframework.ide.vscode.commons.util.Assert; import org.springframework.ide.vscode.commons.util.ExceptionUtil; import org.springframework.ide.vscode.commons.util.ValueParseException; @@ -86,7 +85,7 @@ public abstract class AbstractCFHintsProvider implements Callable Date: Wed, 1 Feb 2017 15:28:24 +0100 Subject: [PATCH 2/5] updated to find version 0.0.2 of manifest ls --- .../server/CloudFoundryManifestLanguageServer.java | 13 ++++++------- 1 file changed, 6 insertions(+), 7 deletions(-) diff --git a/eclipse-language-servers/org.springframework.boot.ide.cloudfoundry.server/src/org/springframework/boot/ide/cloudfoundry/server/CloudFoundryManifestLanguageServer.java b/eclipse-language-servers/org.springframework.boot.ide.cloudfoundry.server/src/org/springframework/boot/ide/cloudfoundry/server/CloudFoundryManifestLanguageServer.java index b40dc9d05..df097eded 100644 --- a/eclipse-language-servers/org.springframework.boot.ide.cloudfoundry.server/src/org/springframework/boot/ide/cloudfoundry/server/CloudFoundryManifestLanguageServer.java +++ b/eclipse-language-servers/org.springframework.boot.ide.cloudfoundry.server/src/org/springframework/boot/ide/cloudfoundry/server/CloudFoundryManifestLanguageServer.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2016 Pivotal, Inc. + * Copyright (c) 2016, 2017 Pivotal, Inc. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at @@ -47,7 +47,6 @@ public class CloudFoundryManifestLanguageServer extends ProcessStreamConnectionP } public void handleMessage(Message message, LanguageServer languageServer, String rootPath) { - System.out.println("custom message arrived: " + message.toString()); } protected String getJDKLocation() { @@ -57,13 +56,13 @@ public class CloudFoundryManifestLanguageServer extends ProcessStreamConnectionP } protected String getLanguageServerJARLocation() { - String languageServer = "vscode-manifest-yaml-0.0.1-SNAPSHOT.jar"; + String languageServer = "vscode-manifest-yaml-0.0.2-SNAPSHOT.jar"; Bundle bundle = Platform.getBundle(Constants.PLUGIN_ID); File dataFile = bundle.getDataFile(languageServer); if (!dataFile.exists()) { try { - copyLanguageServerJAR(); + copyLanguageServerJAR(languageServer); } catch (Exception e) { e.printStackTrace(); @@ -78,11 +77,11 @@ public class CloudFoundryManifestLanguageServer extends ProcessStreamConnectionP return System.getProperty("user.dir"); } - protected void copyLanguageServerJAR() throws Exception { + protected void copyLanguageServerJAR(String languageServerJarName) throws Exception { Bundle bundle = Platform.getBundle(Constants.PLUGIN_ID); - InputStream stream = FileLocator.openStream( bundle, new Path("servers/vscode-manifest-yaml-0.0.1-SNAPSHOT.jar"), false ); + InputStream stream = FileLocator.openStream( bundle, new Path("servers/" + languageServerJarName), false ); - File dataFile = bundle.getDataFile("vscode-manifest-yaml-0.0.1-SNAPSHOT.jar"); + File dataFile = bundle.getDataFile(languageServerJarName); Files.copy(stream, dataFile.toPath(), StandardCopyOption.REPLACE_EXISTING); } From 7dc4713c97ad0dcc2644e2009ee316be3cee613c Mon Sep 17 00:00:00 2001 From: Martin Lippert Date: Wed, 1 Feb 2017 15:30:49 +0100 Subject: [PATCH 3/5] refactored code to avoid duplicate string constants --- .../servers/SpringBootPropertiesLanguageServer.java | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/eclipse-language-servers/org.springframework.boot.ide.properties.servers/src/org/springframework/boot/ide/properties/servers/SpringBootPropertiesLanguageServer.java b/eclipse-language-servers/org.springframework.boot.ide.properties.servers/src/org/springframework/boot/ide/properties/servers/SpringBootPropertiesLanguageServer.java index 3b3536788..eb69d50e3 100644 --- a/eclipse-language-servers/org.springframework.boot.ide.properties.servers/src/org/springframework/boot/ide/properties/servers/SpringBootPropertiesLanguageServer.java +++ b/eclipse-language-servers/org.springframework.boot.ide.properties.servers/src/org/springframework/boot/ide/properties/servers/SpringBootPropertiesLanguageServer.java @@ -78,7 +78,7 @@ public class SpringBootPropertiesLanguageServer extends ProcessStreamConnectionP File dataFile = bundle.getDataFile(languageServer); if (!dataFile.exists()) { try { - copyLanguageServerJAR(); + copyLanguageServerJAR(languageServer); } catch (Exception e) { e.printStackTrace(); @@ -93,11 +93,11 @@ public class SpringBootPropertiesLanguageServer extends ProcessStreamConnectionP return System.getProperty("user.dir"); } - protected void copyLanguageServerJAR() throws Exception { + protected void copyLanguageServerJAR(String languageServerJarName) throws Exception { Bundle bundle = Platform.getBundle(Constants.PLUGIN_ID); - InputStream stream = FileLocator.openStream( bundle, new Path("servers/vscode-boot-properties-0.0.1-SNAPSHOT.jar"), false ); + InputStream stream = FileLocator.openStream( bundle, new Path("servers/" + languageServerJarName), false ); - File dataFile = bundle.getDataFile("vscode-boot-properties-0.0.1-SNAPSHOT.jar"); + File dataFile = bundle.getDataFile(languageServerJarName); Files.copy(stream, dataFile.toPath(), StandardCopyOption.REPLACE_EXISTING); } From d90a76a20a77ca3d0c57ee66e8b3624fa2fd3e22 Mon Sep 17 00:00:00 2001 From: Martin Lippert Date: Wed, 1 Feb 2017 15:31:42 +0100 Subject: [PATCH 4/5] PT ##136024387: show sts/progress message from language server in Eclipse status line --- .../META-INF/MANIFEST.MF | 5 ++- .../SpringBootPropertiesLanguageServer.java | 34 ++++++++++++++----- 2 files changed, 30 insertions(+), 9 deletions(-) diff --git a/eclipse-language-servers/org.springframework.boot.ide.properties.servers/META-INF/MANIFEST.MF b/eclipse-language-servers/org.springframework.boot.ide.properties.servers/META-INF/MANIFEST.MF index b413815e0..c4e708121 100644 --- a/eclipse-language-servers/org.springframework.boot.ide.properties.servers/META-INF/MANIFEST.MF +++ b/eclipse-language-servers/org.springframework.boot.ide.properties.servers/META-INF/MANIFEST.MF @@ -11,7 +11,10 @@ Require-Bundle: org.eclipse.jdt.launching;bundle-version="3.9.0", org.eclipse.jface.text;bundle-version="3.11.100", org.eclipse.jdt.ui;bundle-version="3.13.0", org.eclipse.tm4e.core;bundle-version="1.0.0", - org.eclipse.tm4e.ui;bundle-version="1.0.0" + org.eclipse.tm4e.ui;bundle-version="1.0.0", + org.eclipse.lsp4j, + org.eclipse.ui.workbench, + org.eclipse.jface Import-Package: com.google.gson;version="2.7.0", org.eclipse.jface.preference, org.eclipse.lsp4j.jsonrpc.messages;version="0.1.0.v20170117-0759", diff --git a/eclipse-language-servers/org.springframework.boot.ide.properties.servers/src/org/springframework/boot/ide/properties/servers/SpringBootPropertiesLanguageServer.java b/eclipse-language-servers/org.springframework.boot.ide.properties.servers/src/org/springframework/boot/ide/properties/servers/SpringBootPropertiesLanguageServer.java index eb69d50e3..c160c5c8c 100644 --- a/eclipse-language-servers/org.springframework.boot.ide.properties.servers/src/org/springframework/boot/ide/properties/servers/SpringBootPropertiesLanguageServer.java +++ b/eclipse-language-servers/org.springframework.boot.ide.properties.servers/src/org/springframework/boot/ide/properties/servers/SpringBootPropertiesLanguageServer.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2016 Pivotal, Inc. + * Copyright (c) 2016, 2017 Pivotal, Inc. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at @@ -23,10 +23,12 @@ import org.eclipse.core.runtime.Platform; import org.eclipse.jdt.internal.launching.StandardVMType; import org.eclipse.jdt.launching.IVMInstall; import org.eclipse.jdt.launching.JavaRuntime; +import org.eclipse.jface.action.IStatusLineManager; import org.eclipse.lsp4e.server.ProcessStreamConnectionProvider; import org.eclipse.lsp4j.jsonrpc.messages.Message; import org.eclipse.lsp4j.jsonrpc.messages.NotificationMessage; import org.eclipse.lsp4j.services.LanguageServer; +import org.eclipse.ui.PlatformUI; import org.osgi.framework.Bundle; import com.google.gson.JsonObject; @@ -54,17 +56,33 @@ public class SpringBootPropertiesLanguageServer extends ProcessStreamConnectionP NotificationMessage notificationMessage = (NotificationMessage) message; if ("sts/progress".equals(notificationMessage.getMethod())) { JsonObject params = (JsonObject) notificationMessage.getParams(); - if (params.has("statusMsg")) { - String status = params.get("statusMsg").getAsString(); - System.out.println("STS4 Language Server Status Update: " + status); - } - else { - System.out.println("STS4 Language Server Status Update: DONE"); - } + String status = params.has("statusMsg") ? params.get("statusMsg").getAsString() : ""; + showStatusMessage(status); } } } + private void showStatusMessage(final String status) { + PlatformUI.getWorkbench().getDisplay().asyncExec(new Runnable() { + @Override + public void run() { + IStatusLineManager statusLineManager = getStatusLineManager(); + if (statusLineManager != null) { + statusLineManager.setMessage(status); + } + } + }); + } + + private IStatusLineManager getStatusLineManager() { + try { + return PlatformUI.getWorkbench().getActiveWorkbenchWindow().getActivePage().getActiveEditor().getEditorSite().getActionBars().getStatusLineManager(); + } + catch (NullPointerException e) { + return null; + } + } + protected String getJDKLocation() { IVMInstall jdk = JavaRuntime.getDefaultVMInstall(); File javaExecutable = StandardVMType.findJavaExecutable(jdk.getInstallLocation()); From 07beb2017124aad1a485a4964f24f4f6ca38537b Mon Sep 17 00:00:00 2001 From: Martin Lippert Date: Wed, 1 Feb 2017 15:53:01 +0100 Subject: [PATCH 5/5] reducing index-in-progress messages to real index situations --- .../DefaultSpringPropertyIndexProvider.java | 19 ++++------------- .../SpringPropertiesIndexManager.java | 21 ++++++++++++++++--- .../boot/metadata/PropertiesIndexTest.java | 16 +++++++------- 3 files changed, 31 insertions(+), 25 deletions(-) diff --git a/vscode-extensions/vscode-boot-properties/src/main/java/org/springframework/ide/vscode/boot/metadata/DefaultSpringPropertyIndexProvider.java b/vscode-extensions/vscode-boot-properties/src/main/java/org/springframework/ide/vscode/boot/metadata/DefaultSpringPropertyIndexProvider.java index 0a322a6e4..6434fb19b 100644 --- a/vscode-extensions/vscode-boot-properties/src/main/java/org/springframework/ide/vscode/boot/metadata/DefaultSpringPropertyIndexProvider.java +++ b/vscode-extensions/vscode-boot-properties/src/main/java/org/springframework/ide/vscode/boot/metadata/DefaultSpringPropertyIndexProvider.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2016-2017 Pivotal, Inc. + * Copyright (c) 2016, 2017 Pivotal, Inc. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at @@ -23,7 +23,6 @@ public class DefaultSpringPropertyIndexProvider implements SpringPropertyIndexPr private SpringPropertiesIndexManager indexManager = new SpringPropertiesIndexManager(ValueProviderRegistry.getDefault()); private ProgressService progressService = (id, msg) -> { /*ignore*/ }; - private static int progressIdCt = 0; public DefaultSpringPropertyIndexProvider(JavaProjectFinder javaProjectFinder) { this.javaProjectFinder = javaProjectFinder; @@ -31,23 +30,13 @@ public class DefaultSpringPropertyIndexProvider implements SpringPropertyIndexPr @Override public FuzzyMap getIndex(IDocument doc) { - String progressId = getProgressId(); - progressService.progressEvent(progressId, "Indexing Spring Boot Properties..."); - try { - IJavaProject jp = javaProjectFinder.find(doc); - if (jp!=null) { - return indexManager.get(jp); - } - } finally { - progressService.progressEvent(progressId, null); + IJavaProject jp = javaProjectFinder.find(doc); + if (jp!=null) { + return indexManager.get(jp, progressService); } return null; } - private static synchronized String getProgressId() { - return DefaultSpringPropertyIndexProvider.class.getName()+ (progressIdCt++); - } - public void setProgressService(ProgressService progressService) { this.progressService = progressService; } diff --git a/vscode-extensions/vscode-boot-properties/src/main/java/org/springframework/ide/vscode/boot/metadata/SpringPropertiesIndexManager.java b/vscode-extensions/vscode-boot-properties/src/main/java/org/springframework/ide/vscode/boot/metadata/SpringPropertiesIndexManager.java index a6a3f0f52..d88075998 100644 --- a/vscode-extensions/vscode-boot-properties/src/main/java/org/springframework/ide/vscode/boot/metadata/SpringPropertiesIndexManager.java +++ b/vscode-extensions/vscode-boot-properties/src/main/java/org/springframework/ide/vscode/boot/metadata/SpringPropertiesIndexManager.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2014 Pivotal, Inc. + * Copyright (c) 2014, 2017 Pivotal, Inc. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at @@ -17,6 +17,7 @@ import org.springframework.ide.vscode.boot.metadata.util.FuzzyMap; import org.springframework.ide.vscode.boot.metadata.util.Listener; import org.springframework.ide.vscode.boot.metadata.util.ListenerManager; import org.springframework.ide.vscode.commons.java.IJavaProject; +import org.springframework.ide.vscode.commons.languageserver.ProgressService; /** * Support for Reconciling, Content Assist and Hover Text in spring properties @@ -29,20 +30,30 @@ import org.springframework.ide.vscode.commons.java.IJavaProject; public class SpringPropertiesIndexManager extends ListenerManager> { private Map indexes = null; - final private ValueProviderRegistry valueProviders; + private final ValueProviderRegistry valueProviders; + private static int progressIdCt = 0; public SpringPropertiesIndexManager(ValueProviderRegistry valueProviders) { this.valueProviders = valueProviders; } - public synchronized FuzzyMap get(IJavaProject project) { + public synchronized FuzzyMap get(IJavaProject project, ProgressService progressService) { if (indexes==null) { indexes = new HashMap<>(); } SpringPropertyIndex index = indexes.get(project); if (index==null) { + String progressId = getProgressId(); + if (progressService != null) { + progressService.progressEvent(progressId, "Indexing Spring Boot Properties..."); + } + index = new SpringPropertyIndex(valueProviders, project.getClasspath()); indexes.put(project, index); + + if (progressService != null) { + progressService.progressEvent(progressId, null); + } } return index; } @@ -56,4 +67,8 @@ public class SpringPropertiesIndexManager extends ListenerManager { /*ignore*/ }; @Test public void springStandardPropertyPresent_Maven() throws Exception { SpringPropertiesIndexManager indexManager = new SpringPropertiesIndexManager( ValueProviderRegistry.getDefault()); IJavaProject mavenProject = projects.mavenProject(CUSTOM_PROPERTIES_PROJECT); - FuzzyMap index = indexManager.get(mavenProject); + FuzzyMap index = indexManager.get(mavenProject, progressService); PropertyInfo propertyInfo = index.get("server.port"); assertNotNull(propertyInfo); assertEquals(Integer.class.getName(), propertyInfo.getType()); @@ -51,7 +53,7 @@ public class PropertiesIndexTest { SpringPropertiesIndexManager indexManager = new SpringPropertiesIndexManager( ValueProviderRegistry.getDefault()); IJavaProject mavenProject = projects.mavenProject(CUSTOM_PROPERTIES_PROJECT); - FuzzyMap index = indexManager.get(mavenProject); + FuzzyMap index = indexManager.get(mavenProject, progressService); PropertyInfo propertyInfo = index.get("demo.settings.user"); assertNotNull(propertyInfo); assertEquals(String.class.getName(), propertyInfo.getType()); @@ -63,7 +65,7 @@ public class PropertiesIndexTest { SpringPropertiesIndexManager indexManager = new SpringPropertiesIndexManager( ValueProviderRegistry.getDefault()); IJavaProject mavenProject = projects.mavenProject(CUSTOM_PROPERTIES_PROJECT); - FuzzyMap index = indexManager.get(mavenProject); + FuzzyMap index = indexManager.get(mavenProject, progressService); PropertyInfo propertyInfo = index.get("my.server.port"); assertNull(propertyInfo); } @@ -73,7 +75,7 @@ public class PropertiesIndexTest { SpringPropertiesIndexManager indexManager = new SpringPropertiesIndexManager( ValueProviderRegistry.getDefault()); IJavaProject classpathFileProject = projects.javaProjectWithClasspathFile(CUSTOM_PROPERTIES_PROJECT); - FuzzyMap index = indexManager.get(classpathFileProject); + FuzzyMap index = indexManager.get(classpathFileProject, progressService); PropertyInfo propertyInfo = index.get("server.port"); assertNotNull(propertyInfo); assertEquals(Integer.class.getName(), propertyInfo.getType()); @@ -85,7 +87,7 @@ public class PropertiesIndexTest { SpringPropertiesIndexManager indexManager = new SpringPropertiesIndexManager( ValueProviderRegistry.getDefault()); IJavaProject classpathFileProject = projects.javaProjectWithClasspathFile(CUSTOM_PROPERTIES_PROJECT); - FuzzyMap index = indexManager.get(classpathFileProject); + FuzzyMap index = indexManager.get(classpathFileProject, progressService); PropertyInfo propertyInfo = index.get("demo.settings.user"); assertNotNull(propertyInfo); assertEquals(String.class.getName(), propertyInfo.getType()); @@ -97,7 +99,7 @@ public class PropertiesIndexTest { SpringPropertiesIndexManager indexManager = new SpringPropertiesIndexManager( ValueProviderRegistry.getDefault()); IJavaProject classpathFileProject = projects.javaProjectWithClasspathFile(CUSTOM_PROPERTIES_PROJECT); - FuzzyMap index = indexManager.get(classpathFileProject); + FuzzyMap index = indexManager.get(classpathFileProject, progressService); PropertyInfo propertyInfo = index.get("my.server.port"); assertNull(propertyInfo); }