差分模糊测试器Skill differential-fuzzer

差分模糊测试器是一个用于数据库测试的工具,通过比较Turso与SQLite对随机生成的SQL语句的执行结果,来检测正确性错误。关键词包括:Turso、SQLite、模糊测试、数据库测试、错误检测、Differential Fuzzer、测试自动化、软件质量。

测试 0 次安装 0 次浏览 更新于 3/25/2026

名称: 差分模糊测试器 描述: 关于差分模糊测试器工具的信息,如何运行并使用它来捕获 Turso 中的错误。运行此工具时始终加载此技能。

差分模糊测试器

始终加载 调试技能以供参考

差分模糊测试器比较 Turso 与 SQLite 对生成的 SQL 语句的结果,以发现正确性错误。

位置

testing/differential-oracle/fuzzer/

运行模糊测试器

单次运行

# 基本运行(100条语句,随机种子)
cargo run --bin differential_fuzzer

# 使用特定种子以确保可重复性
cargo run --bin differential_fuzzer -- --seed 12345

# 更多语句,带详细输出
cargo run --bin differential_fuzzer -- -n 1000 --verbose

# 运行后保留数据库文件(用于调试)
cargo run --bin differential_fuzzer -- --seed 12345 --keep-files

# 所有选项
cargo run --bin differential_fuzzer -- \
  --seed <种子>           # 确定性种子
  -n <数量>                # 语句数量(默认: 100)
  -t <数量>                # 表数量(默认: 2)
  -c <数量>                # 每表列数(默认: 5)
  --verbose               # 打印每条 SQL 语句
  --keep-files            # 将 .db 文件持久化到磁盘

连续模糊测试(循环模式)

# 使用随机种子无限运行
cargo run --bin differential_fuzzer -- loop

# 运行50次迭代
cargo run --bin differential_fuzzer -- loop 50

Docker 运行器(CI/生产)

# 从仓库根目录构建和运行
docker build -f testing/differential-oracle/fuzzer/docker-runner/Dockerfile -t fuzzer .
docker run -e GITHUB_TOKEN=xxx -e SLACK_WEBHOOK_URL=xxx fuzzer

Docker 运行器的环境变量:

  • TIME_LIMIT_MINUTES - 总运行时间(默认: 1440 = 24小时)
  • PER_RUN_TIMEOUT_SECONDS - 每次运行超时时间(默认: 1200 = 20分钟)
  • NUM_STATEMENTS - 每次运行语句数(默认: 1000)
  • LOG_TO_STDOUT - 打印模糊测试器输出(默认: false)
  • GITHUB_TOKEN - 用于自动提交问题
  • SLACK_WEBHOOK_URL - 用于通知

输出文件

所有输出到 simulator-output/ 目录:

文件 描述
test.sql 所有执行的 SQL 语句。失败语句前缀为 -- FAILED:,错误前缀为 -- ERROR:
schema.json 运行结束时(或失败时)的数据库模式
test.db Turso 数据库文件(仅在使用 --keep-files 时)
test-sqlite.db SQLite 数据库文件(仅在使用 --keep-files 时)

重现错误

始终遵循以下步骤

  1. 在错误输出中找到种子

    INFO: Starting differential_fuzzer with config: SimConfig { seed: 12345, ... }
    
  2. 使用该种子重新运行

    cargo run --bin differential_fuzzer -- --seed 12345 --verbose --keep-files
    
  3. 检查输出文件

    • simulator-output/test.sql - 查找失败语句(寻找 -- FAILED:
    • simulator-output/schema.json - 检查失败时的表结构
  4. 创建最小重现器

  5. 手动比较行为: 如果需要,尝试比较行为并最终生成报告。 始终先用编辑工具写入临时文件以测试 SQL,然后传递给二进制文件。

    # 对 SQLite 运行失败的 SQL
    sqlite3 :memory: < simulator-output/test.sql
    
    # 对 tursodb CLI 运行
    tursodb :memory: < simulator-output/test.sql
    

理解失败

Oracle 失败类型

  1. 行集不匹配 - Turso 返回与 SQLite 不同的行
  2. Turso 错误但 SQLite 成功 - Turso 拒绝了有效的 SQL
  3. SQLite 错误但 Turso 成功 - Turso 接受了无效的 SQL
  4. 模式不匹配 - DDL 后表/列不同

警告(非致命)

  • 无序 LIMIT 不匹配 - 没有 ORDER BY 的 LIMIT 可能返回不同的有效行

关键源文件

文件 目的
main.rs CLI 解析,入口点
runner.rs 主模拟循环,在两种数据库上执行语句
oracle.rs 比较 Turso 与 SQLite 结果
schema.rs 从两个数据库内省模式
memory/ 用于确定性模拟的内存 I/O

跟踪

设置 RUST_LOG 以获取更详细的输出:

RUST_LOG=debug cargo run --bin differential_fuzzer -- --seed 12345