Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
56 changes: 56 additions & 0 deletions src/installers/conda.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
import { BaseInstaller } from './base'
import * as path from 'path'
import * as fs from 'fs'

export default class CondaInstaller extends BaseInstaller {
name = 'conda'
description = 'Uses conda to install packages. (experimental)'
supportsExtras = false

async installPackage(
name: string,
version: string,
extras: string[],
dev: boolean
): Promise<void> {
const packageName = this.buildPackageName(name, extras)
const versionConstraint = version ? this.buildVersionConstraint(version) : ''
const command = version ? 'install' : 'update'
const installerCmd = 'conda'
const cmd = `${installerCmd} ${command} --channel=conda-forge -y "${packageName}${versionConstraint}"`
await this.condaExec(cmd)
}

async removePackage(name: string, dev: boolean): Promise<void> {
const installerCmd = await this.getInstallerCmd()
const cmd = `${installerCmd} uninstall -n ${dev ? '--dev' : ''} "${name}"`
await this.condaExec(cmd)
}

getCondaMetaPaths(interpreterPath: string): string[] {
const condaMetaDir = 'conda-meta'

const condaEnvDir1 = path.join(path.dirname(interpreterPath), condaMetaDir)
const condaEnvDir2 = path.join(path.dirname(path.dirname(interpreterPath)), condaMetaDir)

return [condaEnvDir1, condaEnvDir2]
}

isPresent(): boolean {
const condaMetaPaths = this.getCondaMetaPaths(this.mainPythonPath)
for (const condaMeta of condaMetaPaths) {
if (fs.existsSync(condaMeta)) {
return true
}
}
return false
}

async condaExec(cmd: string): Promise<{ stdout: string; stderr: string }> {
const condaExe = process.env.CONDA_EXE
const condaEnv = process.env.CONDA_DEFAULT_ENV
const activateCmd = path.join(path.dirname(this.mainPythonPath), 'activate')
const prefix = `${activateCmd} && ${condaExe} activate ${condaEnv}`
return await this.exec(`${prefix} && ${cmd}`)
}
}
5 changes: 4 additions & 1 deletion src/installers/smart.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import { BaseInstaller } from './base'
import { showProgress, getWorkDir } from '../utils'
import { SETTING_INSTALLER } from '../constants'
import { InstallerItem } from '../quickPick'
import CondaInstaller from './conda'

export class SmartInstaller {
pythonPaths: string[]
Expand All @@ -16,6 +17,7 @@ export class SmartInstaller {
poetry: PoetryInstaller
pip: PipInstaller
pipenv: PipenvInstaller
conda: CondaInstaller
installers: BaseInstaller[]
installedPackages: PipPackage[]
context: ExtensionContext
Expand All @@ -28,7 +30,8 @@ export class SmartInstaller {
this.poetry = new PoetryInstaller(this.pythonPaths, this.workDir)
this.pip = new PipInstaller(this.pythonPaths, this.workDir)
this.pipenv = new PipenvInstaller(this.pythonPaths, this.workDir)
this.installers = [this.poetry, this.pipenv, this.pip]
this.conda = new CondaInstaller(this.pythonPaths, this.workDir)
this.installers = [this.poetry, this.pipenv, this.pip, this.conda]
this.installedPackages = []
}

Expand Down