From 05968e9629df53d1207dd1770b471cfbec1936c2 Mon Sep 17 00:00:00 2001 From: Nathan Marz Date: Mon, 22 Jun 2015 14:38:34 -0400 Subject: [PATCH 1/4] 0.5.5 --- CHANGES.md | 3 +++ VERSION | 2 +- 2 files changed, 4 insertions(+), 1 deletion(-) diff --git a/CHANGES.md b/CHANGES.md index 73fada4..0f54829 100644 --- a/CHANGES.md +++ b/CHANGES.md @@ -1,3 +1,6 @@ +## 0.5.5 +* Change filterer to accept a selector (that acts like selected? to determine whether or not to select value) + ## 0.5.4 * Change cond-path and if-path to take in a selector for conditionals (same idea as selected?) diff --git a/VERSION b/VERSION index 7d85683..d1d899f 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -0.5.4 +0.5.5 From 7520dd7e388227c3189b24b6a3415127bfc6f953 Mon Sep 17 00:00:00 2001 From: Nathan Marz Date: Thu, 25 Jun 2015 13:35:01 -0400 Subject: [PATCH 2/4] improve test --- test/clj/com/rpl/specter/core_test.clj | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/test/clj/com/rpl/specter/core_test.clj b/test/clj/com/rpl/specter/core_test.clj index 5e94f01..5e580c2 100644 --- a/test/clj/com/rpl/specter/core_test.clj +++ b/test/clj/com/rpl/specter/core_test.clj @@ -106,9 +106,11 @@ (defspec transform-filterer-all-equivalency (prop/for-all - [v (gen/vector gen/int)] - (let [v2 (transform [(filterer odd?) ALL] inc v) - v3 (transform [ALL odd?] inc v)] + [v (gen/vector gen/int) + pred (gen/elements [even? odd?]) + updater (gen/elements [inc dec])] + (let [v2 (transform [(filterer pred) ALL] updater v) + v3 (transform [ALL pred] updater v)] (= v2 v3)) )) From dc1da8dfcda2ba7b18449046569aded289864f5a Mon Sep 17 00:00:00 2001 From: Nathan Marz Date: Thu, 25 Jun 2015 16:27:27 -0400 Subject: [PATCH 3/4] improve test --- test/clj/com/rpl/specter/core_test.clj | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/test/clj/com/rpl/specter/core_test.clj b/test/clj/com/rpl/specter/core_test.clj index 5e580c2..0111004 100644 --- a/test/clj/com/rpl/specter/core_test.clj +++ b/test/clj/com/rpl/specter/core_test.clj @@ -135,12 +135,13 @@ (defspec transform-last-compound (for-all+ - [v (gen/such-that #(some odd? %) (gen/vector gen/int))] - (let [v2 (transform [(filterer odd?) LAST] inc v) + [pred (gen/elements [odd? even?]) + v (gen/such-that #(some pred %) (gen/vector gen/int))] + (let [v2 (transform [(filterer pred) LAST] inc v) differing-elems (differing-elements v v2)] (and (= (count v2) (count v)) (= (count differing-elems) 1) - (every? even? (drop (first differing-elems) v2)) + (every? (complement pred) (drop (first differing-elems) v2)) )))) ;; max sizes prevent too much data from being generated and keeps test from taking forever From 6a2afccbfda97b492ea2222ec95ecfec4fa2f7c3 Mon Sep 17 00:00:00 2001 From: Nathan Marz Date: Thu, 25 Jun 2015 16:30:27 -0400 Subject: [PATCH 4/4] add multi-path implementation --- src/clj/com/rpl/specter.clj | 6 ++++++ src/clj/com/rpl/specter/impl.clj | 19 +++++++++++++++++++ test/clj/com/rpl/specter/core_test.clj | 17 +++++++++++++++++ 3 files changed, 42 insertions(+) diff --git a/src/clj/com/rpl/specter.clj b/src/clj/com/rpl/specter.clj index f117e99..ee7f494 100644 --- a/src/clj/com/rpl/specter.clj +++ b/src/clj/com/rpl/specter.clj @@ -203,3 +203,9 @@ ([cond-fn if-path] (cond-path cond-fn if-path)) ([cond-fn if-path else-path] (cond-path cond-fn if-path nil else-path))) + +(defn multi-path + "A path that branches on multiple paths. For updates, + applies updates to the paths in order." + [& paths] + (->MultiPath (->> paths (map comp-paths*) doall))) diff --git a/src/clj/com/rpl/specter/impl.clj b/src/clj/com/rpl/specter/impl.clj index 6b864a5..a171ed1 100644 --- a/src/clj/com/rpl/specter/impl.clj +++ b/src/clj/com/rpl/specter/impl.clj @@ -47,6 +47,7 @@ (defprotocol CoerceTransformFunctions (coerce-path [this])) + (defn no-prot-error-str [obj] (str "Protocol implementation cannot be found for object. Extending Specter protocols should not be done inline in a deftype definition @@ -519,3 +520,21 @@ structure ))) +(deftype MultiPath [paths]) + +(extend-protocol StructurePath + MultiPath + (select* [this structure next-fn] + (->> (.paths this) + (mapcat #(compiled-select* % structure)) + (mapcat next-fn) + doall + )) + (transform* [this structure next-fn] + (reduce + (fn [structure selector] + (compiled-transform* selector next-fn structure)) + structure + (.paths this)) + )) + diff --git a/test/clj/com/rpl/specter/core_test.clj b/test/clj/com/rpl/specter/core_test.clj index 0111004..610b4f3 100644 --- a/test/clj/com/rpl/specter/core_test.clj +++ b/test/clj/com/rpl/specter/core_test.clj @@ -345,3 +345,20 @@ (= (select (if-path [k1 pred] k2 k3) m) (select k m)) )))) + +(defspec multi-path-test + (for-all+ + [k1 (max-size 3 gen/keyword) + k2 (max-size 3 gen/keyword) + m (max-size 5 + (gen-map-with-keys + gen/keyword + gen/int + k1 + k2)) + ] + (= (transform (multi-path k1 k2) inc m) + (->> m + (transform k1 inc) + (transform k2 inc))) + ))