ARTICLE DETAIL

资讯详情

深耕网站视觉设计与运营推广的一线实战洞察。

VSCode 配置 Python 运行调试环境全指南

VSCode 配置 Python 运行调试环境全指南 一个同事上周把 PyCharm 卸载了理由很实在公司配的开发机内存只有 8GPyCharm 开着索引动不动吃掉 2 个 G切个分支还要等它重建缓存。他转投 VSCode 之后第一句话是怎么什么都没反应第二句话是F5 按下去弹出来一个 json 我看不懂。这个场景我见得太多了。VSCode 配置 Python 运行调试环境本身并不复杂坑主要集中在它不像 IDE 那样什么都替你做好——编辑器、解释器、调试器是三个独立的东西你得手动把它们连起来。这篇就把这套连接关系拆开讲清楚从 Python 安装、VSCode 装插件、绑定解释器到launch.json逐字段拆解、断点调试、格式化检查与测试流水线全部按我实际用下来最省事的顺序来。不管你是刚写完第一个print(hello)的新手还是被 PyCharm 卡到想换门的熟手照着走一遍基本能把日常开发、调试、测试这条链路跑通。1. 先想清楚这套环境要解决什么问题动手装之前先把角色的分工理清楚后面所有为什么这么配都能自己推导出来。很多人配不好根子不在操作步骤而在于他把 VSCode 当成了一个自带 Python 的软件装完发现跑不起来就懵了。1.1 编辑器、解释器、调试器三个角色别搞混打个厨房的比方。VSCode 是灶台和操作台它负责切菜、摆盘、给你递工具但它自己不会炒菜。Python 解释器才是那口锅里的火真正执行代码的是它。调试器则是插在锅里的温度计加探针它能在你指定的位置把火掐停让你看看锅里现在是什么状态。这三者缺一不可而且必须对上号。一台机器上装三个 Python 版本是常事——系统自带的、官网下载的、conda 建的。VSCode 默认会猜猜错了就会出现我在终端里pip install requests装好了代码里import requests还是飘红这种经典故障。原因很简单终端用的是 A 解释器飘红那行字是 B 解释器在报错两者根本不是同一个环境。想明白这一点后面Python: Select Interpreter那一步的分量就出来了。它不是可有可无的设置项它是把灶台和火连起来的那根管子。1.2 这套配置适合谁能省掉哪些重复劳动我的判断标准很直白只要你的代码需要跑起来看结果这套配置就值得花半小时一次性搞好。写爬虫、写脚本、做数据处理、跑后端服务、写自动化测试全都算在内。配好之后能省掉的事情大致有这些。第一不用每次手动敲python xxx.pyF5 直接跑当前文件ShiftF5 停。第二不用在代码里到处插print看变量鼠标悬停就能看值断点停下可以在调试控制台里随便改表达式。第三不用记一堆命令行的路径虚拟环境切换在状态栏点一下就完事。第四保存时自动格式化、自动整理 import代码风格统一这件事从靠自觉变成靠配置。还有一点常被忽略VSCode 的配置文件是纯文本settings.json、launch.json、tasks.json全都可以跟着项目走进了 Git 之后团队里任何人克隆下来就是同一套环境。这个特性在多人协作里比任何花哨功能都值钱。2. 安装环节Python 与 VSCode 的正确打开方式安装这一步看着最没技术含量实际上大部分环境诡异的问题都埋在这里。我见过太多人因为一个勾没打之后花两小时排查。2.1 Python 安装时那几个选项的取舍从 Python 官网下载安装包双击运行第一个界面底部有个Add Python to PATH的复选框默认是不勾的。这个必须勾上否则你的命令行里敲python会提示不是内部或外部命令。原因在于 Windows 需要靠 PATH 环境变量去找可执行文件不勾就等于把 python.exe 藏在一个系统不知道的角落。第二个界面有个Install for all users的选项如果你的机器是个人用勾不勾都行如果是公司电脑且你有管理员权限勾上更省事之后装包不会因为权限被拒。第三个是安装路径。默认会装到C:\Users\你的用户名\AppData\Local\Programs\Python\Python3xx路径又长又带空格。我的习惯是手动改成C:\Python312这类短路径。理由是后面配虚拟环境、写launch.json的时候能把路径写短一点、少一层转义少踩坑。这个属于个人偏好不改也没问题只是麻烦一点。安装完成后会弹出 Disable path length limit 的选项建议点掉那个限制。Windows 默认 260 字符的路径上限在项目层级深、依赖包名长的时候会突然报错提前解除能省一次莫名其妙的失败。2.2 装完先跑三条命令确认底子干净别急着装 VSCode先在命令行里确认解释器本身是好的。打开 PowerShell 或终端敲下面三条python --version python -c import sys; print(sys.executable) python -c import sys; print(sys.version_info)第一条看版本号比如Python 3.12.4能出结果说明 PATH 配好了。第二条会打印解释器的完整路径这个信息待会儿在 VSCode 里选解释器时能对上号非常重要。第三条确认解释器是 64 位还是 32 位现在主流包基本只提供 64 位轮子32 位迟早出问题。如果你机器上有多个 Python用where pythonWindows或which python3macOS、Linux可以列出所有找到的路径按顺序排列。这个列表就是 VSCode 能发现的解释器候选池看到里面有你想要的版本后面就不慌。提示如果你在 Windows 上装了 Python 但python命令打开的是应用商店那是系统里的应用执行别名在捣乱。到「设置 → 应用 → 高级应用设置 → 应用执行别名」里把两个 python 的开关关掉即可。2.3 VSCode 安装与中文界面切换VSCode 官网下载Windows 用户选 System Installer 或者 User Installer 都行区别在于要不要管理员权限。安装过程中建议勾上将 Code 添加到 PATH和在右键菜单中添加打开方式这两个在命令行里敲code .用当前目录打开编辑器的时候特别顺手。装完第一次打开界面是英文的。切中文的入口在左侧活动栏最下面那个方块图标扩展搜索Chinese (Simplified)找到 Microsoft 官方发布的那个点 Install右下角会弹一个 Restart 提示重启后就是中文了。如果你的机器处于内网或者网络受限扩展市场可能转圈圈打不开。这种情况下可以先检查代理设置或者让运维同事把扩展市场域名放行。这一步不通后面插件都装不上属于优先级最高的事。2.4 插件清单先装四个就够用网上那些VSCode 必装 40 个插件的清单我看了头疼。Python 开发起步阶段真正必需的只有四个装多了反而互相打架。插件名发布方作用是否必需PythonMicrosoft核心插件提供解释器选择、调试、语法分析必需PylanceMicrosoft类型推断、补全、跳转定义装 Python 时通常自动带上必需RuffAstral Software极快的 lint 与格式化替代 flake8 isort 部分 black推荐Even Better TOMLtamasfe编辑pyproject.toml时有语法高亮和校验可选Python 插件装在本地还是远程要留意。如果你用 WSL 或者容器开发有些插件需要装在远端那一侧才生效VSCode 会在插件卡片上显示一个Install in WSL之类的按钮。这个细节不知道的人会陷入插件明明装了但补全就是不动的困境。3. 解释器绑定让 VSCode 认准哪一个 Python这是整个配置里最关键的一步也是配了但没生效的主要来源。理解了这一步后面launch.json为什么那么写就顺了。3.1 Select Interpreter 的三个入口和选择逻辑打开 VSCode用「文件 → 打开文件夹」打开你的项目目录。注意是打开文件夹而不是单个文件单个文件模式下很多功能是残缺的工作区级的配置也无处存放。打开任意一个.py文件后右下角状态栏会出现一个 Python 版本号比如3.12.4 64-bit鼠标点它或者用快捷键CtrlShiftP打开命令面板输入Python: Select Interpreter都能唤出解释器列表。列表里通常会分几组Detected自动探测到的、Conda 环境、以及.venv或venv目录下的虚拟环境。这里有个经验——如果你有计划使用虚拟环境先别急着在系统解释器上选先把虚拟环境建好再选否则你得选两遍。选择之后VSCode 会在项目根目录创建.vscode/settings.json写入python.defaultInterpreterPath。这个文件是你项目的私人配置建议加进版本控制团队里其他人在自己机器上只需要跑一次Select Interpreter就能共享其余全部设置。3.2 venv 的创建、激活与依赖固化为什么强烈建议用虚拟环境因为系统级的 site-packages 一旦被各种项目的依赖污染版本冲突会变成噩梦。某个项目要django3.2另一个要django5.0装在同一个解释器里必然有一个跑不起来。虚拟环境给每个项目一个独立的依赖空间互不干扰。在项目根目录打开集成终端Ctrl 反引号执行python -m venv .venvWindows PowerShell 激活.venv\Scripts\Activate.ps1macOS 或 Linux 激活source .venv/bin/activate激活成功后命令行提示符前面会出现(.venv)字样。这时候再装包装进去的才只属于这个项目。装完别忘了固化一下pip freeze requirements.txt这个文件一定要提交到 Git。团队里别人克隆下来一条pip install -r requirements.txt就复现了你的环境。虚拟环境的目录本身.venv要写进.gitignore因为它跟机器架构绑定提交上去毫无意义还特别大。注意PowerShell 下激活脚本可能被执行策略拦住报无法加载文件因为在此系统上禁止运行脚本。解决办法是以管理员身份运行 PowerShell执行Set-ExecutionPolicy -Scope CurrentUser RemoteSigned确认后即可。这个策略只影响当前用户属于安全可控的范围。3.3 settings.json 关键参数逐条拆解.vscode/settings.json是项目的核心配置文件。下面这份是我常用的底版逐条说下为什么这么写{ python.defaultInterpreterPath: ${workspaceFolder}/.venv/Scripts/python.exe, python.terminal.activateEnvironment: true, python.analysis.typeCheckingMode: basic, python.analysis.autoImportCompletions: true, python.analysis.extraPaths: [./src], editor.formatOnSave: true, files.encoding: utf8, files.eol: \n, python.testing.pytestEnabled: true, python.testing.unittestEnabled: false, python.testing.pytestArgs: [tests] }python.defaultInterpreterPath指定默认解释器。注意路径分隔符在 Windows 上要写正斜杠或用双反斜杠写成\v会被当成转义字符。macOS 和 Linux 上路径是.venv/bin/python没有Scripts那一层这是最常见的复制粘贴错误。python.terminal.activateEnvironment打开后你在 VSCode 里新开的终端会自动激活虚拟环境不用每次手动敲 activate。python.analysis.typeCheckingMode设成basicPylance 会做基础类型检查飘红提示比较克制设成strict会严格很多老项目上打开可能满屏波浪线量力而行。python.analysis.extraPaths在你用了src布局源码放在src/子目录时必须加否则import自己的包会飘红。files.eol设成\n是为了跨平台协作统一换行符。Windows 默认 CRLFLinux 是 LF不统一的话 Git 会显示一堆整文件变更非常难受。如果解释器路径写错了最典型的表现是状态栏那个版本号不见了或者右下角一直转圈。这时候按CtrlShiftP重新执行一次 Select Interpreter 就能修好。4. 调试配置 launch.json 全字段拆解按 F5 第一次运行的时候VSCode 会提示选择调试配置选 Python File 之后它会自动生成launch.json。这个文件在.vscode目录下很多人看都不看就关掉了然后用的时候发现参数传不进去、工作目录不对又回头来找多绕一圈。4.1 launch.json 从哪来为什么不建议手写打开调试面板CtrlShiftD点创建 launch.json 文件选 Python File就会生成一份模板。我建议在自动生成的基础上改不要从空文件手写。原因是 VSCode 的调试配置版本号version: 0.2.0和字段名都比较讲究手写容易漏东西。而且不同版本 VSCode 的调试器类型字段发生过变化早期用type: python新版推荐type: debugpy两者目前都能用但后者是新方向。调试配置写成数组可以放多份通过左上角下拉框切换。这个设计很实用——同一个项目里跑当前脚本和跑 Flask 服务的参数完全不同存两份一键切换比重敲命令快得多。4.2 核心字段速查与含义下面这组分片是我最常用的两种配置配合表格说明每个字段的作用。{ version: 0.2.0, configurations: [ { name: Python: 当前文件, type: debugpy, request: launch, program: ${file}, console: integratedTerminal, cwd: ${workspaceFolder}, env: { PYTHONPATH: ${workspaceFolder} }, args: [], justMyCode: true }, { name: Python: Flask, type: debugpy, request: launch, module: flask, env: { FLASK_APP: app.py, FLASK_DEBUG: 1 }, args: [run, --no-debugger, --no-reload], jinja: true, console: integratedTerminal } ] }字段作用常用取值与说明name配置在界面上显示的名字自定义建议按用途命名type调试器类型debugpy为新版推荐request启动还是附加launch启动新进程attach附加到已有进程program入口脚本路径${file}表示当前打开的文件module用模块方式启动跑flask、pytest这类带入口的包时用console输出到哪个终端integratedTerminal支持输入internalConsole不支持cwd工作目录${workspaceFolder}表示项目根目录env环境变量常用于设PYTHONPATH、FLASK_APPargs命令行参数列表传给你的脚本等价于命令行后面跟的内容justMyCode是否只调试自己的代码true时跳过第三方库内部false可跟进库源码console这个字段坑最多。默认的internalConsole在调试控制台里输出好处是干净坏处是你的程序如果需要读取标准输入比如input()会直接卡死在那里没有任何提示。所以只要你的脚本涉及交互输入一律改成integratedTerminal。justMyCode也值得说一句。默认true的时候断点打不进第三方库栈回溯也只显示你自己的函数。这在日常开发里是好事能过滤掉噪音但当你怀疑是某个库的行为不对想跟进去看就得改成false代价是单步调试会变得很啰嗦。4.3 三种典型场景配置模板场景一跑单个脚本文件。用${file}作为program适合零散脚本、练习代码。这是兜底配置我建议永远保留一份。场景二以模块方式跑带入口的程序。Web 框架、命令行工具包都属于这类。用module字段代替programVSCode 内部执行的是python -m 模块名。这里有个细节——Flask 调试模式的重载器会和调试器打架所以args里要加--no-reload让重载功能交给调试器自己管否则改代码触发的重启会打断你的断点。场景三附加到已经跑起来的进程。有时候程序是脚本启动的或者跑在容器里这时用request: attach配合processId或者connect: { host: ..., port: ... }。用processId时填${command:pickProcess}调试启动时会弹出进程列表让你选这个交互设计挺贴心。还有一类容易忽略的多进程程序。multiprocessing开出来的子进程默认调试器跟不进去你打在子进程函数里的断点不会停。解决办法是把配置里的subProcess: true加上调试器会尝试自动附加到新生的子进程上。5. 调试过程中的高价值技巧配好能跑只是及格线真正拉开效率差距的是下面这些用法。我用了几年之后回头看功能面板上那些按钮我只用了三个剩下的靠命令行和快捷键。5.1 条件断点、日志断点与命中计数普通断点是行号左侧点一下出现红点。但在循环里比如一个要迭代十万次的for每次循环都停下来等于没法用。右键那个红点选编辑断点可以设置表达式条件比如填item[id] 9527只有满足条件时才停。同一个菜单里还有个命中次数的设置填10表示第 10 次经过这行才停填100表示 100 次之后每次停。调试偶发问题的利器你不用手动按 100 次继续。更有意思的是日志断点有时候叫 Logpoint。它不停下来只是在调试控制台打印一条你指定的消息支持用{}插值比如当前 item {item[id]}, 累计 {count}。这相当于给代码插了print但不用改源码、不用删代码。以前调试完忘了删 print 导致上线日志爆炸的事故用这个就能规避。5.2 调试控制台里那几行代码能省多少事程序在断点处停下之后底部会出现调试控制台。这个输入框不是普通的输出窗口它是在当前栈帧的上下文里执行代码的。也就是说你可以直接敲item、len(results)、[x.name for x in users]去看你想看的任何东西完全不用改代码重跑。我经常用的一招变量是个复杂的大字典直接展开看很乱就在控制台里敲json.dumps(data, indent2, ensure_asciiFalse)格式漂亮地打出来。或者type(obj)、dir(obj)快速探一个陌生对象的接口。再进一步控制台里还可以调用函数。程序停在断点处你敲save_to_db(obj)直接执行一遍看效果对不对不对就停在这里继续调不用重跑整个流程。这比反复重启程序省下的时间非常可观。注意在调试控制台执行的代码是真实执行的有副作用。别在里面调用删库、发邮件这类函数除非你确定后果。5.3 调试 Web 服务与多进程程序的坑调试 Web 服务最常见的两个坑一个是热重载和断点冲突一个是超时。热重载冲突前面提过了框架自带的 reloader 会 fork 出子进程调试器附加在父进程上你在子进程里打的断点自然不生效。配置里加上--no-reload或者框架对应的关闭参数就好。超时问题主要出现在调试耗时较长的逻辑时浏览器那边先返回了 504。这时候别急着改代码先确认你的请求是不是真的执行完了——在函数入口打个断点确认进去了没。如果根本没进去问题在路由或中间件不在你的业务逻辑。多进程的坑还有一个是日志。子进程的 stdout 有时候不会汇总到主终端导致你以为程序没输出。这时候可以用logging写入文件再看文件内容比在终端里猜快得多。6. 代码质量流水线格式化、检查、测试一次配好调试是救火格式化检查是防火。这部分配好之后代码风格问题基本不用在 code review 里吵了机器会先把该说的说完。6.1 Ruff 的分工与接入方式早几年流行 black isort flake8 三件套现在我用 Ruff 一个替代。它用 Rust 写的速度比前三个加起来快几十倍而且同时具备 lint、import 排序、格式化三项能力。装法pip install ruff然后在settings.json里加{ [python]: { editor.defaultFormatter: charliermarsh.ruff, editor.formatOnSave: true, editor.codeActionsOnSave: { source.organizeImports: explicit, source.fixAll: explicit } } }formatOnSave保存即格式化。source.organizeImports会自动把import排序并删掉没用到的。source.fixAll会应用 Ruff 能自动修的那些规则比如把x None改成x is None。Ruff 的规则集通过项目根目录的pyproject.toml配置[tool.ruff] line-length 100 target-version py312 [tool.ruff.lint] select [E, F, I, UP, B] ignore [E501]select里的字母是规则类别E是 pycodestyle 错误F是 pyflakesI是 isortUP是 pyupgrade 帮你升级老写法B是 flake8-bugbear 抓常见陷阱。这套组合是我觉得性价比最高的太少没意义太多天天被警告淹没。6.2 pytest 与单元测试的图形化调试在settings.json里打开 pytest 之后左侧活动栏会出现一个烧瓶图标测试面板。VSCode 会自动扫描符合test_*.py或*_test.py命名规则的文件把每个测试函数列成树。点单个用例旁边的播放按钮就能跑失败的时候点一下就能直接跳到断言失败那一行。想让调试器跑测试也很简单在测试函数里打断点然后在测试面板右键选调试测试。这个组合在排查为什么这个用例只在 CI 上挂的时候特别有用你能一行行跟进断言前的状态。pytestArgs那个配置项建议填上测试目录比如[tests]避免 VSCode 去扫描整个项目导致启动慢。6.3 几个能省下大量点击的快捷键快捷键作用使用场景F5启动调试最常用ShiftF5停止调试卡住时的第一反应F9切换断点比鼠标点更快F10单步跳过不想跟进函数内部F11单步进入要跟进函数ShiftF11单步跳出跟进去了想出来CtrlShiftP命令面板记不住功能入口时的万能钥匙CtrlP快速打开文件按名字跳文件Ctrl开关终端频繁使用F5和F10这两个键我一天要按几百次值得形成肌肉记忆。另外别忘了左侧边栏那个运行和调试面板里的变量区它是实时刷新的比在控制台里一个个敲变量名要直观得多。7. 常见问题速查与排查实录前面讲的是怎么配好这一节讲配好之后翻车了怎么办。这些问题我大部分都亲身踩过有些还踩过不止一次。7.1 问题排查速查表现象最可能的原因处理方式左下角没有 Python 版本号没装 Python 插件或打开的是单个文件不是文件夹装插件改用打开文件夹import自己写的包飘红但能跑Pylance 的搜索路径里没有源码目录加python.analysis.extraPaths终端里装了包代码里还是 ModuleNotFoundError终端和调试器用的不是同一个解释器重新 Select Interpreter检查终端前缀有没有(.venv)断点是灰色空心圆调试器没启动或该文件不在调试目标里先按 F5 启动确认program指向的是这个文件断点打上了但停不下来justMyCode挡住了第三方库或代码被优化跳过改justMyCode为 false确认该行确实被执行到中文输出乱码编码不一致Windows 终端默认 GBK设files.encoding为 utf8终端执行chcp 65001程序在input()处卡死调试控制台不支持标准输入把console改成integratedTerminal路径含空格导致启动失败解释器路径没加引号检查defaultInterpreterPath是否需要引号包裹保存时格式化和 lint 打架同时启用了多个格式化器只保留一个作为defaultFormatter改了 launch.json 不生效配置有语法错误JSON 解析失败看编辑器的波浪线提示JSON 不允许尾随逗号7.2 几个踩坑之后才明白的经验第一条.vscode目录一定要提交到 Git除了本地绝对路径那种个人配置。我早期觉得这是编辑器配置没必要提交结果团队里每个人环境不一样同一条命令在不同人机器上跑出不同结果排查成本比配置成本高十倍。正确做法是把settings.json、launch.json、extensions.json提交上去个人偏好放在用户级的 settings 里。第二条别在同一台机器上装太多 Python 版本。理论上多版本共存没问题实际上 VSCode 的解释器探测、pip 的路径、环境变量的优先级都会变成不确定性来源。我现在的做法是系统只保留一个稳定版给工具用所有项目依赖一律走虚拟环境。清爽很多。第三条环境出问题先看解释器路径。我排查过的玄学问题里大概七成都能用一句话定位python -c import sys; print(sys.executable)看输出是不是你期待的那个路径。不是的话问题就找到了。养成看路径的习惯比记住一百个错误码有用。第四条调试配置不要一次写太满。见过有人一上来就把launch.json写成十几个配置的全家桶结果自己都记不清哪个是哪个。我的建议是从当前文件这一份开始遇到真的需要传参、需要跑模块的时候再增量加。配置是工具不是收藏品能跑通当前需求的就是好配置。第五条升级 Python 大版本前先备份requirements.txt。有些包在新版本上还没出对应的轮子升级完发现装不上又降不回去是很浪费时间的事。养成先冻结依赖、再升版本的肌肉记忆能躲过不少麻烦。这套环境我用了几年从写小脚本到带项目改动不大核心就是那三件事解释器选对、launch.json写对、虚拟环境用对。剩下的插件和快捷键都是锦上添花有更好没有也能干活。真要说最大的收益反而是那半个小时的一次性投入——把配置写成文件、跟着项目走之后再也不用在新机器上重新回忆当初是怎么弄好的。
返回列表