生成覆盖率数据
你可以要求运行器从标记为 #[wasm_bindgen_test]
的函数中生成 .profraw
格式的覆盖率数据。
覆盖率仍处于实验性阶段,需要 Rust Nightly,可能不可靠,并且随时可能发生重大更改。
启用该功能
要启用此功能,你需要启用 cfg(wasm_bindgen_unstable_test_coverage)
。
生成数据
需要存在的 RUSTFLAGS
请确保你正在使用 RUSTFLAGS=-Cinstrument-coverage -Zno-profiler-runtime
。
由于 llvm-cov
的当前限制,我们无法从生成的 .wasm
文件中收集性能分析符号。相反,我们可以使用 Clang 通过 --emit=llvm-ir
从 LLVM IR 中获取它们。Clang 或任何 LLVM 工具的使用必须与 Rust 使用的 LLVM 版本匹配。
测试运行器的参数
以下环境变量可用于控制 执行测试运行器时的覆盖率输出
WASM_BINDGEN_UNSTABLE_TEST_PROFRAW_OUT
控制 profraw 的文件名或其所在目录。例如,如果在一个工作区中运行测试,则可能需要提供完整路径。WASM_BINDGEN_UNSTABLE_TEST_PROFRAW_PREFIX
向 profraw 文件添加自定义前缀。如果你连续自动运行测试,这将非常有用。
目标特性
此功能依赖于 minicov crate,它为 WebAssembly 提供了一个性能分析运行时。反过来,它使用 cc 将运行时编译为 Wasm,而 目前不支持考虑目标特性。使用例如 CFLAGS_wasm32_unknown_unknown="-matomics -mbulk-memory"
来解决这个问题。
示例
这改编自 Rustc 书 中的代码,请参阅该书以获取更多示例以及有关测试覆盖率的一般信息。
# Run the tests:
# `--tests` to not run documentation tests, which is currently not supported.
RUSTFLAGS="-Cinstrument-coverage -Zno-profiler-runtime --emit=llvm-ir --cfg=wasm_bindgen_unstable_test_coverage" \
CARGO_TARGET_WASM32_UNKNOWN_UNKNOWN_RUNNER=wasm-bindgen-test-runner \
cargo +nightly test --tests
# Compile to object files:
# - Extract a list of compiled artifacts from Cargo and filter them with `jq`.
# - Figure out the path to the LLVM IR file corresponding to an artifact.
# - Compile to object file with Clang and store for later usage with `llvm-cov`.
crate_name=name_of_the_tested_crate_in_snake_case
objects=()
IFS=$'\n'
for file in $(
RUSTFLAGS="-Cinstrument-coverage -Zno-profiler-runtime --emit=llvm-ir --cfg=wasm_bindgen_unstable_test_coverage" \
cargo +nightly test --tests --no-run --message-format=json | \
jq -r "select(.reason == \"compiler-artifact\") | (select(.target.kind == [\"test\"]) // select(.target.name == \"$crate_name\")) | .filenames[0]"
)
do
if [[ ${file##*.} == "rlib" ]]; then
base=$(basename $file .rlib)
file=$(dirname $file)/${base#"lib"}.ll
else
file=$(dirname $file)/$(basename $file .wasm).ll
fi
output = $(basename $file .ll).o
clang-19 $file -Wno-override-module -c -o $output
objects+=(-object $output)
done
# Merge all generated raw profiling data.
llvm-profdata-19 merge -sparse *.profraw -o coverage.profdata
# Produce test coverage data in the HTML format and pass the object files we generated earlier.
llvm-cov-19 show -show-instantiations=false -Xdemangler=rustfilt -output-dir coverage -format=html -instr-profile=coverage.profdata ${objects[@]} -sources src