与我的previous question相关,但不同。
我尝试使用clj-time.core.DateTimeProtocol
实施deftype
。我使用此而不是defrecord
作为类型签名冲突(请参阅other question)。
我有两个文件。第一个是实现,第二个是测试。如您所见,测试文件尚未执行require
实施文件以外的任何操作。为代码转储道歉,但这是最小的工作版本:
date.clj:
(ns util.date
(:require [clj-time.core :as clj-time])
(:require [clj-time.core :refer [DateTimeProtocol]])
(:gen-class))
(defprotocol IWeirdDate
(as-date [this]))
(deftype WeirdDate [year month day]
IWeirdDate
(as-date [this] (clj-time/date-time year month day)))
(extend-protocol DateTimeProtocol
WeirdDate
(year [this] (clj-time/year (as-date this)))
(month [this] (clj-time/month (as-date this)))
(day [this] (clj-time/day (as-date this)))
(day-of-week [this] (clj-time/day-of-week (as-date this)))
(hour [this] (clj-time/hour (as-date this)))
(minute [this] (clj-time/minute (as-date this)))
(sec [this] (clj-time/sec (as-date this)))
(second [this] (clj-time/second (as-date this)))
(milli [this] (clj-time/milli (as-date this)))
(after? [this that] (clj-time/after? (as-date this) that))
(before? [this that] (clj-time/before? (as-date this) that)))
(defn weird-date [y m d] (WeirdDate. y m d))
(def x (WeirdDate. 1986 5 2))
(def y (clj-time/date-time 2014 5 2))
(prn "Loaded OK source" x y)
date_test.clj
(ns util.date-test
(:require [clojure.test :refer :all]
[util.date :refer [weird-date]])
(:require [clj-time.core :as clj-time]))
(def x (weird-date 1986 5 2))
(def y (clj-time/date-time 2014 5 2))
(prn "Loaded OK in test" x y)
这与lein test
,lein check
,lein compile
等等有关。
奇怪的是源文件似乎工作正常:
"Loaded OK source" #<WeirdDate util.date.WeirdDate@7e793d7a> #<DateTime 2014-05-02T00:00:00.000Z>
Exception in thread "main" java.lang.NoClassDefFoundError: clj_time/core/DateTimeProtocol
问题出在其他地方,例如,在ns
date-test
声明中。我没有在其他任何地方引用DateTimeProtocol
。
如果我注释掉整个extend-protocol
,结果就是:
"Loaded OK source" #<WeirdDate util.date.WeirdDate@3f19c149> #<DateTime 2014-05-02T00:00:00.000Z>
"Loaded OK source" #<WeirdDate util.date.WeirdDate@5c797bc6> #<DateTime 2014-05-02T00:00:00.000Z>
"Loaded OK in test" #<WeirdDate util.date.WeirdDate@19c6a644> #<DateTime 2014-05-02T00:00:00.000Z>
因此,看起来简单地从一个命名空间引用此协议就会阻止另一个命名空间(甚至没有提及它)加载。
什么?