You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Midje:如何为单个实际值应用多个箭头断言函数

解决Midje测试中多断言复用同一目标值的问题

你遇到的问题其实是Midje的语法解析规则导致的:在单个fact里直接连续写多个箭头断言时,只有第一个=>会绑定前面的目标值,后面的=not=>因为没有关联到目标,相当于没有执行实际的断言逻辑,所以不管你怎么改后面的条件,测试都会通过。

针对这个场景,Clojure(Midje)的惯用解决方式有两种,按推荐程度排序:

1. 用facts包裹多个独立断言(简洁直观)

如果目标值比较简单,直接在facts(注意是复数)下写多个断言,每个断言都明确指向目标值。这种方式可读性最高,也是Midje推荐的写法:

(deftest test-test
  (facts "some-fact"
    {:a 1 :b 2} => (contains {:a odd?})
    {:a 1 :b 2} =not=> (contains {:a even?})))

2. 用let封装目标值(避免重复代码)

如果目标值是复杂计算的结果(比如函数调用、大型数据结构),不想重复写,可以在facts内部用let定义一次,然后在多个断言里复用:

(deftest test-test
  (facts "some-fact"
    (let [test-data {:a 1 :b 2}]
      test-data => (contains {:a odd?})
      test-data =not=> (contains {:a even?}))))

为什么不推荐用def?

新手容易想到用全局def来定义目标值,但测试里尽量避免全局变量——全局状态会让测试变得脆弱,比如不同测试用例之间可能互相干扰,而且不符合Clojure推崇的纯函数、无副作用的测试原则。

验证效果

用上面的写法修改后,你把=not=>里的even?改成odd?,测试就会失败,完全符合预期逻辑。

内容的提问来源于stack exchange,提问作者Michal M

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.27 15:54:06