在clojure测试中,如何在测试一个函数时模拟出多个方法?

时间:2016-09-02 20:34:42

标签: unit-testing clojure clojure.test

我正在为我的应用程序中的一个相当大的函数编写一个clojure.test单元测试。此函数对db和外部REST服务进行多次调用并进行一些计算。  例如,我要测试的功能是这样的

(defn myfunc [id]
   (let[
        w (some-security-call id)
        x (some-db-call id)
        y  (some-REST-call x)
        z ( some-audit-call y)

       ]
       (-> y :somekey )))

为了测试此方法,我想要删除或重新定义“ some-audit-call ”和“ some-security-call ”。 Clojure的 with-redefs-fn 只能一次重新定义一个方法。

是否有一种标准的方法来模拟在单元测试的函数中使用的多个函数?

1 个答案:

答案 0 :(得分:1)

with-redefs适用于您想要的任意数量的功能。这是我实际生产测试中的一个编辑示例。

(with-redefs [namespace/redacted            (constantly [])
              namespace/redacted                 (fn [& args] (async/go namespace/redacted))
              namespace/redacted        (constantly [2 4])
              namespace/redacted                (fn [& args] (namespace/redacted sample-redacted-ads))
              namespace/redacted                (fn [_ _ redacted & _]
                                                  (async/go (cond-> namespace/redacted
                                                              namespace/redacted (dissoc redacted))))
              namespace/redacted                   (fn [& args] (async/go nil))
              namespace/redacted       fake-redacted
              namespace/redacted       fake-redacted
              namespace/redacted      namespace/redacted
              namespace/redacted       (go (constantly []))
              namespace/redacted               (fn [_] [])
              namespace/redacted      namespace/redacted
              namespace/redacted      namespace/redacted
              namespace/redacted                        (fn [_] {:redacted "redacted"})]
  (is (= "redacted"
         (get-in (<!!
                  )
                 ))
      "We should return the redacted if we don't pass it in")
  ... many more tests here ...

)

如果您需要重新定义要重新定义的其他函数使用的函数,则必须将调用嵌套到with-redef。这有时会让人们认为with-redefs只适用于一个函数。

除非您知道具体原因,否则您可能不想使用with-redefs-fn