pykeio/ort · 上手攻略
- 仓库:pykeio/ort
- 链接:https://github.com/pykeio/ort
- 分类:llm-infra / app(ONNX Runtime 的 Rust 绑定 + 备选纯 Rust 后端)
- 作者:spark
- 更新:2026-07-30
提示:仓库 README、API 文档链接均指向
ort 2.0系列,本攻略以当前main分支为准(最新示例分支标签为v2.0.0-rc.13,来自仓库 docs 与 examples 中给出的克隆命令)。若你看到更新 rc tag,请以 crates.io 与 docs.rs 的最新版为准。
1. 是什么
ort 是 Rust 生态里跑 ONNX 模型的主流 crate。核心是 Microsoft ONNX Runtime(跨平台、跨加速器)的高层封装,对外暴露 Session / Value / Tensor / I/O binding 等安全 Rust API;同时支持 [actix-web 之外的] 备选后端 ort-candle / ort-tract / ort-web(WASM)。
项目源自现已停摆的 onnxruntime-rs,现在由 Pyke 维护,并以 onnxruntime v1.28.0 为默认二进制(来自 README badge 字段)。它解决的核心问题是:用 Rust 写产品代码时,不愿意拉 Python,又要拿到 ONNX 的所有 Execution Provider(CUDA / TensorRT / DirectML / CoreML / OpenVINO / NNAPI / QNN …)。
2. 解决什么问题
- 在桌面、服务器、移动端、嵌入式上用同一份 Rust 代码跑同个 ONNX 模型,硬件加速自动切到 CUDA/TensorRT/DirectML/CoreML/...
- 在终端、CLI、服务、桌面 App、WASM 中内嵌模型推理,又不想为了 PyTorch 拉整个 Python 运行时。
- 想做真训练(不只是推理):
ort同时暴露了 minimal training API(train-clm/train-clm-simple两个示例)。
不适用的场景:
- 模型是 PyTorch/JAX 但没导出过 ONNX——可以,但
ort-candle/ort-tract后端在多数 PT 模型上兼容性差,建议先导出 ONNX。 - 需要 GPU 自定义算子 ONNX Runtime 没实现的——
custom-ops例子演示了怎么在 Rust 里注册自定义算子核,但要小心跨设备兼容。
3. 快速安装
# Cargo.toml 中
[dependencies]
ort = "2.0" # 主要方式,会拉默认 ONNX Runtime 预编译二进制
CPU 即可直接跑。如果想用 CUDA:
ort = { version = "2.0", features = ["cuda"] }
其他常见 feature flags(来自仓库 README 与文档):tensorrt、directml、coreml、openvino、nnapi、qnn、rocm、vitis-ai、acl、onednn、tvm、xnnpack、tract、candle、web。每个 feature 对应一个 Execution Provider(EP)。
第一次构建会从 Pyke 自己的 CDN 拉 ONNX Runtime 预编译包(参考 README 中的 parcel.pyke.io 图标与 docs 中的 "Prebuilt binaries"),Windows/Linux/macOS 都有。Windows 上 MSVC 工具链要装好;用 Linux glibc < 2.31 的发行版可能要从源码 build。
4. 核心用法
4.1 加载并跑一个 ONNX 模型(CPU)
简化版(仓库 examples/gpt2/gpt2.rs 的最小骨架):
use ort::session::Session;
use ort::value::Tensor;
fn main() -> ort::Result<()> {
// 1. 初始化(只一次)
ort::init()?;
// 2. 加载模型(默认优化级别、性能设置由 builder 控制)
let mut session = Session::builder()?
.commit_from_file("model.onnx")?;
// 3. 构造输入张量(任意实现了 Into<Tensor<...>> 的 ndarray / Vec)
let input = Tensor::from_array(ndarray::Array2::<f32>::zeros((1, 3)))?;
// 4. 跑推理
let outputs = session.run(ort::inputs!["input_name" => input])?;
// 5. 取出结果
let output: Tensor<f32> = outputs["output_name"].try_extract_tensor()?;
println!("{:?}", output);
Ok(())
}
真实使用要写 gpt2/yolov8/phi-3-vision 等例子里那种 tokenizer + 后处理循环。
4.2 跑 examples
git clone https://github.com/pykeio/ort
cd ort
# 想钉到具体 rc 版本(仓库里建议的命令)
# git clone https://github.com/pykeio/ort --branch v2.0.0-rc.13
# 跑 GPT-2 文本生成(CPU)
cargo example-gpt2
# 跑 YOLOv8 目标检测
cargo example-yolov8
# 想用 CUDA EP,加上 feature flag
cargo example-gpt2 --features cuda
# 想用纯 Rust 的 Tract 后端(不依赖 ONNX Runtime)
cargo example-gpt2 --features backend-tract
# 异步 GPT-2 + axum HTTP API + SSE 流式输出
cargo example-async-gpt2-api
# WASM 浏览器端手部检测(ort-web 后端)
cd examples/web-hands
wasm-pack build --target web
仓库提供 gpt2、async-gpt2-api、yolov8、web-hands、semantic-similarity、modnet/cudarc、phi-3-vision、model-info、train-clm/train-clm-simple、custom-ops。README 上写有少量日志噪声,介意可以:
RUST_LOG=ort=warn cargo example-gpt2
4.3 I/O Binding 与 async
- I/O Binding:在 CPU 内存与 GPU 之间预分配 buffer,避免重复拷贝;详见 docs
Performance/I/O Binding章节。 - async:
Session::run_async(...)支持 tokio 异步(async-gpt2-api例子就是 axum + SSE)。
4.4 在浏览器里跑模型
ort-web 后端:构建产物是 WASM,用 wasm-pack build --target web 编译 web-hands 例子即可在浏览器打开摄像头做手部检测(README 里给了 demo 链接 spaces.pyke.io/testwebhands)。
5. 典型适用场景
- CLI 工具 + 本地模型推理:grep 替代品、图片批处理工具、命令行 LLM 包装。
- 自带模型的桌面 / 移动端应用:Tauri、egui、Slint 等 Rust UI 框架内置 ML。
- 服务端低延迟推理:CUDA/TensorRT EP 上跑 LLM / 文本 embedding,比 Python 进程省内存、启动快。
- WASM 端侧:把 ONNX 模型塞进浏览器或边缘设备。
README 里提到 Huggings Face text-embeddings-inference、Google 的 magika、Style-BERT-VITS2 的 sbv2-api、edge-transformers、oar-ocr、FastEmbed-rs、Murmure(Parakeet ASR)、SilentKeys、Xybrid、Ultralytics YOLO Rust Inference 等都用 ort 作为推理引擎——可作为"生产用过"的旁证。
6. 坑与注意
ort::init()一定要在创建任何Session之前调用一次,否则在多线程/多 session 场景会出诡异错误。- Windows 链接 Microsoft Visual C++ Runtime,缺 MSVC 会 link 阶段报错。
- 不同 EP feature 不能同时开:
--features cuda与--features directml可能会冲突,请按 EP 文档互斥选择。 - 1.x → 2.x 是 breaking change,仓库提供迁移指南
https://ort.pyke.io/migrating/v2,API 重命名为Session::run(...)、ort::inputs!宏等。 - 训练 API(
train-clm)相对基础,复杂模型训练仍建议 PyTorch / burn。 - 模型导出 ONNX 时注意 opset 版本与 dynamic_axes,部分 ONNX Runtime EP 对超新 opset 支持滞后。
7. 与同类对比
- vs
tvm-ffi、tch-rs(libtorch Rust 绑定):tch-rs是直接把 PyTorch C++ 接进来,体量大;ort体积小、跨硬件强、但只能跑 ONNX。 - vs
candle(纯 Rust):candle更"ML 框架自训自推";ort偏向"已经训练好、想跑得快"。 - vs
tract:纯 Rust,无原生 GPU EP,CPU 上更轻便;ort默认后端 ONNX Runtime 在 CUDA/TensorRT/DirectML 等加速器上更猛,但二进制更大。 - vs 上层封装(如 Hugging Face
text-embeddings-inference):hf TEI 是 Go 的"开箱用 HTTP 服务";ort是底层,可被 TEI 等服务用。 - vs ONNX Runtime 官方 Python/C++:纯 Python 服务上线时大多也是包 ONNX Runtime,但 Rust 在部署内存、启动延迟、跨语言互操作上有优势。
8. 一句话结论
想用 Rust 把一个 ONNX 模型丢进桌面/服务器/WASM 加速跑,ort 是当下最省心的选择——ONNX Runtime 几乎所有 Execution Provider 都给你接好,连 WASM 浏览器推理和最小训练都顺手覆盖;如果你还在 PyTorch 写研究,先导出 ONNX 再切 ort 也很值。