mirror of
https://git.pleroma.social/pleroma/pleroma.git
synced 2025-02-08 15:22:32 +00:00
CommonAPI: Use object validation pipeline
This commit is contained in:
parent
138ead9856
commit
44c773c814
27 changed files with 141 additions and 35 deletions
0
changelog.d/pipeline-local-create.skip
Normal file
0
changelog.d/pipeline-local-create.skip
Normal file
|
@ -232,6 +232,21 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do
|
|||
end
|
||||
end
|
||||
|
||||
defp maybe_create_activity_expiration(%{data: %{"expires_at" => expires_at}} = activity)
|
||||
when is_bitstring(expires_at) do
|
||||
with {_, {:ok, expires_at, _}} <- {:datetime, DateTime.from_iso8601(expires_at)},
|
||||
{:ok, _job} <-
|
||||
Pleroma.Workers.PurgeExpiredActivity.enqueue(%{
|
||||
activity_id: activity.id,
|
||||
expires_at: expires_at
|
||||
}) do
|
||||
{:ok, activity}
|
||||
else
|
||||
{:datetime, _} -> {:ok, activity}
|
||||
e -> e
|
||||
end
|
||||
end
|
||||
|
||||
defp maybe_create_activity_expiration(activity), do: {:ok, activity}
|
||||
|
||||
defp create_or_bump_conversation(activity, actor) do
|
||||
|
|
|
@ -207,6 +207,7 @@ defmodule Pleroma.Web.ActivityPub.Builder do
|
|||
data =
|
||||
%{
|
||||
"type" => "Note",
|
||||
"id" => Utils.generate_object_id(),
|
||||
"to" => draft.to,
|
||||
"cc" => draft.cc,
|
||||
"content" => draft.content_html,
|
||||
|
|
|
@ -144,7 +144,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidator do
|
|||
do_separate_with_history(object, fn object ->
|
||||
with {:ok, object} <-
|
||||
object
|
||||
|> validator.cast_and_validate()
|
||||
|> validator.cast_and_validate(meta)
|
||||
|> Ecto.Changeset.apply_action(:insert) do
|
||||
object = stringify_keys(object)
|
||||
|
||||
|
|
|
@ -36,7 +36,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.AcceptRejectValidator do
|
|||
|> validate_accept_reject_rights()
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
data
|
||||
|> cast_data
|
||||
|> validate_data
|
||||
|
|
|
@ -26,7 +26,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.AddRemoveValidator do
|
|||
end
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
{:ok, actor} = User.get_or_fetch_by_ap_id(data["actor"])
|
||||
|
||||
{:ok, actor} = maybe_refetch_user(actor)
|
||||
|
|
|
@ -32,7 +32,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.AnnounceValidator do
|
|||
field(:published, ObjectValidators.DateTime)
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
data
|
||||
|> cast_data()
|
||||
|> validate_data()
|
||||
|
|
|
@ -37,7 +37,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.AnswerValidator do
|
|||
|> apply_action(:insert)
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
data
|
||||
|> cast_data()
|
||||
|> validate_data()
|
||||
|
|
|
@ -34,13 +34,15 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.ArticleNotePageValidator do
|
|||
|> apply_action(:insert)
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, meta \\ []) do
|
||||
data
|
||||
|> cast_data()
|
||||
|> validate_data()
|
||||
|> cast_data(meta)
|
||||
|> validate_data(meta)
|
||||
end
|
||||
|
||||
def cast_data(data) do
|
||||
def cast_data(data, meta \\ []) do
|
||||
data = fix(data, meta)
|
||||
|
||||
%__MODULE__{}
|
||||
|> changeset(data)
|
||||
end
|
||||
|
@ -76,7 +78,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.ArticleNotePageValidator do
|
|||
|
||||
def fix_attachments(data), do: data
|
||||
|
||||
defp fix(data) do
|
||||
defp fix(data, _meta) do
|
||||
data
|
||||
|> CommonFixes.fix_actor()
|
||||
|> CommonFixes.fix_object_defaults()
|
||||
|
@ -90,21 +92,29 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.ArticleNotePageValidator do
|
|||
end
|
||||
|
||||
def changeset(struct, data) do
|
||||
data = fix(data)
|
||||
|
||||
struct
|
||||
|> cast(data, __schema__(:fields) -- [:attachment, :tag])
|
||||
|> cast(data, __schema__(:fields) -- [:attachment, :tag, :generator])
|
||||
|> cast_embed(:attachment)
|
||||
|> cast_embed(:tag)
|
||||
|> cast_embed(:generator)
|
||||
end
|
||||
|
||||
defp validate_data(data_cng) do
|
||||
defp validate_data(data_cng, meta) do
|
||||
data_cng
|
||||
|> validate_inclusion(:type, ["Article", "Note", "Page"])
|
||||
|> validate_required([:id, :actor, :attributedTo, :type, :context])
|
||||
|> CommonValidations.validate_any_presence([:cc, :to])
|
||||
|> maybe_to_cc(meta)
|
||||
|> CommonValidations.validate_fields_match([:actor, :attributedTo])
|
||||
|> CommonValidations.validate_actor_presence()
|
||||
|> CommonValidations.validate_host_match()
|
||||
end
|
||||
|
||||
defp maybe_to_cc(data_cng, meta) do
|
||||
if meta[:local] != true do
|
||||
data_cng
|
||||
|> CommonValidations.validate_any_presence([:cc, :to])
|
||||
else
|
||||
data_cng
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -27,7 +27,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.AttachmentValidator do
|
|||
end
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
data
|
||||
|> cast_data()
|
||||
|> validate_data()
|
||||
|
|
|
@ -31,7 +31,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.AudioImageVideoValidator do
|
|||
|> apply_action(:insert)
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
data
|
||||
|> cast_data()
|
||||
|> validate_data()
|
||||
|
@ -109,9 +109,10 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.AudioImageVideoValidator do
|
|||
data = fix(data)
|
||||
|
||||
struct
|
||||
|> cast(data, __schema__(:fields) -- [:attachment, :tag])
|
||||
|> cast(data, __schema__(:fields) -- [:attachment, :tag, :generator])
|
||||
|> cast_embed(:attachment, required: true)
|
||||
|> cast_embed(:tag)
|
||||
|> cast_embed(:generator)
|
||||
end
|
||||
|
||||
defp validate_data(data_cng) do
|
||||
|
|
|
@ -35,7 +35,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.BlockValidator do
|
|||
|> CommonValidations.validate_actor_presence(field_name: :object)
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
data
|
||||
|> cast_data
|
||||
|> validate_data
|
||||
|
|
|
@ -33,7 +33,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.ChatMessageValidator do
|
|||
|> apply_action(:insert)
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
data
|
||||
|> cast_data()
|
||||
|> validate_data()
|
||||
|
|
|
@ -5,6 +5,7 @@
|
|||
defmodule Pleroma.Web.ActivityPub.ObjectValidators.CommonFields do
|
||||
alias Pleroma.EctoType.ActivityPub.ObjectValidators
|
||||
alias Pleroma.Web.ActivityPub.ObjectValidators.AttachmentValidator
|
||||
alias Pleroma.Web.ActivityPub.ObjectValidators.GeneratorValidator
|
||||
alias Pleroma.Web.ActivityPub.ObjectValidators.TagValidator
|
||||
|
||||
# Activities and Objects, except (Create)ChatMessage
|
||||
|
@ -64,6 +65,8 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.CommonFields do
|
|||
|
||||
field(:likes, {:array, ObjectValidators.ObjectID}, default: [])
|
||||
field(:announcements, {:array, ObjectValidators.ObjectID}, default: [])
|
||||
|
||||
embeds_one(:generator, GeneratorValidator)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -82,8 +82,17 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.CreateGenericValidator do
|
|||
defp validate_data(cng, meta) do
|
||||
object = meta[:object_data]
|
||||
|
||||
required = [:actor, :type, :object]
|
||||
|
||||
required =
|
||||
if meta[:local] == true do
|
||||
required
|
||||
else
|
||||
required ++ [:to, :cc]
|
||||
end
|
||||
|
||||
cng
|
||||
|> validate_required([:actor, :type, :object, :to, :cc])
|
||||
|> validate_required(required)
|
||||
|> validate_inclusion(:type, ["Create"])
|
||||
|> CommonValidations.validate_actor_presence()
|
||||
|> validate_actors_match(object)
|
||||
|
|
|
@ -70,7 +70,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.DeleteValidator do
|
|||
!same_domain?(cng)
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
data
|
||||
|> cast_data
|
||||
|> validate_data
|
||||
|
|
|
@ -29,7 +29,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.EmojiReactValidator do
|
|||
field(:content, :string)
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
data
|
||||
|> cast_data()
|
||||
|> validate_data()
|
||||
|
|
|
@ -32,7 +32,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.EventValidator do
|
|||
|> apply_action(:insert)
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
data
|
||||
|> cast_data()
|
||||
|> validate_data()
|
||||
|
@ -54,9 +54,10 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.EventValidator do
|
|||
data = fix(data)
|
||||
|
||||
struct
|
||||
|> cast(data, __schema__(:fields) -- [:attachment, :tag])
|
||||
|> cast(data, __schema__(:fields) -- [:attachment, :tag, :generator])
|
||||
|> cast_embed(:attachment)
|
||||
|> cast_embed(:tag)
|
||||
|> cast_embed(:generator)
|
||||
end
|
||||
|
||||
defp validate_data(data_cng) do
|
||||
|
|
|
@ -36,7 +36,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.FollowValidator do
|
|||
|> validate_actor_presence(field_name: :object)
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
data
|
||||
|> cast_data
|
||||
|> validate_data
|
||||
|
|
|
@ -0,0 +1,40 @@
|
|||
# Pleroma: A lightweight social networking server
|
||||
# Copyright © 2017-2022 Pleroma Authors <https://pleroma.social/>
|
||||
# SPDX-License-Identifier: AGPL-3.0-only
|
||||
|
||||
defmodule Pleroma.Web.ActivityPub.ObjectValidators.GeneratorValidator do
|
||||
use Ecto.Schema
|
||||
|
||||
alias Pleroma.EctoType.ActivityPub.ObjectValidators
|
||||
|
||||
import Ecto.Changeset
|
||||
|
||||
@primary_key false
|
||||
embedded_schema do
|
||||
field(:type, :string)
|
||||
field(:name, :string)
|
||||
field(:url, ObjectValidators.BareUri)
|
||||
end
|
||||
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
data
|
||||
|> cast_data()
|
||||
|> validate_data()
|
||||
end
|
||||
|
||||
def cast_data(data) do
|
||||
%__MODULE__{}
|
||||
|> changeset(data)
|
||||
end
|
||||
|
||||
def changeset(struct, data) do
|
||||
struct
|
||||
|> cast(data, __schema__(:fields))
|
||||
end
|
||||
|
||||
defp validate_data(cng) do
|
||||
cng
|
||||
|> validate_inclusion(:type, ~w[Application])
|
||||
|> validate_required([:name, :url])
|
||||
end
|
||||
end
|
|
@ -26,7 +26,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.LikeValidator do
|
|||
field(:context, :string)
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
data
|
||||
|> cast_data()
|
||||
|> validate_data()
|
||||
|
|
|
@ -40,7 +40,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.QuestionValidator do
|
|||
|> apply_action(:insert)
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
data
|
||||
|> cast_data()
|
||||
|> validate_data()
|
||||
|
@ -72,11 +72,12 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.QuestionValidator do
|
|||
data = fix(data)
|
||||
|
||||
struct
|
||||
|> cast(data, __schema__(:fields) -- [:anyOf, :oneOf, :attachment, :tag])
|
||||
|> cast(data, __schema__(:fields) -- [:anyOf, :oneOf, :attachment, :tag, :generator])
|
||||
|> cast_embed(:attachment)
|
||||
|> cast_embed(:anyOf)
|
||||
|> cast_embed(:oneOf)
|
||||
|> cast_embed(:tag)
|
||||
|> cast_embed(:generator)
|
||||
end
|
||||
|
||||
defp validate_data(data_cng) do
|
||||
|
|
|
@ -33,7 +33,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.TagValidator do
|
|||
field(:id, ObjectValidators.Uri)
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
data
|
||||
|> cast_data()
|
||||
end
|
||||
|
|
|
@ -23,7 +23,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.UndoValidator do
|
|||
end
|
||||
end
|
||||
|
||||
def cast_and_validate(data) do
|
||||
def cast_and_validate(data, _meta \\ []) do
|
||||
data
|
||||
|> cast_data()
|
||||
|> validate_data()
|
||||
|
|
|
@ -198,7 +198,6 @@ defmodule Pleroma.Web.ActivityPub.SideEffects do
|
|||
# - Increase the user note count
|
||||
# - Increase the reply count
|
||||
# - Increase replies count
|
||||
# - Set up ActivityExpiration
|
||||
# - Set up notifications
|
||||
# - Index incoming posts for search (if needed)
|
||||
@impl true
|
||||
|
|
|
@ -691,7 +691,7 @@ defmodule Pleroma.Web.ActivityPub.Utils do
|
|||
#### Create-related helpers
|
||||
|
||||
def make_create_data(params, additional) do
|
||||
published = params.published || make_date()
|
||||
published = Map.get(params, :published) || make_date()
|
||||
|
||||
%{
|
||||
"type" => "Create",
|
||||
|
@ -702,6 +702,11 @@ defmodule Pleroma.Web.ActivityPub.Utils do
|
|||
"context" => params.context
|
||||
}
|
||||
|> Map.merge(additional)
|
||||
|> Maps.put_if_present(
|
||||
"expires_at",
|
||||
additional["expires_at"],
|
||||
&{:ok, DateTime.to_iso8601(&1)}
|
||||
)
|
||||
end
|
||||
|
||||
#### Listen-related helpers
|
||||
|
|
|
@ -462,8 +462,29 @@ defmodule Pleroma.Web.CommonAPI do
|
|||
|
||||
@spec post(User.t(), map()) :: {:ok, Activity.t()} | {:error, any()}
|
||||
def post(user, %{status: _} = data) do
|
||||
with {:ok, draft} <- ActivityDraft.create(user, data) do
|
||||
ActivityPub.create(draft.changes, draft.preview?)
|
||||
published = Utils.make_date()
|
||||
|
||||
with {:ok, %{changes: changes, preview?: fake} = _draft} <- ActivityDraft.create(user, data),
|
||||
changes <-
|
||||
changes
|
||||
|> Map.put_new(:published, published)
|
||||
|> Map.put(
|
||||
"object",
|
||||
changes.object
|
||||
|> Map.put_new("id", Utils.generate_object_id())
|
||||
|> Map.put_new("published", published)
|
||||
|> Map.merge(changes.additional)
|
||||
),
|
||||
create_data <-
|
||||
changes
|
||||
|> Utils.make_create_data(changes.additional),
|
||||
{:fake, false, _data} <- {:fake, fake, create_data},
|
||||
{:ok, create, _} <- Pipeline.common_pipeline(create_data, local: true) do
|
||||
{:ok, create}
|
||||
else
|
||||
{:fake, true, activity} -> {:ok, activity}
|
||||
{:error, _} = e -> e
|
||||
e -> {:error, e}
|
||||
end
|
||||
end
|
||||
|
||||
|
|
Loading…
Reference in a new issue