Java.time

Support more primitive data types such as:

  • java.time.Instant
  • java.time.LocalDate
  • java.time.LocalTime

Currently we are encoding them as strings and serialization / deserialization them in queries and rules.
https://wiki.c2.com/?StringlyTyped

Related Feature Request
https://portal.feedback.eu.pendo.io/app/#/case/17713

3 Likes

Actually I believe datetime is already stored as instant, but what makes be boring that java library requires to pass/returns old java.util.Date

1 Like

The error I get is related to transit not being able to encode an instance of Instant. See also https://github.com/metosin/muuntaja/issues/92 which includes a link to https://clojureverse.org/t/migrating-from-clj-time-to-java-time/3251/6

I just made a transparent solution - using Richelieu advices - for using java.time.Instant in transactions and receiving them in pull results.

See my original post about it here:

For convenience, I will repeat the code here too:

(ns xxx.datomic.client
  "Conveniences for working with the `datomic.client.api`."
  (:require
    [datomic.client.api :as d]
    [richelieu.core :refer :all]
    [tick.alpha.api :as t]
    [clojure.walk :as walk]))

(defn- maybe-instant->inst [i] (if (t/instant? i) (t/inst i) i))

(defadvice ^:private transact-instants [transact conn arg-map]
  (transact conn
            (update arg-map :tx-data
                    (partial walk/postwalk maybe-instant->inst))))

(defonce _transact-instants (advise-var #'d/transact #'transact-instants))

(defn- maybe-inst->instant [i] (if (inst? i) (t/instant i) i))

(defadvice ^:private pull-instants
  ([pull db arg-map]
   (->> (pull db arg-map)
        (walk/postwalk maybe-inst->instant)))
  ([pull db selector eid]
   (->> (pull db selector eid)
        (walk/postwalk maybe-inst->instant))))

(defonce _pull-instants (advise-var #'d/pull #'pull-instants))

Here is an example of a java.time.Instant roundtrip to a Datomic DB:

(comment
  (let [client (d/client {:server-type :dev-local
                          :storage-dir :mem
                          :system      "tick"})
        db-ref {:db-name "demo"}
        _ (d/create-database client db-ref)
        conn (d/connect client db-ref)]
    
    (->> [[{:db/ident      :timestamp
            :db/valueType   :db.type/instant
            :db/cardinality :db.cardinality/one}]
          
          [{:db/ident :t1 
            :timestamp (t/now)}]]
         (reduce (fn [c tx] (d/transact c {:tx-data tx}) c) conn))
    
    (d/pull (d/db conn) [:timestamp] :t1))
  )

It returns {:timestamp #time/instant"2021-05-27T05:54:00.260Z"}.

1 Like

Related question on ask.datomic.com
Support java.time.instant - Datomic Knowledgebase

I’ve added some examples on how datomic.client.impl.shared.io/{read,write}-handlers could be extended, but unfortunately that was not enough for providing support.

I’ve extended transit based on the example on this Github issue:

1 Like