Support the 'following' option on post searches
This commit is contained in:
parent
49eda427fd
commit
66e26882e8
6 changed files with 53 additions and 8 deletions
|
@ -867,9 +867,10 @@
|
||||||
config :pleroma, Pleroma.Search,
|
config :pleroma, Pleroma.Search,
|
||||||
module: Pleroma.Search.DatabaseSearch,
|
module: Pleroma.Search.DatabaseSearch,
|
||||||
extensions: %{
|
extensions: %{
|
||||||
# this features is placed in the ':extensions' section for clarity
|
# these features are placed in the ':extensions' section for clarity
|
||||||
# as this is not in the upstream, at least not yet
|
# as they are not in the upstream, at least not yet
|
||||||
search_type_media: true
|
search_type_media: true,
|
||||||
|
search_option_following: true
|
||||||
}
|
}
|
||||||
|
|
||||||
config :pleroma, Pleroma.Search.Meilisearch,
|
config :pleroma, Pleroma.Search.Meilisearch,
|
||||||
|
|
|
@ -37,6 +37,10 @@ def by_author(query \\ Activity, %User{ap_id: ap_id}) do
|
||||||
from(a in query, where: a.actor == ^ap_id)
|
from(a in query, where: a.actor == ^ap_id)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def by_authors(query \\ Activity, actors) do
|
||||||
|
from(activity in query, where: activity.actor in ^actors)
|
||||||
|
end
|
||||||
|
|
||||||
def find_by_object_ap_id(activities, object_ap_id) do
|
def find_by_object_ap_id(activities, object_ap_id) do
|
||||||
Enum.find(
|
Enum.find(
|
||||||
activities,
|
activities,
|
||||||
|
|
|
@ -23,9 +23,13 @@ def search(user, search_query, options \\ []) do
|
||||||
true -> :gin
|
true -> :gin
|
||||||
end
|
end
|
||||||
|
|
||||||
|
can_search_following =
|
||||||
|
Pleroma.Config.get([Pleroma.Search, :extensions, :search_option_following], true)
|
||||||
|
|
||||||
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)
|
||||||
|
following = can_search_following && Keyword.get(options, :following, false)
|
||||||
only_media = Keyword.get(options, :only_media, false)
|
only_media = Keyword.get(options, :only_media, false)
|
||||||
|
|
||||||
search_function =
|
search_function =
|
||||||
|
@ -44,6 +48,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_restrict_following(user, following)
|
||||||
|> maybe_restrict_media(only_media)
|
|> maybe_restrict_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},
|
||||||
|
@ -67,6 +72,12 @@ def maybe_restrict_author(query, %User{} = author) do
|
||||||
|
|
||||||
def maybe_restrict_author(query, _), do: query
|
def maybe_restrict_author(query, _), do: query
|
||||||
|
|
||||||
|
def maybe_restrict_following(query, %User{} = user, true) do
|
||||||
|
Activity.Queries.by_authors(query, User.following_ap_ids(user))
|
||||||
|
end
|
||||||
|
|
||||||
|
def maybe_restrict_following(query, _, _), do: query
|
||||||
|
|
||||||
def maybe_restrict_blocked(query, %User{} = user) do
|
def maybe_restrict_blocked(query, %User{} = user) do
|
||||||
Activity.Queries.exclude_authors(query, User.blocked_users_ap_ids(user))
|
Activity.Queries.exclude_authors(query, User.blocked_users_ap_ids(user))
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,6 +2,12 @@
|
||||||
# Copyright © 2022-2022 Akkoma Authors <https://git.ihatebeinga.live/IHBAGang/akkoma/>
|
# Copyright © 2022-2022 Akkoma Authors <https://git.ihatebeinga.live/IHBAGang/akkoma/>
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
|
# NOTE: Elasticsearch has never been and will never be well supported.
|
||||||
|
# If you are experiencing strange behaviour such as posts being shuffled or
|
||||||
|
# missing, or the limit option not being respected, this module is the cause.
|
||||||
|
# If this bothers you, I recommend switching to database search or Meilisearch.
|
||||||
|
# Using Elasticsearch with non-humongous web services might be overkill anyway.
|
||||||
|
|
||||||
defmodule Pleroma.Search.Elasticsearch do
|
defmodule Pleroma.Search.Elasticsearch do
|
||||||
@behaviour Pleroma.Search.SearchBackend
|
@behaviour Pleroma.Search.SearchBackend
|
||||||
|
|
||||||
|
@ -9,6 +15,7 @@ defmodule Pleroma.Search.Elasticsearch do
|
||||||
alias Pleroma.Object.Fetcher
|
alias Pleroma.Object.Fetcher
|
||||||
alias Pleroma.Web.ActivityPub.Visibility
|
alias Pleroma.Web.ActivityPub.Visibility
|
||||||
alias Pleroma.Search.Elasticsearch.Parsers
|
alias Pleroma.Search.Elasticsearch.Parsers
|
||||||
|
alias Pleroma.User
|
||||||
|
|
||||||
def es_query(:activity, query, offset, limit) do
|
def es_query(:activity, query, offset, limit) do
|
||||||
must = Parsers.Activity.parse(query)
|
must = Parsers.Activity.parse(query)
|
||||||
|
@ -41,8 +48,12 @@ defp maybe_fetch(:activity, search_query) do
|
||||||
end
|
end
|
||||||
|
|
||||||
def search(user, query, options) do
|
def search(user, query, options) do
|
||||||
|
can_search_following =
|
||||||
|
Pleroma.Config.get([Pleroma.Search, :extensions, :search_option_following], true)
|
||||||
|
|
||||||
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)
|
||||||
|
following = can_search_following && Keyword.get(options, :following, false)
|
||||||
only_media = Keyword.get(options, :only_media, false)
|
only_media = Keyword.get(options, :only_media, false)
|
||||||
|
|
||||||
parsed_query =
|
parsed_query =
|
||||||
|
@ -62,11 +73,21 @@ def search(user, query, options) do
|
||||||
:activities
|
:activities
|
||||||
|> 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" &&
|
Enum.all?([
|
||||||
Visibility.visible_for_user?(x, user) &&
|
x.data["type"] == "Create",
|
||||||
# i'm not going to implement this very seriously because the support for
|
x.object.data["type"] == "Note",
|
||||||
# elasticsearch is already kinda broken
|
Visibility.visible_for_user?(x, user),
|
||||||
if only_media, do: length(x.object.data["attachment"]) > 0, else: true
|
if only_media do
|
||||||
|
length(x.object.data["attachment"]) > 0
|
||||||
|
else
|
||||||
|
true
|
||||||
|
end,
|
||||||
|
if following do
|
||||||
|
Enum.member?(User.following_ap_ids(user), x.object.data["actor"])
|
||||||
|
else
|
||||||
|
true
|
||||||
|
end
|
||||||
|
])
|
||||||
end)
|
end)
|
||||||
end)
|
end)
|
||||||
|
|
||||||
|
|
|
@ -76,9 +76,13 @@ def meili_delete!(path) do
|
||||||
end
|
end
|
||||||
|
|
||||||
def search(user, query, options \\ []) do
|
def search(user, query, options \\ []) do
|
||||||
|
can_search_following =
|
||||||
|
Pleroma.Config.get([Pleroma.Search, :extensions, :search_option_following], true)
|
||||||
|
|
||||||
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)
|
||||||
|
following = can_search_following && Keyword.get(options, :following, false)
|
||||||
only_media = Keyword.get(options, :only_media, false)
|
only_media = Keyword.get(options, :only_media, false)
|
||||||
|
|
||||||
res =
|
res =
|
||||||
|
@ -98,6 +102,7 @@ def search(user, 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_restrict_following(user, following)
|
||||||
|> maybe_restrict_media(only_media)
|
|> maybe_restrict_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"])
|
||||||
|
|
|
@ -92,6 +92,9 @@ def features do
|
||||||
if Config.get([Pleroma.Search, :extensions, :search_type_media], true) do
|
if Config.get([Pleroma.Search, :extensions, :search_type_media], true) do
|
||||||
"bnakkoma:search_type_media"
|
"bnakkoma:search_type_media"
|
||||||
end,
|
end,
|
||||||
|
if Config.get([Pleroma.Search, :extensions, :search_option_following], true) do
|
||||||
|
"bnakkoma:search_option_following"
|
||||||
|
end,
|
||||||
"custom_emoji_reactions",
|
"custom_emoji_reactions",
|
||||||
"pleroma:get:main/ostatus"
|
"pleroma:get:main/ostatus"
|
||||||
]
|
]
|
||||||
|
|
Loading…
Reference in a new issue