diff --git a/lib/pleroma/signature.ex b/lib/pleroma/signature.ex index 91e610fe1..25fad22f7 100644 --- a/lib/pleroma/signature.ex +++ b/lib/pleroma/signature.ex @@ -6,7 +6,6 @@ defmodule Pleroma.Signature do @behaviour HTTPSignatures.Adapter alias Pleroma.User - alias Pleroma.Web.ActivityPub.ActivityPub alias Pleroma.User.SigningKey require Logger diff --git a/lib/pleroma/user/signing_key.ex b/lib/pleroma/user/signing_key.ex index 60f1edb7c..709ee2593 100644 --- a/lib/pleroma/user/signing_key.ex +++ b/lib/pleroma/user/signing_key.ex @@ -4,7 +4,6 @@ defmodule Pleroma.User.SigningKey do import Ecto.Changeset alias Pleroma.User alias Pleroma.Repo - alias Pleroma.HTTP require Logger @@ -136,7 +135,7 @@ def public_key_pem(%User{} = user) do end end - def public_key_pem(e) do + def public_key_pem(_e) do {:error, "key not found"} end @@ -190,7 +189,7 @@ def fetch_remote_key(key_id) do resp = Pleroma.Object.Fetcher.fetch_and_contain_remote_object_from_id(key_id) case resp do - {:ok, _original_url, body} -> + {:ok, _body} -> case handle_signature_response(resp) do {:ok, ap_id, public_key_pem} -> Logger.debug("Fetched remote key: #{ap_id}") @@ -227,16 +226,13 @@ defp extract_key_details(%{"id" => ap_id, "publicKey" => public_key}) do end end - defp handle_signature_response({:ok, _original_url, body}) do - case Jason.decode(body) do - {:ok, %{"id" => _user_id, "publicKey" => _public_key} = body} -> + defp handle_signature_response({:ok, body}) do + case body do + %{"id" => _user_id, "publicKey" => _public_key} -> extract_key_details(body) - {:ok, %{"error" => error}} -> + %{"error" => error} -> {:error, error} - - {:error, _} -> - {:error, "Could not parse key"} end end diff --git a/lib/pleroma/web/plugs/ensure_user_public_key_plug.ex b/lib/pleroma/web/plugs/ensure_user_public_key_plug.ex index 4da9215a3..3eaa131e9 100644 --- a/lib/pleroma/web/plugs/ensure_user_public_key_plug.ex +++ b/lib/pleroma/web/plugs/ensure_user_public_key_plug.ex @@ -14,7 +14,7 @@ def call(conn, _opts) do key_id = key_id_from_conn(conn) unless is_nil(key_id) do - User.SigningKey.fetch_remote_key(key_id) + User.SigningKey.get_or_fetch_by_key_id(key_id) # now we SHOULD have the user that owns the key locally. maybe. # if we don't, we'll error out when we try to validate. end diff --git a/test/pleroma/web/activity_pub/activity_pub_controller_test.exs b/test/pleroma/web/activity_pub/activity_pub_controller_test.exs index 183818159..c41a19cc7 100644 --- a/test/pleroma/web/activity_pub/activity_pub_controller_test.exs +++ b/test/pleroma/web/activity_pub/activity_pub_controller_test.exs @@ -1094,7 +1094,7 @@ test "it returns a note activity in a collection", %{conn: conn} do test "it clears `unreachable` federation status of the sender", %{conn: conn, data: data} do user = - insert(:user) + insert(:user, ap_id: data["actor"]) |> with_signing_key() data = Map.put(data, "bcc", [user.ap_id]) @@ -1277,12 +1277,22 @@ test "forwarded report from mastodon", %{conn: conn} do |> File.read!() |> String.replace("{{DOMAIN}}", remote_domain) - Tesla.Mock.mock(fn %{url: ^remote_actor} -> - %Tesla.Env{ - status: 200, - body: mock_json_body, - headers: [{"content-type", "application/activity+json"}] - } + key_url = "#{remote_actor}#main-key" + + Tesla.Mock.mock(fn + %{url: ^remote_actor} -> + %Tesla.Env{ + status: 200, + body: mock_json_body, + headers: [{"content-type", "application/activity+json"}] + } + + %{url: ^key_url} -> + %Tesla.Env{ + status: 200, + body: mock_json_body, + headers: [{"content-type", "application/activity+json"}] + } end) data = %{ diff --git a/test/pleroma/web/activity_pub/views/user_view_test.exs b/test/pleroma/web/activity_pub/views/user_view_test.exs index 2a367b680..7e251e510 100644 --- a/test/pleroma/web/activity_pub/views/user_view_test.exs +++ b/test/pleroma/web/activity_pub/views/user_view_test.exs @@ -11,7 +11,9 @@ defmodule Pleroma.Web.ActivityPub.UserViewTest do alias Pleroma.Web.CommonAPI test "Renders a user, including the public key" do - user = insert(:user) + user = + insert(:user) + |> with_signing_key() result = UserView.render("user.json", %{user: user}) @@ -37,7 +39,9 @@ test "Renders profile fields" do end test "Renders with emoji tags" do - user = insert(:user, emoji: %{"bib" => "/test"}) + user = + insert(:user, emoji: %{"bib" => "/test"}) + |> with_signing_key() assert %{ "tag" => [ @@ -74,13 +78,18 @@ test "Does not add an avatar image if the user hasn't set one" do end test "renders an invisible user with the invisible property set to true" do - user = insert(:user, invisible: true) + user = + insert(:user, invisible: true) + |> with_signing_key() assert %{"invisible" => true} = UserView.render("service.json", %{user: user}) end test "service has a few essential fields" do - user = insert(:user) + user = + insert(:user) + |> with_signing_key() + result = UserView.render("service.json", %{user: user}) assert result["id"] assert result["type"] == "Application" @@ -120,7 +129,9 @@ test "remote users have an empty endpoints structure" do end test "instance users do not expose oAuth endpoints" do - user = insert(:user, nickname: nil, local: true) + user = + insert(:user, nickname: nil, local: true) + |> with_signing_key() result = UserView.render("user.json", %{user: user})