Use Enum for scrobble rule type

This commit is contained in:
Claudio Ortolina
2025-07-04 14:23:19 +01:00
parent 81f0ec8830
commit aee08cc2bb
7 changed files with 36 additions and 39 deletions
+9 -9
View File
@@ -152,7 +152,7 @@ defmodule MusicLibrary.ScrobbleRules do
{:error, :invalid_rule_type} {:error, :invalid_rule_type}
""" """
def apply_album_rule(%ScrobbleRule{type: "album"} = rule) do def apply_album_rule(%ScrobbleRule{type: :album} = rule) do
update_query = update_query =
from(t in Track, from(t in Track,
where: fragment("json_extract(?, '$.title') = ?", t.album, ^rule.match_value), where: fragment("json_extract(?, '$.title') = ?", t.album, ^rule.match_value),
@@ -186,7 +186,7 @@ defmodule MusicLibrary.ScrobbleRules do
{:error, :invalid_rule_type} {:error, :invalid_rule_type}
""" """
def apply_artist_rule(%ScrobbleRule{type: "artist"} = rule) do def apply_artist_rule(%ScrobbleRule{type: :artist} = rule) do
update_query = update_query =
from(t in Track, from(t in Track,
where: fragment("json_extract(?, '$.name') = ?", t.artist, ^rule.match_value), where: fragment("json_extract(?, '$.name') = ?", t.artist, ^rule.match_value),
@@ -220,11 +220,11 @@ defmodule MusicLibrary.ScrobbleRules do
{:error, "Invalid rule type"} {:error, "Invalid rule type"}
""" """
def apply_rule(%ScrobbleRule{type: "album"} = rule) do def apply_rule(%ScrobbleRule{type: :album} = rule) do
apply_album_rule(rule) apply_album_rule(rule)
end end
def apply_rule(%ScrobbleRule{type: "artist"} = rule) do def apply_rule(%ScrobbleRule{type: :artist} = rule) do
apply_artist_rule(rule) apply_artist_rule(rule)
end end
@@ -234,7 +234,7 @@ defmodule MusicLibrary.ScrobbleRules do
## Examples ## Examples
iex> apply_all_rules() iex> apply_all_rules()
{:ok, [{"album", 5}, {"artist", 10}]} {:ok, [{:album, 5}, {:artist, 10}]}
""" """
def apply_all_rules do def apply_all_rules do
@@ -257,7 +257,7 @@ defmodule MusicLibrary.ScrobbleRules do
5 5
""" """
def count_album_matches(%ScrobbleRule{type: "album"} = rule) do def count_album_matches(%ScrobbleRule{type: :album} = rule) do
query = query =
from(t in Track, from(t in Track,
where: fragment("json_extract(?, '$.title') = ?", t.album, ^rule.match_value), where: fragment("json_extract(?, '$.title') = ?", t.album, ^rule.match_value),
@@ -276,7 +276,7 @@ defmodule MusicLibrary.ScrobbleRules do
10 10
""" """
def count_artist_matches(%ScrobbleRule{type: "artist"} = rule) do def count_artist_matches(%ScrobbleRule{type: :artist} = rule) do
query = query =
from(t in Track, from(t in Track,
where: fragment("json_extract(?, '$.name') = ?", t.artist, ^rule.match_value), where: fragment("json_extract(?, '$.name') = ?", t.artist, ^rule.match_value),
@@ -295,11 +295,11 @@ defmodule MusicLibrary.ScrobbleRules do
5 5
""" """
def count_rule_matches(%ScrobbleRule{type: "album"} = rule) do def count_rule_matches(%ScrobbleRule{type: :album} = rule) do
count_album_matches(rule) count_album_matches(rule)
end end
def count_rule_matches(%ScrobbleRule{type: "artist"} = rule) do def count_rule_matches(%ScrobbleRule{type: :artist} = rule) do
count_artist_matches(rule) count_artist_matches(rule)
end end
end end
@@ -5,7 +5,7 @@ defmodule MusicLibrary.ScrobbleRules.ScrobbleRule do
@type t :: %__MODULE__{ @type t :: %__MODULE__{
id: integer() | nil, id: integer() | nil,
type: String.t(), type: :album | :artist,
match_value: String.t(), match_value: String.t(),
target_musicbrainz_id: String.t(), target_musicbrainz_id: String.t(),
enabled: boolean(), enabled: boolean(),
@@ -14,10 +14,8 @@ defmodule MusicLibrary.ScrobbleRules.ScrobbleRule do
updated_at: NaiveDateTime.t() | nil updated_at: NaiveDateTime.t() | nil
} }
@valid_types ~w(album artist)
schema "scrobble_rules" do schema "scrobble_rules" do
field :type, :string field :type, Ecto.Enum, values: [:album, :artist]
field :match_value, :string field :match_value, :string
field :target_musicbrainz_id, Ecto.UUID field :target_musicbrainz_id, Ecto.UUID
field :enabled, :boolean, default: true field :enabled, :boolean, default: true
@@ -31,6 +29,5 @@ defmodule MusicLibrary.ScrobbleRules.ScrobbleRule do
scrobble_rule scrobble_rule
|> cast(attrs, [:type, :match_value, :target_musicbrainz_id, :enabled, :description]) |> cast(attrs, [:type, :match_value, :target_musicbrainz_id, :enabled, :description])
|> validate_required([:type, :match_value, :target_musicbrainz_id]) |> validate_required([:type, :match_value, :target_musicbrainz_id])
|> validate_inclusion(:type, @valid_types)
end end
end end
@@ -24,8 +24,8 @@ defmodule MusicLibraryWeb.ScrobbleRulesLive.FormComponent do
field={@form[:type]} field={@form[:type]}
label={gettext("Rule Type")} label={gettext("Rule Type")}
options={[ options={[
{gettext("Album"), "album"}, {gettext("Album"), :album},
{gettext("Artist"), "artist"} {gettext("Artist"), :artist}
]} ]}
placeholder={gettext("Select a rule type")} placeholder={gettext("Select a rule type")}
/> />
@@ -119,17 +119,17 @@ defmodule MusicLibraryWeb.ScrobbleRulesLive.FormComponent do
defp match_value_label(type) do defp match_value_label(type) do
case type do case type do
"album" -> gettext("Album Title") :album -> gettext("Album Title")
"artist" -> gettext("Artist Name") :artist -> gettext("Artist Name")
_ -> gettext("Match Value") _other -> gettext("Match Value")
end end
end end
defp match_value_placeholder(type) do defp match_value_placeholder(type) do
case type do case type do
"album" -> gettext("e.g. The Dark Side of the Moon") :album -> gettext("e.g. The Dark Side of the Moon")
"artist" -> gettext("e.g. Pink Floyd") :artist -> gettext("e.g. Pink Floyd")
_ -> gettext("Enter the value to match") _other -> gettext("Enter the value to match")
end end
end end
end end
@@ -6,7 +6,7 @@ defmodule MusicLibrary.ScrobbleRules.ScrobbleRuleTest do
describe "changeset/2" do describe "changeset/2" do
test "valid changeset with all required fields" do test "valid changeset with all required fields" do
attrs = %{ attrs = %{
type: "album", type: :album,
match_value: "Dark Side of the Moon", match_value: "Dark Side of the Moon",
target_musicbrainz_id: "12345678-1234-1234-1234-123456789012", target_musicbrainz_id: "12345678-1234-1234-1234-123456789012",
enabled: true, enabled: true,
@@ -19,7 +19,7 @@ defmodule MusicLibrary.ScrobbleRules.ScrobbleRuleTest do
test "valid changeset with minimal required fields" do test "valid changeset with minimal required fields" do
attrs = %{ attrs = %{
type: "artist", type: :artist,
match_value: "Pink Floyd", match_value: "Pink Floyd",
target_musicbrainz_id: "12345678-1234-1234-1234-123456789012" target_musicbrainz_id: "12345678-1234-1234-1234-123456789012"
} }
@@ -42,7 +42,7 @@ defmodule MusicLibrary.ScrobbleRules.ScrobbleRuleTest do
test "invalid changeset when match_value is missing" do test "invalid changeset when match_value is missing" do
attrs = %{ attrs = %{
type: "artist", type: :artist,
target_musicbrainz_id: "12345678-1234-1234-1234-123456789012" target_musicbrainz_id: "12345678-1234-1234-1234-123456789012"
} }
@@ -53,7 +53,7 @@ defmodule MusicLibrary.ScrobbleRules.ScrobbleRuleTest do
test "invalid changeset when target_musicbrainz_id is missing" do test "invalid changeset when target_musicbrainz_id is missing" do
attrs = %{ attrs = %{
type: "artist", type: :artist,
match_value: "Pink Floyd" match_value: "Pink Floyd"
} }
@@ -64,7 +64,7 @@ defmodule MusicLibrary.ScrobbleRules.ScrobbleRuleTest do
test "invalid changeset when type is not album or artist" do test "invalid changeset when type is not album or artist" do
attrs = %{ attrs = %{
type: "invalid_type", type: :invalid_type,
match_value: "Pink Floyd", match_value: "Pink Floyd",
target_musicbrainz_id: "12345678-1234-1234-1234-123456789012" target_musicbrainz_id: "12345678-1234-1234-1234-123456789012"
} }
@@ -76,7 +76,7 @@ defmodule MusicLibrary.ScrobbleRules.ScrobbleRuleTest do
test "invalid changeset when match_value is empty" do test "invalid changeset when match_value is empty" do
attrs = %{ attrs = %{
type: "artist", type: :artist,
match_value: "", match_value: "",
target_musicbrainz_id: "12345678-1234-1234-1234-123456789012" target_musicbrainz_id: "12345678-1234-1234-1234-123456789012"
} }
@@ -88,7 +88,7 @@ defmodule MusicLibrary.ScrobbleRules.ScrobbleRuleTest do
test "invalid changeset when target_musicbrainz_id is empty" do test "invalid changeset when target_musicbrainz_id is empty" do
attrs = %{ attrs = %{
type: "artist", type: :artist,
match_value: "Pink Floyd", match_value: "Pink Floyd",
target_musicbrainz_id: "" target_musicbrainz_id: ""
} }
@@ -100,7 +100,7 @@ defmodule MusicLibrary.ScrobbleRules.ScrobbleRuleTest do
test "invalid changeset when target_musicbrainz_id is not a valid UUID" do test "invalid changeset when target_musicbrainz_id is not a valid UUID" do
attrs = %{ attrs = %{
type: "artist", type: :artist,
match_value: "Pink Floyd", match_value: "Pink Floyd",
target_musicbrainz_id: "invalid-uuid" target_musicbrainz_id: "invalid-uuid"
} }
@@ -113,7 +113,7 @@ defmodule MusicLibrary.ScrobbleRules.ScrobbleRuleTest do
test "valid changeset with uppercase UUID" do test "valid changeset with uppercase UUID" do
attrs = %{ attrs = %{
type: "artist", type: :artist,
match_value: "Pink Floyd", match_value: "Pink Floyd",
target_musicbrainz_id: "12345678-1234-1234-1234-123456789012" target_musicbrainz_id: "12345678-1234-1234-1234-123456789012"
} }
@@ -124,7 +124,7 @@ defmodule MusicLibrary.ScrobbleRules.ScrobbleRuleTest do
test "valid changeset with lowercase UUID" do test "valid changeset with lowercase UUID" do
attrs = %{ attrs = %{
type: "artist", type: :artist,
match_value: "Pink Floyd", match_value: "Pink Floyd",
target_musicbrainz_id: "abcdefab-abcd-abcd-abcd-abcdefabcdef" target_musicbrainz_id: "abcdefab-abcd-abcd-abcd-abcdefabcdef"
} }
+1 -1
View File
@@ -88,7 +88,7 @@ defmodule MusicLibrary.ScrobbleRulesTest do
assert {:ok, %ScrobbleRule{} = scrobble_rule} = assert {:ok, %ScrobbleRule{} = scrobble_rule} =
ScrobbleRules.create_scrobble_rule(valid_attrs) ScrobbleRules.create_scrobble_rule(valid_attrs)
assert scrobble_rule.type == "album" assert scrobble_rule.type == :album
assert scrobble_rule.match_value == "Dark Side of the Moon" assert scrobble_rule.match_value == "Dark Side of the Moon"
assert scrobble_rule.target_musicbrainz_id == "12345678-1234-1234-1234-123456789012" assert scrobble_rule.target_musicbrainz_id == "12345678-1234-1234-1234-123456789012"
assert scrobble_rule.enabled == true assert scrobble_rule.enabled == true
@@ -9,14 +9,14 @@ defmodule MusicLibraryWeb.ScrobbleRulesLiveTest do
# Test data # Test data
@invalid_attrs %{type: "", match_value: "", target_musicbrainz_id: ""} @invalid_attrs %{type: "", match_value: "", target_musicbrainz_id: ""}
@valid_attrs %{ @valid_attrs %{
type: "album", type: :album,
match_value: "some match_value", match_value: "some match_value",
target_musicbrainz_id: "12345678-1234-1234-1234-123456789012", target_musicbrainz_id: "12345678-1234-1234-1234-123456789012",
description: "some description", description: "some description",
enabled: "true" enabled: "true"
} }
@update_attrs %{ @update_attrs %{
type: "artist", type: :artist,
match_value: "some updated match_value", match_value: "some updated match_value",
target_musicbrainz_id: "87654321-4321-4321-4321-210987654321", target_musicbrainz_id: "87654321-4321-4321-4321-210987654321",
description: "some updated description" description: "some updated description"
@@ -157,7 +157,7 @@ defmodule MusicLibraryWeb.ScrobbleRulesLiveTest do
assert index_live assert index_live
|> form("#scrobble_rule-form", |> form("#scrobble_rule-form",
scrobble_rule: %{ scrobble_rule: %{
type: "album", type: :album,
match_value: "Test Album", match_value: "Test Album",
target_musicbrainz_id: "invalid-uuid" target_musicbrainz_id: "invalid-uuid"
} }
@@ -173,7 +173,7 @@ defmodule MusicLibraryWeb.ScrobbleRulesLiveTest do
# Select album type # Select album type
html = html =
index_live index_live
|> form("#scrobble_rule-form", scrobble_rule: %{type: "album"}) |> form("#scrobble_rule-form", scrobble_rule: %{type: :album})
|> render_change() |> render_change()
assert html =~ "Album Title" assert html =~ "Album Title"
@@ -181,7 +181,7 @@ defmodule MusicLibraryWeb.ScrobbleRulesLiveTest do
# Select artist type # Select artist type
html = html =
index_live index_live
|> form("#scrobble_rule-form", scrobble_rule: %{type: "artist"}) |> form("#scrobble_rule-form", scrobble_rule: %{type: :artist})
|> render_change() |> render_change()
assert html =~ "Artist Name" assert html =~ "Artist Name"
@@ -11,7 +11,7 @@ defmodule MusicLibrary.ScrobbleRulesFixtures do
""" """
def scrobble_rule_fixture(attrs \\ %{}) do def scrobble_rule_fixture(attrs \\ %{}) do
default_attrs = %{ default_attrs = %{
type: "album", type: :album,
match_value: "Dark Side of the Moon", match_value: "Dark Side of the Moon",
target_musicbrainz_id: "12345678-1234-1234-1234-123456789012", target_musicbrainz_id: "12345678-1234-1234-1234-123456789012",
enabled: true, enabled: true,