Zing 论坛

正文

Nvisy Inference:基于 BentoML 的模块化模型推理服务架构

Nvisy Inference 是一个将 OCR 和 NER 模型推理外部化为独立 HTTP/JSON 服务的开源项目,采用 BentoML 和 uv 工作区管理,实现了运行时与 ML 依赖的解耦,支持独立扩缩容和故障隔离。

BentoMLOCRNER模型推理微服务容器化PythonMLOps
发布时间 2026/05/25 18:32最近活动 2026/05/25 18:52预计阅读 7 分钟
Nvisy Inference:基于 BentoML 的模块化模型推理服务架构
1

章节 01

导读 / 主楼:Nvisy Inference:基于 BentoML 的模块化模型推理服务架构

Nvisy Inference 是一个将 OCR 和 NER 模型推理外部化为独立 HTTP/JSON 服务的开源项目,采用 BentoML 和 uv 工作区管理,实现了运行时与 ML 依赖的解耦,支持独立扩缩容和故障隔离。

2

章节 02

原作者与来源

  • 原作者/维护者:nvisycom
  • 来源平台:github
  • 原始标题:inference
  • 原始链接:https://github.com/nvisycom/inference
  • 来源发布时间/更新时间:2026-05-25T10:32:01Z
3

章节 03

补充观点 1

原作者与来源

  • 原作者/维护者:nvisycom
  • 来源平台:github
  • 原始标题:inference
  • 原始链接:https://github.com/nvisycom/inference
  • 来源发布时间/更新时间:2026-05-25T10:32:01Z 原作者与来源\n\n- 原作者/维护者:nvisycom\n- 来源平台:GitHub\n- 原始标题:inference\n- 原始链接https://github.com/nvisycom/inference\n- 发布时间:2026-05-25\n\n项目背景与动机\n\n在现代 AI 应用架构中,模型推理服务与业务运行时的耦合是一个常见痛点。Nvisy Inference 项目正是为了解决这一问题而诞生的——它将原本内嵌在运行时中的机器学习推理能力外部化为独立的 HTTP/JSON 服务,使得主运行时能够以单一二进制文件的形式发布,同时将复杂的 ML 依赖作为可选的 Sidecar 容器运行。\n\n这种架构设计的核心动机来自 Nvisy 运行时团队在实际生产环境中的经验。通过将推理能力外化,他们实现了运行时与 ML 运行时的解耦,这不仅简化了部署流程,还带来了独立扩缩容、故障隔离和灵活替换推理后端等诸多优势。相关的架构决策记录可以在 nvisycom/runtime#194 中找到详细说明。\n\n核心架构设计\n\nNvisy Inference 采用双服务架构,基于 BentoML 框架构建,将两个核心的机器学习能力封装为独立的容器化服务:\n\nnvisy-doctr:OCR 推理服务\n\n该服务基于 docTR(Document Text Recognition)引擎,提供光学字符识别能力。它实现了 OCR 协议契约,对外暴露标准的 HTTP/JSON 接口,接收图像输入并返回识别出的文本内容。服务镜像发布在 ghcr.io/nvisy/inference-doctr。\n\nnvisy-gliner:NER 推理服务\n\n该服务基于 GLiNER(Generalist Lightweight Model for Named Entity Recognition)引擎,提供命名实体识别能力。它实现了 NER 协议契约,能够从非结构化文本中抽取人名、组织、地点等实体信息。服务镜像发布在 ghcr.io/nvisy/inference-gliner。\n\n这两个服务被设计为独立部署的容器,而非单一单体应用。这种设计带来了几个关键优势:独立扩缩容能力(根据 OCR 和 NER 的实际负载分别调整资源)、故障域隔离(一个服务故障不会影响另一个)、以及客户可选性(用户可以根据需求选择部署其中一个或两个服务)。\n\n技术实现细节\n\n协议契约与数据模型\n\nNvisy Inference 的核心设计理念是"数据模型归我,传输协议遵循 BentoML 惯例"。项目中定义了清晰的数据类型契约,使用 Pydantic 模型在 nvisy-core 包中实现:\n\n- OcrRequest/OcrResponse:OCR 服务的请求和响应结构\n- NerRequest/NerResponse:NER 服务的请求和响应结构\n- EntityKind 分类体系:定义了支持的实体类型枚举\n\n这些类型定义构成了"自带推理服务"(Bring Your Own Inference)的契约边界——任何符合这些接口规范的自定义推理服务都可以替代默认实现,而 Rust 运行时无需感知差异。\n\nBentoML 传输协议\n\n服务采用 BentoML 的标准批处理端点格式:请求体为 {'requests': [...]} 的 JSON 对象,响应为 JSON 数组,验证错误遵循 BentoML 的错误格式规范。完整的机器可读契约定义位于 docs/openapi/ 目录下,包含自动生成的 OpenAPI 规范。\n\nuv 工作区管理\n\n项目采用 Astral 公司开发的 uv 作为 Python 包管理工具,构建为单一工作区(workspace)结构:\n\n- 所有子包共享同一个 uv.lock 锁定文件\n- nvisy-core 在本地解析,确保类型定义的一致性\n- 每个服务仅打包自身的依赖子树,保持镜像精简\n- Python 版本锁定在 3.12(因 PaddlePaddle 尚未提供 3.13 的预编译 wheel)\n\n镜像构建流程\n\n与传统的手写 Dockerfile 不同,Nvisy Inference 完全依赖 BentoML 的原生构建能力:\n\n1. 使用 bentoml build 构建 Bento 包\n2. 使用 bentoml containerize 生成容器镜像\n3. 镜像配置定义在各服务的 service.py 中\n4. 各服务的 requirements.txt 通过 scripts/gen_requirements.py 从工作区锁定文件导出\n\n这种构建方式确保了构建过程的可复现性和与 BentoML 生态的深度集成。\n\n开发工作流与工具链\n\n项目通过 Makefile 封装了常见的开发和运维任务,降低了贡献者的上手门槛:\n\nbash\nmake bento 安装 BentoML 和工作区依赖\nmake serve-doctr 本地启动 OCR 服务(或 serve-gliner 启动 NER 服务)\nmake build 构建两个 Bento 包\nmake containerize 构建并打包为本地 Docker 镜像\nmake generate 重新生成 OpenAPI 规范和各服务依赖文件\nmake ci 运行代码检查、漂移检测和测试\n\n\n这种基于 Make 的任务编排方式既保持了简单性,又提供了足够的灵活性,适合小到中型团队的协作需求。\n\n部署模式与配置\n\nNvisy Inference 支持通过 Docker Compose 或 Kubernetes 进行部署。以下是一个典型的 Docker Compose 配置示例:\n\nyaml\nservices:\n inference-doctr:\n image: ghcr.io/nvisy/inference-doctr:1.0\n volumes:\n - ./my-doctr-weights:/models 可选:挂载自定义模型权重\n inference-gliner:\n image: ghcr.io/nvisy/inference-gliner:1.0\n volumes:\n - ./my-gliner-weights:/models 可选:挂载自定义模型权重\n\n\n通过卷挂载机制,用户可以灵活地替换默认模型权重,实现模型版本的快速切换或自定义模型的部署,而无需重新构建镜像。\n\n版本控制与兼容性\n\n项目采用与运行时严格锁定的版本策略:运行时 vX.Y.Z 期望匹配的推理服务版本 vX.Y.Z。这种设计确保了 API 契约的一致性,避免了因版本漂移导致的兼容性 issues。运行时中的 nvisy-inference-client 模块是版本兼容性的最终仲裁者。\n\n开源生态与技术支持\n\nNvisy Inference 采用 Apache 2.0 开源协议,用户可以通过以下渠道获取支持:\n\n- 官方文档:https://docs.nvisy.com\n- GitHub Issues:https://github.com/nvisycom/inference/issues\n- 邮件支持:support@nvisy.com\n\n项目的变更历史和版本发布说明记录在 CHANGELOG.md 文件中。\n\n架构启示与实践价值\n\nNvisy Inference 的架构设计为 AI 应用的工程化部署提供了有价值的参考。其核心启示包括:\n\n1. 关注点分离:将 ML 推理与业务运行时解耦,使两者可以独立演进和部署\n2. 契约驱动设计:通过清晰的接口契约定义,实现了服务实现的可替换性\n3. 云原生友好:容器化的部署形态和 HTTP/JSON 协议天然适合 Kubernetes 等编排平台\n4. 开发体验优先:uv 工作区和 Makefile 封装降低了开发和维护的复杂度\n\n对于正在构建多模态 AI 应用的团队而言,这种将特定 ML 能力(OCR、NER)外部化为独立服务的模式,可以作为平衡开发效率与运维灵活性的有效策略。