Add support for searching media status

w/ some refactors and updates
This commit is contained in:
itepechi 2023-09-16 07:08:07 +09:00
parent c5000d67a6
commit 0ceee820a6
6 changed files with 37 additions and 6 deletions

View file

@ -26,6 +26,7 @@ def search(user, search_query, options \\ []) do
limit = Enum.min([Keyword.get(options, :limit), 40]) limit = Enum.min([Keyword.get(options, :limit), 40])
offset = Keyword.get(options, :offset, 0) offset = Keyword.get(options, :offset, 0)
author = Keyword.get(options, :author) author = Keyword.get(options, :author)
only_media = Keyword.get(options, :only_media, false)
search_function = search_function =
if :persistent_term.get({Pleroma.Repo, :postgres_version}) >= 11 do if :persistent_term.get({Pleroma.Repo, :postgres_version}) >= 11 do
@ -43,6 +44,7 @@ def search(user, search_query, options \\ []) do
|> maybe_restrict_local(user) |> maybe_restrict_local(user)
|> maybe_restrict_author(author) |> maybe_restrict_author(author)
|> maybe_restrict_blocked(user) |> maybe_restrict_blocked(user)
|> maybe_only_media(only_media)
|> Pagination.fetch_paginated( |> Pagination.fetch_paginated(
%{"offset" => offset, "limit" => limit, "skip_order" => index_type == :rum}, %{"offset" => offset, "limit" => limit, "skip_order" => index_type == :rum},
:offset :offset
@ -173,4 +175,12 @@ def maybe_fetch(activities, user, search_query) do
_ -> activities _ -> activities
end end
end end
def maybe_only_media(q, true) do
from([a, o] in q,
where: fragment("not (?)->'attachment' = (?)", o.data, ^[])
)
end
def maybe_only_media(q, _), do: q
end end

View file

@ -43,6 +43,7 @@ defp maybe_fetch(:activity, search_query) do
def search(user, query, options) do def search(user, query, options) do
limit = Enum.min([Keyword.get(options, :limit), 40]) limit = Enum.min([Keyword.get(options, :limit), 40])
offset = Keyword.get(options, :offset, 0) offset = Keyword.get(options, :offset, 0)
only_media = Keyword.get(options, :only_media, false)
parsed_query = parsed_query =
query query
@ -62,7 +63,10 @@ def search(user, query, options) do
|> Pleroma.Search.Elasticsearch.Store.search(q) |> Pleroma.Search.Elasticsearch.Store.search(q)
|> Enum.filter(fn x -> |> Enum.filter(fn x ->
x.data["type"] == "Create" && x.object.data["type"] == "Note" && x.data["type"] == "Create" && x.object.data["type"] == "Note" &&
Visibility.visible_for_user?(x, user) Visibility.visible_for_user?(x, user) &&
# i'm not going to implement this very seriously because the support for
# elasticsearch is already kinda broken
if only_media, do: length(x.object.data["attachment"]) > 0, else: true
end) end)
end) end)

View file

@ -32,7 +32,7 @@ def search(:raw, index, q) do
{:ok, results} {:ok, results}
else else
{:error, e} -> {:error, e} ->
Logger.error(e) Logger.error("Unable to search with Elasiticsearch: #{inspect(e)}")
{:error, e} {:error, e}
end end
end end
@ -44,7 +44,7 @@ def search(:activities, q) do
|> Pleroma.Activity.all_by_ids_with_object() |> Pleroma.Activity.all_by_ids_with_object()
else else
e -> e ->
Logger.error(e) Logger.error("Unable to search with Elasiticsearch: #{inspect(e)}")
[] []
end end
end end

View file

@ -79,6 +79,7 @@ def search(user, query, options \\ []) do
limit = Enum.min([Keyword.get(options, :limit), 40]) limit = Enum.min([Keyword.get(options, :limit), 40])
offset = Keyword.get(options, :offset, 0) offset = Keyword.get(options, :offset, 0)
author = Keyword.get(options, :author) author = Keyword.get(options, :author)
only_media = Keyword.get(options, :only_media, false)
res = res =
meili_post( meili_post(
@ -93,11 +94,11 @@ def search(user, query, options \\ []) do
hits hits
|> Activity.create_by_object_ap_id() |> Activity.create_by_object_ap_id()
|> Activity.with_preloaded_object() |> Activity.with_preloaded_object()
|> Activity.with_preloaded_object()
|> Activity.restrict_deactivated_users() |> Activity.restrict_deactivated_users()
|> maybe_restrict_local(user) |> maybe_restrict_local(user)
|> maybe_restrict_author(author) |> maybe_restrict_author(author)
|> maybe_restrict_blocked(user) |> maybe_restrict_blocked(user)
|> maybe_only_media(only_media)
|> maybe_fetch(user, query) |> maybe_fetch(user, query)
|> order_by([object: obj], desc: obj.data["published"]) |> order_by([object: obj], desc: obj.data["published"])
|> Pleroma.Repo.all() |> Pleroma.Repo.all()

View file

@ -75,7 +75,7 @@ def search2_operation do
Operation.parameter( Operation.parameter(
:type, :type,
:query, :query,
%Schema{type: :string, enum: ["accounts", "hashtags", "statuses"]}, %Schema{type: :string, enum: ["accounts", "hashtags", "statuses", "media"]},
"Search type" "Search type"
), ),
Operation.parameter(:q, :query, %Schema{type: :string}, "What to search for", Operation.parameter(:q, :query, %Schema{type: :string}, "What to search for",

View file

@ -47,7 +47,7 @@ defp do_search(version, %{assigns: %{user: user}} = conn, %{q: query} = params)
query = String.trim(query) query = String.trim(query)
options = search_options(params, user) options = search_options(params, user)
timeout = Keyword.get(Repo.config(), :timeout, 15_000) timeout = Keyword.get(Repo.config(), :timeout, 15_000)
default_values = %{"statuses" => [], "accounts" => [], "hashtags" => []} default_values = %{"statuses" => [], "media" => [], "accounts" => [], "hashtags" => []}
result = result =
default_values default_values
@ -107,6 +107,22 @@ defp resource_search(_, "statuses", query, options) do
) )
end end
defp resource_search(_, "media", query, options) do
statuses =
with_fallback(fn ->
Pleroma.Search.search(
query,
Keyword.put(options, :only_media, true)
)
end)
StatusView.render("index.json",
activities: statuses,
for: options[:for_user],
as: :activity
)
end
defp resource_search(:v2, "hashtags", query, options) do defp resource_search(:v2, "hashtags", query, options) do
tags_path = Endpoint.url() <> "/tag/" tags_path = Endpoint.url() <> "/tag/"