mirror of
https://github.com/penpot/penpot.git
synced 2026-07-31 18:36:18 +00:00
🐛 Fix nitrate sso doesn't notify workspace on activation (#10955)
This commit is contained in:
parent
be5d9f9e9c
commit
03f9393200
@ -11,7 +11,9 @@
|
||||
[app.common.data.macros :as dm]
|
||||
[app.common.schema :as sm]
|
||||
[app.common.time :as ct]
|
||||
[app.common.types.organization :as co]
|
||||
[app.common.types.team :as ctt]
|
||||
[app.config :as cf]
|
||||
[app.main.data.helpers :as dsh]
|
||||
[app.main.data.modal :as modal]
|
||||
[app.main.data.notifications :as ntf]
|
||||
@ -232,6 +234,63 @@
|
||||
;; Delay so the navigation can finish
|
||||
(rx/delay 250))))))))
|
||||
|
||||
(defn- check-team-sso
|
||||
[team-id]
|
||||
(let [url (rt/get-current-href)]
|
||||
(->> (rp/cmd! :check-nitrate-sso {:team-id team-id :url url})
|
||||
(rx/mapcat (fn [{:keys [authorized redirect-uri]}]
|
||||
(if authorized
|
||||
(rx/empty)
|
||||
(if redirect-uri
|
||||
(rx/of (rt/nav-raw :uri (str redirect-uri)))
|
||||
(rx/empty))))))))
|
||||
|
||||
(defn handle-change-team-org
|
||||
"Handle :team-org-change websocket messages on dashboard and workspace.
|
||||
Updates local team org data and redirects to SSO when required."
|
||||
[{:keys [team notification]}]
|
||||
(ptk/reify ::handle-change-team-org
|
||||
ptk/WatchEvent
|
||||
(watch [_ state _]
|
||||
(let [current-team-id (:current-team-id state)
|
||||
organization (:organization team)
|
||||
current-team? (= (:id team) current-team-id)]
|
||||
(when (and (contains? cf/flags :nitrate)
|
||||
current-team?)
|
||||
(rx/concat
|
||||
(when notification
|
||||
(rx/of (ntf/show {:content (tr notification (:name organization))
|
||||
:type :toast
|
||||
:level :info
|
||||
:timeout nil})))
|
||||
(when (:id organization)
|
||||
(check-team-sso current-team-id))))))
|
||||
ptk/UpdateEvent
|
||||
(update [_ state]
|
||||
(if (contains? cf/flags :nitrate)
|
||||
(let [team-id (:id team)
|
||||
team-name (:name team)
|
||||
organization (:organization team)]
|
||||
(d/update-in-when state [:teams team-id]
|
||||
(fn [team]
|
||||
(cond-> (co/apply-organization team organization)
|
||||
team-name (assoc :name team-name)))))
|
||||
state))))
|
||||
|
||||
(defn handle-organization-change-sso
|
||||
"Handle :organization-change-sso websocket messages on dashboard and workspace.
|
||||
Redirects to the org SSO login when the current team belongs to that org."
|
||||
[{:keys [organization-id]}]
|
||||
(ptk/reify ::handle-organization-change-sso
|
||||
ptk/WatchEvent
|
||||
(watch [_ state _]
|
||||
(when (contains? cf/flags :nitrate)
|
||||
(let [team-id (:current-team-id state)
|
||||
team (dm/get-in state [:teams team-id])
|
||||
org-id (dm/get-in team [:organization :id])]
|
||||
(when (= organization-id org-id)
|
||||
(check-team-sso team-id)))))))
|
||||
|
||||
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
;; PROGRESS EVENTS
|
||||
|
||||
@ -13,7 +13,6 @@
|
||||
[app.common.logging :as log]
|
||||
[app.common.schema :as sm]
|
||||
[app.common.time :as ct]
|
||||
[app.common.types.organization :as co]
|
||||
[app.common.types.project :refer [valid-project?]]
|
||||
[app.common.uuid :as uuid]
|
||||
[app.config :as cf]
|
||||
@ -27,7 +26,6 @@
|
||||
[app.main.data.team :as dtm]
|
||||
[app.main.data.websocket :as dws]
|
||||
[app.main.repo :as rp]
|
||||
[app.main.router :as rt]
|
||||
[app.main.store :as st]
|
||||
[app.util.i18n :as i18n :refer [tr]]
|
||||
[app.util.sse :as sse]
|
||||
@ -687,47 +685,6 @@
|
||||
(rx/of (dcm/change-team-role params)
|
||||
(modal/hide)))))
|
||||
|
||||
(defn- check-team-sso
|
||||
[team-id]
|
||||
(let [url (rt/get-current-href)]
|
||||
(->> (rp/cmd! :check-nitrate-sso {:team-id team-id :url url})
|
||||
(rx/mapcat (fn [{:keys [authorized redirect-uri]}]
|
||||
(if authorized
|
||||
(rx/empty)
|
||||
(if redirect-uri
|
||||
(rx/of (rt/nav-raw :uri (str redirect-uri)))
|
||||
(rx/empty))))))))
|
||||
|
||||
(defn handle-change-team-org
|
||||
[{:keys [team notification]}]
|
||||
(ptk/reify ::handle-change-team-org
|
||||
ptk/WatchEvent
|
||||
(watch [_ state _]
|
||||
(let [current-team-id (:current-team-id state)
|
||||
organization (:organization team)
|
||||
current-team? (= (:id team) current-team-id)]
|
||||
(when (and (contains? cf/flags :nitrate)
|
||||
current-team?)
|
||||
(rx/concat
|
||||
(when notification
|
||||
(rx/of (ntf/show {:content (tr notification (:name organization))
|
||||
:type :toast
|
||||
:level :info
|
||||
:timeout nil})))
|
||||
(when (:id organization)
|
||||
(check-team-sso current-team-id))))))
|
||||
ptk/UpdateEvent
|
||||
(update [_ state]
|
||||
(if (contains? cf/flags :nitrate)
|
||||
(let [team-id (:id team)
|
||||
team-name (:name team)
|
||||
organization (:organization team)]
|
||||
(d/update-in-when state [:teams team-id]
|
||||
(fn [team]
|
||||
(cond-> (co/apply-organization team organization)
|
||||
team-name (assoc :name team-name)))))
|
||||
state))))
|
||||
|
||||
(defn- handle-user-org-change
|
||||
[{:keys [organization-id organization-name notification]}]
|
||||
(ptk/reify ::handle-user-org-change
|
||||
@ -772,28 +729,16 @@
|
||||
(when fetch? ;; If the user belonged to the org
|
||||
(rx/of (dtm/fetch-teams)))))))))
|
||||
|
||||
(defn- handle-nitrate-change-sso
|
||||
[{:keys [organization-id]}]
|
||||
(ptk/reify ::handle-nitrate-change-sso
|
||||
ptk/WatchEvent
|
||||
(watch [_ state _]
|
||||
(when (contains? cf/flags :nitrate)
|
||||
(let [team-id (:current-team-id state)
|
||||
team (dm/get-in state [:teams team-id])
|
||||
org-id (dm/get-in team [:organization :id])]
|
||||
(when (= organization-id org-id)
|
||||
(check-team-sso team-id)))))))
|
||||
|
||||
(defn- process-message
|
||||
[{:keys [type] :as msg}]
|
||||
(case type
|
||||
:notification (dcm/handle-notification msg)
|
||||
:team-role-change (handle-change-team-role msg)
|
||||
:team-membership-change (dcm/team-membership-change msg)
|
||||
:team-org-change (handle-change-team-org msg)
|
||||
:team-org-change (dcm/handle-change-team-org msg)
|
||||
:user-org-change (handle-user-org-change msg)
|
||||
:organization-deleted (handle-organization-deleted msg)
|
||||
:organization-change-sso (handle-nitrate-change-sso msg)
|
||||
:organization-change-sso (dcm/handle-organization-change-sso msg)
|
||||
nil))
|
||||
|
||||
|
||||
|
||||
@ -125,18 +125,20 @@
|
||||
(defn- process-message
|
||||
[{:keys [type] :as msg}]
|
||||
(case type
|
||||
:join-file (handle-presence msg)
|
||||
:leave-file (handle-presence msg)
|
||||
:presence (handle-presence msg)
|
||||
:disconnect (handle-presence msg)
|
||||
:pointer-update (handle-pointer-update msg)
|
||||
:file-change (handle-file-change msg)
|
||||
:file-deleted (handle-file-deleted msg)
|
||||
:file-restored (handle-file-restored msg)
|
||||
:library-change (handle-library-change msg)
|
||||
:notification (dc/handle-notification msg)
|
||||
:team-role-change (handle-change-team-role msg)
|
||||
:team-membership-change (dc/team-membership-change msg)
|
||||
:join-file (handle-presence msg)
|
||||
:leave-file (handle-presence msg)
|
||||
:presence (handle-presence msg)
|
||||
:disconnect (handle-presence msg)
|
||||
:pointer-update (handle-pointer-update msg)
|
||||
:file-change (handle-file-change msg)
|
||||
:file-deleted (handle-file-deleted msg)
|
||||
:file-restored (handle-file-restored msg)
|
||||
:library-change (handle-library-change msg)
|
||||
:notification (dc/handle-notification msg)
|
||||
:team-role-change (handle-change-team-role msg)
|
||||
:team-membership-change (dc/team-membership-change msg)
|
||||
:team-org-change (dc/handle-change-team-org msg)
|
||||
:organization-change-sso (dc/handle-organization-change-sso msg)
|
||||
nil))
|
||||
|
||||
(defn- handle-pointer-send
|
||||
|
||||
@ -8,7 +8,7 @@
|
||||
(:require
|
||||
[app.common.uuid :as uuid]
|
||||
[app.config :as cf]
|
||||
[app.main.data.dashboard :as dd]
|
||||
[app.main.data.common :as dcm]
|
||||
[app.main.repo :as rp]
|
||||
[app.main.router :as rt]
|
||||
[beicon.v2.core :as rx]
|
||||
@ -23,7 +23,7 @@
|
||||
current-url (str "https://penpot.example.com/#/dashboard/recent?team-id=" team-id)
|
||||
redirect-url "https://idp.example.com/authorize"
|
||||
state {:current-team-id team-id}
|
||||
event (dd/handle-change-team-org
|
||||
event (dcm/handle-change-team-org
|
||||
{:team {:id team-id :organization organization}
|
||||
:notification nil})]
|
||||
(mock/with-mocks
|
||||
@ -48,3 +48,37 @@
|
||||
(fn []
|
||||
(done')))))
|
||||
done))))
|
||||
|
||||
(t/deftest organization-sso-activation-redirects-current-team
|
||||
(t/async done
|
||||
(let [team-id (uuid/next)
|
||||
org-id (uuid/next)
|
||||
current-url (str "https://penpot.example.com/#/workspace?team-id=" team-id)
|
||||
redirect-url "https://idp.example.com/authorize"
|
||||
state {:current-team-id team-id
|
||||
:teams {team-id {:id team-id
|
||||
:organization {:id org-id}}}}
|
||||
event (dcm/handle-organization-change-sso
|
||||
{:organization-id org-id})]
|
||||
(mock/with-mocks
|
||||
{cf/flags (conj cf/flags :nitrate)
|
||||
rp/cmd! (mock/stub
|
||||
(fn [cmd params]
|
||||
(if (= [:check-nitrate-sso
|
||||
{:team-id team-id :url current-url}]
|
||||
[cmd params])
|
||||
(rx/of {:authorized false :redirect-uri redirect-url})
|
||||
(rx/throw (ex-info "unexpected RPC" {:cmd cmd :params params})))))
|
||||
rt/get-current-href (mock/stub (constantly current-url))}
|
||||
(fn [done']
|
||||
(->> (ptk/watch event state nil)
|
||||
(rx/reduce conj [])
|
||||
(rx/subs!
|
||||
(fn [events]
|
||||
(t/is (= [::rt/nav-raw] (mapv ptk/type events))))
|
||||
(fn [error]
|
||||
(t/is false (str "unexpected error: " error))
|
||||
(done'))
|
||||
(fn []
|
||||
(done')))))
|
||||
done))))
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user