diff --git a/backend/src/app/config.clj b/backend/src/app/config.clj index 39fa0499e..2c1d77aba 100644 --- a/backend/src/app/config.clj +++ b/backend/src/app/config.clj @@ -83,8 +83,7 @@ :ldap-attrs-photo "jpegPhoto" ;; a server prop key where initial project is stored. - :initial-project-skey "initial-project" - }) + :initial-project-skey "initial-project"}) (s/def ::flags ::us/words) diff --git a/backend/src/app/http.clj b/backend/src/app/http.clj index 9ef7a8773..102fd6ab2 100644 --- a/backend/src/app/http.clj +++ b/backend/src/app/http.clj @@ -141,7 +141,8 @@ ["/webhooks" ["/sns" {:post (:sns-webhook cfg)}]] - ["/api" {:middleware [[middleware/etag] + ["/api" {:middleware [[middleware/cors] + [middleware/etag] [middleware/format-response-body] [middleware/params] [middleware/multipart-params] diff --git a/backend/src/app/http/middleware.clj b/backend/src/app/http/middleware.clj index 200718d30..8c8bf1151 100644 --- a/backend/src/app/http/middleware.clj +++ b/backend/src/app/http/middleware.clj @@ -8,6 +8,7 @@ (:require [app.common.logging :as l] [app.common.transit :as t] + [app.config :as cf] [app.metrics :as mtx] [app.util.json :as json] [buddy.core.codecs :as bc] @@ -176,3 +177,29 @@ :uri (str (:uri request) (when qstring (str "?" qstring))) :method (name (:request-method request))) (handler request))))) + +(defn- wrap-cors + [handler] + (if-not (contains? cf/flags :cors) + handler + (letfn [(add-cors-headers [response request] + (-> response + (update + :headers + (fn [headers] + (-> headers + (assoc "access-control-allow-origin" (get-in request [:headers "origin"])) + (assoc "access-control-allow-methods" "GET,POST,DELETE,OPTIONS,PUT,HEAD,PATCH") + (assoc "access-control-allow-credentials" "true") + (assoc "access-control-expose-headers" "x-requested-with, content-type, cookie") + (assoc "access-control-allow-headers" "x-frontend-version, content-type, accept, x-requested-width"))))))] + (fn [request] + (if (= (:request-method request) :options) + (-> {:status 200 :body ""} + (add-cors-headers request)) + (let [response (handler request)] + (add-cors-headers response request))))))) + +(def cors + {:name ::cors + :compile (constantly wrap-cors)}) diff --git a/frontend/src/app/config.cljs b/frontend/src/app/config.cljs index a72f49136..9e308a1ca 100644 --- a/frontend/src/app/config.cljs +++ b/frontend/src/app/config.cljs @@ -93,7 +93,8 @@ (when (false? registration) (swap! flags disj :registration))) -(def public-uri +(defn get-public-uri + [] (let [uri (u/uri (or (obj/get global "penpotPublicURI") (.-origin ^js location)))] ;; Ensure that the path always ends with "/"; this ensures that @@ -102,6 +103,8 @@ (not (str/ends-with? (:path uri) "/")) (update :path #(str % "/"))))) +(def public-uri (get-public-uri)) + ;; --- Helper Functions (defn ^boolean check-browser? [candidate] diff --git a/frontend/src/app/main/repo.cljs b/frontend/src/app/main/repo.cljs index 7ec498c40..9fa42387c 100644 --- a/frontend/src/app/main/repo.cljs +++ b/frontend/src/app/main/repo.cljs @@ -48,6 +48,7 @@ [id params] (->> (http/send! {:method :get :uri (u/join base-uri "api/rpc/query/" (name id)) + :credentials "include" :query params}) (rx/map http/conditional-decode-transit) (rx/mapcat handle-response))) @@ -58,6 +59,7 @@ [id params] (->> (http/send! {:method :post :uri (u/join base-uri "api/rpc/mutation/" (name id)) + :credentials "include" :body (http/transit-data params)}) (rx/map http/conditional-decode-transit) (rx/mapcat handle-response))) @@ -87,7 +89,10 @@ [_ {:keys [provider] :as params}] (let [uri (u/join base-uri "api/auth/oauth/" (d/name provider)) params (dissoc params :provider)] - (->> (http/send! {:method :post :uri uri :query params}) + (->> (http/send! {:method :post + :uri uri + :credentials "include" + :query params}) (rx/map http/conditional-decode-transit) (rx/mapcat handle-response)))) @@ -95,6 +100,7 @@ [_ params] (->> (http/send! {:method :post :uri (u/join base-uri "api/feedback") + :credentials "include" :body (http/transit-data params)}) (rx/map http/conditional-decode-transit) (rx/mapcat handle-response))) @@ -104,6 +110,7 @@ (->> (http/send! {:method :post :uri (u/join base-uri "export") :body (http/transit-data params) + :credentials "include" :response-type :blob}) (rx/mapcat handle-response))) @@ -112,6 +119,7 @@ (->> (http/send! {:method :post :uri (u/join base-uri "export-frames") :body (http/transit-data params) + :credentials "include" :response-type :blob}) (rx/mapcat handle-response))) @@ -123,6 +131,7 @@ [id params] (->> (http/send! {:method :post :uri (u/join base-uri "api/rpc/mutation/" (name id)) + :credentials "include" :body (http/form-data params)}) (rx/map http/conditional-decode-transit) (rx/mapcat handle-response))) diff --git a/frontend/src/app/util/http.cljs b/frontend/src/app/util/http.cljs index fe60147a3..41ac92a38 100644 --- a/frontend/src/app/util/http.cljs +++ b/frontend/src/app/util/http.cljs @@ -54,8 +54,10 @@ {"x-frontend-version" (:full @cfg/version)}) (defn fetch - [{:keys [method uri query headers body mode omit-default-headers] - :or {mode :cors headers {}}}] + [{:keys [method uri query headers body mode omit-default-headers credentials] + :or {mode :cors + headers {} + credentials "same-origin"}}] (rx/Observable.create (fn [subscriber] (let [controller (js/AbortController.) @@ -83,7 +85,7 @@ :body body :mode (d/name mode) :redirect "follow" - :credentials "same-origin" + :credentials credentials :referrerPolicy "no-referrer" :signal signal}] (-> (js/fetch (str uri) params) @@ -165,7 +167,6 @@ :uri uri :response-type :blob :omit-default-headers true}) - (rx/filter #(= 200 (:status %))) (rx/map :body) (rx/mapcat wapi/read-file-as-data-url) diff --git a/frontend/src/app/util/worker.cljs b/frontend/src/app/util/worker.cljs index 914756e96..497a050d5 100644 --- a/frontend/src/app/util/worker.cljs +++ b/frontend/src/app/util/worker.cljs @@ -9,6 +9,8 @@ (:require [app.common.transit :as t] [app.common.uuid :as uuid] + [app.util.globals :refer [global]] + [app.util.object :as obj] [beicon.core :as rx])) (declare handle-response) @@ -28,11 +30,13 @@ data (t/encode-str message) instance (:instance worker)] - (.postMessage instance data) - (->> (:stream worker) - (rx/filter #(= (:reply-to %) sender-id)) - (take-messages) - (rx/map handle-response))))) + (if (some? instance) + (do (.postMessage instance data) + (->> (:stream worker) + (rx/filter #(= (:reply-to %) sender-id)) + (take-messages) + (rx/map handle-response))) + (rx/empty))))) (defn ask! [worker message] @@ -79,6 +83,11 @@ (.addEventListener instance "message" handle-message) (.addEventListener instance "error" handle-error) + (ask! worker + {:cmd :configure + :params + {"penpotPublicURI" (obj/get global "penpotPublicURI")}}) + worker)) (defn- handle-response diff --git a/frontend/src/app/worker/impl.cljs b/frontend/src/app/worker/impl.cljs index 9dfb3bba2..13b7d167f 100644 --- a/frontend/src/app/worker/impl.cljs +++ b/frontend/src/app/worker/impl.cljs @@ -7,6 +7,8 @@ (ns app.worker.impl (:require [app.common.pages.changes :as ch] + [app.util.globals :refer [global]] + [app.util.object :as obj] [okulary.core :as l])) (enable-console-print!) @@ -50,3 +52,8 @@ (assoc :cmd :selection/update-index))) (handler (-> message (assoc :cmd :snaps/update-index)))))) + +(defmethod handler :configure + [{:keys [params]}] + (doseq [[param-key param-value] params] + (obj/set! global param-key param-value))) diff --git a/frontend/src/app/worker/thumbnails.cljs b/frontend/src/app/worker/thumbnails.cljs index 210dfe31b..606f72ec4 100644 --- a/frontend/src/app/worker/thumbnails.cljs +++ b/frontend/src/app/worker/thumbnails.cljs @@ -7,6 +7,8 @@ (ns app.worker.thumbnails (:require ["react-dom/server" :as rds] + [app.common.uri :as u] + [app.config :as cfg] [app.main.exports :as exports] [app.main.fonts :as fonts] [app.util.http :as http] @@ -29,11 +31,15 @@ (defn- request-page [file-id page-id] - (let [uri "/api/rpc/query/page"] + (let [uri (u/join (cfg/get-public-uri) "api/rpc/query/page") + params {:file-id file-id + :id page-id + :strip-thumbnails true}] (->> (http/send! - {:uri uri - :query {:file-id file-id :id page-id :strip-thumbnails true} - :method :get}) + {:method :get + :uri uri + :credentials "include" + :query params}) (rx/map http/conditional-decode-transit) (rx/mapcat handle-response))))