Rust 支持常规的单元测试、集成测试等,甚至还支持文档测试。
单元测试
单元测试需要放到 tests
而且带有 #[cfg(test)]
属性的模块中,测试函数要加上 #[test]
属性。
pub fn add(a: i32, b: i32) -> i32 {
a + b
}
fn main() {
println!("Hello, world!");
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn test_add() {
assert_eq!(add(1, 2), 3);
}
}
当函数中出现 panic
时测试就失败了,如下是常用的断言宏:
assert!(expression)
当表达式的值是false
则panic
,也可以添加失败时的自定义信息。assert_eq!(left, right)
和assert_ne!(left, right)
检验左右两边是否相等、不等。
如果某个函数预期出现 panic
可以通过如下方式配置。
#[test]
#[should_panic(expected = "Your panic info")]
fn test_add() {
assert_eq!(add(1, 2), 3);
}
如果是类似 Result
这种可恢复的错误,那么可以通过如下方式测试。
assert!(some_error().is_err());
assert!(some_error().is_err_and(|e| e.kind() == ErrKind::NotFound));
let e = some_error().unwrap_err();
assert_eq!(e.kind(), ErrKind::NotFound);
然后通过 cargo test
命令执行所有测试用例,或者通过 cargo test test_add
指定某个测试用例,或者通过 cargo test add
匹配所有相关用例。
另外,还可以通过 #[ignore]
标记不执行某个用例,如果要执行则通过 cargo test -- --ignored
执行。
----- 控制并行度
cargo test -- --test-threads=1
----- 显示输出
cargo test -- --show-output
----- 查看所有用例
cargo test -- --list
----- 可以通过 --lib --doc 控制只运行库或者文档测试用例
cargo test --lib --package xxx
上述的 --package
参数指定的是目录下 Cargo.toml
中的 package.name
参数。
Fuzz
关于 Fuzz 测试可以参考 The Fuzzing Book 中的介绍,而 Rust 相关的更多内容可以参考 Rust Fuzz Book 中的介绍。
----- 方式安装升级
cargo install cargo-fuzz
cargo install --force cargo-fuzz
----- 查看帮助信息
cargo fuzz --help
----- 新建工程,一般会生成fuzz目录以及一个简单示例
cargo fuzz init
----- 也可以手动添加新的示例
cargo fuzz add <your-fuzz-name>
此时会生成对应的示例代码,可以根据项目的需要进行修改,包括用例的名称、依赖等。
----- 查看支持的测试列表
cargo fuzz list
----- 开始测试
cargo fuzz run <your-fuzz-name>
如果出现报错,会同时输出包括的数组内容,以及 Reproduce with
以及 Minimize test case with
两条命令,可以手动执行进行验证,可以有效缩短异常的场景。
libfuzzer
这也是默认的,通常会有如下的输出。
#19644289 REDUCE cov: 383 ft: 2112 corp: 639/89Kb lim: 4096 exec/s: 8031 rss: 650Mb L: 1080/3078 MS: 1 EraseBytes-
可以解读为:
#19644289
已经测试过的数据次数。cov
当前已经覆盖的代码块。ft
尝试覆盖信号个数。corp
当前随机序列的入口个数,以及其所占用的内存大小。lim
当前最大为 65535 字节,也就输入的长度。exec/s
迭代速度,每秒多少次。rss
当前内存消耗。L
当前输入实际所占字节。
其它
建议使用 cargo-nextest
查看测试结果,要比原生更加方便使用,执行 cargo nextest run
即可。
文档测试
通常在文档中会维护一些示例代码,为了保证其正确性,可以通过 rustdoc
命令进行测试。
覆盖率
建议使用 tarpaulin
工具,相比 cargo-llvm-cov
来说功能要更丰富,可以通过 cargo install cargo-tarpaulin
安装,然后直接执行 cargo tarpaulin
命令即可。
可以通过 -o html
指定输出 Web 页面。