From 2de585aae6258c488a3ad9829ff21cd01a419a83 Mon Sep 17 00:00:00 2001 From: Kieran Eglin Date: Fri, 16 Feb 2024 15:08:54 -0800 Subject: [PATCH] [WIP] Created onboarding form --- lib/pinchflat/media.ex | 2 + lib/pinchflat/media_source.ex | 5 + lib/pinchflat/profiles.ex | 5 + lib/pinchflat/profiles/media_profile.ex | 2 +- lib/pinchflat_web.ex | 2 + .../custom_components/button_components.ex | 18 +- .../components/layouts/onboarding.html.heex | 18 ++ .../media_profile_controller.ex | 12 +- .../media_profile_form.html.heex | 16 +- .../media_profile_html/new.html.heex | 2 +- .../media_sources/source_controller.ex | 16 +- .../media_sources/source_html/new.html.heex | 2 +- .../source_html/source_form.html.heex | 8 +- .../controllers/page_controller.ex | 9 - .../controllers/page_html/home.html.heex | 202 ------------------ .../controllers/pages/page_controller.ex | 25 +++ .../controllers/{ => pages}/page_html.ex | 2 +- .../pages/page_html/home.html.heex | 1 + .../page_html/onboarding_checklist.html.heex | 50 +++++ lib/pinchflat_web/router.ex | 2 +- 20 files changed, 165 insertions(+), 234 deletions(-) create mode 100644 lib/pinchflat_web/components/layouts/onboarding.html.heex delete mode 100644 lib/pinchflat_web/controllers/page_controller.ex delete mode 100644 lib/pinchflat_web/controllers/page_html/home.html.heex create mode 100644 lib/pinchflat_web/controllers/pages/page_controller.ex rename lib/pinchflat_web/controllers/{ => pages}/page_html.ex (60%) create mode 100644 lib/pinchflat_web/controllers/pages/page_html/home.html.heex create mode 100644 lib/pinchflat_web/controllers/pages/page_html/onboarding_checklist.html.heex diff --git a/lib/pinchflat/media.ex b/lib/pinchflat/media.ex index cdd3fd6..100884c 100644 --- a/lib/pinchflat/media.ex +++ b/lib/pinchflat/media.ex @@ -100,6 +100,8 @@ defmodule Pinchflat.Media do field -> List.wrap(mapped_struct[field]) end) |> List.flatten() + # TODO: test + |> Enum.filter(&is_binary/1) end @doc """ diff --git a/lib/pinchflat/media_source.ex b/lib/pinchflat/media_source.ex index 46fab79..1bdb0a4 100644 --- a/lib/pinchflat/media_source.ex +++ b/lib/pinchflat/media_source.ex @@ -11,6 +11,11 @@ defmodule Pinchflat.MediaSource do alias Pinchflat.MediaSource.Source alias Pinchflat.MediaClient.SourceDetails + # TODO: test + def sources_exist? do + Repo.exists?(Source) + end + @doc """ Returns the list of sources. Returns [%Source{}, ...] """ diff --git a/lib/pinchflat/profiles.ex b/lib/pinchflat/profiles.ex index 01d78b4..ed6b372 100644 --- a/lib/pinchflat/profiles.ex +++ b/lib/pinchflat/profiles.ex @@ -8,6 +8,11 @@ defmodule Pinchflat.Profiles do alias Pinchflat.Profiles.MediaProfile + # TODO: test + def media_profiles_exist? do + Repo.exists?(MediaProfile) + end + @doc """ Returns the list of media_profiles. Returns [%MediaProfile{}, ...] """ diff --git a/lib/pinchflat/profiles/media_profile.ex b/lib/pinchflat/profiles/media_profile.ex index b765055..25bd38c 100644 --- a/lib/pinchflat/profiles/media_profile.ex +++ b/lib/pinchflat/profiles/media_profile.ex @@ -29,7 +29,7 @@ defmodule Pinchflat.Profiles.MediaProfile do schema "media_profiles" do field :name, :string - field :output_path_template, :string, default: "/{{ uploader }}/{{ title }}.{{ ext }}" + field :output_path_template, :string, default: "/{{ uploader }}/{{ title }}/{{ title }}-{{ id }}.{{ ext }}" field :download_subs, :boolean, default: true field :download_auto_subs, :boolean, default: true diff --git a/lib/pinchflat_web.ex b/lib/pinchflat_web.ex index 0ec628b..0df8659 100644 --- a/lib/pinchflat_web.ex +++ b/lib/pinchflat_web.ex @@ -45,6 +45,8 @@ defmodule PinchflatWeb do import Plug.Conn import PinchflatWeb.Gettext + alias PinchflatWeb.Layouts + unquote(verified_routes()) end end diff --git a/lib/pinchflat_web/components/custom_components/button_components.ex b/lib/pinchflat_web/components/custom_components/button_components.ex index 5949ae0..0240f3c 100644 --- a/lib/pinchflat_web/components/custom_components/button_components.ex +++ b/lib/pinchflat_web/components/custom_components/button_components.ex @@ -14,18 +14,22 @@ defmodule PinchflatWeb.CustomComponents.ButtonComponents do attr :color, :string, default: "bg-primary" attr :rounding, :string, default: "rounded-sm" attr :class, :string, default: "" + attr :disabled, :boolean, default: false slot :inner_block, required: true def button(assigns) do ~H""" - """ diff --git a/lib/pinchflat_web/components/layouts/onboarding.html.heex b/lib/pinchflat_web/components/layouts/onboarding.html.heex new file mode 100644 index 0000000..7228a33 --- /dev/null +++ b/lib/pinchflat_web/components/layouts/onboarding.html.heex @@ -0,0 +1,18 @@ +
+
+
+
+
+

Pinchflat

+
+
+
+ +
+
+ <.flash_group flash={@flash} /> + <%= @inner_content %> +
+
+
+
diff --git a/lib/pinchflat_web/controllers/media_profiles/media_profile_controller.ex b/lib/pinchflat_web/controllers/media_profiles/media_profile_controller.ex index 895b219..b95a75b 100644 --- a/lib/pinchflat_web/controllers/media_profiles/media_profile_controller.ex +++ b/lib/pinchflat_web/controllers/media_profiles/media_profile_controller.ex @@ -11,15 +11,23 @@ defmodule PinchflatWeb.MediaProfiles.MediaProfileController do def new(conn, _params) do changeset = Profiles.change_media_profile(%MediaProfile{}) - render(conn, :new, changeset: changeset) + + if get_session(conn, :onboarding) do + render(conn, :new, changeset: changeset, onboarding: true, layout: {Layouts, :onboarding}) + else + render(conn, :new, changeset: changeset, onboarding: false) + end end def create(conn, %{"media_profile" => media_profile_params}) do case Profiles.create_media_profile(media_profile_params) do {:ok, media_profile} -> + redirect_location = + if get_session(conn, :onboarding), do: ~p"/", else: ~p"/media_profiles/#{media_profile}" + conn |> put_flash(:info, "Media profile created successfully.") - |> redirect(to: ~p"/media_profiles/#{media_profile}") + |> redirect(to: redirect_location) {:error, %Ecto.Changeset{} = changeset} -> render(conn, :new, changeset: changeset) diff --git a/lib/pinchflat_web/controllers/media_profiles/media_profile_html/media_profile_form.html.heex b/lib/pinchflat_web/controllers/media_profiles/media_profile_html/media_profile_form.html.heex index cf82606..21c006c 100644 --- a/lib/pinchflat_web/controllers/media_profiles/media_profile_html/media_profile_form.html.heex +++ b/lib/pinchflat_web/controllers/media_profiles/media_profile_html/media_profile_form.html.heex @@ -27,7 +27,7 @@ field={f[:embed_subs]} type="toggle" label="Embed Subtitles" - help="Embeds subtitles in the video file itself, if supported" + help="Embeds subtitles in the video file itself, if supported (recommended)" /> <.input field={f[:sub_langs]} @@ -40,13 +40,23 @@ Thumbnail Options <.input field={f[:download_thumbnail]} type="toggle" label="Download Thumbnail" /> - <.input field={f[:embed_thumbnail]} type="toggle" label="Embed Thumbnail" /> + <.input + field={f[:embed_thumbnail]} + type="toggle" + label="Embed Thumbnail" + help="Embeds thumbnail in the video file itself, if supported (recommended)" + />

Metadata Options

<.input field={f[:download_metadata]} type="toggle" label="Download Metadata" /> - <.input field={f[:embed_metadata]} type="toggle" label="Embed Metadata" /> + <.input + field={f[:embed_metadata]} + type="toggle" + label="Embed Metadata" + help="Embeds metadata in the video file itself, if supported (recommended)" + />

Release Format Options diff --git a/lib/pinchflat_web/controllers/media_profiles/media_profile_html/new.html.heex b/lib/pinchflat_web/controllers/media_profiles/media_profile_html/new.html.heex index 9599619..800f8d2 100644 --- a/lib/pinchflat_web/controllers/media_profiles/media_profile_html/new.html.heex +++ b/lib/pinchflat_web/controllers/media_profiles/media_profile_html/new.html.heex @@ -1,5 +1,5 @@
- <.link navigate={~p"/media_profiles"}> + <.link :if={not @onboarding} navigate={~p"/media_profiles"}> <.icon name="hero-arrow-left" class="w-10 h-10 hover:dark:text-white" />

New Media Profile

diff --git a/lib/pinchflat_web/controllers/media_sources/source_controller.ex b/lib/pinchflat_web/controllers/media_sources/source_controller.ex index e4b28ad..7bc9a18 100644 --- a/lib/pinchflat_web/controllers/media_sources/source_controller.ex +++ b/lib/pinchflat_web/controllers/media_sources/source_controller.ex @@ -16,15 +16,27 @@ defmodule PinchflatWeb.MediaSources.SourceController do def new(conn, _params) do changeset = MediaSource.change_source(%Source{}) - render(conn, :new, changeset: changeset, media_profiles: media_profiles()) + if get_session(conn, :onboarding) do + render(conn, :new, + changeset: changeset, + media_profiles: media_profiles(), + onboarding: true, + layout: {Layouts, :onboarding} + ) + else + render(conn, :new, changeset: changeset, media_profiles: media_profiles(), onboarding: false) + end end def create(conn, %{"source" => source_params}) do case MediaSource.create_source(source_params) do {:ok, source} -> + redirect_location = + if get_session(conn, :onboarding), do: ~p"/", else: ~p"/sources/#{source}" + conn |> put_flash(:info, "Source created successfully.") - |> redirect(to: ~p"/sources/#{source}") + |> redirect(to: redirect_location) {:error, %Ecto.Changeset{} = changeset} -> render(conn, :new, changeset: changeset, media_profiles: media_profiles()) diff --git a/lib/pinchflat_web/controllers/media_sources/source_html/new.html.heex b/lib/pinchflat_web/controllers/media_sources/source_html/new.html.heex index 6bd86c1..2bc31ef 100644 --- a/lib/pinchflat_web/controllers/media_sources/source_html/new.html.heex +++ b/lib/pinchflat_web/controllers/media_sources/source_html/new.html.heex @@ -1,5 +1,5 @@
- <.link navigate={~p"/sources"}> + <.link :if={not @onboarding} navigate={~p"/sources"}> <.icon name="hero-arrow-left" class="w-10 h-10 hover:dark:text-white" />

New Source

diff --git a/lib/pinchflat_web/controllers/media_sources/source_html/source_form.html.heex b/lib/pinchflat_web/controllers/media_sources/source_html/source_form.html.heex index 4244d5d..28c5747 100644 --- a/lib/pinchflat_web/controllers/media_sources/source_html/source_form.html.heex +++ b/lib/pinchflat_web/controllers/media_sources/source_html/source_form.html.heex @@ -3,9 +3,9 @@ Oops, something went wrong! Please check the errors below. - <.input field={f[:original_url]} type="text" label="Source URL" help="URL of a channel or playlist (required)" /> + <.input field={f[:friendly_name]} type="text" label="Custom Name" /> - <.input field={f[:friendly_name]} type="text" label="Friendly Name" /> + <.input field={f[:original_url]} type="text" label="Source URL" help="URL of a channel or playlist (required)" /> <.input field={f[:media_profile_id]} @@ -21,14 +21,14 @@ options={friendly_index_frequencies()} type="select" label="Index Frequency" - help="Roughly how often to check for media to download" + help="The time between one index of this source finishing and the next one starting" /> <.input field={f[:download_media]} type="toggle" label="Download Media?" - help="Unchecking still indexes media but it won't be downloaded" + help="Unchecking still indexes media but it won't be downloaded until you enable this option" /> <:actions> diff --git a/lib/pinchflat_web/controllers/page_controller.ex b/lib/pinchflat_web/controllers/page_controller.ex deleted file mode 100644 index 816b6cf..0000000 --- a/lib/pinchflat_web/controllers/page_controller.ex +++ /dev/null @@ -1,9 +0,0 @@ -defmodule PinchflatWeb.PageController do - use PinchflatWeb, :controller - - def home(conn, _params) do - # The home page is often custom made, - # so skip the default app layout. - render(conn, :home) - end -end diff --git a/lib/pinchflat_web/controllers/page_html/home.html.heex b/lib/pinchflat_web/controllers/page_html/home.html.heex deleted file mode 100644 index 5aa726d..0000000 --- a/lib/pinchflat_web/controllers/page_html/home.html.heex +++ /dev/null @@ -1,202 +0,0 @@ -<.flash_group flash={@flash} /> - -
-
- -

- Phoenix Framework - - v<%= Application.spec(:phoenix, :vsn) %> - -

-

- Peace of mind from prototype to production. -

-

- Build rich, interactive web applications quickly, with less code and fewer moving parts. Join our growing community of developers using Phoenix to craft APIs, HTML5 apps and more, for fun or at scale. -

- -
-
diff --git a/lib/pinchflat_web/controllers/pages/page_controller.ex b/lib/pinchflat_web/controllers/pages/page_controller.ex new file mode 100644 index 0000000..4a91110 --- /dev/null +++ b/lib/pinchflat_web/controllers/pages/page_controller.ex @@ -0,0 +1,25 @@ +defmodule PinchflatWeb.Pages.PageController do + use PinchflatWeb, :controller + + alias Pinchflat.Profiles + alias Pinchflat.MediaSource + + def home(conn, _params) do + media_profiles_exist = Profiles.media_profiles_exist?() + sources_exist = MediaSource.sources_exist?() + + if media_profiles_exist && sources_exist do + conn + |> put_session(:onboarding, false) + |> render(:home) + else + conn + |> put_session(:onboarding, true) + |> render(:onboarding_checklist, + media_profiles_exist: media_profiles_exist, + sources_exist: sources_exist, + layout: {Layouts, :onboarding} + ) + end + end +end diff --git a/lib/pinchflat_web/controllers/page_html.ex b/lib/pinchflat_web/controllers/pages/page_html.ex similarity index 60% rename from lib/pinchflat_web/controllers/page_html.ex rename to lib/pinchflat_web/controllers/pages/page_html.ex index de29b52..16f7731 100644 --- a/lib/pinchflat_web/controllers/page_html.ex +++ b/lib/pinchflat_web/controllers/pages/page_html.ex @@ -1,4 +1,4 @@ -defmodule PinchflatWeb.PageHTML do +defmodule PinchflatWeb.Pages.PageHTML do use PinchflatWeb, :html embed_templates "page_html/*" diff --git a/lib/pinchflat_web/controllers/pages/page_html/home.html.heex b/lib/pinchflat_web/controllers/pages/page_html/home.html.heex new file mode 100644 index 0000000..5ed529e --- /dev/null +++ b/lib/pinchflat_web/controllers/pages/page_html/home.html.heex @@ -0,0 +1 @@ +

hey

diff --git a/lib/pinchflat_web/controllers/pages/page_html/onboarding_checklist.html.heex b/lib/pinchflat_web/controllers/pages/page_html/onboarding_checklist.html.heex new file mode 100644 index 0000000..6e35142 --- /dev/null +++ b/lib/pinchflat_web/controllers/pages/page_html/onboarding_checklist.html.heex @@ -0,0 +1,50 @@ +
+
+
+
+

Welcome to Pinchflat

+

Getting started is easy

+
+
+

1. Create a Media Profile

+

Media Profiles set your preferences for fetching and downloading media.

+
+ <.link navigate={~p"/media_profiles/new"}> + <.button color="bg-primary" rounding="rounded-full" disabled={@media_profiles_exist}> + + New Media Profile + + +
+
+
+

2. Create a Source

+

Sources are the channels and playlists you want to download.

+

+ Each Media Profile can control many Sources so it's easy to add more content! +

+
+ <.link navigate={~p"/sources/new"}> + <.button color="bg-primary" rounding="rounded-full" disabled={not @media_profiles_exist}> + + New Source + + +
+
+
+

3. That's it!

+

Everything is set up and running based on your preferences.

+

+ Remember that indexing and downloading media can take a while, many hours for a large source. +

+

Feel free to add more Media Profiles or Sources in the meantime!

+
+ <.link navigate={~p"/"}> + <.button color="bg-primary" rounding="rounded-full" disabled={not @sources_exist}> + Let's Go 🚀 + + +
+
+
+
+
diff --git a/lib/pinchflat_web/router.ex b/lib/pinchflat_web/router.ex index 0470029..9ec45b6 100644 --- a/lib/pinchflat_web/router.ex +++ b/lib/pinchflat_web/router.ex @@ -17,7 +17,7 @@ defmodule PinchflatWeb.Router do scope "/", PinchflatWeb do pipe_through :browser - get "/", PageController, :home + get "/", Pages.PageController, :home resources "/media_profiles", MediaProfiles.MediaProfileController resources "/search", Searches.SearchController, only: [:show], singleton: true