I am using a groovy library that returns a LinkedHashMap containing ArrayLists and nested LinkedHashMaps. I did not expect any issues working with this in clojure since this type implements java.util.Map I figured everything would just work. However the first thing I tried to do was apply clojure.set/keywordize-keys which didn't keywordize the keys as expected. I then tried map? which returned false, I figured I would then try to convert to clojure map using apply hash-map which threw an illegalargumentexception. into {} however did work. I then attempted to use clojure.walk/postwalk to convert LinkedHashMaps to clojure maps which only visited the top node. However using prewalk did work, so I ended up with the following helper function.
(defn- convert-types
[groovy-result]
(walk/prewalk
(fn [x]
(cond (instance? java.util.LinkedHashMap x) (into {} x)
(instance? java.util.ArrayList x) (vec x) ;; probably not required but I wanted to pr-str to print as vectors rather than #ArrayList ...
:else x)) groovy-result))
clojure map? is defined as:
(fn ^:static map? [x] (instance? clojure.lang.IPersistentMap x)))
Is there any reason map? checks explicitly for clojure.lang.IPersistentMap rather than java.util.Map?
also clojure.walk/walk contains:
..
(instance? clojure.lang.IMapEntry form)
..
but (first m) returns java.util.LinkedHashMap$Entry which extends java.util.Map$Entry and java.util.HashMap$Entry.
I'm not sure why into {} works but apply hash-map doesn't, seems to have to do with first and next don't work on java.util.LinkedHashMap$Entry either.
Seems like many of these functions could be improved to work with java.util.Map and java.util.Map$Entry?
Should a JIRA be created for these?