defmodule VaccinsWeb.LocationComponent do use VaccinsWeb, :live_component alias Vaccins.{LocationStore, Search} @impl true def mount(socket), do: {:ok, socket |> assign( has_availabilities: false, slots_after: [], slots_before: [], loading: false )} @impl true def update(assigns, socket) do {force_refresh, assigns} = assigns |> Map.pop(:force_refresh) assigns = assigns |> integrate_availabilities if is_nil(force_refresh) do {:ok, socket |> assign(assigns) |> assign(loading: false)} else trigger_and_signal_query( assigns |> Map.get(:location, socket.assigns.location), assigns.id ) {:ok, socket |> assign(assigns) |> assign(loading: true)} end end @impl true def handle_event("trigger_query", _, socket = %{assigns: %{id: id, location: location}}) do trigger_and_signal_query(location, id) {:noreply, socket |> assign(loading: true)} end @impl true def render(assigns) do ~L"""
id
<%= @location.id %>
Status
<%= cond do %> <%= @loading -> %>... <%= not has_slots?(assigns) -> %>Pas de créneau <%= has_slots?(assigns) -> %>Des dispos ! <% end %>
booking page
<%= link @location.booking_page, to: @location.booking_page %>
<%= if has_slots?(assigns) do %>
Avant 24h
Après 24h
<% end %>
test availability
""" end defp integrate_availabilities(assigns = %{availabilities: {:error, reason}}), do: assigns |> Map.put(:has_availabilities, false) defp integrate_availabilities(assigns = %{availabilities: {:ok, after_slots}}) when is_list(after_slots), do: assigns |> Map.put(:has_availabilities, true) |> Map.put(:slots_after, after_slots |> Enum.take(5)) defp integrate_availabilities(assigns = %{availabilities: {:ok, before_slots, after_slots}}) when is_list(before_slots), do: assigns |> Map.put(:has_availabilities, true) |> Map.put(:slots_after, after_slots |> Enum.take(5)) |> Map.put(:slots_before, before_slots) defp integrate_availabilities(assigns), do: assigns defp has_slots?(assigns = %{slots_before: before, slots_after: after_}), do: not (before |> Enum.empty?() and after_ |> Enum.empty?()) defp trigger_and_signal_query(location, id) do ref = Search.async_trigger_query(location) send(self(), {:query_sent, id, ref}) end end