On Mon, Jan 23, 2012 at 3:54 AM, Tassilo Horn <tass...@member.fsf.org> wrote: > Michael Klishin <michael.s.klis...@gmail.com> writes: > > Hi Michael, > >> I am trying to make it possible to use functions as Quartz jobs for my >> Clojure DSL on top of Quartz [1]. For that, I need to implement a >> simple 1-method interface. Both gen-class and defrecord with >> additional methods work great but seem too heavyweight in many cases >> so I am trying to add function support using core/proxy. >> >> The interface I need to implement looks like this: >> >> https://gist.github.com/63989c1a081737813f99 >> >> and my code is basically this: >> >> https://gist.github.com/a83687aed4ea62c915f5 >> >> However, when Quartz tries to execute a new job instance, >> UnsupportedOperationException is raised as if execute was not >> implemented. > > I don't know Quartz, but checking your gist, it seems that you don't > actually do anything with the proxy object except getting its class and > "registering" it with some JobBuilder. > > Although the class generated by proxy can be instantiated using a > zero-args constructor, those new instances don't behave like the object > returned by proxy itself. > > Here's an example without additional deps illustrating the issue. > > --8<---------------cut here---------------start------------->8--- > (defn using-fn [f] > (let [prx (proxy [java.util.concurrent.Delayed] [] > (getDelay [tu] > (f 0))) > clazz (class prx)] > [prx clazz])) ;; return the proxy object and its class > > ;; Calling getDelay on the proxy object works > (.getDelay (first (using-fn inc)) java.util.concurrent.TimeUnit/SECONDS) > ;=> 1 > > ;; Creating a new instance of the class generated by proxy also works > (.newInstance (second (using-fn inc))) > ;=> #<Object$Delayed$333735ab > user.proxy$java.lang.Object$Delayed$333735ab@7746e075> > > ;; However, that new instance doesn't work as expected > (.getDelay (.newInstance (second (using-fn inc))) > java.util.concurrent.TimeUnit/SECONDS) > ; getDelay > ; [Thrown class java.lang.UnsupportedOperationException] > ; Evaluation aborted. > --8<---------------cut here---------------end--------------->8--- > > Generally, proxy is for creating proxy objects, and the generation of a > class is more or less a side effect. > > Do I see it correctly that you need a way (1) to have objects > implementing Job which (2) can be instantiated with a zero-args > constructor and (3) whose execute behavior is customizable by providing > an arbitrary function f on the JobExecutionContext? > > If so, I don't see a too good way. deftype would be usable if the > function f would be specified as a field of the type, but then it has no > zero-args constructor...
(let [f (atom (fn [_] (throw (IllegalStateException.))))] (defn set-job-fn! [x] (reset! f x)) (deftype Job [] Job (execute [ctx] (@f ctx)))) Elaborate as you see fit with e.g. a with-job-fn macro or whatever inside the let. -- You received this message because you are subscribed to the Google Groups "Clojure" group. To post to this group, send email to clojure@googlegroups.com Note that posts from new members are moderated - please be patient with your first post. To unsubscribe from this group, send email to clojure+unsubscr...@googlegroups.com For more options, visit this group at http://groups.google.com/group/clojure?hl=en