mirror of
https://github.com/penpot/penpot.git
synced 2025-01-24 23:49:45 -05:00
feat(backend): add etag mechanism for get requests
This commit is contained in:
parent
f3204114cd
commit
d967095b86
3 changed files with 63 additions and 24 deletions
|
@ -10,7 +10,6 @@
|
||||||
|
|
||||||
(defn- allow-origin?
|
(defn- allow-origin?
|
||||||
[value {:keys [origin]}]
|
[value {:keys [origin]}]
|
||||||
(prn "allow-origin?" value origin)
|
|
||||||
(cond
|
(cond
|
||||||
(nil? value) value
|
(nil? value) value
|
||||||
(= origin "*") origin
|
(= origin "*") origin
|
||||||
|
|
54
backend/src/uxbox/http/etag.clj
Normal file
54
backend/src/uxbox/http/etag.clj
Normal file
|
@ -0,0 +1,54 @@
|
||||||
|
;; This Source Code Form is subject to the terms of the Mozilla Public
|
||||||
|
;; License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||||
|
;; file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||||
|
;;
|
||||||
|
;; Copyright (c) 2019 Andrey Antukh <niwi@niwi.nz>
|
||||||
|
|
||||||
|
(ns uxbox.http.etag
|
||||||
|
"ETag calculation helpers."
|
||||||
|
(:require [clojure.java.io :as io]
|
||||||
|
[buddy.core.hash :as hash]
|
||||||
|
[buddy.core.codecs :as codecs]
|
||||||
|
[buddy.core.codecs.base64 :as b64]))
|
||||||
|
|
||||||
|
(defn digest
|
||||||
|
[^bytes data]
|
||||||
|
(-> (hash/blake2b-256 data)
|
||||||
|
(b64/encode true)
|
||||||
|
(codecs/bytes->str)))
|
||||||
|
|
||||||
|
(defn- etag-match?
|
||||||
|
[request new-tag]
|
||||||
|
(when-let [etag (get-in request [:headers "if-none-match"])]
|
||||||
|
(= etag new-tag)))
|
||||||
|
|
||||||
|
(defn stream-bytes
|
||||||
|
[is]
|
||||||
|
(let [baos (java.io.ByteArrayOutputStream.)]
|
||||||
|
(io/copy is baos)
|
||||||
|
(.toByteArray baos)))
|
||||||
|
|
||||||
|
(defn handle-response
|
||||||
|
[request {:keys [body] :as response}]
|
||||||
|
(when (instance? java.io.ByteArrayInputStream body)
|
||||||
|
(let [data (stream-bytes body)
|
||||||
|
etag (digest data)]
|
||||||
|
(.reset body)
|
||||||
|
(if-not (etag-match? request etag)
|
||||||
|
(update response :headers assoc "etag" etag)
|
||||||
|
(-> response
|
||||||
|
(assoc :body "" :status 304)
|
||||||
|
(update :headers assoc "etag" etag))))))
|
||||||
|
|
||||||
|
(defn wrap-etag
|
||||||
|
[handler]
|
||||||
|
(fn [request respond raise]
|
||||||
|
(handler request
|
||||||
|
(fn [response]
|
||||||
|
(prn "wrap-etag" (= (:request-method request) :get))
|
||||||
|
(if (= (:request-method request) :get)
|
||||||
|
(respond (or (handle-response request response) response))
|
||||||
|
(respond response)))
|
||||||
|
raise)))
|
||||||
|
|
||||||
|
|
|
@ -7,9 +7,6 @@
|
||||||
(ns uxbox.http.middleware
|
(ns uxbox.http.middleware
|
||||||
(:require [promesa.core :as p]
|
(:require [promesa.core :as p]
|
||||||
[cuerdas.core :as str]
|
[cuerdas.core :as str]
|
||||||
;; [buddy.core.hash :as hash]
|
|
||||||
;; [buddy.core.codecs :as codecs]
|
|
||||||
;; [buddy.core.codecs.base64 :as b64]
|
|
||||||
[struct.core :as st]
|
[struct.core :as st]
|
||||||
[reitit.ring :as rr]
|
[reitit.ring :as rr]
|
||||||
[reitit.ring.middleware.multipart :as multipart]
|
[reitit.ring.middleware.multipart :as multipart]
|
||||||
|
@ -19,6 +16,7 @@
|
||||||
[ring.middleware.session :refer [wrap-session]]
|
[ring.middleware.session :refer [wrap-session]]
|
||||||
[ring.middleware.session.cookie :refer [cookie-store]]
|
[ring.middleware.session.cookie :refer [cookie-store]]
|
||||||
[ring.middleware.multipart-params :refer [wrap-multipart-params]]
|
[ring.middleware.multipart-params :refer [wrap-multipart-params]]
|
||||||
|
[uxbox.http.etag :refer [wrap-etag]]
|
||||||
[uxbox.http.cors :refer [wrap-cors]]
|
[uxbox.http.cors :refer [wrap-cors]]
|
||||||
[uxbox.http.errors :as errors]
|
[uxbox.http.errors :as errors]
|
||||||
[uxbox.http.response :as rsp]
|
[uxbox.http.response :as rsp]
|
||||||
|
@ -124,26 +122,9 @@
|
||||||
{:name ::cors-middleware
|
{:name ::cors-middleware
|
||||||
:wrap #(wrap-cors % cors-conf)})
|
:wrap #(wrap-cors % cors-conf)})
|
||||||
|
|
||||||
;; (def ^:private cors-middleware
|
(def ^:private etag-middleware
|
||||||
;; {:name ::cors-middleware
|
{:name ::etag-middleware
|
||||||
;; :wrap #(wrap-cors %
|
:wrap wrap-etag})
|
||||||
;; :access-control-allow-origin [#".*"]
|
|
||||||
;; :access-control-allow-methods [:get :put :post :delete]
|
|
||||||
;; :access-control-allow-headers ["x-requested-with"
|
|
||||||
;; "content-type"
|
|
||||||
;; "authorization"])})
|
|
||||||
|
|
||||||
;; (defn digest
|
|
||||||
;; [^bytes data]
|
|
||||||
;; (-> (hash/blake2b-256 data)
|
|
||||||
;; (b64/encode true)
|
|
||||||
;; (codecs/bytes->str)))
|
|
||||||
|
|
||||||
;; (defn- etag-match?
|
|
||||||
;; [^Request request ^String new-tag]
|
|
||||||
;; (let [^Headers headers (.getHeaders request)]
|
|
||||||
;; (when-let [etag (.get headers "if-none-match")]
|
|
||||||
;; (= etag new-tag))))
|
|
||||||
|
|
||||||
(def ^:private exception-middleware
|
(def ^:private exception-middleware
|
||||||
(exception/create-exception-middleware
|
(exception/create-exception-middleware
|
||||||
|
@ -167,6 +148,10 @@
|
||||||
(def middleware
|
(def middleware
|
||||||
[cors-middleware
|
[cors-middleware
|
||||||
session-middleware
|
session-middleware
|
||||||
|
|
||||||
|
;; etag
|
||||||
|
etag-middleware
|
||||||
|
|
||||||
parameters/parameters-middleware
|
parameters/parameters-middleware
|
||||||
muuntaja/format-negotiate-middleware
|
muuntaja/format-negotiate-middleware
|
||||||
;; encoding response body
|
;; encoding response body
|
||||||
|
@ -175,6 +160,7 @@
|
||||||
exception-middleware
|
exception-middleware
|
||||||
;; decoding request body
|
;; decoding request body
|
||||||
muuntaja/format-request-middleware
|
muuntaja/format-request-middleware
|
||||||
|
|
||||||
;; multipart
|
;; multipart
|
||||||
multipart-params-middleware
|
multipart-params-middleware
|
||||||
;; parameters normalization
|
;; parameters normalization
|
||||||
|
|
Loading…
Add table
Reference in a new issue