X-Git-Url: https://git.squeep.com/?a=blobdiff_plain;f=lib%2Fpleroma%2Fweb%2Factivity_pub%2Factivity_pub.ex;h=41f6a0f1f79fde06025d6c14adfe71cb4f4f6f91;hb=c623b4324deaf236334a0f77a81435b5bffadf3c;hp=9f55b3542dcc201c24b09ee57d2e539145003f9c;hpb=41e0304757c5a0d9778f7e685c9ddf481f0e15cb;p=akkoma diff --git a/lib/pleroma/web/activity_pub/activity_pub.ex b/lib/pleroma/web/activity_pub/activity_pub.ex index 9f55b3542..41f6a0f1f 100644 --- a/lib/pleroma/web/activity_pub/activity_pub.ex +++ b/lib/pleroma/web/activity_pub/activity_pub.ex @@ -17,12 +17,14 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do alias Pleroma.Web.ActivityPub.MRF alias Pleroma.Web.ActivityPub.Transmogrifier alias Pleroma.Web.WebFinger + alias Pleroma.Workers.BackgroundWorker import Ecto.Query import Pleroma.Web.ActivityPub.Utils import Pleroma.Web.ActivityPub.Visibility require Logger + require Pleroma.Constants # For Announce activities, we filter the recipients based on following status for any actors # that match actual users. See issue #164 for more information about why this is necessary. @@ -64,12 +66,12 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do if not is_nil(actor) do with user <- User.get_cached_by_ap_id(actor), false <- user.info.deactivated do - :ok + true else - _e -> :reject + _e -> false end else - :ok + true end end @@ -118,10 +120,10 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do def increase_poll_votes_if_vote(_create_data), do: :noop - def insert(map, local \\ true, fake \\ false) when is_map(map) do + def insert(map, local \\ true, fake \\ false, bypass_actor_check \\ false) when is_map(map) do with nil <- Activity.normalize(map), map <- lazy_put_activity_defaults(map, fake), - :ok <- check_actor_is_active(map["actor"]), + true <- bypass_actor_check || check_actor_is_active(map["actor"]), {_, true} <- {:remote_limit_error, check_remote_limit(map)}, {:ok, map} <- MRF.filter(map), {recipients, _, _} = get_recipients(map), @@ -138,13 +140,13 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do # Splice in the child object if we have one. activity = - if !is_nil(object) do + if not is_nil(object) do Map.put(activity, :object, object) else activity end - PleromaJobQueue.enqueue(:background, Pleroma.Web.RichMedia.Helpers, [:fetch, activity]) + BackgroundWorker.enqueue("fetch_data_for_activity", %{"activity_id" => activity.id}) Notification.create_notifications(activity) @@ -207,8 +209,6 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do def stream_out_participations(_, _), do: :noop def stream_out(activity) do - public = "https://www.w3.org/ns/activitystreams#Public" - if activity.data["type"] in ["Create", "Announce", "Delete"] do object = Object.normalize(activity) # Do not stream out poll replies @@ -216,7 +216,7 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do Pleroma.Web.Streamer.stream("user", activity) Pleroma.Web.Streamer.stream("list", activity) - if Enum.member?(activity.data["to"], public) do + if get_visibility(activity) == "public" do Pleroma.Web.Streamer.stream("public", activity) if activity.local do @@ -238,13 +238,8 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do end end else - # TODO: Write test, replace with visibility test - if !Enum.member?(activity.data["cc"] || [], public) && - !Enum.member?( - activity.data["to"], - User.get_cached_by_ap_id(activity.data["actor"]).follower_address - ), - do: Pleroma.Web.Streamer.stream("direct", activity) + if get_visibility(activity) == "direct", + do: Pleroma.Web.Streamer.stream("direct", activity) end end end @@ -273,6 +268,9 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do else {:fake, true, activity} -> {:ok, activity} + + {:error, message} -> + {:error, message} end end @@ -334,12 +332,7 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do end end - def unlike( - %User{} = actor, - %Object{} = object, - activity_id \\ nil, - local \\ true - ) do + def unlike(%User{} = actor, %Object{} = object, activity_id \\ nil, local \\ true) do with %Activity{} = like_activity <- get_existing_like(actor.ap_id, object), unlike_data <- make_unlike_data(actor, like_activity, activity_id), {:ok, unlike_activity} <- insert(unlike_data, local), @@ -391,7 +384,8 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do def follow(follower, followed, activity_id \\ nil, local \\ true) do with data <- make_follow_data(follower, followed, activity_id), {:ok, activity} <- insert(data, local), - :ok <- maybe_federate(activity) do + :ok <- maybe_federate(activity), + _ <- User.set_follow_state_cache(follower.ap_id, followed.ap_id, activity.data["state"]) do {:ok, activity} end end @@ -413,7 +407,7 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do "actor" => ap_id, "object" => %{"type" => "Person", "id" => ap_id} }, - {:ok, activity} <- insert(data, true, true), + {:ok, activity} <- insert(data, true, true, true), :ok <- maybe_federate(activity) do {:ok, user} end @@ -514,13 +508,15 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do end defp fetch_activities_for_context_query(context, opts) do - public = ["https://www.w3.org/ns/activitystreams#Public"] + public = [Pleroma.Constants.as_public()] recipients = if opts["user"], do: [opts["user"].ap_id | opts["user"].following] ++ public, else: public from(activity in Activity) |> maybe_preload_objects(opts) + |> maybe_preload_bookmarks(opts) + |> maybe_set_thread_muted_field(opts) |> restrict_blocked(opts) |> restrict_recipients(recipients, opts["user"]) |> where( @@ -534,6 +530,7 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do ) ) |> exclude_poll_votes(opts) + |> exclude_id(opts) |> order_by([activity], desc: activity.id) end @@ -555,7 +552,7 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do end def fetch_public_activities(opts \\ %{}) do - q = fetch_activities_query(["https://www.w3.org/ns/activitystreams#Public"], opts) + q = fetch_activities_query([Pleroma.Constants.as_public()], opts) q |> restrict_unlisted() @@ -626,6 +623,7 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do params = params |> Map.put("type", ["Create", "Announce"]) + |> Map.put("user", reading_user) |> Map.put("actor_id", user.ap_id) |> Map.put("whole_db", true) |> Map.put("pinned_activity_ids", user.info.pinned_activities) @@ -646,10 +644,9 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do defp user_activities_recipients(%{"reading_user" => reading_user}) do if reading_user do - ["https://www.w3.org/ns/activitystreams#Public"] ++ - [reading_user.ap_id | reading_user.following] + [Pleroma.Constants.as_public()] ++ [reading_user.ap_id | reading_user.following] else - ["https://www.w3.org/ns/activitystreams#Public"] + [Pleroma.Constants.as_public()] end end @@ -753,8 +750,8 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do defp restrict_favorited_by(query, %{"favorited_by" => ap_id}) do from( - activity in query, - where: fragment(~s(? <@ (? #> '{"object","likes"}'\)), ^ap_id, activity.data) + [_activity, object] in query, + where: fragment("(?)->'likes' \\? (?)", object.data, ^ap_id) ) end @@ -790,14 +787,20 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do defp restrict_muted(query, %{"with_muted" => val}) when val in [true, "true", "1"], do: query - defp restrict_muted(query, %{"muting_user" => %User{info: info}}) do + defp restrict_muted(query, %{"muting_user" => %User{info: info}} = opts) do mutes = info.mutes - from( - activity in query, - where: fragment("not (? = ANY(?))", activity.actor, ^mutes), - where: fragment("not (?->'to' \\?| ?)", activity.data, ^mutes) - ) + query = + from([activity] in query, + where: fragment("not (? = ANY(?))", activity.actor, ^mutes), + where: fragment("not (?->'to' \\?| ?)", activity.data, ^mutes) + ) + + unless opts["skip_preload"] do + from([thread_mute: tm] in query, where: is_nil(tm.user_id)) + else + query + end end defp restrict_muted(query, _), do: query @@ -834,7 +837,7 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do fragment( "not (coalesce(?->'cc', '{}'::jsonb) \\?| ?)", activity.data, - ^["https://www.w3.org/ns/activitystreams#Public"] + ^[Pleroma.Constants.as_public()] ) ) end @@ -874,6 +877,12 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do end end + defp exclude_id(query, %{"exclude_id" => id}) when is_binary(id) do + from(activity in query, where: activity.id != ^id) + end + + defp exclude_id(query, _), do: query + defp maybe_preload_objects(query, %{"skip_preload" => true}), do: query defp maybe_preload_objects(query, _) do @@ -892,7 +901,7 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do defp maybe_set_thread_muted_field(query, opts) do query - |> Activity.with_set_thread_muted_field(opts["user"]) + |> Activity.with_set_thread_muted_field(opts["muting_user"] || opts["user"]) end defp maybe_order(query, %{order: :desc}) do @@ -971,7 +980,7 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do where: fragment("? && ?", activity.recipients, ^recipients) or (fragment("? && ?", activity.recipients, ^recipients_with_public) and - "https://www.w3.org/ns/activitystreams#Public" in activity.recipients) + ^Pleroma.Constants.as_public() in activity.recipients) ) end @@ -1010,6 +1019,12 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do "url" => [%{"href" => data["image"]["url"]}] } + fields = + data + |> Map.get("attachment", []) + |> Enum.filter(fn %{"type" => t} -> t == "PropertyValue" end) + |> Enum.map(fn fields -> Map.take(fields, ["name", "value"]) end) + locked = data["manuallyApprovesFollowers"] || false data = Transmogrifier.maybe_fix_user_object(data) @@ -1019,6 +1034,7 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do ap_enabled: true, source_data: data, banner: banner, + fields: fields, locked: locked }, avatar: avatar,