This page is not created by, affiliated with, or supported by Slack Technologies, Inc.
2022-06-22
Channels
- # announcements (7)
- # babashka (1)
- # beginners (87)
- # boot (1)
- # cider (1)
- # clj-kondo (33)
- # cljfx (1)
- # cljs-dev (8)
- # clojars (3)
- # clojure (105)
- # clojure-austin (3)
- # clojure-europe (74)
- # clojure-finland (1)
- # clojure-korea (4)
- # clojure-nl (1)
- # clojure-uk (6)
- # clojurescript (10)
- # conjure (9)
- # cursive (29)
- # datalog (6)
- # datomic (13)
- # emacs (3)
- # events (4)
- # figwheel-main (1)
- # gratitude (1)
- # humbleui (6)
- # introduce-yourself (7)
- # jackdaw (1)
- # jobs (1)
- # lsp (29)
- # malli (3)
- # nbb (2)
- # podcasts (1)
- # portal (5)
- # re-frame (4)
- # reitit (28)
- # remote-jobs (5)
- # shadow-cljs (38)
- # tools-deps (46)
- # vim (6)
- # xtdb (24)
I have a situation where I am ingesting json which is base64 encoded, I have a middleware that decodes it and sets the body to the decoded json, this how ever stops my body coercion, any suggestions how I can use :parameters :body on the decoded body, or will I need to manually do the validation in this instance ?
What does your middleware stack look like? Are you using muuntaja
for content negotiation?
I think it can be made to work so that both decoding and coercion will work but things need to happen in certain order :thinking_face:
For example, if you’re using muuntaja
you could just make it aware of your b64 encoded json format and plug in the decoding and then the rest would probably work as with normal JSON
so currently, I have decode-pubsub-body-json-middleware set as a middleware in a post route, it basically does this
(defn decode-pubsub-body-json-middleware
[handler]
(fn [request]
(handler
(update-in request [:parameters :body] #(-> % process-message-json :message :data)))))
I had not considered I may be able to do this in the muuntaja stage, how would muntaja known when to apply the decoding as most of the time it will not be encoded, only when it comes from a queue is it encoded
Muuntaja uses content-type
header (in case of HTTP) to decide how to decode the request body
although I have a hunch its json, as its a json body with queue data with a message key which has the actual json body encoded
Yep, if you can control the content-type in the pubsub thing that could be one relatively clean way to do it
its looking like its just reported as json unfortunately, so this may stop me doing it with muuntaja
Then you could try to change route middleware to first decode b64 and coerce only after that
yeah that's what I am doing now but it seems to coerce then decode, so unless I can make the middleware run before coercion I will likely have to do it manually
Hmmm could the issue be that the coercer is actually looking from :body-params
and not from [:parameters :body]
:thinking_face:
Did a quick test and this seems to work.. Doing b64 and json decoding in the same middleware but json decoding could happen elsewhere
(def app
(ring/ring-handler
(ring/router
[["/b64"
["/test"
{:coercion reitit.coercion.spec/coercion
:parameters {:body ::decoded-body}
:middleware [(fn [handler]
(fn [req]
(handler (assoc-in req [:body-params] (-> req
:body
slurp
<-base64
<-json)))))
coercion/coerce-request-middleware]
:post (fn [req]
{:status 200
:debug {:body-params (:body-params req)
:params (:params req)}})}]]]
{:data {}})
(ring/create-default-handler)))
oh awesome thanks for that, that would certainly explain it I will give it a try, when I next get a chance
You can apply the special muuntaja instance for certain routes. Others can use the default one
got around to trying this out, for me however the coercion kicks in before it even gets to the decode middleware which is a bit strange yours seems to work, main difference is your using spec not malli can't see much else that's different still digging though