为 Web 构建 ONNX Runtime

构建 ONNX Runtime Web 需要 2 个步骤

  • 获取 ONNX Runtime WebAssembly 工件——可以通过以下方式完成——
    • 为 WebAssembly 构建 ONNX Runtime
    • 下载预构建工件(请参阅以下说明
  • 构建 onnxruntime-web (NPM 包)
    • 此步骤需要 ONNX Runtime WebAssembly 工件

目录

构建 ONNX Runtime Webassembly 工件

前提条件

  • 检出源代码树
    git clone --recursive https://github.com/Microsoft/onnxruntime
    cd onnxruntime
    
  • 安装 cmake-3.26 或更高版本。

  • 安装 Node.js (推荐 16.0+ 或 18.0+)

  • Python (3.9+): https://pythonlang.cn/downloads/
    • 应将 python 添加到 PATH 环境变量中
  • Ninja: https://ninja-build.org/
    pip install ninja
    
  • 准备 emsdk:emsdk 应自动安装在 <ORT_ROOT>/cmake/external/emsdk/emsdk。如果文件夹结构不存在,请在 <ORT_ROOT>/ 中运行以下命令来安装 git 子模块
    git submodule sync --recursive
    git submodule update --init --recursive
    

    (如果您使用的是 Windows,可以跳过此步骤) 在 <ORT_ROOT>/cmake/external/emsdk/ 中,运行以下命令来设置 emsdk

    ./emsdk install latest
    ./emsdk activate latest
    source ./emsdk_env.sh
    

构建说明

ONNX Runtime WebAssembly 可以构建为支持或不支持多线程和单指令多数据 (SIMD)。通过在构建命令中附加以下标志来添加/删除此支持,默认构建选项是不支持。

构建标志 用法
--enable_wasm_threads 构建时支持多线程
--enable_wasm_simd 构建时支持 SIMD

ONNX Runtime Web 可以通过 JavaScript 执行提供程序 (JSEP) 构建为支持 WebGPU 和 WebNN。要构建时支持 JSEP,请使用标志 --use_jsep。构建 WebNN 支持需要额外标志 --use_webnn

ONNX Runtime Web 也可以构建为支持训练 API。要构建时包含训练 API,请使用标志 --enable-training-apis

一个完整的 ONNX Runtime Web 构建的 WebAssembly 工件将包含 3 个“.wasm”文件和 3 个“.mjs”文件。下面的构建命令应为每种配置运行一次。

<ORT_ROOT>/ 中,运行以下命令之一来构建 WebAssembly

# In windows, use 'build' to replace './build.sh'
# It's recommended to use '--skip_tests` in Release & Debug + 'debug info' configruations - please review FAQ for more details

# The following command build debug.
./build.sh --build_wasm --enable_wasm_simd --enable_wasm_threads

# The following command build debug with debug info.
./build.sh --build_wasm --enable_wasm_simd --enable_wasm_threads --skip_tests --enable_wasm_debug_info

# The following command build release.
./build.sh --config Release --build_wasm --skip_tests --disable_wasm_exception_catching --disable_rtti

所需构建工件的完整列表

文件名 使用的构建标志
ort-wasm-simd-threaded.wasm --enable_wasm_simd --enable_wasm_threads
ort-wasm-simd-threaded.mjs --enable_wasm_simd --enable_wasm_threads
ort-wasm-simd-threaded.jsep.wasm --use_jsep --use_webnn --enable_wasm_simd --enable_wasm_threads
ort-wasm-simd-threaded.jsep.mjs --use_jsep --use_webnn --enable_wasm_simd --enable_wasm_threads
ort-training-wasm-simd.wasm --enable_wasm_simd --enable_wasm_threads --enable_training_apis
ort-training-wasm-simd.mjs --enable_wasm_simd --enable_wasm_threads --enable_training_apis

注意

  • 自 v1.19.0 起,ONNX Runtime Web 在未来版本中将停止支持非 SIMD 和非线程构建。
  • WebGPU 和 WebNN 目前作为 ONNX Runtime Web 的实验性功能受到支持。构建说明可能会发生变化。请务必参考 webgpu gistwebnn gist 中的最新文档,以获取 ONNX Runtime Web 的 WebGPU 和 WebNN 详细构建/使用说明。

最小构建支持

ONNX Runtime WebAssembly 可以使用标志 --minimal_build 进行构建。这将生成更小的工件,并减少运行时内存使用。为了使用此 ONNX Runtime 配置,需要 ORT 格式模型(而不是 ONNX 格式)。更多信息请参阅 ORT 格式转换

常见问题

问:在 Release 构建中,单元测试失败。

答:单元测试需要 C++ 异常才能正常工作。然而,出于性能考虑,我们禁用了 emscripten 中的异常捕获。因此,请在 Release 构建中指定 --skip_tests

问:在包含调试信息的 Debug 构建中,单元测试失败。

答:使用调试信息进行构建会生成非常大的工件(单元测试超过 1GB),并且无法在 Node.js 中加载。因此,请在包含调试信息的构建中指定 --skip_tests

问:我有一个用于 Web 场景的 C++ 项目,它使用 ONNX Runtime 运行 ML 模型并生成 WebAssembly 作为输出。ONNX Runtime Web 是否支持静态 WebAssembly 库,以便我的应用程序可以与其链接,并将所有预处理/后处理器一起编译到 WebAssembly 中?

答:使用 --build_wasm,构建脚本会为 Web 场景生成 .wasm.js 文件,并且中间库无法与其他 C/C++ 项目正确链接。当您使用 --build_wasm_static_lib 而不是 --build_wasm 构建 ONNX Runtime Web 时,构建脚本会在输出目录中生成一个名为 libonnxruntime_webassembly.a 的 ONNX Runtime Web 静态库。要运行像 单元测试 这样的简单推理,您需要以下三个头文件和 libonnxruntime_webassembly.a

  • include/onnxruntime/core/session/onnxruntime_c_api.h
  • include/onnxruntime/core/session/onnxruntime_cxx_api.h
  • include/onnxruntime/core/session/onnxruntime_cxx_inline.h

一个重要的注意事项是,ONNX Runtime 依赖于许多第三方库,例如 protobuf、onnx 等。您可能需要将必要的头文件复制到您的项目中。您还需要注意 ONNX Runtime 和您的项目之间库版本冲突或 emsdk 版本冲突的情况。

构建 onnxruntime-web - NPM 包

以下部分是 onnxruntime-web NPM 包的分步安装指南。这是构建过程的最后阶段,请按顺序遵循这些部分。

前提条件

  • 安装 Node.js (推荐 16.0+ 或 18.0+)

  • 用于运行测试的 Chrome 或 Edge 浏览器。

安装 NPM 包

  1. <ORT_ROOT>/js/ 中,运行 npm ci
  2. <ORT_ROOT>/js/common/ 中,运行 npm ci
  3. <ORT_ROOT>/js/web/ 中,运行 npm ci

准备 ONNX Runtime WebAssembly 工件

您可以选择使用预构建工件或自行构建。

  • 通过脚本设置。

    <ORT_ROOT>/js/web/ 中,运行 npm run pull:wasm 从 CI 流水线拉取最新主分支的 WebAssembly 工件。使用 npm run pull:wasm help 以探索更多用法。

    注意:此脚本将覆盖您的 WebAssembly 构建工件。如果您从源代码构建部分工件,常见做法是运行 npm run pull:wasm 来拉取完整预构建工件集,然后将您构建的工件(按照以下说明)复制到目标文件夹,这样您就不需要构建 6 次了。

  • 手动从流水线下载工件。

    您可以从 Windows WebAssembly CI 流水线下载预构建的 WebAssembly 工件。选择一个构建,下载工件“Release_wasm”并解压。请参阅以下说明将文件放入目标文件夹。

  • 构建 WebAssembly 工件。

    1. 构建 ONNX Runtime WebAssembly

      请按照上述说明构建 ONNX Runtime WebAssembly。

    2. 将以下文件从构建输出文件夹复制到 <ORT_ROOT>/js/web/dist/(如果文件夹不存在,请创建)

      • ort-wasm-simd-threaded.wasm (使用标志 --enable_wasm_threads --enable_wasm_simd 构建)
      • ort-wasm-simd-threaded.mjs (使用标志 --enable_wasm_threads --enable_wasm_simd 构建)
      • ort-wasm-simd-threaded.jsep.wasm (使用标志 --use_jsep --use_webnn --enable_wasm_simd --enable_wasm_threads 构建)
      • ort-wasm-simd-threaded.jsep.mjs (使用标志 --use_jsep --use_webnn --enable_wasm_simd --enable_wasm_threads 构建)
      • ort-training-wasm-simd-threaded.wasm (使用标志 --enable_wasm_simd --enable_wasm_threads --enable_training_apis 构建)
      • ort-training-wasm-simd-threaded.mjs (使用标志 --enable_wasm_simd --enable_wasm_threads --enable_training_apis 构建)

完成 onnxruntime 构建

<ORT_ROOT>/js/web 文件夹中运行以下命令进行构建

   npm run build

这将生成最终的 JavaScript 打包文件供使用。它们位于 <ORT_ROOT>/js/web/dist 文件夹下。