Bento 构建选项¶
构建选项是指将 BentoML 项目构建成 Bento 的一组运行时规范。您可以在 pyproject.toml
文件中的 [tool.bentoml.build]
部分或 YAML 文件(通常命名为 bentofile.yaml
)中定义它们。
重要提示
自 v1.3.20 版本起,BentoML 引入了用于定义运行时规范的新 Python SDK。这提供了使用 pyproject.toml
或 bentofile.yaml
的程序化替代方案。虽然 BentoML 保持与这些配置文件的兼容性,但我们建议使用新的 Python SDK 来定义您的运行时环境。
可用字段¶
service
¶
service
是一个必需字段,指向 Service 对象的位置。它通常定义为 service: "service:class-name"
。
service
:Python 模块,即service.py
文件。class-name
:在service.py
中创建的基于类的 Service 的名称,使用@bentoml.service
装饰器修饰。如果service.py
中有多个 Services,您可以在配置中指定接收用户请求的主 Service。其他 Services 将与此主 Service 一起启动。
[tool.bentoml.build]
service = "service:MyService"
service: "service:MyService"
description
¶
description
允许您为 Bento 添加相关文档注释,文档可以是纯文本或 Markdown 格式。您可以内联提供描述或引用外部文件。
内联定义描述
[tool.bentoml.build]
service = "service:svc"
description = "This is an inline description for the Service. BentoML is awesome!"
使用文件定义描述
[tool.bentoml.build]
service = "service:svc"
description = "file: ./README.md"
内联定义描述
service: "service:svc"
description: |
## Description For My Bento 🍱
Use **any markdown syntax** here!
> BentoML is awesome!
使用文件定义描述
service: "service:svc"
description: "file: ./README.md"
对于源自外部文件的描述,您可以使用绝对路径或相对路径。确保在运行 bentoml build
命令时,文件存在于指定的路径。对于相对路径,参考点是 build_ctx
,默认情况下是执行 bentoml build
的目录。
labels
¶
labels
是与对象关联的键值对。在 BentoML 中,Bentos 和模型都可以附加标签。这些标签可以用于各种目的,例如在 BentoCloud 中识别或分类 Bentos 和模型。您可以随时添加或修改标签。
[tool.bentoml.build.labels]
owner = "bentoml-team"
stage = "not-ready"
labels:
owner: bentoml-team
stage: not-ready
args
¶
定义了Service 的模板参数后,您可以使用 args
参数动态设置相应的值。
例如,您可能有如下模板
from pydantic import BaseModel
import bentoml
class BentoArgs(BaseModel):
model_name: str
gpu: int = 8
gpu_type: str = "nvidia-h200-141gb"
args = bentoml.use_arguments(BentoArgs)
@bentoml.service(
resources={
"gpu": args.gpu,
"gpu_type": args.gpu_type
}
)
class LLM:
model = bentoml.models.HuggingFaceModel(args.model_name)
然后您可以在构建配置中为这些参数提供值
[tool.bentoml.build.args]
model_name = deepseek-ai/DeepSeek-V3
gpu = 4
args:
model_name: deepseek-ai/DeepSeek-V3
gpu: 4
include
¶
您可以使用 include
字段在构建 Bento 时包含特定文件。它支持通配符和目录模式匹配。例如,将其设置为 *.py
表示现有 build_ctx
下的所有 Python 文件都将被打包到 Bento 中。
[tool.bentoml.build]
include = ["data/", "**/*.py", "config/*.json", "path/to/a/file.csv"]
include:
- "data/"
- "**/*.py"
- "config/*.json"
- "path/to/a/file.csv"
如果未指定此字段,BentoML 默认包含 build_ctx
下的所有文件,但 exclude
字段中明确设置的文件除外。
注意
两 个 include
和 exclude
字段都支持gitignore 风格的模式匹配。
exclude
¶
您使用 exclude
字段在构建 Bento 时排除特定文件。当工作目录中有许多文件时,这非常有用,因为您只需要指定要忽略的文件。
设置此字段时,您需要指定相对于 build_ctx
目录的文件路径规范(类似于 .gitignore
)。
[tool.bentoml.build]
include = ["data/", "**/*.py"]
exclude = ["tests/", "secrets.key"]
include:
- "data/"
- "**/*.py"
exclude:
- "tests/"
- "secrets.key"
或者,在 build_ctx
目录中创建 .bentoignore
文件,如下所示
__pycache__/
*.py[cod]
*$py.class
.ipynb_checkpoints/
training_data/
注意
exclude
始终在 include
之后应用。
models
¶
您可以使用字符串模型标签或字典来指定用于构建 Bento 的模型。如果您在配置中未定义模型,则使用 Service 中指定的模型来构建 Bento。
[tool.bentoml.build]
models = [
"summarization-model:latest",
{ tag = "summarization-model:version1", filter = "label:staging", alias = "summarization-model_v1" }
]
models:
- "summarization-model:latest" # A string model tag
- tag: "summarization-model:version1" # A dictionary
filter: "label:staging"
alias: "summarization-model_v1"
tag
:模型的名称和版本,用冒号分隔。filter
:此字段使用 BentoCloud 中相同的过滤语法。您可以使用过滤器列出特定模型,例如具有相同标签的模型。您可以为一个模型添加多个逗号分隔的过滤器。alias
:模型的别名。如果指定了此项,您可以在代码中直接使用,例如bentoml.models.BentoModel(alias)
。
Python 包¶
您可以使用 python.packages
字段指定给定 Bento 所需的 Python 包。BentoML 允许您指定所需版本,并从自定义 PyPI 源或从 GitHub 仓库安装包。如果某个包没有指定版本,BentoML 会在构建 Bento 时锁定当前平台和 Python 的所有 Python 包版本。
使用 pyproject.toml
文件时,您可以通过 project.dependencies
定义所需的 Python 包
[project]
dependencies = [
"numpy",
"matplotlib==3.5.1",
"package>=0.2,<0.3",
"torchvision==0.9.2",
"git+https://github.com/username/mylib.git@main",
]
这等同于使用 python.packages
[tool.bentoml.build.python]
packages = [
"numpy",
"matplotlib==3.5.1",
"package>=0.2,<0.3",
"torchvision==0.9.2",
"git+https://github.com/username/mylib.git@main"
]
如果同时指定 project.dependencies
和 tool.bentoml.build.python.packages
,则会将依赖项合并。
python:
packages:
- "numpy"
- "matplotlib==3.5.1"
- "package>=0.2,<0.3"
- "torchvision==0.9.2"
- "git+https://github.com/username/mylib.git@main"
注意
您无需在此字段中将 bentoml
指定为依赖项,因为当前版本的 BentoML 将默认添加到列表中。但是,您可以通过指定不同的 BentoML 版本来覆盖此设置。
如果您已经有一个定义项目所需 Python 包的 requirements.txt 文件,您也可以直接提供 requirements.txt
文件的路径
[tool.bentoml.build.python]
requirements_txt = "./project-a/ml-requirements.txt"
python:
requirements_txt: "./project-a/ml-requirements.txt"
GitHub 仓库¶
要包含来自 GitHub 仓库的包,请使用pip requirements 文件格式。您可以指定仓库 URL、要安装的分支、标签或提交,以及如果 Python 包不在仓库根目录下的子目录。
[tool.bentoml.build.python]
packages = [
"git+https://github.com/username/repository.git@branch_name",
"git+https://github.com/username/repository.git@v1.0.0",
"git+https://github.com/username/repository.git@abcdef1234567890abcdef1234567890abcdef12",
"git+https://github.com/username/repository.git@branch_name#subdirectory=package_dir",
]
python:
packages:
- "git+https://github.com/username/repository.git@branch_name"
- "git+https://github.com/username/repository.git@v1.0.0"
- "git+https://github.com/username/repository.git@abcdef1234567890abcdef1234567890abcdef12"
- "git+https://github.com/username/repository.git@branch_name#subdirectory=package_dir"
您可以使用 pack_git_packages
选项(默认为 true
)来控制是否在构建过程中克隆和打包这些 GitHub 包。这对于通过标准 PyPI 源可能无法获得的依赖项,或直接从 Git 仓库确保依赖项的特定版本(例如,标签和提交)的一致性非常有用。
[tool.bentoml.build.python]
pack_git_packages = true
packages = ["git+https://github.com/username/repository.git@abcdef1234567890abcdef1234567890abcdef12"]
python:
pack_git_packages: true # Enable packaging of Git-based packages
packages:
- "git+https://github.com/username/repository.git@abcdef1234567890abcdef1234567890abcdef12"
请注意,lock_packages
控制是否在构建 Bento 时锁定所有依赖项的版本,而不仅仅是来自 Git 的依赖项。禁用 pack_git_packages
也会禁用包锁定 (lock_packages
),除非明确设置。
注意
BentoML 总是尝试针对 Linux x86_64 平台锁定包版本以匹配部署目标。如果 Bento 包含带有环境标记的依赖项或传递依赖项,它们将针对 Linux x86_64 平台解析。
例如,如果 Bento 需要 torch
,nvidia-*
包也将被包含到最终的锁定结果中,尽管它们仅适用于 Linux x86_64 平台。
如果您想为不同平台构建 Bento,可以在 bentoml build
命令中传递 --platform
选项,并指定目标平台的名称。例如
$ bentoml build --platform macos
使用私有 GitHub 仓库
通过 SSH 从仓库包含 Python 包。请确保运行 BentoML 的环境已配置适当的 SSH 密钥,并且这些密钥已添加到 GitHub。
[tool.bentoml.build.python] packages = [ "git+ssh://git@github.com/username/repository.git@branch_name" # The SSH URL for the repository ]
python: packages: - "git+ssh://git@github.com/username/repository.git@branch_name" # The SSH URL for the repository
确保启用了
pack_git_packages
,以便您的私有包可用于构建。设置环境变量
BENTOML_ENABLE_FEATURES=no_image
。
Pip 安装选项¶
您可以在 python
字段中提供额外的 pip install
参数。如果提供,这些参数将应用于 python.packages
中定义的所有包以及 requirements_txt
文件。
[tool.bentoml.build.python]
requirements_txt = "./requirements.txt"
index_url = "https://my.mirror.com/simple"
no_index = false
trusted_host = ["pypi.python.org", "my.mirror.com"]
find_links = ["https://download.pytorch.org/whl/cu80/stable.html"]
extra_index_url = [
"https://<other api token>:@my.mirror.com/pypi/simple",
"https://pypi.python.org/simple"
]
pip_args = "--pre -U --force-reinstall"
python:
requirements_txt: "./requirements.txt"
index_url: "https://my.mirror.com/simple"
no_index: false
trusted_host:
- "pypi.python.org"
- "my.mirror.com"
find_links:
- "https://download.pytorch.org/whl/cu80/stable.html"
extra_index_url:
- "https://<other api token>:@my.mirror.com/pypi/simple"
- "https://pypi.python.org/simple"
pip_args: "--pre -U --force-reinstall"
注意
默认情况下,BentoML 会缓存所有本地镜像构建中的 pip artifacts 以加快构建过程.
如果您想强制重新下载而不是使用缓存,您可以在 bentofile.yaml
文件中指定 pip_args: "--no-cache-dir"
选项,或在 bentoml containerize
命令中使用 --no-cache
选项。例如
$ bentoml containerize my_bento:latest --no-cache
PyPI 包锁定¶
默认情况下,BentoML 会自动锁定所有包版本及其依赖图中的所有包,并生成一个包含所有包及其确切版本的 requirements.txt
文件。此过程内部使用 uv pip compile。
如果您已经为每个包指定了版本或想跳过此过程,您可以通过将 lock_packages
字段设置为 false
来选择性地禁用此行为
[tool.bentoml.build.python]
requirements_txt = "./requirements.txt"
lock_packages = false
python:
requirements_txt: "./requirements.txt"
lock_packages: false
Python 选项表¶
下表提供了 python
字段的完整可用配置列表。
字段 |
描述 |
---|---|
requirements_txt |
自定义 |
packages |
要包含在此 Bento 中的包 |
lock_packages |
是否锁定包 |
index_url |
|
no_index |
是否包含 |
trusted_host |
使用 |
find_links |
使用 |
extra_index_url |
使用 |
pip_args |
安装包时要添加的任何额外 pip 参数 |
wheels |
要包含在 Bento 中的 wheel 文件的路径列表 |
envs
¶
环境变量对于以安全灵活的方式管理配置和密钥非常重要。它们允许您配置 BentoML Services,而无需硬编码敏感信息,例如 API 密钥、数据库凭据或在不同环境之间可能更改的可配置参数。
您可以在 bentofile.yaml
文件中的 envs
键下设置环境变量。每个环境变量都使用 name
和 value
键定义。例如
[tool.bentoml.build]
envs = [
{ name = "VAR_NAME", value = "value" },
{ name = "API_KEY", value = "your_api_key_here" }
]
envs:
- name: "VAR_NAME"
value: "value"
- name: "API_KEY"
value: "your_api_key_here"
指定的环境变量将注入到 Bento 容器中。
注意
如果您将 BentoML Service 部署到 BentoCloud,您可以通过配置中的 envs
或在运行 bentoml deploy
时使用 --env
标志来设置环境变量。有关详细信息,请参阅环境变量。
conda
¶
可以在 conda
字段下指定 Conda 依赖项。例如
[tool.bentoml.build.conda]
channels = ["default"]
dependencies = ["h2o"]
pip = ["scikit-learn==1.2.0"]
conda:
channels:
- default
dependencies:
- h2o
pip:
- "scikit-learn==1.2.0"
channels
:要使用的自定义 conda 频道。如果未指定,BentoML 将默认使用社区维护的conda-forge
频道。dependencies
:要包含在环境中的自定义 conda 依赖项。pip
:要包含的特定pip
conda 依赖项。
或者,您可以将现有 conda 环境中的所有依赖项导出到 environment.yml
文件中,并在您的 pyproject.toml
或 bentofile.yaml
文件中提供此文件。如果指定了此文件,它将覆盖任何其他指定的选项。
导出 conda 环境
conda env export > environment.yml
将其添加到配置中
[tool.bentoml.build.conda]
environment_yml = "./environment.yml"
conda:
environment_yml: "./environment.yml"
注意
与 Python 包不同,BentoML 不支持自动锁定 conda 包版本。我们建议您在配置文件中指定版本。
另请参阅
提供 conda
选项时,BentoML 将选择一个 Docker 基础镜像,该镜像在生成的 Dockerfile 中预装了 Miniconda。请注意,只有 debian
和 alpine
发行版支持 conda
。在下面的 docker
部分了解更多信息。
docker
¶
BentoML 可以轻松将 Bento 部署到 Docker 容器。它提供了一组选项,用于自定义从 Bento 生成的 Docker 镜像。
以下 docker
字段包含一些基本的 Docker 配置
[tool.bentoml.build.docker]
distro = "debian"
python_version = "3.11"
system_packages = ["libblas-dev", "liblapack-dev", "gfortran"]
docker:
distro: debian
python_version: "3.11"
system_packages:
- libblas-dev
- liblapack-dev
- gfortran
BentoML 使用BuildKit,这是一个缓存高效的构建工具包,用于将 Bentos 容器化。BuildKit 随附于Docker 18.09。这意味着如果您通过 Docker Desktop 使用 Docker,BuildKit 将默认可用。如果您使用的是独立版本的 Docker,可以按照此处的说明安装 BuildKit。
以下部分提供了特定 Docker 配置的详细说明。
操作系统发行版¶
BentoML 目前支持以下操作系统发行版
debian
:默认值,类似于 Ubuntualpine
:基于 Alpine Linux 的最小 Docker 镜像ubi8
:Red Hat Universal Base Imageamazonlinux
:Amazon Linux 2
安装脚本¶
对于高级 Docker 自定义,您还可以使用 setup_script
字段在镜像构建过程中注入任何脚本。例如,对于 NLP 项目,您可以通过设置以下值在镜像中预下载 NLTK 数据。
[tool.bentoml.build.python]
packages = ["nltk"]
[tool.bentoml.build.docker]
setup_script = "./setup.sh"
python:
packages:
- "nltk"
docker:
setup_script: "./setup.sh"
在 setup.sh
文件中
#!/bin/bash
set -euxo pipefail
echo "Downloading NLTK data.."
python -m nltk.downloader all
构建一个新的 Bento,然后运行 bentoml containerize MY_BENTO --progress plain
查看 Docker 镜像构建进度。新构建的 Docker 镜像将包含预下载的 NLTK 数据集。
提示
处理 bash 脚本时,我们建议您在开头添加 set -euxo pipefail
。特别是当缺少 set -e 时,脚本将在 bentoml containerize
期间静默失败,而不会引发异常。了解更多关于Bash Set builtin的信息。
也可以提供 Python 脚本来初始化 Docker 镜像。示例如下
[tool.bentoml.build.python]
packages = ["nltk"]
[tool.bentoml.build.docker]
setup_script = "./setup.py"
python:
packages:
- "nltk"
docker:
setup_script: "./setup.py"
在 setup.py
文件中
#!/usr/bin/env python
import nltk
print("Downloading NLTK data..")
nltk.download('treebank')
注意
注意上面示例脚本第一行中的 #!/bin/bash
和 #!/usr/bin/env python
。它们被称为 Shebang,并且是提供给 BentoML 的安装脚本所必需的。
安装脚本总是在指定的 Python 包、conda 依赖项和系统包安装后执行。因此,您可以在安装脚本中导入和利用这些库进行初始化过程。
Docker 选项表¶
下表提供了 docker
字段的完整可用配置列表。
字段 |
描述 |
---|---|
distro |
Docker 镜像上的操作系统发行版。默认为 |
python_version |
Docker 镜像上的 Python 版本。默认为构建环境中的 Python 版本。 |
cuda_version |
已弃用。用于在 Docker 镜像上运行需要 GPU 的模型的 CUDA 版本。当使用 PyTorch 或 TensorFlow 在 GPU 上运行模型时,我们建议您使用 |
system_packages |
将安装在容器中的系统包。 |
setup_script |
将在 Docker 构建过程中执行的 Python 或 Shell 脚本。 |
base_image |
用户提供的 Docker 基础镜像。这将覆盖镜像的所有其他自定义属性。 |
dockerfile_template |
通过提供一个扩展默认 Dockerfile 的 Jinja2 模板来自定义生成的 Dockerfile。 |
自定义构建上下文¶
对于作为大型代码库一部分并与本地其他 Python 模块交互的项目,或者包含多个 Bentos/Services 的项目,可能无法将所有 Service 定义代码和 pyproject.toml
(或 bentofile.yaml
)文件放在项目的根目录中。
BentoML 允许将 Service 定义和 pyproject.toml
(或 bentofile.yaml
)文件放置在项目目录中的任何位置。在这种情况下,在运行 bentoml build
命令时指定 build_ctx
和 bentofile
参数。
build_ctx
:构建上下文表示 Python 项目的工作目录。在构建过程中,它将被添加到 PYTHONPATH 的前面,确保本地 Python 模块的正确导入。默认情况下,它被设置为执行bentoml build
命令的当前目录。bentofile
:默认情况下,它指向构建上下文中的pyproject.toml
(或bentofile.yaml
)文件。
要自定义它们的值,请使用以下方式
bentoml build -f ./src/my_project_a/bento_fraud_detect.yaml ./src/
结构¶
默认情况下,所有创建的 Bentos 都存储在 BentoML Bento Store 中,它本质上是一个本地目录。您可以通过运行以下命令进入特定的 Bento 目录
cd $(bentoml get BENTO_TAG -o path)
在目录内部,您可能会看到不同的文件和子目录,具体取决于 pyproject.toml
(或 bentofile.yaml
)中的配置。一个典型的 Bento 包含以下关键子目录
src
:包含在include
字段中指定的文件。这些文件是相对于用户 Python 代码的 CWD(当前工作目录)的,这使得在用户代码内部导入相对模块和文件路径成为可能。apis
:包含从 Service 的 API 规范自动生成的 API 定义。env
:包含 Bento 初始化相关的环境文件。这些文件是根据pyproject.toml
(或bentofile.yaml
)中指定的构建选项生成的。
警告
我们不建议您直接修改 Bento 中的文件,除非是为了调试目的。