From 8cbcdad690e505c0b01f856a7b45c7059078602d Mon Sep 17 00:00:00 2001 From: "Vladislav.Soroka" Date: Tue, 21 Aug 2018 14:25:17 +0300 Subject: [PATCH] Gradle: do not show Import dialog when creating/opening gradle projects in CLion (IDEA-191523) --- .../execution/ExternalSystemJdkUtil.java | 36 ++++- .../manage/ContentRootDataService.java | 7 +- .../project/GradleProjectOpenProcessor.java | 137 ++++++++++++------ 3 files changed, 128 insertions(+), 52 deletions(-) diff --git a/platform/external-system-impl/src/com/intellij/openapi/externalSystem/service/execution/ExternalSystemJdkUtil.java b/platform/external-system-impl/src/com/intellij/openapi/externalSystem/service/execution/ExternalSystemJdkUtil.java index 7c24f9947fed..175d10b3a565 100644 --- a/platform/external-system-impl/src/com/intellij/openapi/externalSystem/service/execution/ExternalSystemJdkUtil.java +++ b/platform/external-system-impl/src/com/intellij/openapi/externalSystem/service/execution/ExternalSystemJdkUtil.java @@ -9,12 +9,14 @@ import com.intellij.openapi.projectRoots.*; import com.intellij.openapi.projectRoots.impl.JavaAwareProjectJdkTableImpl; import com.intellij.openapi.roots.ModuleRootManager; import com.intellij.openapi.roots.ProjectRootManager; +import com.intellij.openapi.util.Computable; import com.intellij.openapi.util.Pair; import com.intellij.openapi.util.text.StringUtil; import com.intellij.util.EnvironmentUtil; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; +import java.util.Collection; import java.util.List; import java.util.stream.Stream; @@ -75,8 +77,7 @@ public class ExternalSystemJdkUtil { @NotNull public static Pair getAvailableJdk(@Nullable Project project) throws ExternalSystemJdkException { - // JavaSdk.getInstance() can be null for non-java IDE - SdkType javaSdkType = JavaSdk.getInstance() == null ? SimpleJavaSdkType.getInstance() : JavaSdk.getInstance(); + SdkType javaSdkType = getJavaSdkType(); if (project != null) { Stream projectSdks = Stream.concat( @@ -107,6 +108,18 @@ public class ExternalSystemJdkUtil { return pair(USE_INTERNAL_JAVA, JavaAwareProjectJdkTableImpl.getInstanceEx().getInternalJdk()); } + @NotNull + public static Collection suggestJdkHomePaths() { + return getJavaSdkType().suggestHomePaths(); + } + + @NotNull + public static SdkType getJavaSdkType() { + // JavaSdk.getInstance() can be null for non-java IDE + JavaSdk javaSdk = JavaSdk.getInstance(); + return javaSdk == null ? SimpleJavaSdkType.getInstance() : javaSdk; + } + /** @deprecated trivial (to be removed in IDEA 2019) */ @Deprecated public static boolean checkForJdk(@NotNull Project project, @Nullable String jdkName) { @@ -121,4 +134,23 @@ public class ExternalSystemJdkUtil { public static boolean isValidJdk(@Nullable String homePath) { return !StringUtil.isEmptyOrSpaces(homePath) && (JdkUtil.checkForJdk(homePath) || JdkUtil.checkForJre(homePath)); } + + @NotNull + public static Sdk addJdk(String homePath) { + // JavaSdk.getInstance() can be null for non-java IDE + JavaSdk javaSdk = JavaSdk.getInstance(); + if (javaSdk == null) { + SimpleJavaSdkType simpleJavaSdkType = SimpleJavaSdkType.getInstance(); + return simpleJavaSdkType.createJdk(simpleJavaSdkType.suggestSdkName(null, homePath), homePath); + } + else { + return ApplicationManager.getApplication().runWriteAction( + (Computable)() -> { + Sdk jdk = javaSdk.createJdk(javaSdk.suggestSdkName(null, homePath), homePath, false); + ProjectJdkTable.getInstance().addJdk(jdk); + return jdk; + } + ); + } + } } \ No newline at end of file diff --git a/platform/external-system-impl/src/com/intellij/openapi/externalSystem/service/project/manage/ContentRootDataService.java b/platform/external-system-impl/src/com/intellij/openapi/externalSystem/service/project/manage/ContentRootDataService.java index 31fc43863967..f9676b9d81d7 100644 --- a/platform/external-system-impl/src/com/intellij/openapi/externalSystem/service/project/manage/ContentRootDataService.java +++ b/platform/external-system-impl/src/com/intellij/openapi/externalSystem/service/project/manage/ContentRootDataService.java @@ -39,6 +39,7 @@ import com.intellij.openapi.project.Project; import com.intellij.openapi.roots.ContentEntry; import com.intellij.openapi.roots.ModifiableRootModel; import com.intellij.openapi.roots.SourceFolder; +import com.intellij.openapi.startup.StartupManager; import com.intellij.openapi.util.Ref; import com.intellij.openapi.util.registry.Registry; import com.intellij.openapi.util.text.StringUtil; @@ -130,8 +131,10 @@ public class ContentRootDataService extends AbstractProjectDataService 0) { VirtualFile virtualFile = roots[0]; ExternalSystemUtil.invokeLater(project, ModalityState.NON_MODAL, () -> { - final ProjectView projectView = ProjectView.getInstance(project); - projectView.changeViewCB(ProjectViewPane.ID, null).doWhenProcessed(() -> projectView.selectCB(null, virtualFile, false)); + StartupManager.getInstance(project).runWhenProjectIsInitialized(() -> { + final ProjectView projectView = ProjectView.getInstance(project); + projectView.changeViewCB(ProjectViewPane.ID, null).doWhenProcessed(() -> projectView.selectCB(null, virtualFile, false)); + }); }); } } diff --git a/plugins/gradle/src/org/jetbrains/plugins/gradle/service/project/GradleProjectOpenProcessor.java b/plugins/gradle/src/org/jetbrains/plugins/gradle/service/project/GradleProjectOpenProcessor.java index 1d906985df1a..ca091d662efa 100644 --- a/plugins/gradle/src/org/jetbrains/plugins/gradle/service/project/GradleProjectOpenProcessor.java +++ b/plugins/gradle/src/org/jetbrains/plugins/gradle/service/project/GradleProjectOpenProcessor.java @@ -8,6 +8,7 @@ import com.intellij.ide.util.projectWizard.WizardContext; import com.intellij.ide.wizard.AbstractWizard; import com.intellij.ide.wizard.CommitStepException; import com.intellij.openapi.application.ModalityState; +import com.intellij.openapi.extensions.Extensions; import com.intellij.openapi.externalSystem.ExternalSystemModulePropertyManager; import com.intellij.openapi.externalSystem.importing.ImportSpec; import com.intellij.openapi.externalSystem.importing.ImportSpecBuilder; @@ -33,12 +34,19 @@ import com.intellij.openapi.projectRoots.Sdk; import com.intellij.openapi.roots.ModifiableRootModel; import com.intellij.openapi.roots.ui.configuration.ModulesProvider; import com.intellij.openapi.ui.DialogWrapper; +import com.intellij.openapi.util.Disposer; import com.intellij.openapi.util.Pair; +import com.intellij.openapi.util.io.FileUtilRt; +import com.intellij.openapi.util.text.StringUtil; +import com.intellij.openapi.vfs.LocalFileSystem; +import com.intellij.openapi.vfs.VfsUtil; import com.intellij.openapi.vfs.VirtualFile; import com.intellij.projectImport.ProjectOpenProcessor; import com.intellij.psi.PsiFile; import com.intellij.psi.PsiManager; +import com.intellij.util.ObjectUtils; import com.intellij.util.ThreeState; +import com.intellij.util.containers.ContainerUtil; import icons.GradleIcons; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; @@ -50,6 +58,9 @@ import org.jetbrains.plugins.gradle.util.GradleBundle; import org.jetbrains.plugins.gradle.util.GradleConstants; import javax.swing.*; +import java.io.File; +import java.nio.file.Path; +import java.nio.file.Paths; import java.util.Arrays; import java.util.Collection; @@ -88,60 +99,91 @@ public class GradleProjectOpenProcessor extends ProjectOpenProcessor { @Nullable @Override public Project doOpenProject(@NotNull VirtualFile virtualFile, @Nullable Project projectToClose, boolean forceOpenInNewFrame) { - final WizardContext wizardContext = new WizardContext(null, null); - if (virtualFile.isDirectory()) { + projectToClose = forceOpenInNewFrame ? null : projectToClose; + Path path = Paths.get(virtualFile.getPath()); + return openGradleProject(null, projectToClose, path); + } + + @Nullable + public static Project openGradleProject(@Nullable Project projectToOpen, + @Nullable Project projectToClose, + @NotNull Path path) { + GradleProjectOpenProcessor gradleProjectOpenProcessor = + Extensions.findExtension(ProjectOpenProcessor.EXTENSION_POINT_NAME, GradleProjectOpenProcessor.class); + VirtualFile virtualFile = VfsUtil.findFile(path, false); + if (virtualFile != null && virtualFile.isDirectory()) { for (VirtualFile file : virtualFile.getChildren()) { - if (canOpenProject(file)) { + if (gradleProjectOpenProcessor.canOpenProject(file)) { virtualFile = file; break; } } } - VirtualFile baseDir = virtualFile.getParent(); - String pathToOpen = baseDir.getPath(); - wizardContext.setProjectFileDirectory(pathToOpen); + String pathToOpen = virtualFile != null ? virtualFile.getParent().getPath() : path.toString(); - GradleAbstractWizard wizard = new GradleAbstractWizard(wizardContext, pathToOpen); + final WizardContext wizardContext = new WizardContext(null, null); + wizardContext.setProjectFileDirectory(pathToOpen); + GradleProjectSettings gradleProjectSettings = createDefaultProjectSettings(); + gradleProjectSettings.setExternalProjectPath(pathToOpen); + boolean jvmFound = setupGradleJvm(ObjectUtils.chooseNotNull(projectToOpen, projectToClose), gradleProjectSettings); + GradleAbstractWizard wizard = new GradleAbstractWizard(wizardContext, gradleProjectSettings); AbstractExternalModuleBuilder wizardBuilder = wizard.getBuilder(); try { - wizard.show(); - if (DialogWrapper.OK_EXIT_CODE == wizard.getExitCode()) { - final Project projectToOpen; - projectToOpen = ProjectManagerEx.getInstanceEx().newProject(wizardContext.getProjectName(), pathToOpen, true, false); - if (projectToOpen == null) return null; - if (!wizardBuilder.validate(projectToClose, projectToOpen)) { - return null; + if (!jvmFound) { + wizard.show(); + } + if (jvmFound || DialogWrapper.OK_EXIT_CODE == wizard.getExitCode()) { + if (projectToOpen == null) { + projectToOpen = ProjectManagerEx.getInstanceEx().newProject(wizardContext.getProjectName(), pathToOpen, true, false); } + if (projectToOpen == null) return null; ExternalProjectsManagerImpl.getInstance(projectToOpen).setStoreExternally(true); VirtualFile finalVirtualFile = virtualFile; + Project finalProjectToOpen = projectToOpen; ExternalSystemApiUtil.subscribe(projectToOpen, GradleConstants.SYSTEM_ID, new GradleSettingsListenerAdapter() { @Override public void onProjectsLinked(@NotNull Collection settings) { - createProjectPreview(projectToOpen, pathToOpen, finalVirtualFile); + createProjectPreview(finalProjectToOpen, pathToOpen, finalVirtualFile); } }); wizardBuilder.commit(projectToOpen, null, ModulesProvider.EMPTY_MODULES_PROVIDER); projectToOpen.save(); - if (!forceOpenInNewFrame) { + if (projectToClose != null) { closePreviousProject(projectToClose); } - ProjectUtil.updateLastProjectLocation(pathToOpen); projectToOpen.putUserData(ExternalSystemDataKeys.NEWLY_IMPORTED_PROJECT, Boolean.TRUE); - ProjectManagerEx.getInstanceEx().openProject(projectToOpen); + if (!projectToOpen.isOpen()) { + ProjectManagerEx.getInstanceEx().openProject(projectToOpen); + } return projectToOpen; } } finally { wizardBuilder.cleanup(); + Disposer.dispose(wizard.getDisposable()); } return null; } - public static void closePreviousProject(final Project projectToClose) { + public static void attachGradleProjectAndRefresh(@NotNull Project project, @NotNull String gradleProjectPath) { + openGradleProject(project, null, Paths.get(gradleProjectPath)); + } + + @NotNull + private static GradleProjectSettings createDefaultProjectSettings() { + GradleProjectSettings settings = new GradleProjectSettings(); + settings.setDistributionType(DistributionType.DEFAULT_WRAPPED); + settings.setStoreProjectFilesExternally(ThreeState.YES); + settings.setUseQualifiedModuleNames(true); + return settings; + } + + + private static void closePreviousProject(final Project projectToClose) { Project[] openProjects = ProjectManager.getInstance().getOpenProjects(); if (openProjects.length > 0) { int exitCode = ProjectUtil.confirmOpenNewProject(true); @@ -154,26 +196,36 @@ public class GradleProjectOpenProcessor extends ProjectOpenProcessor { private static class GradleAbstractWizard extends AbstractWizard { private final AbstractExternalModuleBuilder myBuilder; - public GradleAbstractWizard(WizardContext wizardContext, String rootProjectPath) { + public GradleAbstractWizard(WizardContext wizardContext, GradleProjectSettings gradleProjectSettings) { super("Open Gradle Project", (Project)null); - GradleProjectSettings gradleProjectSettings = createDefaultProjectSettings(); myBuilder = new AbstractExternalModuleBuilder(GradleConstants.SYSTEM_ID, gradleProjectSettings) { @Override protected void setupModule(Module module) throws ConfigurationException { super.setupModule(module); - assert rootProjectPath != null; - // it will be set later in any case, but save is called immediately after project creation, so, to ensure that it will be properly saved as external system module ExternalSystemModulePropertyManager.getInstance(module).setExternalId(GradleConstants.SYSTEM_ID); final Project project = module.getProject(); FileDocumentManager.getInstance().saveAllDocuments(); final GradleProjectSettings gradleProjectSettings = getExternalProjectSettings(); - attachGradleProjectAndRefresh(project, rootProjectPath, gradleProjectSettings); + attachGradleProjectAndRefresh(project, gradleProjectSettings); } @Override public void setupRootModel(ModifiableRootModel modifiableRootModel) { + String contentEntryPath = getContentEntryPath(); + if (StringUtil.isEmpty(contentEntryPath)) { + return; + } + File contentRootDir = new File(contentEntryPath); + FileUtilRt.createDirectory(contentRootDir); + LocalFileSystem fileSystem = LocalFileSystem.getInstance(); + VirtualFile modelContentRootDir = fileSystem.refreshAndFindFileByIoFile(contentRootDir); + if (modelContentRootDir == null) { + return; + } + + modifiableRootModel.addContentEntry(modelContentRootDir); } @Override @@ -210,26 +262,8 @@ public class GradleProjectOpenProcessor extends ProjectOpenProcessor { } } - public static void attachGradleProjectAndRefresh(@NotNull Project project, @NotNull String gradleProjectPath) { - GradleProjectSettings gradleProjectSettings = createDefaultProjectSettings(); - setupGradleJvm(project, gradleProjectSettings); - attachGradleProjectAndRefresh(project, gradleProjectPath, gradleProjectSettings); - } - - @NotNull - public static GradleProjectSettings createDefaultProjectSettings() { - GradleProjectSettings settings = new GradleProjectSettings(); - settings.setDistributionType(DistributionType.DEFAULT_WRAPPED); - settings.setStoreProjectFilesExternally(ThreeState.YES); - settings.setUseQualifiedModuleNames(true); - return settings; - } - - private static void attachGradleProjectAndRefresh(@NotNull Project project, - @NotNull String gradleProjectPath, - @NotNull GradleProjectSettings gradleProjectSettings) { + private static void attachGradleProjectAndRefresh(@NotNull Project project, @NotNull GradleProjectSettings gradleProjectSettings) { Runnable runnable = () -> { - gradleProjectSettings.setExternalProjectPath(gradleProjectPath); AbstractExternalSystemSettings settings = ExternalSystemApiUtil.getSettings(project, GradleConstants.SYSTEM_ID); //noinspection unchecked settings.linkProject(gradleProjectSettings); @@ -238,7 +272,7 @@ public class GradleProjectOpenProcessor extends ProjectOpenProcessor { .use(ProgressExecutionMode.IN_BACKGROUND_ASYNC) .useDefaultCallback() .build(); - ExternalSystemUtil.refreshProject(gradleProjectPath, importSpec); + ExternalSystemUtil.refreshProject(gradleProjectSettings.getExternalProjectPath(), importSpec); }; ExternalProjectsManagerImpl.getInstance(project) .runWhenInitialized( @@ -249,20 +283,27 @@ public class GradleProjectOpenProcessor extends ProjectOpenProcessor { ExternalSystemUtil.invokeLater(project, ModalityState.NON_MODAL, runnable); } - private static void setupGradleJvm(@NotNull Project project, @NotNull GradleProjectSettings projectSettings) { + private static boolean setupGradleJvm(@Nullable Project project, @NotNull GradleProjectSettings projectSettings) { final Pair sdkPair = ExternalSystemJdkUtil.getAvailableJdk(project); if (!ExternalSystemJdkUtil.USE_INTERNAL_JAVA.equals(sdkPair.first)) { projectSettings.setGradleJvm(sdkPair.first); + return true; } - else { - projectSettings.setGradleJvm(ExternalSystemJdkUtil.USE_JAVA_HOME); + + String jdkPath = ContainerUtil.iterateAndGetLastItem(ExternalSystemJdkUtil.suggestJdkHomePaths()); + if (jdkPath != null) { + Sdk sdk = ExternalSystemJdkUtil.addJdk(jdkPath); + projectSettings.setGradleJvm(sdk.getName()); + return true; } + return false; } - private static void createProjectPreview(Project project, String rootProjectPath, VirtualFile virtualFile) { + private static void createProjectPreview(@NotNull Project project, @NotNull String rootProjectPath, @Nullable VirtualFile virtualFile) { ExternalSystemUtil.refreshProject(project, GradleConstants.SYSTEM_ID, rootProjectPath, true, ProgressExecutionMode.MODAL_SYNC); ExternalProjectsManagerImpl.getInstance(project).runWhenInitialized(() -> DumbService.getInstance(project).runWhenSmart(() -> { ExternalSystemUtil.ensureToolWindowInitialized(project, GradleConstants.SYSTEM_ID); + if (virtualFile == null) return; final PsiFile psiFile = PsiManager.getInstance(project).findFile(virtualFile); if (psiFile != null) { ProjectView.getInstance(project).selectPsiElement(psiFile, false);