/
zip.clj
62 lines (53 loc) · 1.32 KB
/
zip.clj
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
(ns rewrite-indented.zip
(:refer-clojure :exclude [next update])
(:require
[clojure.zip :as zip]
[rewrite-indented.parser :as parser]))
(def next
"Alias for zip/next"
zip/next)
(defn update
[zloc f]
(let [parent-vector-loc (zip/up zloc)
parent-node (zip/node parent-vector-loc)]
(-> parent-vector-loc
(zip/replace (clojure.core/update parent-node 0 f))
(zip/down))))
(defn move-to-root
[loc]
(loop [loc loc]
(if-let [loc' (zip/up loc)]
(recur loc')
loc)))
(defn find-next
([zloc p?]
(find-next zloc zip/next p?))
([zloc f p?]
(when (and zloc (not (zip/end? zloc)))
(if (p? (zip/node zloc))
zloc
(recur (f zloc) f p?)))))
(defn find-next-string
[zloc p?]
(find-next zloc
#(and (string? %)
(p? %))))
(defn find-ancestor-string
[zloc p?]
(find-next zloc zip/up #(and (vector? %)
(string? (first %))
(p? (first %)))))
(defn of-string
[s]
(->> (parser/parse s)
(zip/zipper vector? seq
(fn [existing-node new-node]
(with-meta new-node (meta existing-node))))))
(defn of-file
[f]
(of-string (slurp f)))
(defn root-string
[zloc]
(-> (move-to-root zloc)
(zip/node)
(parser/unparse)))