Skip to content

Commit 82c1092

Browse files
Will Actonswannodette
authored andcommitted
CLJS-2999: Update datafy to use inherent support for protocols via metadata
- Moves cljs.core/IDatafiable to clojure.core.protocols/Datafiable - Moves cljs.core/INavigable to clojure.core.protocols/Navigable - Enables :extend-via-metadata on Datafiable and Navigable fix tests
1 parent fc7abd0 commit 82c1092

File tree

4 files changed

+52
-37
lines changed

4 files changed

+52
-37
lines changed

src/main/cljs/cljs/core.cljs

Lines changed: 2 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -867,13 +867,6 @@
867867
(-iterator [coll]
868868
"Returns an iterator for coll."))
869869

870-
(defprotocol IDatafiable
871-
(-datafy [o] "return a representation of o as data (default identity)"))
872-
873-
(defprotocol INavigable
874-
(-nav [coll k v] "return (possibly transformed) v in the context of coll and k (a key/index or nil),
875-
defaults to returning v."))
876-
877870
;; Printing support
878871

879872
(deftype StringBufferWriter [sb]
@@ -1366,10 +1359,7 @@ defaults to returning v."))
13661359

13671360
(extend-type nil
13681361
ICounted
1369-
(-count [_] 0)
1370-
1371-
IDatafiable
1372-
(-datafy [_] nil))
1362+
(-count [_] 0))
13731363

13741364
;; TODO: we should remove this and handle date equality checking
13751365
;; by some other means, probably by adding a new primitive type
@@ -1418,13 +1408,7 @@ defaults to returning v."))
14181408
(extend-type default
14191409
IHash
14201410
(-hash [o]
1421-
(goog/getUid o))
1422-
1423-
IDatafiable
1424-
(-datafy [o] o)
1425-
1426-
INavigable
1427-
(-nav [_ _ x] x))
1411+
(goog/getUid o)))
14281412

14291413
;;this is primitive because & emits call to array-seq
14301414
(defn inc
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
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 clojure.core.protocols)
10+
11+
(defprotocol Datafiable
12+
:extend-via-metadata true
13+
(datafy [o] "return a representation of o as data (default identity)"))
14+
15+
(extend-protocol Datafiable
16+
nil
17+
(datafy [_] nil)
18+
19+
default
20+
(datafy [o] o))
21+
22+
(defprotocol Navigable
23+
:extend-via-metadata true
24+
(nav [coll k v] "return (possibly transformed) v in the context of coll and k (a key/index or nil),
25+
defaults to returning v."))
26+
27+
(extend-protocol Navigable
28+
default
29+
(nav [_ _ x] x))

src/main/cljs/clojure/datafy.cljs

Lines changed: 19 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -8,48 +8,50 @@
88

99
(ns
1010
^{:doc "Functions to turn objects into data. Alpha, subject to change"}
11-
clojure.datafy)
11+
clojure.datafy
12+
(:require [clojure.core.protocols :as p]))
1213

1314
(defn datafy
14-
"Attempts to return x as data. If :clojure.datafy/datafy is present
15-
as metadata of x, it will be called with x as an argument, else
16-
datafy will return the value of clojure.protocols/datafy. If the
17-
value has been transformed and the result supports
15+
"Attempts to return x as data.
16+
datafy will return the value of clojure.protocols/datafy. If
17+
the value has been transformed and the result supports
1818
metadata, :clojure.datafy/obj will be set on the metadata to the
1919
original value of x."
2020
[x]
21-
(let [v ((or (-> x meta ::datafy) -datafy) x)]
21+
(let [v (p/datafy x)]
2222
(if (identical? v x)
2323
v
2424
(if (implements? IWithMeta v)
25-
(vary-meta v assoc ::obj x)
25+
(vary-meta v assoc ::obj x
26+
;; Circling back to this at a later date per @dnolen
27+
;; ::class (-> x .-constructor .-name symbol)
28+
)
2629
v))))
2730

2831
(defn nav
2932
"Returns (possibly transformed) v in the context of coll and k (a
3033
key/index or nil). Callers should attempt to provide the key/index
3134
context k for Indexed/Associative/ILookup colls if possible, but not
32-
to fabricate one e.g. for sequences (pass nil). If :clojure.datafy/nav is
33-
present as metadata on coll, it will be called with coll, k and v as
34-
arguments, else nav will call :clojure.protocols/nav."
35+
to fabricate one e.g. for sequences (pass nil). nav will return the
36+
value of clojure.core.protocols/nav."
3537
[coll k v]
36-
((or (-> coll meta ::nav) -nav) coll k v))
38+
(p/nav coll k v))
3739

3840
(defn- datify-ref [r]
3941
(with-meta [(deref r)] (meta r)))
4042

41-
(extend-protocol IDatafiable
43+
(extend-protocol p/Datafiable
4244
Var
43-
(-datafy [r] (datify-ref r))
45+
(datafy [r] (datify-ref r))
4446

4547
Reduced
46-
(-datafy [r] (datify-ref r))
48+
(datafy [r] (datify-ref r))
4749

4850
Atom
49-
(-datafy [r] (datify-ref r))
51+
(datafy [r] (datify-ref r))
5052

5153
Volatile
52-
(-datafy [r] (datify-ref r))
54+
(datafy [r] (datify-ref r))
5355

5456
Delay
55-
(-datafy [r] (datify-ref r)))
57+
(datafy [r] (datify-ref r)))

src/test/cljs/clojure/datafy_test.cljs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,11 +14,11 @@
1414
(deftest datafy-test
1515
(testing "Datafy works when datafied value is arbitrary JS objects"
1616
(let [datafied #js {}
17-
x (with-meta [1 2 3] {:clojure.datafy/datafy (fn [_] datafied)})]
17+
x (with-meta [1 2 3] {`clojure.core.protocols/datafy (fn [_] datafied)})]
1818
(is (= datafied (d/datafy x)))))
1919
(testing "Datafy adds ::obj metadata when return value != original value and supports metadata"
2020
(let [datafied [2 3 4]
2121
original [1 2 3]
22-
x (with-meta original {:clojure.datafy/datafy (fn [_] datafied)})]
22+
x (with-meta original {`clojure.core.protocols/datafy (fn [_] datafied)})]
2323
(is (= datafied (d/datafy x)))
2424
(is (= {:clojure.datafy/obj original} (meta (d/datafy x)))))))

0 commit comments

Comments
 (0)