2.6 KiB · text History 6280797
defmodule GitGudWeb.SymsLive.Show do
@moduledoc """
The repositories a user has marked with one symbol.
"""
use GitGudWeb, :live_view
alias GitGud.Accounts
alias GitGud.Repositories.Storage
alias GitGud.Syms
@impl true
def mount(%{"handle" => handle, "sym" => sym}, _session, socket) do
user = Accounts.get_user_by_handle(handle)
cond do
is_nil(user) ->
{:ok, socket |> put_flash(:error, "User not found.") |> push_navigate(to: ~p"/")}
# A symbol this instance doesn't configure has no page, whether it
# was retired or never existed.
not Syms.known?(sym) ->
{:ok,
socket
|> put_flash(:error, "No such symbol on this instance.")
|> push_navigate(to: ~p"/u/#{handle}/syms")}
true ->
viewer = socket.assigns.current_scope && socket.assigns.current_scope.user
repos = user |> Syms.list_marked(sym) |> Enum.filter(&readable?(&1, viewer))
{:ok,
socket
|> assign(:user, user)
|> assign(:sym, sym)
|> assign(:repos, repos)
|> assign(:page_title, "@#{user.handle}: #{sym}")}
end
end
# Marked repos can belong to anyone, so this is a per-repo check, not
# "does the viewer own the marking user's repos".
defp readable?(%{visibility: v}, _viewer) when v in ["public", "internal"], do: true
defp readable?(%{owner_id: oid}, %{id: oid}), do: true
defp readable?(_, _), do: false
@impl true
def render(assigns) do
~H"""
<Layouts.app flash={@flash} current_scope={@current_scope}>
<div class="space-y-4 max-w-2xl">
<h1 class="text-xl font-semibold flex items-center gap-2">
<.link navigate={~p"/u/#{@user.handle}"} class="link link-hover">
@{@user.handle}
</.link>
<span class="opacity-50">/</span>
<.link navigate={~p"/u/#{@user.handle}/syms"} class="link link-hover">syms</.link>
<span class="opacity-50">/</span>
<span class="text-2xl leading-none">{@sym}</span>
</h1>
<p :if={@repos == []} class="text-sm opacity-60">
Nothing marked {@sym} yet.
</p>
<ul class="divide-y divide-base-300">
<li :for={repo <- @repos} class="py-3">
<.link
navigate={~p"/r/#{Storage.repo_handle(repo)}/#{repo.name}"}
class="font-medium link link-hover"
>
{Storage.repo_handle(repo)}/{repo.name}
</.link>
<p :if={repo.description} class="text-xs opacity-60">{repo.description}</p>
</li>
</ul>
</div>
</Layouts.app>
"""
end
end