Foundry测试入门指南:从 forge test 到 fuzz 测试的完整起步路径
Foundry 是近年来快速崛起的 Solidity 工具链,其中 forge test 把链上测试做成了纯 Solidity 编写,速度极快。本文围绕 Foundry测试入门指南,把环境搭建、第一份测试、fuzz 测试、分叉测试串成一条完整起步路径。系统教程可以同时参考 Foundry测试完整教程。
一、Foundry 安装与目录结构
首先用 foundryup 安装:
- 执行
curl -L https://foundry.paradigm.xyz | bash - 再跑
foundryup安装 forge、cast、anvil、chisel 四件套 - 新建项目
forge init MyProject
目录结构清晰:src/ 放合约、test/ 放测试、script/ 放部署脚本、foundry.toml 是配置文件。这一结构与 Foundry测试新手入门 介绍的标准布局完全一致。
二、第一份测试合约
打开 test/Counter.t.sol,写一份最简单的测试:
- 继承自
forge-std/Test.sol提供的Test基类 - 在
setUp()中部署被测合约 - 用
function test_Increment()命名约定标记测试函数 - 用
assertEq等断言库做校验
运行 forge test -vv,看到绿色的 PASS 就说明环境正常。-vv 等级会打印 console.log 输出,调试非常方便。
三、断言与作弊码 cheatcodes
Foundry 提供大量「作弊码」帮助测试覆盖更多场景:
vm.prank(address):让下一笔调用以指定地址发出vm.warp(timestamp):跳到指定时间vm.deal(addr, amount):给地址发送 ETHvm.expectRevert(...):断言下一笔调用会回退vm.expectEmit(...):断言事件触发
这些 cheatcodes 是 Foundry 与 Hardhat 体验差异最大的地方,初学者必须熟练掌握。配合 Foundry测试中文文档 阅读,能更快建立直觉。
四、fuzz 测试入门
Foundry 自带 fuzz 能力,把测试函数参数声明为类型即可:
function test_Deposit(uint256 amount)会自动生成 256 组随机输入- 使用
vm.assume(amount > 0)过滤无效输入 bound(amount, 1, 1e18)把输入约束到合理范围- 失败用例会被缓存,下次运行优先重放
fuzz 测试能在几秒内覆盖手写难以企及的边界条件,是 Foundry 最具吸引力的能力之一,这也是 Foundry测试最佳实践 重点强调的内容。
五、分叉测试 fork testing
分叉测试让你能在本地以真实链状态运行测试:
- 在
foundry.toml配置eth_rpc_url - 在测试中
vm.createSelectFork(rpc_url, block)拉取特定区块 - 直接调用主网或币安智能链上的真实合约
这种能力对于复现线上事故、验证集成合约行为极其有用。币安智能链上的分叉测试需要在 foundry.toml 中加入 bsc 节点 URL。
六、覆盖率与 Gas 报告
forge coverage输出行覆盖率forge test --gas-report输出每个函数的 Gas 消耗- 配合 CI 中的阈值校验,可以阻止覆盖率下降
这些指标是工程化测试的重要抓手,能让团队对测试质量有量化感知。
七、与 Hardhat 互操作
Foundry 与 Hardhat 可以共存:
- 用 Hardhat 跑 TypeScript 部署脚本
- 用 Foundry 跑高速 Solidity 测试
- 共享同一份 ABI 与 deployments 目录
这种组合在大型项目中越来越普遍。详细对比可看 Foundry测试入门指南(即本系列其他文章)与 Hardhat 部署系列。
八、入门后的进阶方向
掌握了入门后,下一步可以学习:
- 不变量测试 invariant testing
- 模糊覆盖率引导
- 与 Echidna 等更高级 fuzz 工具的对比
- 自定义 cheatcodes
入门只是开始,Foundry 的真正威力在于把测试做成可以指导设计的工具,这才是 Solidity 工程化的最大价值。