贡献指南
感谢您对 pyutils 项目的关注!我们欢迎各种形式的贡献,包括但不限于:
报告 bug
提出新功能建议
改进文档
提交代码修复
添加新功能
优化性能
开发环境设置
推荐使用 uv 进行开发环境管理:
克隆仓库:
git clone https://github.com/your-username/pyutils.git cd pyutils
安装 uv (如果尚未安装):
# Windows powershell -ExecutionPolicy ByPass -c "irm https://astral.sh/uv/install.ps1 | iex" # macOS/Linux curl -LsSf https://astral.sh/uv/install.sh | sh
设置开发环境:
uv sync --all-extras --dev
安装 pre-commit 钩子:
uv run pre-commit install uv run pre-commit install --hook-type commit-msg
验证环境:
uv run pytest tests/ uv run ruff check src/ uv run mypy src/
开发工作流
我们使用现代化的开发工具链来确保代码质量:
代码质量检查
# 代码格式化
uv run ruff format src/ tests/
# 代码检查和自动修复
uv run ruff check --fix src/ tests/
# 类型检查
uv run mypy src/
# 安全检查
uv run bandit -r src/
测试
# 运行所有测试
uv run pytest tests/
# 运行测试并生成覆盖率报告
uv run pytest --cov=src --cov-report=html --cov-report=term
# 运行特定测试
uv run pytest tests/test_string.py
# 运行性能基准测试
uv run python benchmark.py
使用 Makefile
项目提供了 Makefile 来简化常用命令:
# 查看所有可用命令
make help
# 快速检查(格式化 + 检查 + 类型检查)
make quick-check
# 运行所有 CI 检查
make ci
# 设置开发环境
make dev-setup
提交代码
分支策略
main- 主分支,包含稳定的发布版本develop- 开发分支,包含最新的开发代码feature/*- 功能分支bugfix/*- 修复分支hotfix/*- 紧急修复分支
提交流程
创建功能分支:
git checkout -b feature/your-feature-name
进行开发,确保遵循代码规范
运行测试和检查:
make quick-check uv run pytest tests/
提交代码:
git add . git commit -m "feat: add your feature description"
推送分支:
git push origin feature/your-feature-name
创建 Pull Request
提交信息规范
我们使用 Conventional Commits 规范:
<type>[optional scope]: <description>
[optional body]
[optional footer(s)]
类型说明:
feat: 新功能fix: 修复 bugdocs: 文档更新style: 代码格式化(不影响功能)refactor: 重构代码perf: 性能优化test: 添加或修改测试chore: 构建过程或辅助工具的变动
示例:
feat(string): add fuzzy matching function
fix(array): handle empty array in chunk function
docs: update installation guide for uv
test(math): add tests for clamp function edge cases
代码规范
代码风格
使用 Ruff 进行代码格式化和检查
行长度限制为 88 字符
使用 Google 风格的 docstring
遵循 PEP 8 规范
类型注解
所有公共函数必须有完整的类型注解
使用
typing模块的类型提示复杂类型使用
TypeVar和Generic
示例:
from typing import List, Optional, TypeVar, Union
T = TypeVar('T')
def chunk(array: List[T], size: int) -> List[List[T]]:
"""将数组分割成指定大小的块。
Args:
array: 要分割的数组
size: 每块的大小
Returns:
分割后的数组列表
Raises:
ValueError: 当 size 小于等于 0 时
Examples:
>>> chunk([1, 2, 3, 4, 5], 2)
[[1, 2], [3, 4], [5]]
"""
if size <= 0:
raise ValueError("Size must be positive")
return [array[i:i + size] for i in range(0, len(array), size)]
文档规范
使用 Google 风格的 docstring
包含参数说明、返回值说明和示例
重要函数需要包含异常说明
复杂算法需要说明时间复杂度
测试规范
测试结构
每个模块对应一个测试文件:
test_<module_name>.py使用 pytest 框架
测试函数命名:
test_<function_name>_<scenario>使用参数化测试处理多种输入情况
示例:
import pytest
from pyutils.array import chunk
class TestChunk:
"""测试 chunk 函数。"""
def test_chunk_normal_case(self):
"""测试正常情况。"""
result = chunk([1, 2, 3, 4, 5], 2)
assert result == [[1, 2], [3, 4], [5]]
def test_chunk_empty_array(self):
"""测试空数组。"""
result = chunk([], 2)
assert result == []
@pytest.mark.parametrize("array,size,expected", [
([1, 2, 3, 4], 2, [[1, 2], [3, 4]]),
([1, 2, 3, 4, 5], 3, [[1, 2, 3], [4, 5]]),
([1], 1, [[1]]),
])
def test_chunk_parametrized(self, array, size, expected):
"""参数化测试。"""
assert chunk(array, size) == expected
def test_chunk_invalid_size(self):
"""测试无效的 size 参数。"""
with pytest.raises(ValueError, match="Size must be positive"):
chunk([1, 2, 3], 0)
覆盖率要求
新代码的测试覆盖率应达到 90% 以上
关键功能必须有完整的测试覆盖
边界条件和异常情况必须测试
性能测试
对于性能敏感的功能,需要添加基准测试:
def test_chunk_performance(benchmark):
"""测试 chunk 函数性能。"""
large_array = list(range(10000))
result = benchmark(chunk, large_array, 100)
assert len(result) == 100
文档贡献
文档类型
API 文档:自动从 docstring 生成
用户指南:手写的教程和示例
开发文档:贡献指南、架构说明等
构建文档
# 构建 HTML 文档
make docs
# 或者直接使用 Sphinx
cd docs
uv run sphinx-build -b html . _build/html
发布流程
版本管理
使用语义化版本号:
MAJOR.MINOR.PATCH在
pyproject.toml中更新版本号创建 git tag:
git tag v1.2.3
自动发布
项目配置了 GitHub Actions 自动发布:
推送 tag 到 GitHub
GitHub Actions 自动构建和测试
自动发布到 PyPI
手动发布
# 构建发布包
make build
# 发布到 PyPI
make release
问题报告
报告 Bug
请在 GitHub Issues 中报告 bug,包含以下信息:
Python 版本
pyutils 版本
操作系统
重现步骤
期望行为
实际行为
错误信息(如有)
功能请求
提出新功能建议时,请说明:
功能描述
使用场景
预期 API 设计
是否愿意实现
获取帮助
如果您在贡献过程中遇到问题,可以:
查看现有的 Issues 和 Pull Requests
在 GitHub Discussions 中提问
发送邮件给维护者
感谢您的贡献!🎉