clojurewise / wrap.clj

(defn- no-arguments? [method]
  (zero? (count (.getParameterTypes method))))

(defn- getter? [method]
  (let [name (.getName method)]
    (and (no-arguments? method)
         (not (= name "getClass"))
         (.startsWith name "get"))))

(defn- obj-getters [obj]
  (let [cls (if (class? obj) obj (class obj))]
    (filter getter? (.getMethods cls))))

(defn- name->keyword 
  "\".getTimezoneoffset\" -> :timezone-offset"
  [n]
  (keyword (-> n (.replaceAll "([A-Z])" "-$1") (.substring 4) (.toLowerCase))))

; FIXME: This is currently doing one level conversion, it'll be nice if it'll
; recursivly convert collections, hash maps ...
(defn wrap 
  "Convert Java object to a hash map, using zero arguments getters

  user=> (wrap (new Date))
  {:timezone-offset 480, :day 2, :year 110, :time 1267559056404, :seconds 16, :month 2, :minutes 44, :hours 11, :date 2}
  "
  [obj]
  (let [getters (obj-getters obj)
        keywords (map name->keyword (map #(.getName %) getters))
        values (map #(.invoke % obj nil) getters)]
    (zipmap keywords values)))
Tip: Filter by directory path e.g. /media app.js to search for public/media/app.js.
Tip: Use camelCasing e.g. ProjME to search for ProjectModifiedEvent.java.
Tip: Filter by extension type e.g. /repo .js to search for all .js files in the /repo directory.
Tip: Separate your search with spaces e.g. /ssh pom.xml to search for src/ssh/pom.xml.
Tip: Use ↑ and ↓ arrow keys to navigate and return to view the file.
Tip: You can also navigate files with Ctrl+j (next) and Ctrl+k (previous) and view the file with Ctrl+o.
Tip: You can also navigate files with Alt+j (next) and Alt+k (previous) and view the file with Alt+o.