【问题标题】:How to require a namespace programmatically如何以编程方式要求命名空间
【发布时间】:2014-05-10 17:31:43
【问题描述】:

我正在 Clojure 中处理 Liberator 项目。我定义了一系列路由,这些路由返回由其他命名空间中的逻辑计算的 JSON 数据。我希望能够以编程方式更改实现逻辑的命名空间,以便可以执行以下操作:

JAVA_OPTS='-DgameLogicNamespace=foo.logic.mock' lein ring server-headless 8080

我目前正在这样做:

(ns foo.routes
  (:require [compojure.core :refer :all]
            [liberator.core :as lib :refer [defresource request-method-in]]
            [liberator.representation :refer [ring-response]]))

(require
 (vec
  (cons (symbol (System/getProperty "gameLogicNamespace" "foo.logic.real"))
        '[:as logic])))

这可行,但感觉有点笨拙。有没有一种惯用的方式来完成我想要的?

我的主要动机之一实际上是使用模拟数据对路由进行单元测试,所以如果有一个很好的解决方案可以仅在测试中提供模拟逻辑(而不是作为 JVM 系统属性),欢迎提出建议。

【问题讨论】:

    标签: clojure namespaces


    【解决方案1】:

    我的主要动机之一实际上是使用模拟数据对路由进行单元测试,所以如果有一个很好的解决方案可以仅在测试中提供模拟逻辑(而不是作为 JVM 系统属性),欢迎提出建议。

    如果您还没有,请查看ring-mock,了解一些不错的实用程序来生成模拟请求以测试您的 Ring 处理程序。

    如果您有兴趣提供在单元测试期间提供应用程序逻辑实现的函数的模拟版本,请考虑使用with-redefs;它几乎是为此目的而定制的。

    (ns my-app.handlers-test
      (:require [clojure.test]
                [my-app.handlers :as h]
                [my-app.logic :as l]
                [ring.mock.request :as r]))
    
    (deftest test-simple-handler
      (with-redefs [l/my-complicated-logic #(update-in % [:a] inc)]
        (is (= {:a 2}
               (h/my-handler (r/request :post "/foo" {:a 1}))))))
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2017-09-29
      • 2012-05-30
      • 2018-03-24
      • 2011-07-18
      • 1970-01-01
      • 1970-01-01
      • 2013-05-14
      • 1970-01-01
      相关资源
      最近更新 更多