mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
PY-26492 Package indices based on Pipfile.lock
This commit is contained in:
@@ -62,6 +62,9 @@ public class PyPackageManagersImpl extends PyPackageManagers {
|
||||
if (PyCondaPackageManagerImpl.isConda(sdk)) {
|
||||
return new PyCondaManagementService(project, sdk);
|
||||
}
|
||||
else if (PipenvKt.isPipEnv(sdk)) {
|
||||
return new PyPipEnvPackageManagementService(project, sdk);
|
||||
}
|
||||
return new PyPackageManagementService(project, sdk);
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,67 @@
|
||||
// Copyright 2000-2018 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
|
||||
package com.jetbrains.python.packaging
|
||||
|
||||
import com.intellij.execution.ExecutionException
|
||||
import com.intellij.openapi.project.Project
|
||||
import com.intellij.openapi.projectRoots.Sdk
|
||||
import com.intellij.util.CatchingConsumer
|
||||
import com.intellij.webcore.packaging.InstalledPackage
|
||||
import com.intellij.webcore.packaging.RepoPackage
|
||||
import com.jetbrains.python.packaging.ui.PyPackageManagementService
|
||||
import com.jetbrains.python.sdk.flavors.pipFileLockSources
|
||||
import java.lang.Exception
|
||||
|
||||
/**
|
||||
* @author vlan
|
||||
*/
|
||||
class PyPipEnvPackageManagementService(project: Project, sdk: Sdk) : PyPackageManagementService(project, sdk) {
|
||||
override fun getAllRepositories(): List<String>? = null
|
||||
|
||||
override fun canInstallToUser() = false
|
||||
|
||||
override fun getAllPackages(): List<RepoPackage> {
|
||||
PyPIPackageUtil.INSTANCE.loadAdditionalPackages(sdk.pipFileLockSources, false)
|
||||
return allPackagesCached
|
||||
}
|
||||
|
||||
override fun reloadAllPackages(): List<RepoPackage> {
|
||||
PyPIPackageUtil.INSTANCE.loadAdditionalPackages(sdk.pipFileLockSources, true)
|
||||
return allPackagesCached
|
||||
}
|
||||
|
||||
override fun getAllPackagesCached(): List<RepoPackage> =
|
||||
PyPIPackageUtil.INSTANCE.getAdditionalPackages(sdk.pipFileLockSources)
|
||||
|
||||
override fun installPackage(repoPackage: RepoPackage,
|
||||
version: String?,
|
||||
forceUpgrade: Boolean,
|
||||
extraOptions: String?,
|
||||
listener: Listener,
|
||||
installToUser: Boolean) {
|
||||
val ui = PyPackageManagerUI(project, sdk, object : PyPackageManagerUI.Listener {
|
||||
override fun started() {
|
||||
listener.operationStarted(repoPackage.name)
|
||||
}
|
||||
|
||||
override fun finished(exceptions: List<ExecutionException>?) {
|
||||
listener.operationFinished(repoPackage.name, toErrorDescription(exceptions, sdk))
|
||||
}
|
||||
})
|
||||
val requirement = when {
|
||||
version != null -> PyRequirement(repoPackage.name, version)
|
||||
else -> PyRequirement(repoPackage.name)
|
||||
}
|
||||
val extraArgs = extraOptions?.split(" +".toRegex()) ?: emptyList()
|
||||
ui.install(listOf(requirement), extraArgs)
|
||||
}
|
||||
|
||||
override fun fetchPackageVersions(packageName: String?, consumer: CatchingConsumer<MutableList<String>, Exception>?) {
|
||||
// TODO: Override it for pipenv indices
|
||||
super.fetchPackageVersions(packageName, consumer)
|
||||
}
|
||||
|
||||
override fun fetchLatestVersion(pkg: InstalledPackage, consumer: CatchingConsumer<String, Exception>) {
|
||||
// TODO: Override it for pipenv indices
|
||||
super.fetchLatestVersion(pkg, consumer)
|
||||
}
|
||||
}
|
||||
@@ -56,8 +56,8 @@ public class PyPackageManagementService extends PackageManagementServiceEx {
|
||||
|
||||
@NonNls private static final String TEXT_SUFFIX = "</body></html>";
|
||||
|
||||
private final Project myProject;
|
||||
protected final Sdk mySdk;
|
||||
@NotNull private final Project myProject;
|
||||
@NotNull protected final Sdk mySdk;
|
||||
protected final ExecutorService myExecutorService;
|
||||
|
||||
public PyPackageManagementService(@NotNull Project project, @NotNull Sdk sdk) {
|
||||
@@ -72,6 +72,11 @@ public class PyPackageManagementService extends PackageManagementServiceEx {
|
||||
return mySdk;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public Project getProject() {
|
||||
return myProject;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<String> getAllRepositories() {
|
||||
|
||||
@@ -1,6 +1,9 @@
|
||||
// Copyright 2000-2018 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
|
||||
package com.jetbrains.python.sdk.flavors
|
||||
|
||||
import com.google.gson.Gson
|
||||
import com.google.gson.JsonSyntaxException
|
||||
import com.google.gson.annotations.SerializedName
|
||||
import com.intellij.codeInspection.LocalQuickFix
|
||||
import com.intellij.codeInspection.ProblemDescriptor
|
||||
import com.intellij.execution.ExecutionException
|
||||
@@ -10,6 +13,8 @@ import com.intellij.execution.configurations.PathEnvironmentVariableUtil
|
||||
import com.intellij.execution.process.CapturingProcessHandler
|
||||
import com.intellij.execution.process.ProcessOutput
|
||||
import com.intellij.openapi.application.ApplicationManager
|
||||
import com.intellij.openapi.application.ReadAction
|
||||
import com.intellij.openapi.fileEditor.FileDocumentManager
|
||||
import com.intellij.openapi.module.Module
|
||||
import com.intellij.openapi.module.ModuleUtilCore
|
||||
import com.intellij.openapi.progress.ProgressIndicator
|
||||
@@ -21,6 +26,7 @@ import com.intellij.openapi.projectRoots.impl.SdkConfigurationUtil
|
||||
import com.intellij.openapi.roots.ui.configuration.projectRoot.ProjectSdksModel
|
||||
import com.intellij.openapi.util.SystemInfo
|
||||
import com.intellij.openapi.util.io.FileUtil
|
||||
import com.intellij.openapi.vfs.StandardFileSystems
|
||||
import com.intellij.openapi.vfs.VirtualFile
|
||||
import com.intellij.util.PathUtil
|
||||
import com.jetbrains.python.packaging.PyExecutionException
|
||||
@@ -35,6 +41,8 @@ import javax.swing.Icon
|
||||
*/
|
||||
|
||||
const val PIP_FILE: String = "Pipfile"
|
||||
const val PIP_FILE_LOCK: String = "Pipfile.lock"
|
||||
const val PIPENV_DEFAULT_SOURCE_URL: String = "https://pypi.org/simple"
|
||||
|
||||
// TODO: Provide a special icon for pipenv
|
||||
val PIPENV_ICON: Icon = PythonIcons.Python.PythonClosed
|
||||
@@ -171,6 +179,13 @@ fun detectAndSetupPipEnv(project: Project?, module: Module?, existingSdks: List<
|
||||
return setupPipEnvSdkUnderProgress(project, module, existingSdks, null, null, false)
|
||||
}
|
||||
|
||||
/**
|
||||
* URLs of package sources configured in the Pipfile.lock of the module associated with this SDK.
|
||||
*/
|
||||
val Sdk.pipFileLockSources: List<String>
|
||||
get() = parsePipFileLock()?.meta?.sources?.mapNotNull { it.url } ?:
|
||||
listOf(PIPENV_DEFAULT_SOURCE_URL)
|
||||
|
||||
/**
|
||||
* A quick-fix for setting up the pipenv for the module of the current PSI element.
|
||||
*/
|
||||
@@ -209,3 +224,27 @@ class UsePipEnvQuickFix : LocalQuickFix {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private fun Sdk.parsePipFileLock(): PipFileLock? {
|
||||
// TODO: Log errors if Pipfile.lock is not found
|
||||
val file = pipFileLock ?: return null
|
||||
val text = ReadAction.compute<String, Throwable> { FileDocumentManager.getInstance().getDocument(file)?.text }
|
||||
return try {
|
||||
Gson().fromJson(text, PipFileLock::class.java)
|
||||
}
|
||||
catch (e: JsonSyntaxException) {
|
||||
// TODO: Log errors
|
||||
return null
|
||||
}
|
||||
}
|
||||
|
||||
private val Sdk.pipFileLock: VirtualFile?
|
||||
get() =
|
||||
associatedModulePath?.let { StandardFileSystems.local().findFileByPath(it)?.findChild(PIP_FILE_LOCK) }
|
||||
|
||||
private data class PipFileLock(@SerializedName("_meta") var meta: PipFileLockMeta?)
|
||||
|
||||
private data class PipFileLockMeta(@SerializedName("sources") var sources: List<PipFileLockSource>?)
|
||||
|
||||
private data class PipFileLockSource(@SerializedName("url") var url: String?)
|
||||
|
||||
|
||||
Reference in New Issue
Block a user