Skip to content

Commit

Permalink
Implement basic team switcher
Browse files Browse the repository at this point in the history
  • Loading branch information
zoldar committed Feb 6, 2025
1 parent a7cba82 commit 5fb8b28
Show file tree
Hide file tree
Showing 5 changed files with 119 additions and 1 deletion.
13 changes: 13 additions & 0 deletions lib/plausible/teams/users.ex
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,19 @@ defmodule Plausible.Teams.Users do
)
end

def teams(user) do
from(
tm in Teams.Membership,
inner_join: t in assoc(tm, :team),
where: tm.user_id == ^user.id,
where: tm.role != :guest,
select: t,
order_by: [t.name, t.id]
)
|> Repo.all()
|> Repo.preload(:owners)
end

def team_member?(user, opts \\ []) do
excluded_team_ids = Keyword.get(opts, :except, [])

Expand Down
66 changes: 65 additions & 1 deletion lib/plausible_web/controllers/auth_controller.ex
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ defmodule PlausibleWeb.AuthController do
use Plausible.Repo

alias Plausible.Auth
alias Plausible.Teams
alias PlausibleWeb.TwoFactor
alias PlausibleWeb.UserAuth

Expand Down Expand Up @@ -33,7 +34,9 @@ defmodule PlausibleWeb.AuthController do
:verify_2fa_setup_form,
:verify_2fa_setup,
:disable_2fa,
:generate_2fa_recovery_codes
:generate_2fa_recovery_codes,
:select_team,
:switch_team
]
)

Expand All @@ -52,6 +55,67 @@ defmodule PlausibleWeb.AuthController do
TwoFactor.Session.clear_2fa_user(conn)
end

def select_team(conn, _params) do
current_user = conn.assigns.current_user

owner_name_fn = fn owner ->
if owner.id == current_user.id do
"You"
else
owner.name
end
end

teams =
current_user
|> Teams.Users.teams()
|> Enum.map(fn team ->
current_team? = team.id == conn.assigns.current_team.id

owners =
Enum.map_join(team.owners, ", ", &owner_name_fn.(&1))

many_owners? = length(team.owners) > 1

%{
identifier: team.identifier,
name: team.name,
current?: current_team?,
many_owners?: many_owners?,
owners: owners
}
end)

render(conn, "select_team.html", teams: teams)
end

def switch_team(conn, params) do
current_user = conn.assigns.current_user
team = Teams.get(params["team_id"])

if team do
case Teams.Memberships.team_role(team, current_user) do
{:ok, role} when role != :guest ->
conn
|> put_session("current_team_id", team.identifier)
|> put_flash(
:success,
"You have switched to \"#{conn.assigns.current_team.name}\" team"
)
|> redirect(to: Routes.site_path(conn, :index))

_ ->
conn
|> put_flash(:error, "You have select an invalid team")
|> redirect(to: Routes.site_path(conn, :index))
end
else
conn
|> put_flash(:error, "You have select an invalid team")
|> redirect(to: Routes.site_path(conn, :index))
end
end

def activate_form(conn, params) do
user = conn.assigns.current_user
flow = params["flow"] || PlausibleWeb.Flows.register()
Expand Down
3 changes: 3 additions & 0 deletions lib/plausible_web/router.ex
Original file line number Diff line number Diff line change
Expand Up @@ -400,6 +400,9 @@ defmodule PlausibleWeb.Router do
get "/logout", AuthController, :logout
delete "/me", AuthController, :delete_me

get "/team/select", AuthController, :select_team
post "/team/select/:team_id", AuthController, :switch_team

get "/auth/google/callback", AuthController, :google_auth_callback

on_ee do
Expand Down
29 changes: 29 additions & 0 deletions lib/plausible_web/templates/auth/select_team.html.heex
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
<.focus_box>
<:title>Switch Team</:title>

<:subtitle>Switch your current team.</:subtitle>

<div>
<ul>
<li :for={team <- @teams} class={if team.current?, do: ["border-l m-2"], else: ["m-2"]}>
<.unstyled_link
method={if team.current?, do: "get", else: "post"}
href={
if team.current?,
do: "#",
else: Routes.auth_path(@conn, :switch_team, team.identifier)
}
>
<div class="hover:bg-gray-700 p-4">
<p class="truncate font-medium text-gray-900 dark:text-gray-100" role="none">
{team.name}
</p>
<p class="text-xs text-gray-500 dark:text-gray-400">
Owner{if team.many_owners?, do: "s"}: {team.owners}
</p>
</div>
</.unstyled_link>
</li>
</ul>
</div>
</.focus_box>
9 changes: 9 additions & 0 deletions lib/plausible_web/templates/layout/_header.html.heex
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,15 @@
{@conn.assigns[:current_user].email}
</p>
</.dropdown_item>
<.dropdown_item :if={@conn.assigns[:current_team]}>
<div class="text-xs text-gray-500 dark:text-gray-400">Team</div>
<p class="truncate font-medium text-gray-900 dark:text-gray-100" role="none">
{@current_team.name}
</p>
</.dropdown_item>
<.dropdown_item href={Routes.auth_path(@conn, :select_team)}>
Switch Team
</.dropdown_item>
<.dropdown_divider />
<.dropdown_item href={Routes.settings_path(@conn, :index)}>
Account Settings
Expand Down

0 comments on commit 5fb8b28

Please sign in to comment.