下级分类
Go 开发编程语言
Go、Python 等语言实践与实现记录。
专题分组
下级分类
gRPC 使用
这篇笔记以一个只有 Predict 方法的 MyService 为例,串起 gRPC 与 Protocol Buffers 的基本使用路径:先在 .proto 文件中定义 package、service、rpc 方法以及 PredictRequest、PredictResponse 消息,再通过 protoc 生成 Python 侧的数据模型和 RPC 桩代码。内容区分了 my_service_pb2.py 与 my_service_pb2_grpc.py 的职责,前者承载 message、enum 对应的序列化与反序列化类型,后者提供服务端基类、注册函数和客户端 Stub,用来连接业务实现与远程调用。服务端部分展示了继承 MyServiceServicer、实现 Predict、使用线程池创建 grpc.server、注册服务并监听 50051 端口的完整流程,同时解释了生成文件中 DescriptorPool、AddSerializedFile 和 BuildTopDescriptorsAndMessages 动态注册消息类的现象,说明为什么 IDE 可能找不到定义但运行时可正常使用。客户端部分则说明如何通过 insecure_channel 建立连接、创建 MyServiceStub、构造 PredictRequest 并像调用本地方法一样执行远程 Predict,同时提醒未加密通道更适合本地测试,生产环境应考虑 TLS。文章还补充了 Go 客户端通过 protoc 插件生成代码、Dial 连接、创建客户端并带超时上下文调用服务的写法,用来体现一份 IDL 支撑跨语言调用的价值。最后将 gRPC 与 tRPC、HSF、SOFA RPC 等框架放在同一类实现思路下理解:先定义接口协议,再生成存根,服务端实现接口,客户端调用 Stub,底层负责序列化、网络传输与错误处理,适合刚开始学习 RPC、后端服务通信或跨语言接口开发的读者建立整体框架。
Python 开发s3上传文件sdk
这份笔记围绕兼容 S3 API 的 Python 异步文件上传封装展开,适用于 AWS S3、MinIO 等对象存储的接入场景。代码基于 aiobotocore 创建异步 S3 客户端,并用 aiofiles 读取本地文件,封装了普通 put_object 上传和 Multipart Upload 分块上传两条路径,同时支持自定义 endpoint、bucket、region、访问密钥和 Content-Type。普通上传会先读取完整文件再提交,调用方式简单,适合体积较小或对内存压力不敏感的文件;分块上传则以 8 MiB 为块大小,通过 asyncio.Semaphore 将并发上传限制在 4 路,并在完成前收集每个分片的 ETag 与 PartNumber 用于组装。文章还补充了对象键生成和 CDN URL 拼接方法,示例中通过 MinIO 配置构造客户端,分别演示普通上传与流式分块上传后返回访问地址的用法。分块说明部分强调了这种方案在大文件上传中的价值:降低一次性内存占用、提升网络吞吐,并让单个分片失败时具备更明确的重试边界。需要注意的是,普通上传示例虽然使用异步文件读取,但仍会把文件内容读入内存;而分块上传依赖同一个 async 上下文管理文件和 S3 客户端,更适合已经在 asyncio 环境中处理文件上传的后端开发者或对象存储接入场景。
uv包管理器
这篇笔记围绕 uv 作为新一代 Python 包管理器的日常使用展开,重点说明它如何在兼容 pip、requirements.txt 和 pyproject.toml 的同时,通过 Rust 实现、缓存、内置虚拟环境和锁文件机制提升依赖安装速度与环境一致性。正文给出从 curl 安装、配置 PATH、检查 uv 版本,到使用 uv pip install、uv venv、uv pip compile 管理依赖和生成锁文件的基础流程,并特别强调 uv 默认会依据当前终端中的 python 路径选择解释器。文章还记录了在项目中指定 Python 3.12 创建 .venv、激活环境、验证解释器路径,以及从已有 requirements.txt 平滑迁移到 uv init、uv add 和 pyproject.toml 的操作方式。关于环境模型,作者将 Python 项目与 Maven、npm/yarn 类比,解释“共享解释器、隔离依赖”的实践:多个项目可以复用系统 Python,但各自维护独立 .venv 和 site-packages。后半部分对 pip、conda、uv 的适用场景做了区分:uv 更适合 Web、AI 项目和 CI/CD 中的快速构建,conda 更偏向需要 C/Fortran 依赖的科研计算,pip 则适合作为通用基础工具。文章最后用 requests 版本约束示例解释依赖冲突,指出 uv 相比传统 pip 会先构建依赖树、解析约束并通过锁定文件减少版本漂移,适合希望改造 Python 项目依赖管理流程的开发者参考。
sqladmin管理工具
SQLAdmin 被定位为适合 FastAPI 项目的 SQLAlchemy 管理后台工具,提供类似 Django Admin 的模型管理体验,并通过 Tabler/Bootstrap 风格界面自动生成 CRUD、搜索过滤、多数据库管理和可扩展认证能力。文章明确了它的模型边界:必须基于 SQLAlchemy ORM,兼容 SQLAlchemy 1.x 与 2.x,0.15.0 之后全面支持 2.x,但不支持 Tortoise ORM 和 Django ORM。围绕异步 Python 项目的选型,内容对比了 SQLAlchemy 2.0 async、Tortoise ORM 与 asyncpg,指出 SQLAlchemy 2.0 在原生异步 API、声明式映射、类型提示、事务语义和长期维护方向上更适合需要强 ORM、类型检查与扩展性的 FastAPI 场景。示例部分使用 SQLite 搭建完整后台:定义 User、JsonConfig 两个模型,创建 FastAPI 应用,将 Admin 挂载到 /super,并通过 AuthenticationBackend 实现登录、登出和会话认证。配置示例还展示了 ModelView 的常用定制方式,包括中文列名、展示字段控制、插入和更新时拦截 password 字段并进行 MD5 加盐处理,以及 JSON 字段在后台页面中的录入注意点。适合正在为 FastAPI 内部系统、配置管理页面或轻量运维后台选型的开发者,用来快速判断 SQLAdmin 的适用范围,并参考其最小可运行集成方式。
Python协程调度
这篇笔记聚焦 Python 中 asyncio 的协程调度机制,核心是说明单线程如何借助事件循环、协程、Future 和 Task 实现 I/O 密集任务的并发执行。正文从 async def、await、asyncio.run、async for、async with 等基础用法切入,解释协程在遇到 await 时会挂起当前执行、把控制权交还给事件循环,并在异步操作完成后被重新唤醒。示例重点对比了 create_task 后再顺序 await、直接 await 协程,以及使用 asyncio.gather 的差异:create_task 会立即把任务提交给事件循环并发启动,而 await task 只等待当前协程,不会阻塞其他已调度任务;直接 await 多个协程则会形成串行执行。文中还强调 asyncio.sleep 是非阻塞延时,只挂起当前任务,不占用线程资源。后半部分引入 threading 示例,说明线程由操作系统抢占式调度,多个线程共享进程内存但存在数据竞争风险,并在 CPython 中受到 GIL 限制,因此更适合 I/O 场景而非 CPU 密集计算。整体适合正在区分进程、线程、协程调度模型的 Python 后端或异步编程学习者,用来建立“协作式事件循环”和“抢占式系统线程”之间的基本判断框架。
工厂基类的使用
这篇笔记聚焦一个用于 Python 本地函数管理的工具工厂基类,目标是把分散的工具函数集中注册、统一生成 OpenAI tool calling 可用的 tools 描述,并通过名称完成动态调用。示例中的 BaseTool 维护 registry 字典,使用 @BaseTool.register 类方法装饰器在函数定义阶段把函数名和函数对象写入注册表,因此 get_weather、get_time 这类函数不需要额外手工汇总。get_tools() 遍历已注册函数,借助 inspect.signature(fn) 读取参数签名,再组装出包含 type、function、description、parameters、required 等字段的 function schema,便于直接传给 OpenAI。call(name, args) 则根据工具名查找对应函数并用关键字参数执行,若名称未注册会抛出 ValueError,从而把调用入口收敛到一个方法中。文章还用“装饰器等价于 BaseTool.register(get_weather)”的展开方式解释了注册机制,帮助读者理解 registry.items() 中 name 与 fn 的来源。适合正在把 Python 函数接入 OpenAI tools、或想先掌握装饰器、注册表、函数签名提取三者协作方式的 AI 应用开发者参考。
pytest测试代码专用
这份笔记围绕 Python 项目中的 pytest 测试代码编写展开,先从 pytest 的定位、安装方式、pytest.ini 中 testpaths 与 pythonpath 的基础配置讲起,再用 tests 目录下的最小 test_example 示例说明普通函数加 assert 的测试入口。内容整理了常见测试写法,包括任意 Python 表达式断言、pytest.mark.parametrize 参数化、fixture 复用数据准备与清理逻辑、pytest.raises 捕捉异常、用 class 组织测试,以及通过文件、类、方法路径或 -k 关键字精确运行用例。命令行部分覆盖 -v、-x、--maxfail 等常用参数,适合快速建立本地测试执行习惯。后半部分转向 FastAPI 路由测试,同步接口使用 fastapi.testclient.TestClient,异步接口则结合 pytest-asyncio、httpx.AsyncClient 与 ASGITransport,在内存中直接向 ASGI app 发请求,避免启动 uvicorn 和真实端口。文章特别提示 AsyncClient(app=...) 已弃用且可能引发 502、生命周期未触发或路由异常等问题,推荐显式使用 transport=ASGITransport(app=app)。整体更像一份面向后端开发者的 pytest 与 FastAPI 接口测试速查模板,读者可以据此搭建基础测试目录、编写常见用例,并理解 ASGITransport 在异步接口测试中的作用边界。
python-格式化利器
这份笔记围绕 Python 项目的代码格式化与质量检查工具链展开,推荐用 Ruff 作为核心工具统一承担格式化、lint 和 import 排序,减少 Black、flake8、isort 分散配置带来的维护成本。配置流程从使用 uv 安装 ruff、mypy、pytest-cov、bandit、pre-commit 开始,再将 Ruff 与 mypy 配置集中写入 pyproject.toml,其中包含 100 字符行宽、自动 import 排序、自动修复,以及 SQLAlchemy 2.0 mypy 插件、未标注函数检查等类型约束。执行层面给出 ruff format、ruff check、mypy app、bandit -r app、pytest 覆盖率测试等常用命令,并说明应先 format 再 lint,以避免先看到大量可自动修复的格式报错。自动化部分覆盖 pre-commit 钩子配置、全量检查命令,以及 GitHub Actions 中在 push 和 pull_request 时运行 Ruff、mypy、bandit 的 CI 示例。文末还提供面向 FastAPI + SQLAlchemy 项目的 Makefile 模板,把 format、lint、typecheck、security、test、all 等任务封装成统一入口。适合希望快速建立本地开发、提交前检查和 CI 流程一致性的 Python 后端项目参考,尤其适用于已有 app 目录结构并使用类型检查、测试覆盖率和安全扫描的团队。
docker使用uv安装依赖
这篇笔记围绕 FastAPI 官方 Dockerfile 中用 uv 构建 Python 项目依赖的缓存优化展开,重点解释为什么同一个镜像构建流程里会出现两次 uv sync。第一次执行 uv sync --frozen --no-install-project 时,只根据 pyproject.toml 和 uv.lock 安装依赖,不安装项目源码,并借助 BuildKit 的 cache mount 与 bind mount 形成可复用的依赖层;只要锁文件和项目配置不变,修改 .py 文件就不会触发整层依赖重装。第二次 uv sync 则用于把当前项目本身安装进虚拟环境,弥补第一次跳过项目安装的结果,使源码变更只影响项目层而不是依赖层。文章还说明了 FastAPI 官方示例中没有直接 COPY 配置文件的原因:它利用 BuildKit 挂载文件参与构建,后续再通过 COPY . . 放入项目代码,从而减少无关变更对缓存的破坏。末尾给出一个基于 python:3.12-slim、uv 0.5.11、/app/.venv、PYTHONPATH=. 和 uvicorn 启动命令的 Dockerfile 雏形,可作为 FastAPI 项目镜像构建的改造参考。需要注意的是,文中示例更偏向说明依赖层缓存思路,实际项目仍应结合是否多阶段构建、是否需要第二次 uv sync 以及源码复制顺序进行调整。
定时任务(python)
这篇笔记梳理了在 Python 中实现定时任务的常见路径,适用于需要定期采集数据、固定时间发送通知、周期清理缓存或在常驻服务中触发后台逻辑的场景。内容先从 while True 加 time.sleep 的最小实现讲起,说明它无需依赖、控制直接,但会阻塞当前线程,且任务执行耗时会影响间隔,也不适合“每天几点几分”这类精确调度。随后对比 schedule 库的用法,展示 every().seconds、day.at、monday.at 等轻量语法,并解释 run_pending 加 sleep(1) 的轮询机制,强调 sleep 只是检查间隔,不等于改变任务周期。更完整的方案部分聚焦 APScheduler,说明 BlockingScheduler、BackgroundScheduler、AsyncIOScheduler 等调度器差异,以及 interval、cron、date 三类触发方式、内部任务计划表、轮询 tick、线程池执行和任务持久化能力。后半部分给出 asyncio 自定义调度示例,通过固定时间列表计算下一次运行时间,并结合 Redis 有序集合、去重 key 和 setex 过期时间实现订阅推送检查。整体结论是:脚本或一次性小任务可以用 schedule,少量异步任务且需要和 Redis 协调时可自定义 asyncio,但服务常驻、需要异步、cron、并发和更好维护性的场景更适合 APScheduler。