PY-30540 Associate new Python environment with new project immediately

We have enough data to associate a new Python environment with a new
project being created since we know the path to it. It is required
for Pipenv in order to be able to locate the project for creating a
virtualenv for it and a Pipfile inside it. PyCharm installs Django
during project creation so we need Pipenv to function correctly before
the project is set up.
This commit is contained in:
Andrey Vlasovskikh
2018-06-21 20:53:02 +03:00
parent d9e3f4f373
commit ee4680fa75
9 changed files with 12 additions and 35 deletions

View File

@@ -58,7 +58,7 @@ class PythonSdkConfigurator : DirectoryProjectConfigurator {
findDetectedAssociatedEnvironment(module, existingSdks)?.let {
val newSdk = it.setupAssociated(existingSdks, module.basePath) ?: return
SdkConfigurationUtil.addSdk(newSdk)
newSdk.associateWithModule(module, false)
newSdk.associateWithModule(module, null)
SdkConfigurationUtil.setDirectoryProjectSdk(project, newSdk)
return
}

View File

@@ -20,7 +20,6 @@ import com.intellij.ide.util.projectWizard.ProjectSettingsStepBase;
import com.intellij.ide.util.projectWizard.WebProjectTemplate;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.projectRoots.Sdk;
import com.intellij.openapi.projectRoots.SdkAdditionalData;
import com.intellij.openapi.projectRoots.impl.SdkConfigurationUtil;
import com.intellij.openapi.ui.Messages;
import com.intellij.openapi.util.io.FileUtil;
@@ -29,13 +28,9 @@ import com.intellij.platform.ProjectGeneratorPeer;
import com.intellij.util.BooleanFunction;
import com.jetbrains.python.newProject.PyNewProjectSettings;
import com.jetbrains.python.newProject.PythonProjectGenerator;
import com.jetbrains.python.sdk.PythonSdkAdditionalData;
import com.jetbrains.python.sdk.PythonSdkType;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.util.List;
public class PythonGenerateProjectCallback<T> extends AbstractNewProjectStep.AbstractCallback<T> {
@Override
@@ -71,13 +66,6 @@ public class PythonGenerateProjectCallback<T> extends AbstractNewProjectStep.Abs
if (newProject != null && generator instanceof PythonProjectGenerator) {
SdkConfigurationUtil.setDirectoryProjectSdk(newProject, sdk);
final List<Sdk> sdks = PythonSdkType.getAllSdks();
for (Sdk s : sdks) {
final SdkAdditionalData additionalData = s.getSdkAdditionalData();
if (additionalData instanceof PythonSdkAdditionalData) {
((PythonSdkAdditionalData)additionalData).reAssociateWithCreatedProject(newProject);
}
}
((PythonProjectGenerator)generator).afterProjectGenerated(newProject);
}
}

View File

@@ -93,10 +93,10 @@ fun createSdkByGenerateTask(generateSdkHomePath: Task.WithResult<String, Executi
false, null, suggestedName) ?: return null
}
fun Sdk.associateWithModule(module: Module?, isNewProject: Boolean) {
fun Sdk.associateWithModule(module: Module?, newProjectPath: String?) {
getOrCreateAdditionalData().apply {
when {
isNewProject -> associateWithNewProject()
newProjectPath != null -> associateWithModulePath(newProjectPath)
module != null -> associateWithModule(module)
}
}

View File

@@ -18,7 +18,6 @@ package com.jetbrains.python.sdk;
import com.google.common.collect.Sets;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.module.Module;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.projectRoots.Sdk;
import com.intellij.openapi.projectRoots.SdkAdditionalData;
import com.intellij.openapi.util.JDOMExternalizer;
@@ -54,7 +53,6 @@ public class PythonSdkAdditionalData implements SdkAdditionalData {
private final PythonSdkFlavor myFlavor;
private String myAssociatedModulePath;
private boolean myAssociateWithNewProject;
public PythonSdkAdditionalData(@Nullable PythonSdkFlavor flavor) {
myFlavor = flavor;
@@ -67,7 +65,6 @@ public class PythonSdkAdditionalData implements SdkAdditionalData {
myAddedPaths = from.myAddedPaths.clone(ApplicationManager.getApplication());
myExcludedPaths = from.myExcludedPaths.clone(ApplicationManager.getApplication());
myAssociatedModulePath = from.myAssociatedModulePath;
myAssociateWithNewProject = from.myAssociateWithNewProject;
}
@NotNull
@@ -99,25 +96,17 @@ public class PythonSdkAdditionalData implements SdkAdditionalData {
public void setAssociatedModulePath(@Nullable String associatedModulePath) {
myAssociatedModulePath = associatedModulePath;
myAssociateWithNewProject = false;
}
public void associateWithModule(@NotNull Module module) {
final String path = PySdkExtKt.getBasePath(module);
if (path != null) {
myAssociatedModulePath = FileUtil.toSystemIndependentName(path);
associateWithModulePath(path);
}
myAssociateWithNewProject = false;
}
public void associateWithNewProject() {
myAssociateWithNewProject = true;
}
public void reAssociateWithCreatedProject(@NotNull Project project) {
if (myAssociateWithNewProject) {
setAssociatedModulePath(project.getBasePath());
}
public void associateWithModulePath(@NotNull String modulePath) {
myAssociatedModulePath = FileUtil.toSystemIndependentName(modulePath);
}
public void save(@NotNull final Element rootElement) {

View File

@@ -56,7 +56,7 @@ class PyAddExistingCondaEnvPanel(private val project: Project?,
return when (sdk) {
is PyDetectedSdk -> sdk.setupAssociated(existingSdks, newProjectPath ?: project?.basePath)?.apply {
if (!makeSharedField.isSelected) {
associateWithModule(module, newProjectPath != null)
associateWithModule(module, newProjectPath)
}
}
else -> sdk

View File

@@ -58,7 +58,7 @@ class PyAddExistingVirtualEnvPanel(private val project: Project?,
return when (sdk) {
is PyDetectedSdk -> sdk.setupAssociated(existingSdks, newProjectPath ?: project?.basePath)?.apply {
if (!makeSharedField.isSelected) {
associateWithModule(module, newProjectPath != null)
associateWithModule(module, newProjectPath)
}
}
else -> sdk

View File

@@ -123,7 +123,7 @@ class PyAddNewCondaEnvPanel(private val project: Project?,
val associatedPath = if (!shared) projectBasePath else null
val sdk = createSdkByGenerateTask(task, existingSdks, null, associatedPath, null) ?: return null
if (!shared) {
sdk.associateWithModule(module, newProjectPath != null)
sdk.associateWithModule(module, newProjectPath)
}
PyCondaPackageService.getInstance().PREFERRED_CONDA_PATH = condaPath
return sdk

View File

@@ -111,7 +111,7 @@ class PyAddNewVirtualEnvPanel(private val project: Project?,
val associatedPath = if (!shared) projectBasePath else null
val sdk = createSdkByGenerateTask(task, existingSdks, baseSdkField.selectedSdk, associatedPath, null) ?: return null
if (!shared) {
sdk.associateWithModule(module, newProjectPath != null)
sdk.associateWithModule(module, newProjectPath)
}
excludeDirectoryFromProject(root, project)
with(PySdkSettings.instance) {

View File

@@ -155,7 +155,7 @@ fun setupPipEnvSdkUnderProgress(project: Project?,
val suggestedName = "Pipenv (${PathUtil.getFileName(projectPath)})"
return createSdkByGenerateTask(task, existingSdks, null, projectPath, suggestedName)?.apply {
isPipEnv = true
associateWithModule(module, newProjectPath != null)
associateWithModule(module, newProjectPath)
}
}
@@ -282,7 +282,7 @@ class UsePipEnvQuickFix(sdk: Sdk?, module: Module) : LocalQuickFix {
SdkConfigurationUtil.addSdk(newSdk)
}
else {
sdk.associateWithModule(module, false)
sdk.associateWithModule(module, null)
}
project.pythonSdk = sdk
module.pythonSdk = sdk