Fork me on GitHub
#ring-swagger
<
2017-10-17
>
slipset08:10:53

@ikitommi some sort of (st/add-custom-coersion [:body :formats "application/json" :timestamp] json-timestamp->long)

slipset08:10:00

would be a nice function to have.

slipset08:10:40

for some permutation of [:body :formats "application/json" :timestamp]

ikitommi08:10:55

What if we turn this around and add the coercers directly to Spec (Records)?

ikitommi08:10:46

(st/spec
   {:pred (partial DateTime)
    :coercion {:string str->date-time}
    :json-schema/examples "..."})

slipset08:10:47

(st/spec {:coercer json-timestamp->long :type :timestamp})

slipset08:10:25

yeah, you need the map there right?

slipset08:10:02

So the keys in the coercion-map would be #{:string :json :edn}

slipset08:10:27

and how would you then control which part of the lifecycle you’d want coercion in (request/response)?

ikitommi08:10:46

There are three scopes for coercion (`:request`, :response and :string), but only two modes (`:json` and :string).

slipset08:10:52

I guess if you need finegrained control, you do as you did in your gist.

slipset08:10:06

make the simple case simple, and the hard case possible 🙂

slipset08:10:59

As a newcomer to this project, I guess the fact that :string is present both in scope and mode kind of confuses me. But that might just be me.

ikitommi08:10:14

That is confusing.

ikitommi08:10:27

the Spec Records should not know anything about the request/response, but they should know what kind of coercion should occur. Schema had string and json.

ikitommi08:10:45

spec-tools has those too

slipset08:10:00

And don’t get me wrong. I’m super happy for this work and your help.

slipset08:10:30

Any criticism here is just so we can make this better.

ikitommi08:10:11

thanks, want to make things easy too. There was an idea with schemas, how to bundle ceorcion + encoding + decoding into a one concept: adding a type could be done in one place. I think we could do that now, for both Schemas & Specs. Idea is described here: https://github.com/metosin/web-schemas

ikitommi08:10:08

As jsonista supports explicit mappings (opposed to Cheshire having global extensions), we can do this now.

ikitommi08:10:36

e.g. introduce MyNewType, one can describe all the things (encode, decode (multiple formats: json, edn, transit), coercion in different types, docs) in single definition. With syntax validation. Muuntaja, Jsonista and Schema/Spec-tools would take parts of those and together they would just work. And there would be a test-suite: “which types can I pass in which contexts?”

ikitommi08:10:25

Currently, if a EDN-writer is missing for a custom type, it can fail at runtime when first time tried to pass over the wire. Temporal runtime coupling. Which is BAD.

ikitommi08:10:01

Spec Record could be the host for all the info, just need to figure out the format in which. Ideas welcome.

ikitommi08:10:35

And this should be a small micro-library, might be good for other web libs too.

ikitommi08:10:51

can’t remember how this is/was solved in the java/scala-land.

slipset08:10:16

It’s a bit much for me to wrap my head around right now 🙂

ikitommi08:10:26

me too, off to lunch 😉

slipset08:10:45

It could be cool if the coercer was a multi-method though?

slipset09:10:32

(defmethod coerce [:time-tamp :json :request] [{:keys [value]] ...)

slipset09:10:19

(defmulti coerce type-mode-scope)

slipset09:10:05

(defn type-mode-scope [{:keys [type mode scope]}] [type mode scope])

slipset09:10:21

Or something along these lines.

slipset09:10:12

Problem with this is that you get the temporal coupling. If I don’t implement the multi-method for a given type/mode/scope combination, it might blow up in production.