redplanetlabs/specter

How to continue recursive process on a transformed object

caumond opened this issue ยท 0 comments

Hi guys,
Really impressed by the high quality of this library. Congrats. ๐Ÿฅ‡

A little bit hard to use at the beginning, but I'm still a little bit new to clojure, and I start with non-trivial cases ๐Ÿ˜œ

I'm parsing a json structure (maps and collections), in which I want to drop some intermediate levels but keep the subtree: so I expect a submap to be move at a higher level.

I achieved the following recursive path, finding exactly what I am seeking:

(defn SELECT-ATTRIBUTES-PATH [list-attrs]
  (recursive-path [] p
                  (multi-path
                   [map? (compact (submap list-attrs)) ]
                   [coll? (compact ALL) p]
                   ))
  )

But when trying to achieve my modifications, I didn't find a better way than doing it in vanilla clojure:

(defn nested-maps-to-attribute [maps]
  (when (map? maps)
    (apply merge
           (for [[_ nested-map] maps]
             (when (map? nested-map)
               nested-map)
             ))))

and then apply it with a transform:

(transform (SELECT-ATTRIBUTES-PATH #{:a :j})
           nested-maps-to-attribute
           {:a :b
            :f 0
            :g [1 2]
            :h "foo"
            :c {:d :e
                :j {:y :z}
                :a :c
                :i {}
                :h [ :i :j]
                :k [ {:l :m :n :o} {:p :q}]}}
           )

This works exactly as wanted, dropping :a even if nested, and moving :j submap to the upper level:

{:f 0,
 :g [1 2],
 :h "foo",
 :c {:d :e, :h [:i :j], :k [{:l :m, :n :o} {:p :q}], :y :z}}

My issue is that I would like to apply recursively these transformations, so the following:

(transform (SELECT-ATTRIBUTES-PATH #{:c :j})
           nested-maps-to-attribute
            {:c { :j {:y :z}}}
 )

should move [:y :z] directly at the root map --> {:y :z}

Instead, I find {:j {:y :z}.

Please help ๐Ÿ†˜ , I don't even know where to search...