Skip to content

Commit

Permalink
create episodes in frontend
Browse files Browse the repository at this point in the history
  • Loading branch information
lukad committed May 19, 2024
1 parent 77f47ce commit ab9e771
Show file tree
Hide file tree
Showing 5 changed files with 84 additions and 43 deletions.
20 changes: 4 additions & 16 deletions lib/radiator/podcast.ex
Original file line number Diff line number Diff line change
Expand Up @@ -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 """
Expand Down
50 changes: 50 additions & 0 deletions lib/radiator_web/live/episode_live/index.ex
Original file line number Diff line number Diff line change
Expand Up @@ -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
Expand All @@ -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

Expand Down Expand Up @@ -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},
Expand Down
27 changes: 26 additions & 1 deletion lib/radiator_web/live/episode_live/index.html.heex
Original file line number Diff line number Diff line change
@@ -1,8 +1,13 @@
<div class="grid grid-cols-12 gap-24">
<aside class="col-span-12 sm:col-span-4">
<button class="block w-full my-4 rounded text-white bg-[#df7366] px-8 py-2">
<button
:if={@action != :new_episode}
class="block w-full my-4 rounded text-white bg-[#df7366] px-8 py-2"
phx-click="new_episode"
>
Create Episode
</button>

<ol>
<li
:for={{episode, i} <- Enum.with_index(@episodes)}
Expand All @@ -16,6 +21,26 @@
</li>
</ol>
</aside>

<section :if={@action == :new_episode} class="col-span-12 sm:col-span-8">
<div class="p-4 my-4 bg-[#f0f4f4]">
<h3 class="text-xl">Create Episode</h3>
<.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" />
<div class="flex items-center justify-between gap-6 mt-2">
<div
class="px-3 py-2 text-sm font-semibold leading-6 border rounded-lg cursor-pointer phx-submit-loading:opacity-75 border-zinc-900 hover:border-zinc-700 text-zinc-900 active:text-zinc-900/80"
phx-click="cancel"
>
Cancel
</div>
<.button phx-disable-with="Saving...">Save Episode</.button>
</div>
</.form>
</div>
</section>

<section :if={@selected_episode} class="col-span-12 sm:col-span-8">
<h2 class="text-2xl"><%= @selected_episode.number %> <%= @selected_episode.title %></h2>
<img class="my-4" src={~p"/images/pic06.jpg"} alt="" />
Expand Down
26 changes: 1 addition & 25 deletions test/radiator/podcast_test.exs
Original file line number Diff line number Diff line change
Expand Up @@ -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

Expand Down
4 changes: 3 additions & 1 deletion test/support/fixtures/podcast_fixtures.ex
Original file line number Diff line number Diff line change
Expand Up @@ -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()

Expand Down

0 comments on commit ab9e771

Please sign in to comment.