defmodule MusicLibraryWeb.ImportComponent do
use MusicLibraryWeb, :live_component
import MusicLibraryWeb.RecordComponents,
only: [toggle_actions_menu: 1, close_actions_menu: 1, format_label: 1, type_label: 1]
alias MusicBrainz.ReleaseGroupSearchResult
alias MusicLibrary.Records
@impl true
def render(assigns) do
~H"""
<.simple_form
for={@form}
id={:import_form}
phx-target={@myself}
phx-change="search"
phx-submit="search"
class="px-4"
>
<.input
id={:mb_query}
name={:mb_query}
field={@form[:mb_query]}
type="text"
label={gettext("Search for a record on MusicBrainz")}
prompt={gettext("Search for records")}
phx-debounce="500"
autocorrect="off"
autocapitalize="none"
autofocus
/>
-
{gettext("No results")}
<.result
:for={{id, release_group} <- @streams.release_groups}
id={id}
release_group={release_group}
icon_name={@icon_name}
/>
"""
end
attr :id, :string, required: true
attr :icon_name, :string, required: true
attr :release_group, MusicBrainz.ReleaseGroupSearchResult, required: true
defp result(assigns) do
~H"""
})
~p"/images/cover-not-found.png" <> "';"}
/>
{@release_group.artists}
{@release_group.title}
{Records.Record.format_release(@release_group.release)} ยท {type_label(@release_group.type)}
<.focus_wrap
id={"actions-#{@release_group.id}"}
class={[
"hidden pointer-events-auto absolute right-0 z-10 mt-2 w-48 origin-top-right rounded-md bg-white dark:bg-zinc-800 py-2 shadow-lg ring-1 ring-zinc-900/5 focus:outline-hidden"
]}
role="menu"
aria-orientation="vertical"
aria-labelledby="options-menu-0-button"
>
<.link
:for={format <- Records.Record.formats()}
class="block px-3 py-1 text-sm leading-6 text-zinc-900 dark:text-zinc-400 hover:bg-zinc-50 dark:hover:text-zinc-300 dark:hover:bg-zinc-700"
role="menuitem"
tabindex="0"
id={"actions-#{@release_group.id}-#{format}-import"}
phx-click={
JS.push("import", value: %{id: @release_group.id, format: format}, page_loading: true)
}
>
{format_label(format)}
"""
end
attr :type, :string, required: true
defp type_badge(assigns) do
~H"""
{@type}
"""
end
@impl true
def mount(socket) do
{:ok,
socket
|> stream_configure(:release_groups,
dom_id: fn rg -> "musicbrainz_#{rg.id}" end
)
|> stream(:release_groups, [])
|> assign(:form, to_form(%{"mb_query" => ""}))}
end
@impl true
def handle_event("search", %{"mb_query" => mb_query}, socket) do
{:ok, release_groups} = search(mb_query)
{:noreply,
socket
|> stream(:release_groups, release_groups, reset: true)
|> assign(:form, to_form(%{"mb_query" => mb_query}))}
end
defp search(""), do: {:ok, []}
defp search(mb_query) do
MusicBrainz.search_release_group(mb_query, limit: 10)
end
end