Python 项目管理
掌握 Poetry 和 uv 包管理器,理解 Python 项目的依赖管理和虚拟环境
📖 学习目标
- 理解 Python 包管理的发展历程
- 掌握 poetry 项目管理工具
- 学会使用 uv 包管理器
- 理解虚拟环境的概念和使用
- 掌握依赖版本管理
- 学会使用 pyproject.toml 配置项目
预计学习时间:1-2 天
难度:⭐⭐
1. Python 包管理发展历程
1.1 传统方式:pip + requirements.txt
bash
# 安装包
pip install requests
# 列出已安装的包
pip list
# 导出依赖
pip freeze > requirements.txt
# 从文件安装
pip install -r requirements.txtrequirements.txt 示例:
txt
requests==2.31.0
flask==3.0.0
pandas==2.1.0问题:
- 没有真正的依赖解析(可能产生依赖冲突)
- 无法区分直接依赖和间接依赖
- 版本锁定不够精确
- 无法管理开发依赖和生产依赖
1.2 现代方式:Poetry / uv
| 特性 | pip | Poetry | uv |
|---|---|---|---|
| 依赖解析 | ❌ | ✅ | ✅ |
| 锁文件 | ❌ | ✅ poetry.lock | ✅ uv.lock |
| 依赖分组 | ❌ | ✅ | ✅ |
| 虚拟环境 | 手动 | 自动 | 自动 |
| 发布包 | 需要 setuptools | ✅ | ❌ |
| 性能 | 慢 | 中等 | 极快 ⚡ |
2. Poetry 项目管理
2.1 安装 Poetry
bash
# macOS/Linux
curl -sSL https://install.python-poetry.org | python3 -
# 或使用 pip(不推荐)
pip install poetry
# 验证安装
poetry --version
# 配置(可选)
poetry config virtualenvs.in-project true # 在项目目录创建 .venv2.2 创建新项目
bash
# 创建新项目
poetry new my-project
# 项目结构
my-project/
├── my_project/
│ └── __init__.py
├── tests/
│ └── __init__.py
├── pyproject.toml
└── README.md
# 或者在现有项目初始化
cd existing-project
poetry init2.3 pyproject.toml 详解
toml
[tool.poetry]
name = "my-project"
version = "0.1.0"
description = "My awesome project"
authors = ["Your Name <you@example.com>"]
readme = "README.md"
packages = [{include = "my_project"}]
[tool.poetry.dependencies]
# 主要依赖
python = "^3.11" # Python 版本要求
requests = "^2.31.0" # ^ 表示兼容版本
flask = "~3.0.0" # ~ 表示不更新主版本号
pandas = ">=2.0.0,<3.0.0" # 指定范围
# 可选依赖
numpy = {version = "^1.24.0", optional = true}
[tool.poetry.group.dev.dependencies]
# 开发依赖
pytest = "^7.4.0"
black = "^23.0.0"
mypy = "^1.5.0"
[tool.poetry.group.docs]
# 文档依赖(可选组)
optional = true
[tool.poetry.group.docs.dependencies]
sphinx = "^7.0.0"
[build-system]
requires = ["poetry-core"]
build-backend = "poetry.core.masonry.api"版本约束语法:
^2.31.0:>=2.31.0, <3.0.0(推荐,保持主版本兼容)~2.31.0:>=2.31.0, <2.32.0(只更新修订版本)*:任意版本==2.31.0:精确版本>=2.31.0:最低版本
2.4 管理依赖
bash
# 添加依赖
poetry add requests # 添加到主依赖
poetry add pytest --group dev # 添加到开发依赖
poetry add sphinx --group docs # 添加到文档依赖
# 添加特定版本
poetry add "requests>=2.25.0,<3.0.0"
poetry add "flask^3.0.0"
# 更新依赖
poetry update # 更新所有依赖
poetry update requests # 更新指定包
# 删除依赖
poetry remove requests
# 显示依赖树
poetry show --tree
# 显示过时的包
poetry show --outdated2.5 虚拟环境管理
bash
# 创建虚拟环境
poetry install # 安装所有依赖(包括 dev)
poetry install --without dev # 不安装 dev 依赖
poetry install --with docs # 安装可选的 docs 依赖
# 激活虚拟环境
poetry shell
# 在虚拟环境中运行命令
poetry run python script.py
poetry run pytest
poetry run black .
# 查看虚拟环境信息
poetry env info
# 列出所有虚拟环境
poetry env list
# 删除虚拟环境
poetry env remove python3.112.6 锁文件(poetry.lock)
bash
# poetry.lock 文件
# - 锁定所有依赖的精确版本
# - 确保团队成员使用相同的版本
# - 应该提交到版本控制
# 生成/更新锁文件
poetry lock
# 只更新锁文件,不安装
poetry lock --no-update
# 根据锁文件安装(推荐)
poetry install3. uv 包管理器
3.1 安装 uv
bash
# macOS/Linux
curl -LsSf https://astral.sh/uv/install.sh | sh
# Windows
powershell -c "irm https://astral.sh/uv/install.ps1 | iex"
# 验证安装
uv --version3.2 uv 基本使用
bash
# 创建虚拟环境
uv venv
# 激活虚拟环境
source .venv/bin/activate # Linux/Mac
.venv\Scripts\activate # Windows
# 安装包
uv pip install requests
uv pip install -r requirements.txt
# 同步依赖(根据 pyproject.toml)
uv sync
# 添加依赖
uv add requests
uv add pytest --dev
# 运行命令
uv run python script.py
uv run pytest
# 速度对比
# pip: 约 30s
# poetry: 约 15s
# uv: 约 2s ⚡3.3 uv vs Poetry
python
# pyproject.toml(uv 格式)
[project]
name = "my-project"
version = "0.1.0"
requires-python = ">=3.11"
dependencies = [
"requests>=2.31.0",
"flask>=3.0.0",
]
[dependency-groups]
dev = [
"pytest>=7.4.0",
"black>=23.0.0",
]
[tool.uv]
dev-dependencies = [
"pytest>=7.4.0",
]何时选择 uv:
- ✅ 追求极致的安装速度
- ✅ 大型项目with众多依赖
- ✅ CI/CD 环境
- ❌ 需要发布包到 PyPI(用 Poetry)
何时选择 Poetry:
- ✅ 需要发布 Python 包
- ✅ 需要更成熟的生态
- ✅ 项目不是特别大
- ✅ 团队已经熟悉 Poetry
4. Dify 项目分析
4.1 Dify API pyproject.toml
bash
# 查看 Dify 的依赖管理
cd /Users/zhangjinhe/Documents/my/codes/dify/api
cat pyproject.toml- Python 版本:3.11+
Dify 最新版(1.9.2):
- 迁移到 uv
- Python 版本:3.11+
- 使用 uv.lock 锁定依赖
4.2 依赖组织
toml
# Dify 的依赖分组策略
# 主依赖:运行时必需
[project.dependencies]
flask = "~3.1.0"
celery = "~5.5.0"
sqlalchemy = "~2.0.29"
# ...
# 存储相关(可选)
[dependency-groups]
storage = [
"azure-storage-blob==12.26.0",
"google-cloud-storage==2.16.0",
]
# 向量数据库(可选)
vdb = [
"weaviate-client==4.17.0",
"qdrant-client==1.9.0",
"pymilvus~=2.5.0",
]
# 开发工具
dev = [
"pytest~=8.3.2",
"ruff~=0.14.0",
"basedpyright~=1.31.0",
]4.3 环境搭建实践
bash
# 1. Clone Dify
git clone https://github.com/langgenius/dify.git
cd dify/api
# 2. 创建虚拟环境(使用 uv)
uv venv
# 3. 激活虚拟环境
source .venv/bin/activate # Linux/Mac
# 4. 安装依赖
uv sync # 安装所有默认依赖组
# 5. 配置环境变量
cp .env.example .env
# 编辑 .env 文件
# 6. 初始化数据库
flask db upgrade
# 7. 运行开发服务器
flask run --host 0.0.0.0 --port 5001 --debug5. 虚拟环境深入
5.1 为什么需要虚拟环境?
python
"""
问题场景:
- 项目 A 需要 requests==2.25.0
- 项目 B 需要 requests==2.31.0
- 系统只能安装一个版本
解决方案:虚拟环境
- 每个项目有独立的 Python 环境
- 依赖隔离,互不干扰
"""
# 对比 Node.js
"""
Node.js:
- 每个项目有 node_modules 目录
- 天然隔离
Python:
- 默认全局安装到系统
- 需要虚拟环境隔离
"""5.2 虚拟环境工具对比
bash
# 1. venv(Python 内置,推荐新手)
python -m venv .venv
source .venv/bin/activate
pip install -r requirements.txt
# 2. virtualenv(功能更强)
pip install virtualenv
virtualenv venv
source venv/bin/activate
# 3. Poetry(自动管理)
poetry install # 自动创建虚拟环境
poetry shell # 激活
# 4. uv(最快)
uv venv
source .venv/bin/activate
uv sync
# 5. conda(适合数据科学)
conda create -n myenv python=3.11
conda activate myenv5.3 虚拟环境最佳实践
bash
# 1. 虚拟环境目录命名
.venv # Poetry/uv 默认(推荐)
venv # 常见
env # 也常见
# 2. 添加到 .gitignore
echo ".venv/" >> .gitignore
echo "venv/" >> .gitignore
echo "*.pyc" >> .gitignore
echo "__pycache__/" >> .gitignore
# 3. 文档化 Python 版本
echo "python_version = \"3.11\"" >> .python-version
# 或使用 pyenv
pyenv local 3.11.7
# 4. 依赖管理
# ✅ 使用 poetry.lock 或 uv.lock
# ✅ 提交到版本控制
# ❌ 不要提交 .venv/ 目录6. Python 版本管理
6.1 pyenv 管理多个 Python 版本
bash
# 安装 pyenv
curl https://pyenv.run | bash
# 列出可安装的版本
pyenv install --list
# 安装特定版本
pyenv install 3.11.7
pyenv install 3.12.1
# 设置全局版本
pyenv global 3.11.7
# 设置项目版本
cd my-project
pyenv local 3.11.7 # 创建 .python-version 文件
# 查看已安装版本
pyenv versions6.2 使用多个 Python 版本测试
bash
# tox:多版本测试工具
pip install tox
# tox.ini
[tox]
envlist = py311,py312
[testenv]
deps = pytest
commands = pytest tests/
# 运行测试
tox7. 实践项目
项目 1:创建一个完整的 Python 项目
bash
# 1. 创建项目
poetry new my-api
cd my-api
# 2. 添加依赖
poetry add flask
poetry add flask-sqlalchemy
poetry add pydantic
# 3. 添加开发依赖
poetry add pytest --group dev
poetry add black --group dev
poetry add mypy --group dev
# 4. 创建项目结构
mkdir -p my_api/{routes,models,services}
touch my_api/{__init__,app,config}.py
# 5. 配置工具
cat > pyproject.toml << 'EOF'
[tool.black]
line-length = 100
target-version = ['py311']
[tool.mypy]
python_version = "3.11"
strict = true
EOF
# 6. 运行工具
poetry run black .
poetry run mypy my_api/
poetry run pytest项目 2:迁移 requirements.txt 到 Poetry
bash
# 1. 在现有项目中初始化
poetry init
# 2. 从 requirements.txt 导入
cat requirements.txt | xargs poetry add
# 3. 分离开发依赖
# 编辑 requirements-dev.txt
cat requirements-dev.txt | xargs poetry add --group dev
# 4. 验证
poetry install
poetry run python -m pytest项目 3:搭建 Dify 开发环境
bash
#!/bin/bash
# setup_dify_dev.sh
# 1. 设置 Python 版本
pyenv install 3.11.7
pyenv local 3.11.7
# 2. 安装 uv
curl -LsSf https://astral.sh/uv/install.sh | sh
# 3. 克隆项目
git clone https://github.com/langgenius/dify.git
cd dify
# 4. 后端设置
cd api
uv venv
source .venv/bin/activate
uv sync
# 5. 配置环境变量
cp .env.example .env
# 编辑 .env
# 6. 初始化数据库
flask db upgrade
# 7. 前端设置(另一个终端)
cd ../web
pnpm install
pnpm dev
# 8. 启动后端
cd ../api
flask run --debug8. 常见问题
8.1 依赖冲突
bash
# 问题:包 A 需要 requests==2.25, 包 B 需要 requests>=2.30
# 解决:使用依赖解析器(Poetry/uv)
# Poetry 会自动解决
poetry add package-a package-b
# 如果无法解决,查看冲突
poetry add package-a package-b --dry-run
# 手动指定版本
poetry add "requests>=2.30"8.2 锁文件同步问题
bash
# 问题:poetry.lock 和 pyproject.toml 不同步
# 解决:更新锁文件
poetry lock --no-update
# 重新安装
poetry install8.3 虚拟环境激活问题
bash
# 问题:激活虚拟环境后仍使用系统 Python
# 检查
which python
python --version
# 确保正确激活
source .venv/bin/activate # 注意路径
# 或使用 poetry run
poetry run python script.py9. 思考题
- Poetry 和 npm/pnpm 有什么相似之处?
- 为什么需要锁文件(poetry.lock / uv.lock)?
- 什么是依赖解析?为什么重要?
- Dify 为什么从 Poetry 迁移到 uv?
- 如何在 Docker 中使用 Poetry/uv?
10. 检查清单
- [ ] 理解 Python 包管理的发展
- [ ] 能够使用 Poetry 管理项目
- [ ] 了解 uv 的优势和使用
- [ ] 掌握虚拟环境的创建和使用
- [ ] 能够读懂 pyproject.toml
- [ ] 成功搭建 Dify 开发环境
11. 完成 01-基础篇
恭喜!完成了 Python 基础篇的所有内容。现在你应该能够:
- ✅ 流畅编写 Python 代码
- ✅ 使用 Python 高级特性
- ✅ 编写异步程序
- ✅ 管理 Python 项目
12. 下一步
继续学习:
- 02-架构篇 - Dify 整体架构