为什么学这个?
在做 Python 项目开发时,我经常面临一个尴尬的套路:
- 打开项目文件夹。
- 启动 Conda 环境(为了系统级依赖或特定 Python 版本)。
- 激活项目目录下的
.venv(为了隔离项目包)。 - 手动修改 VS Code 的
settings.json确保解释器路径正确。
这套动作每天重复十几次,极其琐碎。为了彻底解放双手,我研究并编写了一套自动化脚本,实现“进入目录即准备就绪”。
核心实现逻辑
我将这套方案拆解为两个部分:自动化脚本逻辑与 VS Code 深度集成。
1. 脚本核心:双层环境自动识别
通过编写 activate_dev.ps1 脚本,在Windows系统下我实现了以下自动化流程:
-
智能探测: 脚本会自动寻找当前目录下的
.venv。如果不存在,则静默退出,不干扰普通目录。 -
Conda 回溯: 通过解析
.venv/pyvenv.cfg文件中的home字段,脚本能自动识别该虚拟环境是基于哪个 Conda 环境创建的,并自动执行conda activate。 -
VS Code 配置自动化: 脚本会自动在
.vscode/settings.json中写入python.defaultInterpreterPath。核心代码逻辑:
PowerShell
$newSettings = @{ "python.defaultInterpreterPath" = "`${workspaceFolder}.venv\Scripts\python.exe" "python.terminal.activateEnvironment" = $true } # 自动合并现有配置,避免覆盖用户的自定义设置
2. VS Code 终端一键联动
为了让脚本在打开终端时自动运行,我修改了 VS Code 的全局配置:
JSON
"terminal.integrated.profiles.windows": {
"PowerShell": {
"source": "PowerShell",
"args": [
"-NoExit",
"-Command",
". ${env:HOME}\.vscode_scripts\activate_dev.ps1"
]
}
}
这样,每次我在项目内打开终端,环境就已经完全配好,连代理变量(http_proxy)都已自动注入。
附录:完整代码实现
为了方便大家直接复刻这套环境,我将核心脚本和 VS Code 全局配置整理如下。
1. 核心 PowerShell 脚本 (activate_dev.ps1)
建议将此脚本保存在用户目录下(如 ${env:HOME}.vscode_scripts\activate_dev.ps1)。
PowerShell
<#
.SYNOPSIS
自动检测并激活当前目录下的 .venv 虚拟环境及其关联的 Conda 环境,并自动配置 VS Code。
#>
$venvActivate = ".venv\Scripts\Activate.ps1"
if (-not (Test-Path $venvActivate)) {
return
}
Write-Host "🔍 发现 .venv,正在检测环境来源..." -ForegroundColor Cyan
# --- 1. 初始化 Conda 检查 ---
try {
if (-not (Get-Command conda -ErrorAction SilentlyContinue)) {
throw "conda 命令不可用"
}
} catch {
Write-Host "⚠️ Conda 未找到或未初始化,跳过 Conda 激活。" -ForegroundColor Yellow
}
$CONDA_ENV = $null
$pyvenvCfg = ".venv\pyvenv.cfg"
# --- 2. 环境自动探测逻辑 ---
if (Test-Path $pyvenvCfg) {
$content = Get-Content $pyvenvCfg -Raw
if ($content -match 'home\s*=\s*(.+)') {
$homePath = $matches[1].Trim()
if ($homePath -match 'envs[\/]([^\/]+)') {
$CONDA_ENV = $matches[1]
}
}
}
# --- 3. 手动选择回退机制 ---
if (-not $CONDA_ENV -and (Get-Command conda -ErrorAction SilentlyContinue)) {
Write-Host "❌ 无法自动检测 Conda 环境,请选择:" -ForegroundColor Yellow
$envList = conda env list | Where-Object { $_ -notmatch '^#' -and $_.Trim() -ne '' } | ForEach-Object { ($_ -split '\s+')[0] }
if ($envList.Count -gt 0) {
$index = 1
$options = @{}
foreach ($env in $envList) {
Write-Host " $index. $env"
$options[$index] = $env
$index++
}
Write-Host " $index. 跳过"
$options[$index] = $null
do {
$choice = Read-Host "请输入数字选择 (1-$index)"
} while ($choice -notmatch '^\d+$' -or [int]$choice -lt 1 -or [int]$choice -gt $index)
$CONDA_ENV = $options[[int]$choice]
}
}
# --- 4. 执行激活动作 ---
if ($CONDA_ENV) {
Write-Host "🔄 正在激活 Conda 环境: $CONDA_ENV" -ForegroundColor Cyan
conda activate $CONDA_ENV 2>$null
}
Write-Host "🔄 正在激活项目 venv" -ForegroundColor Cyan
. $venvActivate
# --- 5. 自动同步 VS Code 配置 (Windows) ---
$vscodeDir = ".vscode"
$settingsFile = "$vscodeDir\settings.json"
if (-not (Test-Path $vscodeDir)) {
New-Item -ItemType Directory -Path $vscodeDir | Out-Null
}
$newSettings = @{
"python.defaultInterpreterPath" = "`${workspaceFolder}.venv\Scripts\python.exe"
"python.terminal.activateEnvironment" = $true
}
if (Test-Path $settingsFile) {
try {
$currentSettings = Get-Content $settingsFile -Raw | ConvertFrom-Json -AsHashtable
foreach ($key in $newSettings.Keys) { $currentSettings[$key] = $newSettings[$key] }
$currentSettings | ConvertTo-Json -Depth 10 | Set-Content $settingsFile
} catch {
$newSettings | ConvertTo-Json -Depth 10 | Set-Content $settingsFile
}
} else {
$newSettings | ConvertTo-Json -Depth 10 | Set-Content $settingsFile
}
# --- 6. 状态汇总与清理函数 ---
Write-Host "`n✅ 开发环境已准备就绪!" -ForegroundColor Green
Write-Host " Python 路径: $((Get-Command python).Source)"
Write-Host " Python 版本: $(python --version 2>&1)"
function global:venv_exit {
Write-Host "退出虚拟环境..." -ForegroundColor Cyan
if (Get-Command deactivate -ErrorAction SilentlyContinue) { deactivate }
if ($CONDA_ENV) { conda deactivate 2>$null }
Write-Host "✅ 已退出所有环境" -ForegroundColor Green
}
Write-Host "💡 快捷命令:venv_exit (一键还原环境)`n" -ForegroundColor Cyan
2. VS Code 全局设置 (settings.json)
按下 Ctrl + Shift + P,输入 User Settings (JSON),添加以下配置:
JSON
{
// 默认终端使用 PowerShell
"terminal.integrated.defaultProfile.windows": "PowerShell",
"terminal.integrated.profiles.windows": {
"PowerShell": {
"source": "PowerShell",
"args": [
"-NoExit",
"-Command",
// 注意:请确保路径与你存放脚本的实际位置一致
". ${env:USERPROFILE}\.vscode_scripts\activate_dev.ps1"
]
}
},
// 终端环境变量注入(代理设置)
"terminal.integrated.env.windows": {
"http_proxy": "http://127.0.0.1:17897",
"https_proxy": "http://127.0.0.1:17897",
"all_proxy": "socks5://127.0.0.1:17897"
}
}
博主注: 记得将脚本中的代理端口修改为你自己常用的端口(如 7890 或 17897),祝编码愉快!