Created
August 25, 2013 03:45
-
-
Save daveray/6331871 to your computer and use it in GitHub Desktop.
rxjava Func* and Action* generators
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
(defmacro ^:private reify-callable | |
"Reify a bunch of Func* interfaces | |
prefix fully qualified interface name. numbers will be appended | |
arities vector of desired arities | |
f the function to execute | |
" | |
[prefix arities f] | |
(let [f-name (gensym "rc")] | |
`(let [~f-name ~f] | |
(reify | |
~@(mapcat (clojure.core/fn [n] | |
(let [ifc-sym (symbol (str prefix n)) | |
arg-syms (map #(symbol (str "v" %)) (range n))] | |
`(~ifc-sym | |
(~'call ~(vec (cons 'this arg-syms)) | |
~(cons f-name arg-syms))))) | |
arities) )))) | |
(defn fn* | |
"Given function f, returns an object that implements rx.util.functions.Func0-9 | |
by delegating to the given function. | |
See: | |
http://netflix.github.io/RxJava/javadoc/rx/util/functions/Func0.html | |
" | |
[f] | |
(reify-callable "rx.util.functions.Func" [0 1 2 3 4 5 6 7 8 9] f)) | |
(defn fnN* | |
"Given function f, returns an object that implements rx.util.functions.FuncN | |
by delegating to the given function. | |
Unfortunately, this can't be included in fn* because of ambiguities between | |
the single arg call() method and the var args call method. | |
See: | |
http://netflix.github.io/RxJava/javadoc/rx/util/functions/FuncN.html | |
" | |
[f] | |
(reify rx.util.functions.FuncN | |
(call [this objects] | |
(apply f objects)))) | |
(defmacro fn | |
"Like clojure.core/fn, but returns the appropriate rx.util.functions.Func* | |
interface. | |
Example: | |
(.map my-observable (rx/fn [a] (* 2 a))) | |
" | |
[& fn-form] | |
; TODO at the moment, returns something that implements Func0-9. Introspect on arg list | |
; to only reify the exact interfaces needed. | |
; have to qualify fn*. Otherwise bad things happen with the low-level fn* in clojure | |
`(com.netflix.indigena.rx.fn/fn* (clojure.core/fn ~@fn-form))) | |
(defn action* | |
"Given function f, returns an object that implements rx.util.functions.Action0-9 | |
by delegating to the given function. | |
See: | |
http://netflix.github.io/RxJava/javadoc/rx/util/functions/Action0.html | |
" | |
[f] | |
(reify-callable "rx.util.functions.Action" [0 1 2 3] f)) | |
(defmacro action | |
"Like clojure.core/fn, but returns the appropriate rx.util.functions.Action* | |
interface. | |
Example: | |
(.map my-observable (rx/action [a] (* 2 a))) | |
" | |
[& fn-form] | |
; TODO at the moment, returns something that implements Action0-3. Introspect on arg list | |
; to only reify the exact interfaces needed. | |
`(action* (clojure.core/fn ~@fn-form))) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment