Save project before applying recipe. Try to use content from docs cache

This commit is contained in:
aboyko
2022-11-07 19:45:55 -05:00
parent b8d1670306
commit 1725d7f5a1
7 changed files with 196 additions and 150 deletions

View File

@@ -34,7 +34,8 @@ Require-Bundle: org.eclipse.jdt.launching;bundle-version="3.9.0",
org.springsource.ide.eclipse.commons.boot.ls,
org.springframework.ide.eclipse.editor.support,
com.google.guava,
org.eclipse.core.expressions
org.eclipse.core.expressions,
org.springsource.ide.eclipse.commons.core;bundle-version="4.17.0"
Import-Package: com.google.common.base,
com.google.common.collect,
com.google.gson;version="2.7.0",

View File

@@ -37,6 +37,7 @@ import org.eclipse.swt.widgets.Display;
import org.eclipse.ui.PlatformUI;
import org.eclipse.ui.handlers.HandlerUtil;
import org.springframework.tooling.boot.ls.BootLanguageServerPlugin;
import org.springsource.ide.eclipse.commons.core.CoreUtil;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
@@ -85,71 +86,75 @@ public class RewriteRefactoringsHandler extends AbstractHandler {
} else if (o instanceof IAdaptable) {
project = ((IAdaptable) o).getAdapter(IProject.class);
}
if (project != null) {
List<@NonNull LanguageServer> usedLanguageServers = LanguageServiceAccessor
.getActiveLanguageServers(serverCapabilities -> true);
try {
if (project != null && CoreUtil.promptForProjectSave(project)) {
List<@NonNull LanguageServer> usedLanguageServers = LanguageServiceAccessor
.getActiveLanguageServers(serverCapabilities -> true);
if (!usedLanguageServers.isEmpty()) {
final String uri = project.getLocationURI().toString();
ExecuteCommandParams commandParams = new ExecuteCommandParams();
commandParams.setCommand(REWRITE_REFACTORINGS_LIST);
commandParams.setArguments(List.of(uri));
if (!usedLanguageServers.isEmpty()) {
final String uri = project.getLocationURI().toString();
ExecuteCommandParams commandParams = new ExecuteCommandParams();
commandParams.setCommand(REWRITE_REFACTORINGS_LIST);
commandParams.setArguments(List.of(uri));
try {
List<Object> allRewriteRecipesJson = new ArrayList<>();
List<Object> syncRecipesJson = Collections.synchronizedList(allRewriteRecipesJson);
CompletableFuture.allOf(usedLanguageServers.stream()
.map(ls -> ls.getWorkspaceService().executeCommand(commandParams).thenAccept(or -> {
if (or != null) {
syncRecipesJson.add(or);
}
}).exceptionally(t -> null))
.toArray(CompletableFuture[]::new)).thenRun(() -> {
allRewriteRecipesJson.stream().filter(List.class::isInstance).map(List.class::cast).findFirst().ifPresent(obj -> {
RecipeDescriptor[] descriptors = serializationGson.fromJson(serializationGson.toJson(obj), RecipeDescriptor[].class);
PlatformUI.getWorkbench().getDisplay().asyncExec(() -> {
RecipeTreeModel recipesModel = new RecipeTreeModel(descriptors);
int returnCode = new SelectRecipesDialog(Display.getCurrent().getActiveShell(), recipesModel).open();
if (returnCode == Window.OK) {
try {
RecipeDescriptor recipeToApply = recipesModel.getSelectedRecipeDescriptors();
PlatformUI.getWorkbench().getProgressService().run(true, false, monitor -> {
try {
if (!usedLanguageServers.isEmpty()) {
monitor.beginTask("Applying recipe '" + recipeToApply.displayName + "'", IProgressMonitor.UNKNOWN);
ExecuteCommandParams cmdParams = new ExecuteCommandParams();
cmdParams.setCommand(REWRITE_REFACTORINGS_EXEC);
cmdParams.setArguments(List.of(
uri,
serializationGson.toJsonTree(recipeToApply)
));
CompletableFuture.allOf(usedLanguageServers.stream()
.map(ls -> ls.getWorkspaceService().executeCommand(cmdParams))
.toArray(CompletableFuture[]::new)).get();
try {
List<Object> allRewriteRecipesJson = new ArrayList<>();
List<Object> syncRecipesJson = Collections.synchronizedList(allRewriteRecipesJson);
CompletableFuture.allOf(usedLanguageServers.stream()
.map(ls -> ls.getWorkspaceService().executeCommand(commandParams).thenAccept(or -> {
if (or != null) {
syncRecipesJson.add(or);
}
}).exceptionally(t -> null))
.toArray(CompletableFuture[]::new)).thenRun(() -> {
allRewriteRecipesJson.stream().filter(List.class::isInstance).map(List.class::cast).findFirst().ifPresent(obj -> {
RecipeDescriptor[] descriptors = serializationGson.fromJson(serializationGson.toJson(obj), RecipeDescriptor[].class);
PlatformUI.getWorkbench().getDisplay().asyncExec(() -> {
RecipeTreeModel recipesModel = new RecipeTreeModel(descriptors);
int returnCode = new SelectRecipesDialog(Display.getCurrent().getActiveShell(), recipesModel).open();
if (returnCode == Window.OK) {
try {
RecipeDescriptor recipeToApply = recipesModel.getSelectedRecipeDescriptors();
PlatformUI.getWorkbench().getProgressService().run(true, false, monitor -> {
try {
if (!usedLanguageServers.isEmpty()) {
monitor.beginTask("Applying recipe '" + recipeToApply.displayName + "'", IProgressMonitor.UNKNOWN);
ExecuteCommandParams cmdParams = new ExecuteCommandParams();
cmdParams.setCommand(REWRITE_REFACTORINGS_EXEC);
cmdParams.setArguments(List.of(
uri,
serializationGson.toJsonTree(recipeToApply)
));
CompletableFuture.allOf(usedLanguageServers.stream()
.map(ls -> ls.getWorkspaceService().executeCommand(cmdParams))
.toArray(CompletableFuture[]::new)).get();
}
} catch (Exception e) {
throw new InvocationTargetException(e);
} finally {
monitor.done();
}
} catch (Exception e) {
throw new InvocationTargetException(e);
} finally {
monitor.done();
}
});
} catch (CoreException | InvocationTargetException | InterruptedException e) {
BootLanguageServerPlugin.getDefault().getLog().error(e.getMessage(), e);
MessageDialog.openError(Display.getCurrent().getActiveShell(), "Error", "Failed to apply Rewrite recipe(s). See error log for more details.");
});
} catch (CoreException | InvocationTargetException | InterruptedException e) {
BootLanguageServerPlugin.getDefault().getLog().error(e.getMessage(), e);
MessageDialog.openError(Display.getCurrent().getActiveShell(), "Error", "Failed to apply Rewrite recipe(s). See error log for more details.");
}
}
}
});
});
});
});
} catch (Exception e) {
throw new ExecutionException("Failed to apply Rewrite recipe(s)", e);
} catch (Exception e) {
throw new ExecutionException("Failed to apply Rewrite recipe(s)", e);
}
}
}
}
} catch (Exception e) {
throw new ExecutionException("Failed to save project resource(s)", e);
}
return null;
}

View File

@@ -12,7 +12,14 @@ package org.springsource.ide.eclipse.commons.core;
import java.util.Properties;
import org.eclipse.core.resources.IProject;
import org.eclipse.core.runtime.Assert;
import org.eclipse.core.runtime.IStatus;
import org.eclipse.core.runtime.Status;
import org.eclipse.debug.core.DebugPlugin;
import org.eclipse.debug.core.ILaunchConfiguration;
import org.eclipse.debug.core.IStatusHandler;
import org.eclipse.debug.core.model.LaunchConfigurationDelegate;
/**
* @author Steffen Pingel
@@ -24,7 +31,7 @@ public class CoreUtil {
* <code>properties</code>. Placeholders use the following format:
* <code>${key}</code>. If the key is not found in <code>properties</code>
* the placeholder is retained.
*
*
* @param text the text
* @param properties key value pairs for substitution
* @return the substituted text
@@ -56,4 +63,58 @@ public class CoreUtil {
return sb.toString();
}
/*
*
* The following constants are copied from LaunchConfigurationDelegate
*
*
*/
/**
* Constant to define debug.core for the status codes
*
* @since 3.2
*/
private static final String DEBUG_CORE = "org.eclipse.debug.core";
/**
* Constant to define debug.ui for the status codes
*
* @since 3.2
*/
private static final String DEBUG_UI = "org.eclipse.debug.ui";
/**
* Status code for which a UI prompter is registered.
*/
protected static final IStatus promptStatus = new Status(IStatus.INFO, DEBUG_UI, 200, "", null);
/**
* Status code for which a prompter will ask the user to save any/all of the dirty editors which have only to do
* with this launch (scoping them to the current launch/build)
*
* @since 3.2
*/
protected static final IStatus saveScopedDirtyEditors = new Status(IStatus.INFO, DEBUG_CORE, 222, "", null);
/**
* Derived from {@link LaunchConfigurationDelegate}
* @param project
* @return true if project was saved. False if canceled
* @throws Exception
*/
public static boolean promptForProjectSave(IProject project) throws Exception {
IStatusHandler prompter = DebugPlugin.getDefault().getStatusHandler(promptStatus);
if(prompter != null) {
IProject[] projects = new IProject[] {project};
ILaunchConfiguration configuration = null;
if(!((Boolean)prompter.handleStatus(saveScopedDirtyEditors, new Object[]{configuration, projects})).booleanValue()) {
return false;
}
}
return true;
}
}