I'm trying to test a library that involves stuffing data into a JSONB column. I tried to avoid making assumptions about whether or not a user has extended SettableParameter and Readable column as documented in the next.jdbc Tips & Tricks. So internally I'm thinking I just check if I have a clojure type or not coming back from the DB. But in my tests (against a real psql instance) ... is it possible to both extend the protocol and, er, "de-extend" it to get coverage on both cases? Seems like this is at a JVM-level and not a datasource level.
Ah, I figured out something that will work that I can do at a per-test level:
(def ^:dynamic *serialize*? false)
(defn clj->pgobject [x]
(if *serialize?*
(let [pgtype (or (:pgtype (meta x)) "jsonb")]
(doto (PGobject.)
(.setType pgtype)
(.setValue (x->json x))))
x))
(defn init-json-write-helper []
;; if a SQL parameter is a Clojure hash map or vector, it'll be transformed
;; to a PGobject for JSON/JSONB:
(extend-protocol next.jdbc.prepare/SettableParameter
clojure.lang.IPersistentMap
(set-parameter [m ^PreparedStatement s i]
(.setObject s i (clj->pgobject m)))
clojure.lang.IPersistentVector
(set-parameter [v ^PreparedStatement s i]
(.setObject s i (clj->pgobject v)))))
(binding [*serialize?* true]
;; do the test involving serialization
)I guess I could test without extending the protocols first, then extend them, then test again, but the test order dependency seems a bit declassé.
Small issue in the docs: https://cljdoc.org/d/com.github.seancorfield/next.jdbc/1.3.925/doc/all-the-options?q=%3Aschema-opts#datafying--navigating-rows-and-result-sets the link in See datafy, nav, and :schema for more details. takes you to a GitHub 404.
Can you open a GitHub issue so this doesn't get forgotten?
https://github.com/seancorfield/next-jdbc/issues/278 Thanks @seancorfield.
Much appreciated.
Is there a way to get nav to play nice with rs/as-kebab-maps? It looks like _ is accepted and optional, but when your result set uses -id instead, nav'ing doesn't work.
That's what the recently-added :schema-opts stuff is for... but maybe you can provide more detail of what you expected to work and what the actual behavior was?
I think if I use {:schema-opts {:fk-suffix "id" :pk "did"}} but my foreign keys look like :foo-id it will not work because it's expecting :foo_id. Does that make sense, or maybe I'm missing something?
> For :fk-suffix, the is still permitted and optional in the column name, so if you specified :schema-opts {:fk-suffix "fk"} then addressfk and addressfk would both be treated as foreign keys into the address table.
but no mention of address-fk which is what the field names would show up like in the REPL if rs/as-kebab-maps is used.
Can you open a GH issue with details? It may be straightforward to make this work...
Yeah, I think this could be a one-line change (to the regex on line 1040 of result_set.clj) and some doc updates.
https://github.com/seancorfield/next-jdbc/issues/280 for reference. Thanks again, @seancorfield.