Skip to content

Commit 9979fea

Browse files
committed
CLJS-2909: clojure.walk/postwalk does not preserve MapEntry type objects
And ports clojure.walk tests from Clojure.
1 parent 260556d commit 9979fea

4 files changed

Lines changed: 87 additions & 1 deletion

File tree

src/main/cljs/clojure/walk.cljs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,8 @@ the sorting function."}
4444
[inner outer form]
4545
(cond
4646
(list? form) (outer (apply list (map inner form)))
47-
(map-entry? form) (outer (vec (map inner form)))
47+
(map-entry? form)
48+
(outer (MapEntry. (inner (key form)) (inner (val form)) nil))
4849
(seq? form) (outer (doall (map inner form)))
4950
(record? form) (outer (reduce (fn [r x] (conj r (inner x))) form form))
5051
(coll? form) (outer (into (empty form) (map inner form)))

src/test/cljs/cljs/walk_test.cljs

Lines changed: 81 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,81 @@
1+
;; Copyright (c) Rich Hickey. All rights reserved.
2+
;; The use and distribution terms for this software are covered by the
3+
;; Eclipse Public License 1.0 (http://opensource.org/licenses/eclipse-1.0.php)
4+
;; which can be found in the file epl-v10.html at the root of this distribution.
5+
;; By using this software in any fashion, you are agreeing to be bound by
6+
;; the terms of this license.
7+
;; You must not remove this notice, or any other, from this software.
8+
9+
(ns cljs.walk-test
10+
(:require [cljs.test :refer-macros [deftest testing is]]
11+
[clojure.walk :as w]))
12+
13+
(deftest t-prewalk-replace
14+
(is (= (w/prewalk-replace {:a :b} [:a {:a :a} (list 3 :c :a)])
15+
[:b {:b :b} (list 3 :c :b)])))
16+
17+
(deftest t-postwalk-replace
18+
(is (= (w/postwalk-replace {:a :b} [:a {:a :a} (list 3 :c :a)])
19+
[:b {:b :b} (list 3 :c :b)])))
20+
21+
(deftest t-stringify-keys
22+
(is (= (w/stringify-keys {:a 1, nil {:b 2 :c 3}, :d 4})
23+
{"a" 1, nil {"b" 2 "c" 3}, "d" 4})))
24+
25+
(deftest t-prewalk-order
26+
(is (= (let [a (atom [])]
27+
(w/prewalk (fn [form] (swap! a conj form) form)
28+
[1 2 {:a 3} (list 4 [5])])
29+
@a)
30+
[[1 2 {:a 3} (list 4 [5])]
31+
1 2 {:a 3} [:a 3] :a 3 (list 4 [5])
32+
4 [5] 5])))
33+
34+
(deftest t-postwalk-order
35+
(is (= (let [a (atom [])]
36+
(w/postwalk (fn [form] (swap! a conj form) form)
37+
[1 2 {:a 3} (list 4 [5])])
38+
@a)
39+
[1 2
40+
:a 3 [:a 3] {:a 3}
41+
4 5 [5] (list 4 [5])
42+
[1 2 {:a 3} (list 4 [5])]])))
43+
44+
(defrecord Foo [a b c])
45+
46+
(defmulti get-comparator type)
47+
48+
(defmethod get-comparator PersistentTreeMap
49+
[o] (.-comp o))
50+
51+
(defmethod get-comparator PersistentTreeSet
52+
[o] (get-comparator (.-tree-map o)))
53+
54+
(deftest walk
55+
"Checks that walk returns the correct result and type of collection"
56+
(let [colls ['(1 2 3)
57+
[1 2 3]
58+
#{1 2 3}
59+
(sorted-set-by > 1 2 3)
60+
{:a 1, :b 2, :c 3}
61+
(sorted-map-by > 1 10, 2 20, 3 30)
62+
(->Foo 1 2 3)
63+
(map->Foo {:a 1 :b 2 :c 3 :extra 4})]]
64+
(doseq [c colls]
65+
(let [walked (w/walk identity identity c)]
66+
(is (= c walked))
67+
;;(is (= (type c) (type walked)))
68+
(if (map? c)
69+
(is (= (w/walk #(update-in % [1] inc) #(reduce + (vals %)) c)
70+
(reduce + (map (comp inc val) c))))
71+
(is (= (w/walk inc #(reduce + %) c)
72+
(reduce + (map inc c)))))
73+
(when (or (instance? PersistentTreeMap c)
74+
(instance? PersistentTreeSet c))
75+
(is (= (get-comparator c) (get-comparator walked))))))))
76+
77+
(deftest walk-mapentry
78+
"Checks that walk preserves the MapEntry type. See CLJS-2909."
79+
(let [coll [:html {:a ["b" 1]} ""]
80+
f (fn [e] (if (and (vector? e) (not (map-entry? e))) (apply list e) e))]
81+
(is (= (list :html {:a (list "b" 1)} "") (w/postwalk f coll)))))

src/test/cljs/test_runner.cljs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,7 @@
4747
[cljs.recur-test]
4848
[cljs.array-access-test]
4949
[cljs.inference-test]
50+
[cljs.walk-test]
5051
[cljs.extend-to-native-test]))
5152

5253
(set! *print-newline* false)
@@ -92,4 +93,5 @@
9293
'cljs.recur-test
9394
'cljs.array-access-test
9495
'cljs.inference-test
96+
'cljs.walk-test
9597
'cljs.extend-to-native-test)

src/test/self/self_parity/test.cljs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -312,6 +312,7 @@
312312
[cljs.recur-test]
313313
[cljs.array-access-test]
314314
[cljs.inference-test]
315+
[cljs.walk-test]
315316
[cljs.extend-to-native-test]))
316317
(fn [{:keys [value error]}]
317318
(if error
@@ -356,6 +357,7 @@
356357
'cljs.recur-test
357358
'cljs.array-access-test
358359
'cljs.inference-test
360+
'cljs.walk-test
359361
'cljs.extend-to-native-test)
360362
(fn [{:keys [value error]}]
361363
(when error

0 commit comments

Comments
 (0)