Skip to content

Commit

Permalink
support quickfix for gradle jpms projects
Browse files Browse the repository at this point in the history
Signed-off-by: Shi Chen <chenshi@microsoft.com>
  • Loading branch information
CsCherrYY committed Nov 1, 2022
1 parent e110f57 commit 5761d47
Show file tree
Hide file tree
Showing 8 changed files with 107 additions and 16 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
import java.util.Map;

import org.apache.commons.lang3.StringUtils;
import org.eclipse.buildship.core.internal.util.gradle.GradleVersion;
import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.jdt.ls.core.internal.commands.BuildPathCommand;
Expand All @@ -32,7 +33,6 @@
import org.eclipse.jdt.ls.core.internal.handlers.FormatterHandler;
import org.eclipse.jdt.ls.core.internal.handlers.ResolveSourceMappingHandler;
import org.eclipse.jdt.ls.core.internal.managers.GradleProjectImporter;
import org.eclipse.jdt.ls.core.internal.managers.GradleUtils;
import org.eclipse.lsp4j.ResolveTypeHierarchyItemParams;
import org.eclipse.lsp4j.SymbolInformation;
import org.eclipse.lsp4j.TextDocumentPositionParams;
Expand Down Expand Up @@ -125,7 +125,7 @@ public Object executeCommand(String commandId, List<Object> arguments, IProgress
String projectUri = (String) arguments.get(0);
String gradleVersion = arguments.size() > 1 ? (String) arguments.get(1) : null;
if (gradleVersion == null) {
gradleVersion = GradleUtils.CURRENT_GRADLE;
gradleVersion = GradleVersion.current().getVersion();
}
return GradleProjectImporter.upgradeGradleVersion(projectUri, gradleVersion, monitor);
case "java.project.resolveWorkspaceSymbol":
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -313,6 +313,8 @@ private CorrectionMessages() {
public static String NewCUCompletionUsingWizardProposal_tooltip_enclosingtype;
public static String NewCUCompletionUsingWizardProposal_tooltip_package;

public static String NotAccessibleType_upgrade_Gradle_label;

public static String JavaCorrectionProcessor_addquote_description;
public static String JavaCorrectionProcessor_error_quickfix_message;
public static String JavaCorrectionProcessor_error_status;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -396,6 +396,8 @@ NewCUCompletionUsingWizardProposal_dialogtitle=New
NewCUCompletionUsingWizardProposal_tooltip_enclosingtype=Enclosing Type:
NewCUCompletionUsingWizardProposal_tooltip_package=Package:

NotAccessibleType_upgrade_Gradle_label=Upgrade Gradle version to 7.0

JavaCorrectionProcessor_addquote_description=Insert missing quote
JavaCorrectionProcessor_error_quickfix_message=An error occurred while computing quick fixes. Check log for details.
JavaCorrectionProcessor_error_status=Exception while processing quick fixes or quick assists
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,20 +33,25 @@
import org.eclipse.core.runtime.CoreException;
import org.eclipse.jdt.core.IBuffer;
import org.eclipse.jdt.core.ICompilationUnit;
import org.eclipse.jdt.core.IJavaProject;
import org.eclipse.jdt.core.JavaModelException;
import org.eclipse.jdt.core.compiler.IProblem;
import org.eclipse.jdt.internal.ui.text.correction.IProblemLocationCore;
import org.eclipse.jdt.ls.core.internal.ProjectUtils;
import org.eclipse.jdt.ls.core.internal.corrections.proposals.ChangeCorrectionProposal;
import org.eclipse.jdt.ls.core.internal.corrections.proposals.GetterSetterCorrectionSubProcessor;
import org.eclipse.jdt.ls.core.internal.corrections.proposals.GradleCompatibilityProcessor;
import org.eclipse.jdt.ls.core.internal.corrections.proposals.IProposalRelevance;
import org.eclipse.jdt.ls.core.internal.corrections.proposals.JavadocTagsSubProcessor;
import org.eclipse.jdt.ls.core.internal.corrections.proposals.LocalCorrectionsSubProcessor;
import org.eclipse.jdt.ls.core.internal.corrections.proposals.ReorgCorrectionsSubProcessor;
import org.eclipse.jdt.ls.core.internal.corrections.proposals.ReplaceCorrectionProposal;
import org.eclipse.jdt.ls.core.internal.corrections.proposals.TypeMismatchSubProcessor;
import org.eclipse.jdt.ls.core.internal.corrections.proposals.UnresolvedElementsSubProcessor;
import org.eclipse.jdt.ls.core.internal.text.correction.CUCorrectionCommandProposal;
import org.eclipse.jdt.ls.core.internal.text.correction.ModifierCorrectionSubProcessor;
import org.eclipse.lsp4j.CodeActionKind;
import org.eclipse.lsp4j.CodeActionParams;

/**
*/
Expand All @@ -67,7 +72,7 @@ private static int moveBack(int offset, int start, String ignoreCharacters, ICom
return start;
}

public List<ChangeCorrectionProposal> getCorrections(IInvocationContext context, IProblemLocationCore[] locations) throws CoreException {
public List<ChangeCorrectionProposal> getCorrections(CodeActionParams params, IInvocationContext context, IProblemLocationCore[] locations) throws CoreException {
if (locations == null || locations.length == 0) {
return Collections.emptyList();
}
Expand All @@ -76,7 +81,7 @@ public List<ChangeCorrectionProposal> getCorrections(IInvocationContext context,
for (int i = 0; i < locations.length; i++) {
IProblemLocationCore curr = locations[i];
if (handledProblems(curr, locations, handledProblems)) {
process(context, curr, resultingCollections);
process(params, context, curr, resultingCollections);
}
}
return resultingCollections;
Expand All @@ -99,7 +104,7 @@ private static boolean handledProblems(IProblemLocationCore location, IProblemLo
return handledProblems.add(problemId);
}

private void process(IInvocationContext context, IProblemLocationCore problem, Collection<ChangeCorrectionProposal> proposals) throws CoreException {
private void process(CodeActionParams params, IInvocationContext context, IProblemLocationCore problem, Collection<ChangeCorrectionProposal> proposals) throws CoreException {
int id = problem.getProblemId();
if (id == 0) { // no proposals for none-problem locations
return;
Expand Down Expand Up @@ -546,6 +551,9 @@ private void process(IInvocationContext context, IProblemLocationCore problem, C
case IProblem.PotentiallyUnclosedCloseable:
LocalCorrectionsSubProcessor.getTryWithResourceProposals(context, problem, proposals);
break;
case IProblem.NotAccessibleType:
GradleCompatibilityProcessor.getGradleCompatibilityProposals(context, problem, proposals);
break;
// case IProblem.MissingSynchronizedModifierInInheritedMethod:
// ModifierCorrectionSubProcessor.addSynchronizedMethodProposal(context,
// problem, proposals);
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
/*******************************************************************************
* Copyright (c) 2022 Microsoft Corporation and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License 2.0
* which accompanies this distribution, and is available at
* https://www.eclipse.org/legal/epl-2.0/
*
* SPDX-License-Identifier: EPL-2.0
*
* Contributors:
* Microsoft Corporation - initial API and implementation
*******************************************************************************/
package org.eclipse.jdt.ls.core.internal.corrections.proposals;

import java.net.URI;
import java.util.Arrays;
import java.util.Collection;

import org.eclipse.buildship.core.internal.CorePlugin;
import org.eclipse.buildship.core.internal.preferences.PersistentModel;
import org.eclipse.buildship.core.internal.util.gradle.GradleVersion;
import org.eclipse.core.internal.resources.Workspace;
import org.eclipse.core.resources.IProject;
import org.eclipse.core.resources.IResource;
import org.eclipse.jdt.core.ICompilationUnit;
import org.eclipse.jdt.core.IJavaProject;
import org.eclipse.jdt.internal.ui.text.correction.IProblemLocationCore;
import org.eclipse.jdt.ls.core.internal.ProjectUtils;
import org.eclipse.jdt.ls.core.internal.corrections.CorrectionMessages;
import org.eclipse.jdt.ls.core.internal.corrections.IInvocationContext;
import org.eclipse.jdt.ls.core.internal.managers.GradleUtils;
import org.eclipse.jdt.ls.core.internal.text.correction.CUCorrectionCommandProposal;
import org.eclipse.lsp4j.CodeActionKind;

public class GradleCompatibilityProcessor {
public static void getGradleCompatibilityProposals(IInvocationContext context, IProblemLocationCore problem, Collection<ChangeCorrectionProposal> proposals) {
IJavaProject javaProject = context.getCompilationUnit().getJavaProject();
IProject project = javaProject.getProject();
if (!ProjectUtils.isGradleProject(project)) {
return;
}
PersistentModel model = CorePlugin.modelPersistence().loadModel(project);
if (!model.isPresent()) {
return;
}
GradleVersion gradleVersion = model.getGradleVersion();
if (gradleVersion != null && gradleVersion.compareTo(GradleVersion.version(GradleUtils.JPMS_SUPPORTED_VERSION)) < 0) {
IResource resource = javaProject.getResource();
if (resource == null) {
return;
}
URI uri = resource.getLocationURI();
if (uri == null) {
return;
}
proposals.add(new CUCorrectionCommandProposal(CorrectionMessages.NotAccessibleType_upgrade_Gradle_label, CodeActionKind.QuickFix, context.getCompilationUnit(), IProposalRelevance.CONFIGURE_BUILD_PATH, "java.project.upgradeGradle", Arrays.asList(uri.toString(), GradleUtils.JPMS_SUPPORTED_VERSION)));
}

}
}
Original file line number Diff line number Diff line change
Expand Up @@ -159,7 +159,7 @@ public List<Either<Command, CodeAction>> getCodeActionCommands(CodeActionParams
if (containsKind(codeActionKinds, CodeActionKind.QuickFix)) {
try {
codeActions.addAll(nonProjectFixProcessor.getCorrections(params, context, locations));
List<ChangeCorrectionProposal> quickfixProposals = this.quickFixProcessor.getCorrections(context, locations);
List<ChangeCorrectionProposal> quickfixProposals = this.quickFixProcessor.getCorrections(params, context, locations);
Set<ChangeCorrectionProposal> quickSet = new TreeSet<>(comparator);
quickSet.addAll(quickfixProposals);
proposals.addAll(quickSet);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,10 +37,12 @@
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.Properties;
import java.util.Set;
import java.util.stream.Collectors;


import org.apache.commons.lang3.StringUtils;
import org.eclipse.buildship.core.BuildConfiguration;
import org.eclipse.buildship.core.GradleBuild;
Expand All @@ -49,8 +51,10 @@
import org.eclipse.buildship.core.SynchronizationResult;
import org.eclipse.buildship.core.WrapperGradleDistribution;
import org.eclipse.buildship.core.internal.CorePlugin;
import org.eclipse.buildship.core.internal.DefaultGradleBuild;
import org.eclipse.buildship.core.internal.preferences.PersistentModel;
import org.eclipse.buildship.core.internal.util.gradle.GradleVersion;
import org.eclipse.core.resources.IContainer;
import org.eclipse.core.resources.IFile;
import org.eclipse.core.resources.IMarker;
import org.eclipse.core.resources.IProject;
Expand Down Expand Up @@ -254,7 +258,7 @@ public void importToWorkspace(IProgressMonitor monitor) throws CoreException {
}
}
if (JavaLanguageServerPlugin.getProjectsManager() != null && JavaLanguageServerPlugin.getProjectsManager().getConnection() != null) {
GradleCompatibilityInfo info = new GradleCompatibilityInfo(gradleStatus.getProjectUri(), gradleStatus.getMessage(), gradleStatus.getHighestJavaVersion(), GradleUtils.CURRENT_GRADLE);
GradleCompatibilityInfo info = new GradleCompatibilityInfo(gradleStatus.getProjectUri(), gradleStatus.getMessage(), gradleStatus.getHighestJavaVersion(), GradleVersion.current().getVersion());
EventNotification notification = new EventNotification().withType(EventType.IncompatibleGradleJdkIssue).withData(info);
JavaLanguageServerPlugin.getProjectsManager().getConnection().sendEventNotification(notification);
}
Expand All @@ -278,7 +282,7 @@ public void importToWorkspace(IProgressMonitor monitor) throws CoreException {
IMarker marker = ResourceUtils.createWarningMarker(GRADLE_UPGRADE_WRAPPER_MARKER_ID, wrapperProperties, GRADLE_INVALID_TYPE_CODE_MESSAGE, INVALID_TYPE_CODE_ID, reader.getLineNumber());
marker.setAttribute(GRADLE_MARKER_COLUMN_START, 0);
marker.setAttribute(GRADLE_MARKER_COLUMN_END, line.length());
UpgradeGradleWrapperInfo info = new UpgradeGradleWrapperInfo(gradleStatus.getProjectUri(), GRADLE_INVALID_TYPE_CODE_MESSAGE, GradleUtils.CURRENT_GRADLE);
UpgradeGradleWrapperInfo info = new UpgradeGradleWrapperInfo(gradleStatus.getProjectUri(), GRADLE_INVALID_TYPE_CODE_MESSAGE, GradleVersion.current().getVersion());
EventNotification notification = new EventNotification().withType(EventType.UpgradeGradleWrapper).withData(info);
JavaLanguageServerPlugin.getProjectsManager().getConnection().sendEventNotification(notification);
break;
Expand Down Expand Up @@ -535,17 +539,34 @@ public boolean accept(File dir, String name) {
return shouldSynchronize;
}

public static boolean upgradeGradleVersion(String projectUri, String gradleVersion, IProgressMonitor monitor) {
/**
* update the gradle wrapper to the given version
* @param projectUri uri of the project
* @param gradleVersion the target gradle version
* @param monitor the progress monitor
* @return the path to the new gradle-wrapper.properties file
*/
public static String upgradeGradleVersion(String projectUri, String gradleVersion, IProgressMonitor monitor) {
String newDistributionUrl = String.format("https://services.gradle.org/distributions/gradle-%s-bin.zip", gradleVersion);
Path projectFolder = Paths.get(URI.create(projectUri));
// try to get root project directory
IProject project = ProjectUtils.getProjectFromUri(projectUri);
Optional<GradleBuild> build = GradleCore.getWorkspace().getBuild(project);
if (!build.isPresent()) {
return null;
}
GradleBuild gradleBuild = build.get();
if (gradleBuild instanceof DefaultGradleBuild) {
projectFolder = ((DefaultGradleBuild) gradleBuild).getBuildConfig().getRootProjectDirectory().toPath();
}
File propertiesFile = projectFolder.resolve("gradle").resolve("wrapper").resolve("gradle-wrapper.properties").toFile();
Properties properties = new Properties();
if (propertiesFile.exists()) {
try (FileInputStream stream = new FileInputStream(propertiesFile)) {
properties.load(stream);
properties.setProperty("distributionUrl", newDistributionUrl);
} catch (IOException e) {
return false;
return null;
}
} else {
properties.setProperty("distributionBase", "GRADLE_USER_HOME");
Expand All @@ -557,10 +578,8 @@ public static boolean upgradeGradleVersion(String projectUri, String gradleVersi
try {
properties.store(new FileOutputStream(propertiesFile), null);
} catch (Exception e) {
return false;
return null;
}
BuildConfiguration build = getBuildConfiguration(projectFolder);
GradleBuild gradleBuild = GradleCore.getWorkspace().createBuild(build);
try {
gradleBuild.withConnection(connection -> {
connection.newBuild().forTasks("wrapper").run();
Expand All @@ -569,7 +588,7 @@ public static boolean upgradeGradleVersion(String projectUri, String gradleVersi
} catch (Exception e) {
// Do nothing
}
return true;
return propertiesFile.getAbsolutePath();
}

/**
Expand Down Expand Up @@ -677,7 +696,7 @@ private static File getGradleInitScriptTempFile(String scriptPath) {
* <ul>
* @param initScript the init script file.
* @param checksum the expected checksum of the file.
*
*
* @throws IOException
* @throws NoSuchAlgorithmException
*/
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,9 +28,9 @@
public class GradleUtils {

public static String MAX_SUPPORTED_JAVA = JavaCore.VERSION_17;
public static String CURRENT_GRADLE = "7.3.1";
// see https://github.com/gradle/gradle/pull/17397
public static String INVALID_TYPE_FIXED_VERSION = "7.2";
public static String JPMS_SUPPORTED_VERSION = "7.0";

public static boolean isIncompatible(GradleVersion gradleVersion, String javaVersion) {
if (gradleVersion == null || javaVersion == null || javaVersion.isEmpty()) {
Expand Down

0 comments on commit 5761d47

Please sign in to comment.