diff --git a/assets/js/burger.js b/assets/js/burger.js index c76e5ae8..c7a573f4 100644 --- a/assets/js/burger.js +++ b/assets/js/burger.js @@ -26,7 +26,7 @@ function close(burger, content, body, root) { }, 300); } -function copyUserLinksTo(burger) { +function copyArtistLinksTo(burger) { const copy = links => { burger.appendChild(document.createElement('hr')); @@ -50,7 +50,7 @@ function setupBurgerMenu() { const body = document.body; const root = document.documentElement; - copyUserLinksTo(burger); + copyArtistLinksTo(burger); toggle.addEventListener('click', event => { event.stopPropagation(); diff --git a/docker/app/run-development b/docker/app/run-development index d76bcfc3..ebd5d481 100755 --- a/docker/app/run-development +++ b/docker/app/run-development @@ -3,7 +3,7 @@ background() { while :; do mix run -e 'Philomena.Release.update_channels()' - mix run -e 'Philomena.Release.verify_user_links()' + mix run -e 'Philomena.Release.verify_artist_links()' mix run -e 'Philomena.Release.update_stats()' sleep 300 diff --git a/lib/philomena/artist_links.ex b/lib/philomena/artist_links.ex new file mode 100644 index 00000000..48af30ca --- /dev/null +++ b/lib/philomena/artist_links.ex @@ -0,0 +1,185 @@ +defmodule Philomena.ArtistLinks do + @moduledoc """ + The ArtistLinks context. + """ + + import Ecto.Query, warn: false + alias Ecto.Multi + alias Philomena.Repo + + alias Philomena.ArtistLinks.ArtistLink + alias Philomena.ArtistLinks.AutomaticVerifier + alias Philomena.Badges.Badge + alias Philomena.Badges.Award + alias Philomena.Tags.Tag + + @doc """ + Check links pending verification to see if the user placed + the appropriate code on the page. + """ + def automatic_verify! do + now = DateTime.utc_now() |> DateTime.truncate(:second) + + # Automatically retry in an hour if we don't manage to + # successfully verify any given link + recheck_time = DateTime.add(now, 3600, :second) + + recheck_query = + from ul in ArtistLink, + where: ul.aasm_state == "unverified", + where: ul.next_check_at < ^now + + recheck_query + |> Repo.all() + |> Enum.map(fn link -> + ArtistLink.automatic_verify_changeset(link, AutomaticVerifier.check_link(link, recheck_time)) + end) + |> Enum.map(&Repo.update!/1) + end + + @doc """ + Gets a single artist_link. + + Raises `Ecto.NoResultsError` if the Artist link does not exist. + + ## Examples + + iex> get_artist_link!(123) + %ArtistLink{} + + iex> get_artist_link!(456) + ** (Ecto.NoResultsError) + + """ + def get_artist_link!(id), do: Repo.get!(ArtistLink, id) + + @doc """ + Creates a artist_link. + + ## Examples + + iex> create_artist_link(%{field: value}) + {:ok, %ArtistLink{}} + + iex> create_artist_link(%{field: bad_value}) + {:error, %Ecto.Changeset{}} + + """ + def create_artist_link(user, attrs \\ %{}) do + tag = fetch_tag(attrs["tag_name"]) + + %ArtistLink{} + |> ArtistLink.creation_changeset(attrs, user, tag) + |> Repo.insert() + end + + @doc """ + Updates a artist_link. + + ## Examples + + iex> update_artist_link(artist_link, %{field: new_value}) + {:ok, %ArtistLink{}} + + iex> update_artist_link(artist_link, %{field: bad_value}) + {:error, %Ecto.Changeset{}} + + """ + def update_artist_link(%ArtistLink{} = artist_link, attrs) do + tag = fetch_tag(attrs["tag_name"]) + + artist_link + |> ArtistLink.edit_changeset(attrs, tag) + |> Repo.update() + end + + def verify_artist_link(%ArtistLink{} = artist_link, user) do + artist_link_changeset = + artist_link + |> ArtistLink.verify_changeset(user) + + Multi.new() + |> Multi.update(:artist_link, artist_link_changeset) + |> Multi.run(:add_award, fn repo, _changes -> + now = DateTime.utc_now() |> DateTime.truncate(:second) + + with badge when not is_nil(badge) <- repo.get_by(limit(Badge, 1), title: "Artist"), + nil <- repo.get_by(limit(Award, 1), badge_id: badge.id, user_id: artist_link.user_id) do + %Award{ + badge_id: badge.id, + user_id: artist_link.user_id, + awarded_by_id: user.id, + awarded_on: now + } + |> Award.changeset(%{}) + |> repo.insert() + else + _ -> + {:ok, nil} + end + end) + |> Repo.transaction() + end + + def reject_artist_link(%ArtistLink{} = artist_link) do + artist_link + |> ArtistLink.reject_changeset() + |> Repo.update() + end + + def contact_artist_link(%ArtistLink{} = artist_link, user) do + artist_link + |> ArtistLink.contact_changeset(user) + |> Repo.update() + end + + @doc """ + Deletes a ArtistLink. + + ## Examples + + iex> delete_artist_link(artist_link) + {:ok, %ArtistLink{}} + + iex> delete_artist_link(artist_link) + {:error, %Ecto.Changeset{}} + + """ + def delete_artist_link(%ArtistLink{} = artist_link) do + Repo.delete(artist_link) + end + + @doc """ + Returns an `%Ecto.Changeset{}` for tracking artist_link changes. + + ## Examples + + iex> change_artist_link(artist_link) + %Ecto.Changeset{source: %ArtistLink{}} + + """ + def change_artist_link(%ArtistLink{} = artist_link) do + ArtistLink.changeset(artist_link, %{}) + end + + def count_artist_links(user) do + if Canada.Can.can?(user, :index, %ArtistLink{}) do + ArtistLink + |> where([ul], ul.aasm_state in ^["unverified", "link_verified", "contacted"]) + |> Repo.aggregate(:count, :id) + else + nil + end + end + + defp fetch_tag(name) do + Tag + |> preload(:aliased_tag) + |> where(name: ^name) + |> Repo.one() + |> case do + nil -> nil + tag -> tag.aliased_tag || tag + end + end +end diff --git a/lib/philomena/user_links/user_link.ex b/lib/philomena/artist_links/artist_link.ex similarity index 70% rename from lib/philomena/user_links/user_link.ex rename to lib/philomena/artist_links/artist_link.ex index 2f670fcd..1cc91307 100644 --- a/lib/philomena/user_links/user_link.ex +++ b/lib/philomena/artist_links/artist_link.ex @@ -1,4 +1,4 @@ -defmodule Philomena.UserLinks.UserLink do +defmodule Philomena.ArtistLinks.ArtistLink do use Ecto.Schema import Ecto.Changeset @@ -24,59 +24,69 @@ defmodule Philomena.UserLinks.UserLink do end @doc false - def changeset(user_link, attrs) do - user_link + def changeset(artist_link, attrs) do + artist_link |> cast(attrs, []) |> validate_required([]) end - def edit_changeset(user_link, attrs, nil) do - user_link + def edit_changeset(artist_link, attrs, nil) do + artist_link |> cast(attrs, [:uri, :public]) |> put_change(:tag_id, nil) |> validate_required([:user, :uri, :public]) |> parse_uri() end - def edit_changeset(user_link, attrs, tag) do - user_link + def edit_changeset(artist_link, attrs, tag) do + artist_link |> cast(attrs, [:uri, :public]) |> put_change(:tag_id, tag.id) |> validate_required([:user, :uri, :public]) |> parse_uri() end - def creation_changeset(user_link, attrs, user, tag) do - user_link + def creation_changeset(artist_link, attrs, user, tag) do + artist_link |> cast(attrs, [:uri, :public]) |> put_assoc(:tag, tag) |> put_assoc(:user, user) |> validate_required([:user, :uri, :public]) |> validate_required([:tag], message: "must exist") |> validate_format(:uri, ~r|\Ahttps?://|) + |> validate_category() |> parse_uri() |> put_verification_code() |> put_next_check_at() end - def reject_changeset(user_link) do - change(user_link, aasm_state: "rejected") + def validate_category(changeset) do + tag = get_field(changeset, :tag) + + case tag.category in ["origin", "content-fanmade"] do + false -> add_error(changeset, :tag, "must be a creator tag") + true -> changeset + end end - def automatic_verify_changeset(user_link, attrs) do - cast(user_link, attrs, [:next_check_at, :aasm_state]) + def reject_changeset(artist_link) do + change(artist_link, aasm_state: "rejected") end - def verify_changeset(user_link, user) do - change(user_link) + def automatic_verify_changeset(artist_link, attrs) do + cast(artist_link, attrs, [:next_check_at, :aasm_state]) + end + + def verify_changeset(artist_link, user) do + change(artist_link) |> put_change(:verified_by_user_id, user.id) |> put_change(:aasm_state, "verified") end - def contact_changeset(user_link, user) do + def contact_changeset(artist_link, user) do now = DateTime.utc_now() |> DateTime.truncate(:second) - change(user_link) + change(artist_link) |> put_change(:contacted_by_user_id, user.id) |> put_change(:contacted_at, now) |> put_change(:aasm_state, "contacted") diff --git a/lib/philomena/user_links/automatic_verifier.ex b/lib/philomena/artist_links/automatic_verifier.ex similarity index 67% rename from lib/philomena/user_links/automatic_verifier.ex rename to lib/philomena/artist_links/automatic_verifier.ex index 7cd3e6b5..1fd303a4 100644 --- a/lib/philomena/user_links/automatic_verifier.ex +++ b/lib/philomena/artist_links/automatic_verifier.ex @@ -1,8 +1,8 @@ -defmodule Philomena.UserLinks.AutomaticVerifier do - def check_link(user_link, recheck_time) do - user_link.uri +defmodule Philomena.ArtistLinks.AutomaticVerifier do + def check_link(artist_link, recheck_time) do + artist_link.uri |> Philomena.Http.get() - |> contains_verification_code?(user_link.verification_code) + |> contains_verification_code?(artist_link.verification_code) |> case do true -> %{next_check_at: nil, aasm_state: "link_verified"} diff --git a/lib/philomena/images/dnp_validator.ex b/lib/philomena/images/dnp_validator.ex index 7e7ea2ab..9652b7b7 100644 --- a/lib/philomena/images/dnp_validator.ex +++ b/lib/philomena/images/dnp_validator.ex @@ -3,7 +3,7 @@ defmodule Philomena.Images.DnpValidator do import Ecto.Query alias Philomena.Repo alias Philomena.Tags.Tag - alias Philomena.UserLinks.UserLink + alias Philomena.ArtistLinks.ArtistLink def validate_dnp(changeset, uploader) do tags = @@ -60,7 +60,7 @@ defmodule Philomena.Images.DnpValidator do defp valid_user?(_dnp_entry, nil), do: false defp valid_user?(dnp_entry, user) do - UserLink + ArtistLink |> where(tag_id: ^dnp_entry.tag_id) |> where(aasm_state: "verified") |> where(user_id: ^user.id) diff --git a/lib/philomena/release.ex b/lib/philomena/release.ex index 6ee19331..4820775d 100644 --- a/lib/philomena/release.ex +++ b/lib/philomena/release.ex @@ -19,9 +19,9 @@ defmodule Philomena.Release do Philomena.Channels.update_tracked_channels!() end - def verify_user_links do + def verify_artist_links do start_app() - Philomena.UserLinks.automatic_verify!() + Philomena.ArtistLinks.automatic_verify!() end def update_stats do diff --git a/lib/philomena/tags.ex b/lib/philomena/tags.ex index 6e2c513d..a1523bc4 100644 --- a/lib/philomena/tags.ex +++ b/lib/philomena/tags.ex @@ -14,7 +14,7 @@ defmodule Philomena.Tags do alias Philomena.Users.User alias Philomena.Filters.Filter alias Philomena.Images.Tagging - alias Philomena.UserLinks.UserLink + alias Philomena.ArtistLinks.ArtistLink alias Philomena.DnpEntries.DnpEntry alias Philomena.Channels.Channel @@ -228,7 +228,7 @@ defmodule Philomena.Tags do |> Repo.delete_all() # Update other assocations - UserLink + ArtistLink |> where(tag_id: ^tag.id) |> Repo.update_all(set: [tag_id: target_tag.id]) diff --git a/lib/philomena/tags/tag.ex b/lib/philomena/tags/tag.ex index 15be1017..6cd3b108 100644 --- a/lib/philomena/tags/tag.ex +++ b/lib/philomena/tags/tag.ex @@ -5,7 +5,7 @@ defmodule Philomena.Tags.Tag do alias Philomena.Channels.Channel alias Philomena.DnpEntries.DnpEntry - alias Philomena.UserLinks.UserLink + alias Philomena.ArtistLinks.ArtistLink alias Philomena.Tags.Tag alias Philomena.Slug alias Philomena.Repo @@ -68,8 +68,8 @@ defmodule Philomena.Tags.Tag do join_through: "tags_implied_tags", join_keys: [implied_tag_id: :id, tag_id: :id] - has_many :public_links, UserLink, where: [public: true, aasm_state: "verified"] - has_many :hidden_links, UserLink, where: [public: false, aasm_state: "verified"] + has_many :public_links, ArtistLink, where: [public: true, aasm_state: "verified"] + has_many :hidden_links, ArtistLink, where: [public: false, aasm_state: "verified"] has_many :dnp_entries, DnpEntry, where: [aasm_state: "listed"] field :slug, :string diff --git a/lib/philomena/user_links.ex b/lib/philomena/user_links.ex deleted file mode 100644 index 6609939f..00000000 --- a/lib/philomena/user_links.ex +++ /dev/null @@ -1,185 +0,0 @@ -defmodule Philomena.UserLinks do - @moduledoc """ - The UserLinks context. - """ - - import Ecto.Query, warn: false - alias Ecto.Multi - alias Philomena.Repo - - alias Philomena.UserLinks.UserLink - alias Philomena.UserLinks.AutomaticVerifier - alias Philomena.Badges.Badge - alias Philomena.Badges.Award - alias Philomena.Tags.Tag - - @doc """ - Check links pending verification to see if the user placed - the appropriate code on the page. - """ - def automatic_verify! do - now = DateTime.utc_now() |> DateTime.truncate(:second) - - # Automatically retry in an hour if we don't manage to - # successfully verify any given link - recheck_time = DateTime.add(now, 3600, :second) - - recheck_query = - from ul in UserLink, - where: ul.aasm_state == "unverified", - where: ul.next_check_at < ^now - - recheck_query - |> Repo.all() - |> Enum.map(fn link -> - UserLink.automatic_verify_changeset(link, AutomaticVerifier.check_link(link, recheck_time)) - end) - |> Enum.map(&Repo.update!/1) - end - - @doc """ - Gets a single user_link. - - Raises `Ecto.NoResultsError` if the User link does not exist. - - ## Examples - - iex> get_user_link!(123) - %UserLink{} - - iex> get_user_link!(456) - ** (Ecto.NoResultsError) - - """ - def get_user_link!(id), do: Repo.get!(UserLink, id) - - @doc """ - Creates a user_link. - - ## Examples - - iex> create_user_link(%{field: value}) - {:ok, %UserLink{}} - - iex> create_user_link(%{field: bad_value}) - {:error, %Ecto.Changeset{}} - - """ - def create_user_link(user, attrs \\ %{}) do - tag = fetch_tag(attrs["tag_name"]) - - %UserLink{} - |> UserLink.creation_changeset(attrs, user, tag) - |> Repo.insert() - end - - @doc """ - Updates a user_link. - - ## Examples - - iex> update_user_link(user_link, %{field: new_value}) - {:ok, %UserLink{}} - - iex> update_user_link(user_link, %{field: bad_value}) - {:error, %Ecto.Changeset{}} - - """ - def update_user_link(%UserLink{} = user_link, attrs) do - tag = fetch_tag(attrs["tag_name"]) - - user_link - |> UserLink.edit_changeset(attrs, tag) - |> Repo.update() - end - - def verify_user_link(%UserLink{} = user_link, user) do - user_link_changeset = - user_link - |> UserLink.verify_changeset(user) - - Multi.new() - |> Multi.update(:user_link, user_link_changeset) - |> Multi.run(:add_award, fn repo, _changes -> - now = DateTime.utc_now() |> DateTime.truncate(:second) - - with badge when not is_nil(badge) <- repo.get_by(limit(Badge, 1), title: "Artist"), - nil <- repo.get_by(limit(Award, 1), badge_id: badge.id, user_id: user_link.user_id) do - %Award{ - badge_id: badge.id, - user_id: user_link.user_id, - awarded_by_id: user.id, - awarded_on: now - } - |> Award.changeset(%{}) - |> repo.insert() - else - _ -> - {:ok, nil} - end - end) - |> Repo.transaction() - end - - def reject_user_link(%UserLink{} = user_link) do - user_link - |> UserLink.reject_changeset() - |> Repo.update() - end - - def contact_user_link(%UserLink{} = user_link, user) do - user_link - |> UserLink.contact_changeset(user) - |> Repo.update() - end - - @doc """ - Deletes a UserLink. - - ## Examples - - iex> delete_user_link(user_link) - {:ok, %UserLink{}} - - iex> delete_user_link(user_link) - {:error, %Ecto.Changeset{}} - - """ - def delete_user_link(%UserLink{} = user_link) do - Repo.delete(user_link) - end - - @doc """ - Returns an `%Ecto.Changeset{}` for tracking user_link changes. - - ## Examples - - iex> change_user_link(user_link) - %Ecto.Changeset{source: %UserLink{}} - - """ - def change_user_link(%UserLink{} = user_link) do - UserLink.changeset(user_link, %{}) - end - - def count_user_links(user) do - if Canada.Can.can?(user, :index, %UserLink{}) do - UserLink - |> where([ul], ul.aasm_state in ^["unverified", "link_verified", "contacted"]) - |> Repo.aggregate(:count, :id) - else - nil - end - end - - defp fetch_tag(name) do - Tag - |> preload(:aliased_tag) - |> where(name: ^name) - |> Repo.one() - |> case do - nil -> nil - tag -> tag.aliased_tag || tag - end - end -end diff --git a/lib/philomena/users/ability.ex b/lib/philomena/users/ability.ex index 22c384b0..c755af6a 100644 --- a/lib/philomena/users/ability.ex +++ b/lib/philomena/users/ability.ex @@ -17,7 +17,7 @@ defimpl Canada.Can, for: [Atom, Philomena.Users.User] do alias Philomena.Filters.Filter alias Philomena.Galleries.Gallery alias Philomena.DnpEntries.DnpEntry - alias Philomena.UserLinks.UserLink + alias Philomena.ArtistLinks.ArtistLink alias Philomena.Tags.Tag alias Philomena.TagChanges.TagChange alias Philomena.Reports.Report @@ -76,11 +76,11 @@ defimpl Canada.Can, for: [Atom, Philomena.Users.User] do def can?(%User{role: "moderator"}, :show, %Report{}), do: true def can?(%User{role: "moderator"}, :edit, %Report{}), do: true - # Manage user links + # Manage artist links def can?(%User{role: "moderator"}, :create_links, %User{}), do: true def can?(%User{role: "moderator"}, :edit_links, %User{}), do: true - def can?(%User{role: "moderator"}, _action, UserLink), do: true - def can?(%User{role: "moderator"}, _action, %UserLink{}), do: true + def can?(%User{role: "moderator"}, _action, ArtistLink), do: true + def can?(%User{role: "moderator"}, _action, %ArtistLink{}), do: true # Reveal anon users def can?(%User{role: "moderator"}, :reveal_anon, _object), do: true @@ -262,24 +262,24 @@ defimpl Canada.Can, for: [Atom, Philomena.Users.User] do def can?(%User{role: "assistant", role_map: %{"Tag" => "moderator"}}, :batch_update, Tag), do: true - # User link assistant actions - def can?(%User{role: "assistant", role_map: %{"UserLink" => "moderator"}}, _action, %UserLink{}), + # Artist link assistant actions + def can?(%User{role: "assistant", role_map: %{"ArtistLink" => "moderator"}}, _action, %ArtistLink{}), do: true def can?( - %User{role: "assistant", role_map: %{"UserLink" => "moderator"}}, + %User{role: "assistant", role_map: %{"ArtistLink" => "moderator"}}, :create_links, %User{} ), do: true - def can?(%User{role: "assistant", role_map: %{"UserLink" => "moderator"}}, :edit, %UserLink{}), + def can?(%User{role: "assistant", role_map: %{"ArtistLink" => "moderator"}}, :edit, %ArtistLink{}), do: true - def can?(%User{role: "assistant", role_map: %{"UserLink" => "moderator"}}, :edit_links, %User{}), + def can?(%User{role: "assistant", role_map: %{"ArtistLink" => "moderator"}}, :edit_links, %User{}), do: true - def can?(%User{role: "assistant", role_map: %{"UserLink" => "moderator"}}, :index, %UserLink{}), + def can?(%User{role: "assistant", role_map: %{"ArtistLink" => "moderator"}}, :index, %ArtistLink{}), do: true # View forums @@ -322,9 +322,9 @@ defimpl Canada.Can, for: [Atom, Philomena.Users.User] do def can?(%User{id: id}, action, %Filter{user_id: id}) when action in [:edit, :update, :delete], do: true - # View user links they've created + # View artist links they've created def can?(%User{id: id}, :create_links, %User{id: id}), do: true - def can?(%User{id: id}, :show, %UserLink{user_id: id}), do: true + def can?(%User{id: id}, :show, %ArtistLink{user_id: id}), do: true # Edit their commissions def can?(%User{id: id}, action, %Commission{user_id: id}) diff --git a/lib/philomena/users/user.ex b/lib/philomena/users/user.ex index 719d45b6..1a085461 100644 --- a/lib/philomena/users/user.ex +++ b/lib/philomena/users/user.ex @@ -9,7 +9,7 @@ defmodule Philomena.Users.User do alias Philomena.Schema.Search alias Philomena.Filters.Filter - alias Philomena.UserLinks.UserLink + alias Philomena.ArtistLinks.ArtistLink alias Philomena.Badges alias Philomena.Notifications.UnreadNotification alias Philomena.Galleries.Gallery @@ -24,9 +24,9 @@ defmodule Philomena.Users.User do @derive {Phoenix.Param, key: :slug} @derive {Inspect, except: [:password]} schema "users" do - has_many :links, UserLink - has_many :verified_links, UserLink, where: [aasm_state: "verified"] - has_many :public_links, UserLink, where: [public: true, aasm_state: "verified"] + has_many :links, ArtistLink + has_many :verified_links, ArtistLink, where: [aasm_state: "verified"] + has_many :public_links, ArtistLink, where: [public: true, aasm_state: "verified"] has_many :galleries, Gallery, foreign_key: :creator_id has_many :awards, Badges.Award has_many :unread_notifications, UnreadNotification diff --git a/lib/philomena_web/controllers/admin/artist_link/contact_controller.ex b/lib/philomena_web/controllers/admin/artist_link/contact_controller.ex new file mode 100644 index 00000000..ce7d87a1 --- /dev/null +++ b/lib/philomena_web/controllers/admin/artist_link/contact_controller.ex @@ -0,0 +1,22 @@ +defmodule PhilomenaWeb.Admin.ArtistLink.ContactController do + use PhilomenaWeb, :controller + + alias Philomena.ArtistLinks.ArtistLink + alias Philomena.ArtistLinks + + plug PhilomenaWeb.CanaryMapPlug, create: :edit + + plug :load_and_authorize_resource, + model: ArtistLink, + id_name: "artist_link_id", + persisted: true, + preload: [:user] + + def create(conn, _params) do + {:ok, _} = ArtistLinks.contact_artist_link(conn.assigns.artist_link, conn.assigns.current_user) + + conn + |> put_flash(:info, "Artist successfully marked as contacted.") + |> redirect(to: Routes.admin_artist_link_path(conn, :index)) + end +end diff --git a/lib/philomena_web/controllers/admin/artist_link/reject_controller.ex b/lib/philomena_web/controllers/admin/artist_link/reject_controller.ex new file mode 100644 index 00000000..7c1dbca3 --- /dev/null +++ b/lib/philomena_web/controllers/admin/artist_link/reject_controller.ex @@ -0,0 +1,22 @@ +defmodule PhilomenaWeb.Admin.ArtistLink.RejectController do + use PhilomenaWeb, :controller + + alias Philomena.ArtistLinks.ArtistLink + alias Philomena.ArtistLinks + + plug PhilomenaWeb.CanaryMapPlug, create: :edit + + plug :load_and_authorize_resource, + model: ArtistLink, + id_name: "artist_link_id", + persisted: true, + preload: [:user] + + def create(conn, _params) do + {:ok, _} = ArtistLinks.reject_artist_link(conn.assigns.artist_link) + + conn + |> put_flash(:info, "Artist link successfully marked as rejected.") + |> redirect(to: Routes.admin_artist_link_path(conn, :index)) + end +end diff --git a/lib/philomena_web/controllers/admin/artist_link/verification_controller.ex b/lib/philomena_web/controllers/admin/artist_link/verification_controller.ex new file mode 100644 index 00000000..0b7d7d8e --- /dev/null +++ b/lib/philomena_web/controllers/admin/artist_link/verification_controller.ex @@ -0,0 +1,22 @@ +defmodule PhilomenaWeb.Admin.ArtistLink.VerificationController do + use PhilomenaWeb, :controller + + alias Philomena.ArtistLinks.ArtistLink + alias Philomena.ArtistLinks + + plug PhilomenaWeb.CanaryMapPlug, create: :edit + + plug :load_and_authorize_resource, + model: ArtistLink, + id_name: "artist_link_id", + persisted: true, + preload: [:user] + + def create(conn, _params) do + {:ok, _} = ArtistLinks.verify_artist_link(conn.assigns.artist_link, conn.assigns.current_user) + + conn + |> put_flash(:info, "Artist link successfully verified.") + |> redirect(to: Routes.admin_artist_link_path(conn, :index)) + end +end diff --git a/lib/philomena_web/controllers/admin/user_link_controller.ex b/lib/philomena_web/controllers/admin/artist_link_controller.ex similarity index 74% rename from lib/philomena_web/controllers/admin/user_link_controller.ex rename to lib/philomena_web/controllers/admin/artist_link_controller.ex index 36e04644..298dba81 100644 --- a/lib/philomena_web/controllers/admin/user_link_controller.ex +++ b/lib/philomena_web/controllers/admin/artist_link_controller.ex @@ -1,27 +1,27 @@ -defmodule PhilomenaWeb.Admin.UserLinkController do +defmodule PhilomenaWeb.Admin.ArtistLinkController do use PhilomenaWeb, :controller - alias Philomena.UserLinks.UserLink + alias Philomena.ArtistLinks.ArtistLink alias Philomena.Repo import Ecto.Query plug :verify_authorized def index(conn, %{"all" => _value}) do - load_links(UserLink, conn) + load_links(ArtistLink, conn) end def index(conn, %{"q" => query}) do query = "%#{query}%" - UserLink + ArtistLink |> join(:inner, [ul], _ in assoc(ul, :user)) |> where([ul, u], ilike(u.name, ^query) or ilike(ul.uri, ^query)) |> load_links(conn) end def index(conn, _params) do - UserLink + ArtistLink |> where([u], u.aasm_state in ^["unverified", "link_verified", "contacted"]) |> load_links(conn) end @@ -38,11 +38,11 @@ defmodule PhilomenaWeb.Admin.UserLinkController do ]) |> Repo.paginate(conn.assigns.scrivener) - render(conn, "index.html", title: "Admin - User Links", user_links: links) + render(conn, "index.html", title: "Admin - Artist Links", artist_links: links) end defp verify_authorized(conn, _opts) do - case Canada.Can.can?(conn.assigns.current_user, :index, %UserLink{}) do + case Canada.Can.can?(conn.assigns.current_user, :index, %ArtistLink{}) do true -> conn false -> PhilomenaWeb.NotAuthorizedPlug.call(conn) end diff --git a/lib/philomena_web/controllers/admin/user_link/contact_controller.ex b/lib/philomena_web/controllers/admin/user_link/contact_controller.ex deleted file mode 100644 index 5cc34fbf..00000000 --- a/lib/philomena_web/controllers/admin/user_link/contact_controller.ex +++ /dev/null @@ -1,22 +0,0 @@ -defmodule PhilomenaWeb.Admin.UserLink.ContactController do - use PhilomenaWeb, :controller - - alias Philomena.UserLinks.UserLink - alias Philomena.UserLinks - - plug PhilomenaWeb.CanaryMapPlug, create: :edit - - plug :load_and_authorize_resource, - model: UserLink, - id_name: "user_link_id", - persisted: true, - preload: [:user] - - def create(conn, _params) do - {:ok, _} = UserLinks.contact_user_link(conn.assigns.user_link, conn.assigns.current_user) - - conn - |> put_flash(:info, "User link successfully marked as contacted.") - |> redirect(to: Routes.admin_user_link_path(conn, :index)) - end -end diff --git a/lib/philomena_web/controllers/admin/user_link/reject_controller.ex b/lib/philomena_web/controllers/admin/user_link/reject_controller.ex deleted file mode 100644 index 9603c416..00000000 --- a/lib/philomena_web/controllers/admin/user_link/reject_controller.ex +++ /dev/null @@ -1,22 +0,0 @@ -defmodule PhilomenaWeb.Admin.UserLink.RejectController do - use PhilomenaWeb, :controller - - alias Philomena.UserLinks.UserLink - alias Philomena.UserLinks - - plug PhilomenaWeb.CanaryMapPlug, create: :edit - - plug :load_and_authorize_resource, - model: UserLink, - id_name: "user_link_id", - persisted: true, - preload: [:user] - - def create(conn, _params) do - {:ok, _} = UserLinks.reject_user_link(conn.assigns.user_link) - - conn - |> put_flash(:info, "User link successfully marked as rejected.") - |> redirect(to: Routes.admin_user_link_path(conn, :index)) - end -end diff --git a/lib/philomena_web/controllers/admin/user_link/verification_controller.ex b/lib/philomena_web/controllers/admin/user_link/verification_controller.ex deleted file mode 100644 index a6e1271e..00000000 --- a/lib/philomena_web/controllers/admin/user_link/verification_controller.ex +++ /dev/null @@ -1,22 +0,0 @@ -defmodule PhilomenaWeb.Admin.UserLink.VerificationController do - use PhilomenaWeb, :controller - - alias Philomena.UserLinks.UserLink - alias Philomena.UserLinks - - plug PhilomenaWeb.CanaryMapPlug, create: :edit - - plug :load_and_authorize_resource, - model: UserLink, - id_name: "user_link_id", - persisted: true, - preload: [:user] - - def create(conn, _params) do - {:ok, _} = UserLinks.verify_user_link(conn.assigns.user_link, conn.assigns.current_user) - - conn - |> put_flash(:info, "User link successfully verified.") - |> redirect(to: Routes.admin_user_link_path(conn, :index)) - end -end diff --git a/lib/philomena_web/controllers/profile/artist_link_controller.ex b/lib/philomena_web/controllers/profile/artist_link_controller.ex new file mode 100644 index 00000000..682989fb --- /dev/null +++ b/lib/philomena_web/controllers/profile/artist_link_controller.ex @@ -0,0 +1,84 @@ +defmodule PhilomenaWeb.Profile.ArtistLinkController do + use PhilomenaWeb, :controller + + alias Philomena.ArtistLinks.ArtistLink + alias Philomena.ArtistLinks + alias Philomena.Users.User + alias Philomena.Repo + import Ecto.Query + + plug PhilomenaWeb.FilterBannedUsersPlug when action in [:new, :create] + + plug :load_and_authorize_resource, + model: ArtistLink, + only: [:show, :edit, :update], + preload: [:user, :tag, :contacted_by_user] + + plug PhilomenaWeb.CanaryMapPlug, + index: :create_links, + new: :create_links, + create: :create_links, + show: :create_links, + edit: :edit_links, + update: :edit_links + + plug :load_and_authorize_resource, + model: User, + id_field: "slug", + id_name: "profile_id", + persisted: true + + def index(conn, _params) do + user = conn.assigns.current_user + + artist_links = + ArtistLink + |> where(user_id: ^user.id) + |> Repo.all() + + render(conn, "index.html", title: "Artist Links", artist_links: artist_links) + end + + def new(conn, _params) do + changeset = ArtistLinks.change_artist_link(%ArtistLink{}) + render(conn, "new.html", title: "New Artist Link", changeset: changeset) + end + + def create(conn, %{"artist_link" => artist_link_params}) do + case ArtistLinks.create_artist_link(conn.assigns.user, artist_link_params) do + {:ok, artist_link} -> + conn + |> put_flash( + :info, + "Link submitted! Please put '#{artist_link.verification_code}' on your linked webpage now." + ) + |> redirect(to: Routes.profile_artist_link_path(conn, :show, conn.assigns.user, artist_link)) + + {:error, %Ecto.Changeset{} = changeset} -> + render(conn, "new.html", changeset: changeset) + end + end + + def show(conn, _params) do + artist_link = conn.assigns.artist_link + render(conn, "show.html", title: "Showing Artist Link", artist_link: artist_link) + end + + def edit(conn, _params) do + changeset = ArtistLinks.change_artist_link(conn.assigns.artist_link) + + render(conn, "edit.html", title: "Editing Artist Link", changeset: changeset) + end + + def update(conn, %{"artist_link" => artist_link_params}) do + case ArtistLinks.update_artist_link(conn.assigns.artist_link, artist_link_params) do + {:ok, artist_link} -> + conn + |> put_flash(:info, "Link successfully updated.") + |> redirect(to: Routes.profile_artist_link_path(conn, :show, conn.assigns.user, artist_link)) + + {:error, changeset} -> + render(conn, "edit.html", changeset: changeset) + end + end +end diff --git a/lib/philomena_web/controllers/profile/commission_controller.ex b/lib/philomena_web/controllers/profile/commission_controller.ex index b2b93817..2254c8d1 100644 --- a/lib/philomena_web/controllers/profile/commission_controller.ex +++ b/lib/philomena_web/controllers/profile/commission_controller.ex @@ -148,7 +148,7 @@ defmodule PhilomenaWeb.Profile.CommissionController do false -> conn - |> put_flash(:error, "You must have a verified user link to create a commission listing.") + |> put_flash(:error, "You must have a verified artist link to create a commission listing.") |> redirect(to: Routes.commission_path(conn, :index)) |> halt() end diff --git a/lib/philomena_web/controllers/profile/user_link_controller.ex b/lib/philomena_web/controllers/profile/user_link_controller.ex deleted file mode 100644 index 577b4cd1..00000000 --- a/lib/philomena_web/controllers/profile/user_link_controller.ex +++ /dev/null @@ -1,84 +0,0 @@ -defmodule PhilomenaWeb.Profile.UserLinkController do - use PhilomenaWeb, :controller - - alias Philomena.UserLinks.UserLink - alias Philomena.UserLinks - alias Philomena.Users.User - alias Philomena.Repo - import Ecto.Query - - plug PhilomenaWeb.FilterBannedUsersPlug when action in [:new, :create] - - plug :load_and_authorize_resource, - model: UserLink, - only: [:show, :edit, :update], - preload: [:user, :tag, :contacted_by_user] - - plug PhilomenaWeb.CanaryMapPlug, - index: :create_links, - new: :create_links, - create: :create_links, - show: :create_links, - edit: :edit_links, - update: :edit_links - - plug :load_and_authorize_resource, - model: User, - id_field: "slug", - id_name: "profile_id", - persisted: true - - def index(conn, _params) do - user = conn.assigns.current_user - - user_links = - UserLink - |> where(user_id: ^user.id) - |> Repo.all() - - render(conn, "index.html", title: "User Links", user_links: user_links) - end - - def new(conn, _params) do - changeset = UserLinks.change_user_link(%UserLink{}) - render(conn, "new.html", title: "New User Link", changeset: changeset) - end - - def create(conn, %{"user_link" => user_link_params}) do - case UserLinks.create_user_link(conn.assigns.user, user_link_params) do - {:ok, user_link} -> - conn - |> put_flash( - :info, - "Link submitted! Please put '#{user_link.verification_code}' on your linked webpage now." - ) - |> redirect(to: Routes.profile_user_link_path(conn, :show, conn.assigns.user, user_link)) - - {:error, %Ecto.Changeset{} = changeset} -> - render(conn, "new.html", changeset: changeset) - end - end - - def show(conn, _params) do - user_link = conn.assigns.user_link - render(conn, "show.html", title: "Showing User Link", user_link: user_link) - end - - def edit(conn, _params) do - changeset = UserLinks.change_user_link(conn.assigns.user_link) - - render(conn, "edit.html", title: "Editing User Link", changeset: changeset) - end - - def update(conn, %{"user_link" => user_link_params}) do - case UserLinks.update_user_link(conn.assigns.user_link, user_link_params) do - {:ok, user_link} -> - conn - |> put_flash(:info, "Link successfully updated.") - |> redirect(to: Routes.profile_user_link_path(conn, :show, conn.assigns.user, user_link)) - - {:error, changeset} -> - render(conn, "edit.html", changeset: changeset) - end - end -end diff --git a/lib/philomena_web/plugs/admin_counters_plug.ex b/lib/philomena_web/plugs/admin_counters_plug.ex index 480bc692..ac9cb938 100644 --- a/lib/philomena_web/plugs/admin_counters_plug.ex +++ b/lib/philomena_web/plugs/admin_counters_plug.ex @@ -7,7 +7,7 @@ defmodule PhilomenaWeb.AdminCountersPlug do alias Philomena.DuplicateReports alias Philomena.Reports - alias Philomena.UserLinks + alias Philomena.ArtistLinks alias Philomena.DnpEntries import Plug.Conn, only: [assign: 3] @@ -33,13 +33,13 @@ defmodule PhilomenaWeb.AdminCountersPlug do defp maybe_assign_admin_metrics(conn, user, true) do duplicate_reports = DuplicateReports.count_duplicate_reports(user) reports = Reports.count_reports(user) - user_links = UserLinks.count_user_links(user) + artist_links = ArtistLinks.count_artist_links(user) dnps = DnpEntries.count_dnp_entries(user) conn |> assign(:duplicate_report_count, duplicate_reports) |> assign(:report_count, reports) - |> assign(:user_link_count, user_links) + |> assign(:artist_link_count, artist_links) |> assign(:dnp_entry_count, dnps) end diff --git a/lib/philomena_web/router.ex b/lib/philomena_web/router.ex index d3dadef5..6160aefc 100644 --- a/lib/philomena_web/router.ex +++ b/lib/philomena_web/router.ex @@ -261,7 +261,7 @@ defmodule PhilomenaWeb.Router do only: [:edit, :update], singleton: true - resources "/user_links", Profile.UserLinkController + resources "/artist_links", Profile.ArtistLinkController resources "/awards", Profile.AwardController, except: [:index, :show] resources "/details", Profile.DetailController, only: [:index] @@ -321,13 +321,13 @@ defmodule PhilomenaWeb.Router do resources "/close", Report.CloseController, only: [:create], singleton: true end - resources "/user_links", UserLinkController, only: [:index] do - resources "/verification", UserLink.VerificationController, + resources "/artist_links", ArtistLinkController, only: [:index] do + resources "/verification", ArtistLink.VerificationController, only: [:create], singleton: true - resources "/contact", UserLink.ContactController, only: [:create], singleton: true - resources "/reject", UserLink.RejectController, only: [:create], singleton: true + resources "/contact", ArtistLink.ContactController, only: [:create], singleton: true + resources "/reject", ArtistLink.RejectController, only: [:create], singleton: true end resources "/dnp_entries", DnpEntryController, only: [:index] do diff --git a/lib/philomena_web/templates/admin/user_link/index.html.slime b/lib/philomena_web/templates/admin/artist_link/index.html.slime similarity index 64% rename from lib/philomena_web/templates/admin/user_link/index.html.slime rename to lib/philomena_web/templates/admin/artist_link/index.html.slime index 0600322e..b9d0e8db 100644 --- a/lib/philomena_web/templates/admin/user_link/index.html.slime +++ b/lib/philomena_web/templates/admin/artist_link/index.html.slime @@ -1,21 +1,21 @@ -h1 User Links +h1 Artist Links p Link creation is done via the Users menu. p Verifying a link will automatically award an artist badge if the link is public, no artist badge exists, and an "artist:" tag is specified. -= form_for :user_link, Routes.admin_user_link_path(@conn, :index), [method: "get", class: "hform"], fn f -> += form_for :artist_link, Routes.admin_artist_link_path(@conn, :index), [method: "get", class: "hform"], fn f -> .field = text_input f, :q, name: :q, value: @conn.params["q"], class: "input hform__text", placeholder: "Search query", autocapitalize: "none" = submit "Search", class: "hform__button button" -- route = fn p -> Routes.admin_user_link_path(@conn, :index, p) end -- pagination = render PhilomenaWeb.PaginationView, "_pagination.html", page: @user_links, route: route, params: link_scope(@conn), conn: @conn +- route = fn p -> Routes.admin_artist_link_path(@conn, :index, p) end +- pagination = render PhilomenaWeb.PaginationView, "_pagination.html", page: @artist_links, route: route, params: link_scope(@conn), conn: @conn .block .block__header = if @conn.params["all"] do - = link "Show unverified only", to: Routes.admin_user_link_path(@conn, :index) + = link "Show unverified only", to: Routes.admin_artist_link_path(@conn, :index) - else - = link "Show all", to: Routes.admin_user_link_path(@conn, :index, all: "true") + = link "Show all", to: Routes.admin_artist_link_path(@conn, :index, all: "true") = pagination @@ -30,7 +30,7 @@ p Verifying a link will automatically award an artist badge if the link is publi th Mark th Public tbody - = for link <- @user_links do + = for link <- @artist_links do tr td class=link_state_class(link) strong @@ -56,20 +56,20 @@ p Verifying a link will automatically award an artist badge if the link is publi = render PhilomenaWeb.TagView, "_tag.html", tag: link.tag, conn: @conn td - => link "View", to: Routes.profile_user_link_path(@conn, :show, link.user, link) + => link "View", to: Routes.profile_artist_link_path(@conn, :show, link.user, link) ' • - = link "Edit", to: Routes.profile_user_link_path(@conn, :edit, link.user, link) + = link "Edit", to: Routes.profile_artist_link_path(@conn, :edit, link.user, link) td - => link "Verify", to: Routes.admin_user_link_verification_path(@conn, :create, link), method: :post + => link "Verify", to: Routes.admin_artist_link_verification_path(@conn, :create, link), method: :post ' • - => link "Reject", to: Routes.admin_user_link_reject_path(@conn, :create, link), method: :post + => link "Reject", to: Routes.admin_artist_link_reject_path(@conn, :create, link), method: :post br = if not verified?(link) do = if contacted?(link) do ' Artist contacted - else - = link "Artist contacted", to: Routes.admin_user_link_contact_path(@conn, :create, link), method: :post + = link "Artist contacted", to: Routes.admin_artist_link_contact_path(@conn, :create, link), method: :post td = public_text(link) diff --git a/lib/philomena_web/templates/admin/user/index.html.slime b/lib/philomena_web/templates/admin/user/index.html.slime index 485575de..cf240141 100644 --- a/lib/philomena_web/templates/admin/user/index.html.slime +++ b/lib/philomena_web/templates/admin/user/index.html.slime @@ -85,8 +85,8 @@ h1 Users => link to: Routes.admin_user_ban_path(@conn, :new, username: user.name) do i.fa.fa-fw.fa-ban ' Ban - = if can?(@conn, :edit, Philomena.UserLinks.UserLink) do - => link to: Routes.profile_user_link_path(@conn, :new, user) do + = if can?(@conn, :edit, Philomena.ArtistLinks.ArtistLink) do + => link to: Routes.profile_artist_link_path(@conn, :new, user) do i.fa.fa-fw.fa-link ' Add link diff --git a/lib/philomena_web/templates/dnp_entry/index.html.slime b/lib/philomena_web/templates/dnp_entry/index.html.slime index 0edda2f4..a72adb2f 100644 --- a/lib/philomena_web/templates/dnp_entry/index.html.slime +++ b/lib/philomena_web/templates/dnp_entry/index.html.slime @@ -21,12 +21,12 @@ br = link "My Listings", to: Routes.dnp_entry_path(@conn, :index, mine: "1") - not is_nil(@current_user) -> - ' You must have a verified user link to create and manage DNP entries. - = link "Request a user link", to: Routes.profile_user_link_path(@conn, :new, @current_user) + ' You must have a verified artist link to create and manage DNP entries. + = link "Request an artist link", to: Routes.profile_artist_link_path(@conn, :new, @current_user) | . - true -> - ' You must be logged in and have a verified user link to create and manage DNP entries. + ' You must be logged in and have a verified artist link to create and manage DNP entries. h3 The List diff --git a/lib/philomena_web/templates/layout/_header.html.slime b/lib/philomena_web/templates/layout/_header.html.slime index c675e320..98afd3ae 100644 --- a/lib/philomena_web/templates/layout/_header.html.slime +++ b/lib/philomena_web/templates/layout/_header.html.slime @@ -83,7 +83,7 @@ header.header a.header__link href="/posts?pq=my:posts" i.fas.fa-fw.fa-pen-square> | Posts - a.header__link href=Routes.profile_user_link_path(@conn, :index, @current_user) + a.header__link href=Routes.profile_artist_link_path(@conn, :index, @current_user) i.fa.fa-fw.fa-link> | Links a.header__link href="/settings/edit" diff --git a/lib/philomena_web/templates/layout/_header_staff_links.html.slime b/lib/philomena_web/templates/layout/_header_staff_links.html.slime index 9720b751..ca6b65ad 100644 --- a/lib/philomena_web/templates/layout/_header_staff_links.html.slime +++ b/lib/philomena_web/templates/layout/_header_staff_links.html.slime @@ -53,11 +53,11 @@ span.header__counter__admin = @report_count - = if @user_link_count do - = link to: Routes.admin_user_link_path(@conn, :index), class: "header__link", title: "User Links" do + = if @artist_link_count do + = link to: Routes.admin_artist_link_path(@conn, :index), class: "header__link", title: "Artist Links" do ' L span.header__counter__admin - = @user_link_count + = @artist_link_count = if @dnp_entry_count do = link to: Routes.admin_dnp_entry_path(@conn, :index), class: "header__link", title: "DNP Requests" do diff --git a/lib/philomena_web/templates/profile/_admin_block.html.slime b/lib/philomena_web/templates/profile/_admin_block.html.slime index d4b597a3..81ddaf04 100644 --- a/lib/philomena_web/templates/profile/_admin_block.html.slime +++ b/lib/philomena_web/templates/profile/_admin_block.html.slime @@ -141,11 +141,11 @@ a.label.label--primary.label--block href="#" data-click-toggle=".js-admin__optio i.fas.fa-fw.fa-dollar-sign span.admin__button Donations - = if can?(@conn, :edit, %Philomena.UserLinks.UserLink{}) do + = if can?(@conn, :edit, %Philomena.ArtistLinks.ArtistLink{}) do li - = link to: Routes.profile_user_link_path(@conn, :new, @user) do + = link to: Routes.profile_artist_link_path(@conn, :new, @user) do i.fa.fa-fw.fa-link - span.admin__button Add User Link + span.admin__button Add Artist Link = if can?(@conn, :create, Philomena.Bans.User) do li diff --git a/lib/philomena_web/templates/profile/_commission.html.slime b/lib/philomena_web/templates/profile/_commission.html.slime index 4998029a..b6a47d74 100644 --- a/lib/philomena_web/templates/profile/_commission.html.slime +++ b/lib/philomena_web/templates/profile/_commission.html.slime @@ -24,9 +24,15 @@ = link "More information", to: Routes.profile_commission_path(@conn, :show, @user) - current?(@user, @conn.assigns.current_user) -> - em - ' You don't have any commission information listed yet. - => link "Click here", to: Routes.profile_commission_path(@conn, :new, @user) - ' to set it up. + = if Enum.any?(@conn.assigns.user.verified_links) do + em + ' You don't have any commission information listed yet. + => link "Click here", to: Routes.profile_commission_path(@conn, :new, @user) + ' to set it up. + - else + em + ' You must have a verified Artist Link to create a commission page. + => link "Click here", to: Routes.profile_artist_link_path(@conn, :new, @user) + ' to set one up. - true -> diff --git a/lib/philomena_web/templates/profile/user_link/_form.html.slime b/lib/philomena_web/templates/profile/artist_link/_form.html.slime similarity index 62% rename from lib/philomena_web/templates/profile/user_link/_form.html.slime rename to lib/philomena_web/templates/profile/artist_link/_form.html.slime index a3dac77a..296ed189 100644 --- a/lib/philomena_web/templates/profile/user_link/_form.html.slime +++ b/lib/philomena_web/templates/profile/artist_link/_form.html.slime @@ -7,19 +7,15 @@ .field p label for="tag_name" - ' The tag, - em> specific - ' to you, usually - code> - | artist: - em artist name here - ' or a series name - = text_input f, :tag_name, value: assigns[:tag_name], class: "input", autocomplete: "off", placeholder: "artist:name", data: [ac: "true", ac_min_length: "3", ac_source: "/tags/autocomplete?term="] + ' Artist Link validation is intended for artists. Validating your link will give you control over how your art is shared on the site and will allow you to create a + a> href="/commissions" commissions + ' listing. Do not request a link if the source has no artwork that you yourself did not create. + = text_input f, :tag_name, value: assigns[:tag_name], class: "input", autocomplete: "off", placeholder: "artist:your-name", data: [ac: "true", ac_min_length: "3", ac_source: "/tags/autocomplete?term="] = error_tag f, :tag .field label for="uri" - ' URL of your art webpage + ' URL of your art webpage (may be your Derpibooru profile page if you have no other sources) = url_input f, :uri, class: "input input--wide", placeholder: "https://www.deviantart.com/your-name", required: true = error_tag f, :uri diff --git a/lib/philomena_web/templates/profile/artist_link/edit.html.slime b/lib/philomena_web/templates/profile/artist_link/edit.html.slime new file mode 100644 index 00000000..7c643cf4 --- /dev/null +++ b/lib/philomena_web/templates/profile/artist_link/edit.html.slime @@ -0,0 +1,2 @@ +h1 Edit Link += render PhilomenaWeb.Profile.ArtistLinkView, "_form.html", conn: @conn, changeset: @changeset, tag_name: tag_name(@artist_link), action: Routes.profile_artist_link_path(@conn, :update, @artist_link.user, @artist_link) diff --git a/lib/philomena_web/templates/profile/artist_link/index.html.slime b/lib/philomena_web/templates/profile/artist_link/index.html.slime new file mode 100644 index 00000000..15f2999b --- /dev/null +++ b/lib/philomena_web/templates/profile/artist_link/index.html.slime @@ -0,0 +1,23 @@ +h1 Artist Links +p + a.button href=Routes.profile_artist_link_path(@conn, :new, @user) + ' Request a link +p + ' Artist links associate your account on Derpibooru with tags about content you create and with accounts on sites elsewhere. This allows users to easily identify artists and staff to act more rapidly on takedown requests. + +table.table + thead + tr + th URI + th Options + th Verification Code + th Verified? + th Public + tbody + = for link <- @artist_links do + tr + td = link link.uri, to: link.uri + td = link "View Details", to: Routes.profile_artist_link_path(@conn, :show, @user, link) + td = link.verification_code + th = verified_as_string(link) + th = public_as_string(link) diff --git a/lib/philomena_web/templates/profile/artist_link/new.html.slime b/lib/philomena_web/templates/profile/artist_link/new.html.slime new file mode 100644 index 00000000..762d9be9 --- /dev/null +++ b/lib/philomena_web/templates/profile/artist_link/new.html.slime @@ -0,0 +1,2 @@ +h1 Request Artist Link += render PhilomenaWeb.Profile.ArtistLinkView, "_form.html", changeset: @changeset, action: Routes.profile_artist_link_path(@conn, :create, @user), conn: @conn diff --git a/lib/philomena_web/templates/profile/user_link/show.html.slime b/lib/philomena_web/templates/profile/artist_link/show.html.slime similarity index 57% rename from lib/philomena_web/templates/profile/user_link/show.html.slime rename to lib/philomena_web/templates/profile/artist_link/show.html.slime index c5cdcaf7..f35a62cd 100644 --- a/lib/philomena_web/templates/profile/user_link/show.html.slime +++ b/lib/philomena_web/templates/profile/artist_link/show.html.slime @@ -1,73 +1,72 @@ h1 ' Link to - = link @user_link.uri, to: @user_link.uri + = link @artist_link.uri, to: @artist_link.uri h3 Status = cond do - - verified?(@user_link) -> + - verified?(@artist_link) -> p This link has been verified by a member of the administration team. p You can now remove the verification text from your website if you have not done so already. - - contacted?(@user_link) -> + - contacted?(@artist_link) -> p strong This link is awaiting your reply on the linked website in order to be verified. p ' An administrator - => "(#{@user_link.contacted_by_user.name})" + => "(#{@artist_link.contacted_by_user.name})" ' has manually contacted you at the address above, as your verification code was not found on the website. Please respond to the message from the administrator to confirm your link. p The verification code is: p code - h1 = @user_link.verification_code + h1 = @artist_link.verification_code - - link_verified?(@user_link) -> + - link_verified?(@artist_link) -> p strong This link is pending verification by a member of the administration team. p We've now found the verification code on your website. An administrator still needs to check the tag list before verifying the link. Please leave the code on your website until verification is complete. p If you need it again, your verification code is: p code - h1 = @user_link.verification_code + h1 = @artist_link.verification_code - - unverified?(@user_link) -> + - unverified?(@artist_link) -> p strong This link is pending verification by a member of the administration team. - p - h3 To have your link verified as fast as possible, please place this text somewhere on the page you are linking. - p - code - h1 = @user_link.verification_code + .dnp-warning + h3 To have your link verified as fast as possible, please place this text somewhere on the page you are linking. + code + h1 = @artist_link.verification_code p Otherwise, an administrator will have to contact you to verify your identity. p Once the link has been verified you can remove the text; the text simply allows the team to directly check with your website rather than messaging you and waiting for a reply. - - rejected?(@user_link) -> + - rejected?(@artist_link) -> p This link has been rejected by a member of the administration team; this is probably because you were not reachable in a timely manner (~1 week) to verify the link. h3 Visibility -= if public?(@user_link) do += if public?(@artist_link) do p This link is public, and will be shown around the site. - else p This link is not public, and will only be shown to administrators. h3 Associated tag -= if @user_link.tag do += if @artist_link.tag do .tag-list - = render PhilomenaWeb.TagView, "_tag.html", tag: @user_link.tag, conn: @conn + = render PhilomenaWeb.TagView, "_tag.html", tag: @artist_link.tag, conn: @conn - else p There is no tag associated with this link. -= if can?(@conn, :index, Philomena.UserLinks.UserLink) do += if can?(@conn, :index, Philomena.ArtistLinks.ArtistLink) do p - => link "Edit", to: Routes.profile_user_link_path(@conn, :edit, @user, @user_link) + => link "Edit", to: Routes.profile_artist_link_path(@conn, :edit, @user, @artist_link) ' • - => link "Verify", to: Routes.admin_user_link_verification_path(@conn, :create, @user_link), method: :post + => link "Verify", to: Routes.admin_artist_link_verification_path(@conn, :create, @artist_link), method: :post ' • - => link "Reject", to: Routes.admin_user_link_reject_path(@conn, :create, @user_link), method: :post - = if not verified?(@user_link) do + => link "Reject", to: Routes.admin_artist_link_reject_path(@conn, :create, @artist_link), method: :post + = if not verified?(@artist_link) do ' • - = if contacted?(@user_link) do + = if contacted?(@artist_link) do ' Artist contacted - else - = link "Artist contacted", to: Routes.admin_user_link_contact_path(@conn, :create, @user_link), method: :post + = link "Artist contacted", to: Routes.admin_artist_link_contact_path(@conn, :create, @artist_link), method: :post -= link "Back", to: Routes.profile_user_link_path(@conn, :index, @user) += link "Back", to: Routes.profile_artist_link_path(@conn, :index, @user) diff --git a/lib/philomena_web/templates/profile/commission/_listing_sidebar.html.slime b/lib/philomena_web/templates/profile/commission/_listing_sidebar.html.slime index 69644e68..51474803 100644 --- a/lib/philomena_web/templates/profile/commission/_listing_sidebar.html.slime +++ b/lib/philomena_web/templates/profile/commission/_listing_sidebar.html.slime @@ -58,12 +58,12 @@ .block__content.commission__block_body == @rendered.will_not_create -/ User link block +/ Artist link block /.block - .block__header: span.block__header__title User Links + .block__header: span.block__header__title Artist Links - is_current = (current_user && current_user.id == @user.id) - if @links.present? || is_current - = render partial: 'profiles/user_link_area' + = render partial: 'profiles/artist_link_area' / Options block .block diff --git a/lib/philomena_web/templates/profile/show.html.slime b/lib/philomena_web/templates/profile/show.html.slime index d0641d01..ef368950 100644 --- a/lib/philomena_web/templates/profile/show.html.slime +++ b/lib/philomena_web/templates/profile/show.html.slime @@ -65,10 +65,10 @@ .block = if current?(@user, @conn.assigns.current_user) or manages_links?(@conn, @user) do - a.block__header--single-item href=Routes.profile_user_link_path(@conn, :new, @user) User Links + a.block__header--single-item href=Routes.profile_artist_link_path(@conn, :new, @user) Artist Links - else .block__header - span.block__header__title User Links + span.block__header__title Artist Links = for link <- @user.verified_links, should_see_link?(@conn, @user, link) do - watchers = if link.tag, do: @watcher_counts[link.tag.id] || 0, else: 0 @@ -91,10 +91,10 @@ - else ' Hidden ' • - a href=Routes.profile_user_link_path(@conn, :edit, @user, link) + a href=Routes.profile_artist_link_path(@conn, :edit, @user, link) ' Edit ' • - a href=Routes.admin_user_link_reject_path(@conn, :create, link) data-method="post" + a href=Routes.admin_artist_link_reject_path(@conn, :create, link) data-method="post" ' Reject - else => unless link.public do diff --git a/lib/philomena_web/templates/profile/user_link/edit.html.slime b/lib/philomena_web/templates/profile/user_link/edit.html.slime deleted file mode 100644 index 9dcff18a..00000000 --- a/lib/philomena_web/templates/profile/user_link/edit.html.slime +++ /dev/null @@ -1,2 +0,0 @@ -h1 Edit Link -= render PhilomenaWeb.Profile.UserLinkView, "_form.html", conn: @conn, changeset: @changeset, tag_name: tag_name(@user_link), action: Routes.profile_user_link_path(@conn, :update, @user_link.user, @user_link) diff --git a/lib/philomena_web/templates/profile/user_link/index.html.slime b/lib/philomena_web/templates/profile/user_link/index.html.slime deleted file mode 100644 index 9a057306..00000000 --- a/lib/philomena_web/templates/profile/user_link/index.html.slime +++ /dev/null @@ -1,23 +0,0 @@ -h1 User Links -p - a.button href=Routes.profile_user_link_path(@conn, :new, @user) - ' Create a link -p - ' User links associate your account on Derpibooru with tags about content you create and with accounts on sites elsewhere. This allows users to easily identify artists and admins to act more rapidly on takedown requests. - -table.table - thead - tr - th URI - th Options - th Verification Code - th Verified? - th Public - tbody - = for link <- @user_links do - tr - td = link link.uri, to: link.uri - td = link "View Details", to: Routes.profile_user_link_path(@conn, :show, @user, link) - td = link.verification_code - th = verified_as_string(link) - th = public_as_string(link) diff --git a/lib/philomena_web/templates/profile/user_link/new.html.slime b/lib/philomena_web/templates/profile/user_link/new.html.slime deleted file mode 100644 index f132997d..00000000 --- a/lib/philomena_web/templates/profile/user_link/new.html.slime +++ /dev/null @@ -1,2 +0,0 @@ -h1 Create Link -= render PhilomenaWeb.Profile.UserLinkView, "_form.html", changeset: @changeset, action: Routes.profile_user_link_path(@conn, :create, @user), conn: @conn diff --git a/lib/philomena_web/templates/report/new.html.slime b/lib/philomena_web/templates/report/new.html.slime index 57ae7b78..785ae79b 100644 --- a/lib/philomena_web/templates/report/new.html.slime +++ b/lib/philomena_web/templates/report/new.html.slime @@ -23,7 +23,7 @@ p strong> Only an owner of an image's rights (normally the artist) can request a takedown. ' If you're the artist, you'll strong> need - ' a verified user link. + ' a verified artist link. p ' For more information, please read the = link "takedown policy", to: "/pages/takedowns" diff --git a/lib/philomena_web/templates/tag/_tag_info_row.html.slime b/lib/philomena_web/templates/tag/_tag_info_row.html.slime index 3cd4680a..bb00d2bb 100644 --- a/lib/philomena_web/templates/tag/_tag_info_row.html.slime +++ b/lib/philomena_web/templates/tag/_tag_info_row.html.slime @@ -43,10 +43,10 @@ strong.comment_deleted> Hidden links: br - = for user_link <- @tag.hidden_links do - => link user_link.user.name, to: Routes.profile_path(@conn, :show, user_link.user) + = for artist_link <- @tag.hidden_links do + => link artist_link.user.name, to: Routes.profile_path(@conn, :show, artist_link.user) ' → - => link user_link.uri, to: user_link.uri + => link artist_link.uri, to: artist_link.uri br diff --git a/lib/philomena_web/views/admin/user_link_view.ex b/lib/philomena_web/views/admin/artist_link_view.ex similarity index 92% rename from lib/philomena_web/views/admin/user_link_view.ex rename to lib/philomena_web/views/admin/artist_link_view.ex index 313256f5..7977641c 100644 --- a/lib/philomena_web/views/admin/user_link_view.ex +++ b/lib/philomena_web/views/admin/artist_link_view.ex @@ -1,4 +1,4 @@ -defmodule PhilomenaWeb.Admin.UserLinkView do +defmodule PhilomenaWeb.Admin.ArtistLinkView do use PhilomenaWeb, :view alias Philomena.Tags.Tag @@ -35,7 +35,7 @@ defmodule PhilomenaWeb.Admin.UserLinkView do def rejected?(%{aasm_state: state}), do: state == "rejected" def public_text(%{public: true}), do: "Yes" - def public_text(_user_link), do: "No" + def public_text(_artist_link), do: "No" def public?(%{public: public}), do: !!public end diff --git a/lib/philomena_web/views/admin/user_view.ex b/lib/philomena_web/views/admin/user_view.ex index 949ea682..c502343e 100644 --- a/lib/philomena_web/views/admin/user_view.ex +++ b/lib/philomena_web/views/admin/user_view.ex @@ -43,7 +43,7 @@ defmodule PhilomenaWeb.Admin.UserView do def description("moderator", "Image"), do: "Manage images" def description("moderator", "DuplicateReport"), do: "Manage duplicates" def description("moderator", "Comment"), do: "Manage comments" - def description("moderator", "UserLink"), do: "Manage user links" + def description("moderator", "ArtistLink"), do: "Manage artist links" def description("moderator", "Topic"), do: "Moderate forums" def description("moderator", "Tag"), do: "Manage tag details" @@ -77,7 +77,7 @@ defmodule PhilomenaWeb.Admin.UserView do ["moderator", "DuplicateReport"], ["moderator", "Comment"], ["moderator", "Tag"], - ["moderator", "UserLink"], + ["moderator", "ArtistLink"], ["moderator", "Topic"] ] end diff --git a/lib/philomena_web/views/api/json/user_link_view.ex b/lib/philomena_web/views/api/json/artist_link_view.ex similarity index 60% rename from lib/philomena_web/views/api/json/user_link_view.ex rename to lib/philomena_web/views/api/json/artist_link_view.ex index 778af786..00d8326c 100644 --- a/lib/philomena_web/views/api/json/user_link_view.ex +++ b/lib/philomena_web/views/api/json/artist_link_view.ex @@ -1,11 +1,11 @@ -defmodule PhilomenaWeb.Api.Json.UserLinkView do +defmodule PhilomenaWeb.Api.Json.ArtistLinkView do use PhilomenaWeb, :view - def render("user_link.json", %{user_link: %{public: false}}) do + def render("artist_link.json", %{artist_link: %{public: false}}) do nil end - def render("user_link.json", %{user_link: link}) do + def render("artist_link.json", %{artist_link: link}) do %{ user_id: link.user_id, created_at: link.created_at, diff --git a/lib/philomena_web/views/api/json/profile_view.ex b/lib/philomena_web/views/api/json/profile_view.ex index 92c9d0ec..d8ad5078 100644 --- a/lib/philomena_web/views/api/json/profile_view.ex +++ b/lib/philomena_web/views/api/json/profile_view.ex @@ -21,8 +21,8 @@ defmodule PhilomenaWeb.Api.Json.ProfileView do links: render_many( user.public_links, - PhilomenaWeb.Api.Json.UserLinkView, - "user_link.json", + PhilomenaWeb.Api.Json.ArtistLinkView, + "artist_link.json", assigns ), awards: render_many(user.awards, PhilomenaWeb.Api.Json.AwardView, "award.json", assigns) diff --git a/lib/philomena_web/views/profile/user_link_view.ex b/lib/philomena_web/views/profile/artist_link_view.ex similarity index 80% rename from lib/philomena_web/views/profile/user_link_view.ex rename to lib/philomena_web/views/profile/artist_link_view.ex index b74e006d..8e765996 100644 --- a/lib/philomena_web/views/profile/user_link_view.ex +++ b/lib/philomena_web/views/profile/artist_link_view.ex @@ -1,4 +1,4 @@ -defmodule PhilomenaWeb.Profile.UserLinkView do +defmodule PhilomenaWeb.Profile.ArtistLinkView do use PhilomenaWeb, :view def verified?(%{aasm_state: state}), do: state == "verified" @@ -10,10 +10,10 @@ defmodule PhilomenaWeb.Profile.UserLinkView do def public?(%{public: public}), do: !!public def verified_as_string(%{aasm_state: "verified"}), do: "Yes" - def verified_as_string(_user_link), do: "No" + def verified_as_string(_artist_link), do: "No" def public_as_string(%{public: true}), do: "Yes" - def public_as_string(_user_link), do: "No" + def public_as_string(_artist_link), do: "No" def tag_name(%{tag: nil}), do: nil def tag_name(%{tag: tag}), do: tag.name diff --git a/lib/philomena_web/views/tag_view.ex b/lib/philomena_web/views/tag_view.ex index dd0b12eb..ada8ffdd 100644 --- a/lib/philomena_web/views/tag_view.ex +++ b/lib/philomena_web/views/tag_view.ex @@ -155,7 +155,7 @@ defmodule PhilomenaWeb.TagView do end defp manages_links?(conn), - do: can?(conn, :index, Philomena.UserLinks.UserLink) + do: can?(conn, :index, Philomena.ArtistLinks.ArtistLink) defp manages_dnp?(conn), do: can?(conn, :index, Philomena.DnpEntries.DnpEntry) diff --git a/priv/repo/seeds.json b/priv/repo/seeds.json index aae34185..a98e4602 100644 --- a/priv/repo/seeds.json +++ b/priv/repo/seeds.json @@ -80,7 +80,7 @@ {"name": "moderator", "resource_type": "DuplicateReport"}, {"name": "moderator", "resource_type": "Comment"}, {"name": "moderator", "resource_type": "Tag"}, - {"name": "moderator", "resource_type": "UserLink"}, + {"name": "moderator", "resource_type": "ArtistLink"}, {"name": "admin", "resource_type": "Tag"}, {"name": "moderator", "resource_type": "User"}, {"name": "admin", "resource_type": "SiteNotice"},