This commit is contained in:
byte[] 2019-11-29 01:26:05 -05:00
parent 482b8c2e80
commit c621c83ac8
12 changed files with 141 additions and 9 deletions

View file

@ -15,6 +15,7 @@ config :philomena,
tumblr_api_key: "fuiKNFp9vQFvjLNvx4sUwti4Yb5yGutBN4Xh10LXZhhRKjWlV4",
image_url_root: "/img",
avatar_url_root: "/avatars",
advert_url_root: "/spns",
badge_url_root: "/media",
image_file_root: "priv/static/system/images",
cdn_host: "",

View file

@ -18,6 +18,7 @@ config :philomena,
anonymous_name_salt: System.get_env("ANONYMOUS_NAME_SALT"),
password_pepper: System.get_env("PASSWORD_PEPPER"),
avatar_url_root: System.get_env("AVATAR_URL_ROOT"),
advert_url_root: System.get_env("ADVERT_URL_ROOT"),
image_file_root: System.get_env("IMAGE_FILE_ROOT"),
tumblr_api_key: System.get_env("TUMBLR_API_KEY"),
otp_secret_key: System.get_env("OTP_SECRET_KEY"),

View file

@ -8,17 +8,71 @@ defmodule Philomena.Adverts do
alias Philomena.Adverts.Advert
@doc """
Returns the list of adverts.
## Examples
def random_live do
now = DateTime.utc_now()
iex> list_adverts()
[%Advert{}, ...]
Advert
|> where(live: true, restrictions: "none")
|> where([a], a.start_date < ^now and a.finish_date > ^now)
|> order_by(asc: fragment("random()"))
|> limit(1)
|> Repo.one()
|> record_impression()
end
"""
def list_adverts do
Repo.all(Advert)
def random_live_for(image) do
image = Repo.preload(image, :tags)
now = DateTime.utc_now()
Advert
|> where(live: true)
|> where([a], a.restrictions in ^restrictions(image))
|> where([a], a.start_date < ^now and a.finish_date > ^now)
|> order_by(asc: fragment("random()"))
|> limit(1)
|> Repo.one()
|> record_impression()
end
def click(%Advert{} = advert) do
spawn fn ->
query = where(Advert, id: ^advert.id)
Repo.update_all(query, inc: [clicks: 1])
end
end
defp record_impression(nil), do: nil
defp record_impression(advert) do
spawn fn ->
query = where(Advert, id: ^advert.id)
Repo.update_all(query, inc: [impressions: 1])
end
advert
end
defp sfw?(image) do
image_tags = MapSet.new(image.tags |> Enum.map(& &1.name))
sfw_tags = MapSet.new(["safe", "suggestive"])
intersect = MapSet.intersection(image_tags, sfw_tags)
MapSet.size(intersect) > 0
end
defp nsfw?(image) do
image_tags = MapSet.new(image.tags |> Enum.map(& &1.name))
nsfw_tags = MapSet.new(["questionable", "explicit"])
intersect = MapSet.intersection(image_tags, nsfw_tags)
MapSet.size(intersect) > 0
end
defp restrictions(image) do
restrictions = ["none"]
restrictions = if nsfw?(image), do: ["nsfw" | restrictions], else: restrictions
restrictions = if sfw?(image), do: ["sfw" | restrictions], else: restrictions
restrictions
end
@doc """

View file

@ -0,0 +1,17 @@
defmodule PhilomenaWeb.AdvertController do
use PhilomenaWeb, :controller
alias Philomena.Adverts
alias Philomena.Adverts.Advert
plug :load_resource, model: Advert
def show(conn, _params) do
advert = conn.assigns.advert
Adverts.click(advert)
conn
|> redirect(external: advert.link)
end
end

View file

@ -15,6 +15,7 @@ defmodule PhilomenaWeb.ImageController do
plug PhilomenaWeb.UserAttributionPlug when action in [:create]
plug PhilomenaWeb.CaptchaPlug when action in [:create]
plug PhilomenaWeb.ScraperPlug, [params_name: "image", params_key: "image"] when action in [:create]
plug PhilomenaWeb.AdvertPlug when action in [:show]
def index(conn, _params) do
query = conn.assigns.compiled_filter

View file

@ -9,6 +9,7 @@ defmodule PhilomenaWeb.TopicController do
plug PhilomenaWeb.FilterBannedUsersPlug when action in [:new, :create]
plug PhilomenaWeb.UserAttributionPlug when action in [:new, :create]
plug PhilomenaWeb.AdvertPlug when action in [:show]
plug :load_and_authorize_resource, model: Forum, id_name: "forum_id", id_field: "short_name", persisted: true
def show(conn, %{"id" => slug} = params) do

View file

@ -0,0 +1,27 @@
defmodule PhilomenaWeb.AdvertPlug do
alias Philomena.Adverts
alias Plug.Conn
def init([]), do: []
def call(conn, _opts) do
user = conn.assigns.current_user
image = conn.assigns[:image]
show_ads? = show_ads?(user)
conn
|> maybe_assign_ad(image, show_ads?)
end
defp maybe_assign_ad(conn, nil, true),
do: Conn.assign(conn, :advert, Adverts.random_live())
defp maybe_assign_ad(conn, image, true),
do: Conn.assign(conn, :advert, Adverts.random_live_for(image))
defp maybe_assign_ad(conn, _image, _false),
do: conn
defp show_ads?(%{hide_advertisements: false}),
do: true
defp show_ads?(_user),
do: true
end

View file

@ -122,6 +122,7 @@ defmodule PhilomenaWeb.Router do
resources "/posts", PostController, only: [:index]
resources "/commissions", CommissionController, only: [:index, :show]
resources "/galleries", GalleryController, only: [:index, :show]
resources "/adverts", AdvertController, only: [:show]
get "/:id", ImageController, :show
# get "/:forum_id", ForumController, :show # impossible to do without constraints

View file

@ -0,0 +1,14 @@
.block#imagespns
.spnstxt
' Interested in advertising on Derpibooru?
= link "Click here", to: "/pages/advertising"
' for information!
a href=Routes.advert_path(@conn, :show, @advert) rel="nofollow" title=@advert.title
img src=advert_image_url(@advert) alt=@advert.title width="700" height="80"
p
strong
' Derpibooru costs over $25 a day to operate -
= link "help support us financially", to: "/pages/donations"
' !

View file

@ -2,6 +2,9 @@
= render PhilomenaWeb.ImageView, "_image_page.html", image: @image, conn: @conn
.layout--narrow
= if @conn.assigns.advert do
= render PhilomenaWeb.Advertview, "_box.html", advert: @conn.assigns.advert, conn: @conn
.image-description
= render PhilomenaWeb.ImageView, "_description.html", image: @image, body: @description, conn: @conn
= render PhilomenaWeb.Image.DescriptionView, "_form.html", image: @image, changeset: @image_changeset, conn: @conn

View file

@ -38,7 +38,8 @@ h1 = @topic.title
= for {post, body} <- @posts, !post.destroyed_content do
= render PhilomenaWeb.PostView, "_post.html", conn: @conn, post: post, body: body
/include ../adverts/_box.html.slim
= if @conn.assigns.advert do
= render PhilomenaWeb.Advertview, "_box.html", advert: @conn.assigns.advert, conn: @conn
/ Post editability data for JS
/.js-editable-posts data-editable=editable_communications(@posts).to_json

View file

@ -0,0 +1,11 @@
defmodule PhilomenaWeb.AdvertView do
use PhilomenaWeb, :view
def advert_image_url(%{image: image}) do
advert_url_root() <> image
end
defp advert_url_root do
Application.get_env(:philomena, :advert_url_root)
end
end