From ab9e77132c8289b6160f8d05d2ad4d98077634df Mon Sep 17 00:00:00 2001 From: Luka Dornhecker Date: Sun, 19 May 2024 22:56:28 +0200 Subject: [PATCH] create episodes in frontend --- lib/radiator/podcast.ex | 20 ++------ lib/radiator_web/live/episode_live/index.ex | 50 +++++++++++++++++++ .../live/episode_live/index.html.heex | 27 +++++++++- test/radiator/podcast_test.exs | 26 +--------- test/support/fixtures/podcast_fixtures.ex | 4 +- 5 files changed, 84 insertions(+), 43 deletions(-) diff --git a/lib/radiator/podcast.ex b/lib/radiator/podcast.ex index d9b779af..f4c60b19 100644 --- a/lib/radiator/podcast.ex +++ b/lib/radiator/podcast.ex @@ -297,31 +297,19 @@ defmodule Radiator.Podcast do """ def create_episode(attrs \\ %{}) do - attrs_with_number = set_number(attrs) - %Episode{} - |> Episode.changeset(attrs_with_number) + |> Episode.changeset(attrs) |> Repo.insert() end - defp set_number(%{number: _number} = attrs), do: attrs - - defp set_number(%{show_id: show_id} = episode_attrs) do - number = get_highest_number(show_id) + 1 - Map.put(episode_attrs, :number, number) - end - - defp set_number(%{} = episode_attrs) do - Map.put(episode_attrs, :number, 0) - end - - defp get_highest_number(show_id) do + def get_next_episode_number(show_id) do query = from e in Episode, select: max(e.number), where: [show_id: ^show_id] - Repo.one(query) || 0 + max_number = Repo.one(query) || 0 + max_number + 1 end @doc """ diff --git a/lib/radiator_web/live/episode_live/index.ex b/lib/radiator_web/live/episode_live/index.ex index 6402c35b..cf8dda68 100644 --- a/lib/radiator_web/live/episode_live/index.ex +++ b/lib/radiator_web/live/episode_live/index.ex @@ -4,6 +4,7 @@ defmodule RadiatorWeb.EpisodeLive.Index do alias Radiator.Outline.{Dispatch, NodeRepository} alias Radiator.Outline.Event.{NodeContentChangedEvent, NodeDeletedEvent, NodeInsertedEvent} alias Radiator.Podcast + alias Radiator.Podcast.Episode @impl true def mount(%{"show" => show_id}, _session, socket) do @@ -14,6 +15,7 @@ defmodule RadiatorWeb.EpisodeLive.Index do # |> assign(:page_description, "") |> assign(:show, show) |> assign(:episodes, show.episodes) + |> assign(action: nil, episode: nil, form: nil) |> reply(:ok) end @@ -75,6 +77,54 @@ defmodule RadiatorWeb.EpisodeLive.Index do |> reply(:noreply) end + def handle_event("new_episode", _params, socket) do + show = socket.assigns.show + number = Podcast.get_next_episode_number(show.id) + + episode = %Podcast.Episode{} + changeset = Episode.changeset(episode, %{number: number}) + + socket + |> assign(:action, :new_episode) + |> assign(:episode, episode) + |> assign(:form, to_form(changeset)) + |> reply(:noreply) + end + + @impl true + def handle_event("validate", %{"episode" => params}, socket) do + changeset = socket.assigns.episode |> Episode.changeset(params) |> Map.put(:action, :validate) + + socket + |> assign(:form, to_form(changeset)) + |> reply(:noreply) + end + + @impl true + def handle_event("save", %{"episode" => params}, socket) do + show_id = socket.assigns.show.id + + params = Map.put(params, "show_id", show_id) + + case Podcast.create_episode(params) do + {:ok, episode} -> + show = Podcast.get_show!(show_id, preload: :episodes) + + socket + |> assign(:action, nil) + |> assign(:episodes, show.episodes) + |> put_flash(:info, "Episode created successfully") + |> push_patch(to: ~p"/admin/podcast/#{show}/#{episode}") + |> reply(:noreply) + + {:error, %Ecto.Changeset{} = changeset} -> + socket + |> assign(:form, to_form(changeset)) + |> put_flash(:info, "Episode could not be created") + |> reply(:noreply) + end + end + @impl true def handle_info( %{node: node, event_id: <<_::binary-size(36)>> <> ":" <> id}, diff --git a/lib/radiator_web/live/episode_live/index.html.heex b/lib/radiator_web/live/episode_live/index.html.heex index 295ae610..0dd0099f 100644 --- a/lib/radiator_web/live/episode_live/index.html.heex +++ b/lib/radiator_web/live/episode_live/index.html.heex @@ -1,8 +1,13 @@
+ +
+
+

Create Episode

+ <.form :let={f} for={@form} id="episode-form" phx-change="validate" phx-submit="save"> + <.input field={f[:number]} type="text" label="Number" /> + <.input field={f[:title]} type="text" label="Title" /> +
+
+ Cancel +
+ <.button phx-disable-with="Saving...">Save Episode +
+ +
+
+

<%= @selected_episode.number %> <%= @selected_episode.title %>

diff --git a/test/radiator/podcast_test.exs b/test/radiator/podcast_test.exs index b751c825..beaaf46e 100644 --- a/test/radiator/podcast_test.exs +++ b/test/radiator/podcast_test.exs @@ -140,35 +140,11 @@ defmodule Radiator.PodcastTest do test "create_episode/1 with valid data creates a episode" do show = show_fixture() - valid_attrs = %{title: "some title", show_id: show.id} + valid_attrs = %{title: "some title", show_id: show.id, number: 5} assert {:ok, %Episode{} = episode} = Podcast.create_episode(valid_attrs) assert episode.title == "some title" assert episode.show_id == show.id - end - - test "create_episode/1 sets for first episode number 1" do - episode_attrs = %{title: "a new episode", show_id: show_fixture().id} - - {:ok, %Episode{} = episode} = Podcast.create_episode(episode_attrs) - assert episode.number > 0 - end - - test "create_episode/1 finds the next highest number " do - show = show_fixture() - episode_fixture(show_id: show.id, number: 23) - episode_attrs = %{title: "my new episode", show_id: show.id} - - {:ok, %Episode{} = episode} = Podcast.create_episode(episode_attrs) - assert episode.number == 24 - end - - test "create_episode/1 can be set explict" do - show = show_fixture() - episode_fixture(show_id: show.id, number: 2) - episode_attrs = %{title: "my new episode", number: 5, show_id: show.id} - - {:ok, %Episode{} = episode} = Podcast.create_episode(episode_attrs) assert episode.number == 5 end diff --git a/test/support/fixtures/podcast_fixtures.ex b/test/support/fixtures/podcast_fixtures.ex index 0c592060..17a35d6a 100644 --- a/test/support/fixtures/podcast_fixtures.ex +++ b/test/support/fixtures/podcast_fixtures.ex @@ -41,12 +41,14 @@ defmodule Radiator.PodcastFixtures do """ def episode_fixture(attrs \\ %{}) do show = get_show(attrs) + number = Podcast.get_next_episode_number(show.id) {:ok, episode} = attrs |> Enum.into(%{ title: "my show episode 23", - show_id: show.id + show_id: show.id, + number: number }) |> Podcast.create_episode()