diff options
| author | rinpatch <rinpatch@sdf.org> | 2019-04-17 12:22:32 +0300 | 
|---|---|---|
| committer | rinpatch <rinpatch@sdf.org> | 2019-04-17 12:22:32 +0300 | 
| commit | 627e5a0a4992cc19fc65a7e93a09c470c8e2bf33 (patch) | |
| tree | 0f38b475e8554863a1cbbd7750c19d4cd1336eb1 /test/web/activity_pub/activity_pub_controller_test.exs | |
| parent | d6ab701a14f7c9fb4d59953648c425e04725fc62 (diff) | |
| parent | 73df3046e014ae16e03f16a9c82921652cefcb54 (diff) | |
| download | pleroma-627e5a0a4992cc19fc65a7e93a09c470c8e2bf33.tar.gz pleroma-627e5a0a4992cc19fc65a7e93a09c470c8e2bf33.zip | |
Merge branch 'develop' into feature/database-compaction
Diffstat (limited to 'test/web/activity_pub/activity_pub_controller_test.exs')
| -rw-r--r-- | test/web/activity_pub/activity_pub_controller_test.exs | 402 | 
1 files changed, 392 insertions, 10 deletions
| diff --git a/test/web/activity_pub/activity_pub_controller_test.exs b/test/web/activity_pub/activity_pub_controller_test.exs index 1c24b348c..7b1c60f15 100644 --- a/test/web/activity_pub/activity_pub_controller_test.exs +++ b/test/web/activity_pub/activity_pub_controller_test.exs @@ -1,9 +1,21 @@ +# Pleroma: A lightweight social networking server +# Copyright © 2017-2018 Pleroma Authors <https://pleroma.social/> +# SPDX-License-Identifier: AGPL-3.0-only +  defmodule Pleroma.Web.ActivityPub.ActivityPubControllerTest do    use Pleroma.Web.ConnCase    import Pleroma.Factory -  alias Pleroma.Web.ActivityPub.{UserView, ObjectView} -  alias Pleroma.{Repo, User}    alias Pleroma.Activity +  alias Pleroma.Instances +  alias Pleroma.Object +  alias Pleroma.User +  alias Pleroma.Web.ActivityPub.ObjectView +  alias Pleroma.Web.ActivityPub.UserView + +  setup_all do +    Tesla.Mock.mock_global(fn env -> apply(HttpRequestMock, :request, [env]) end) +    :ok +  end    describe "/relay" do      test "with the relay active, it returns the relay user", %{conn: conn} do @@ -18,17 +30,34 @@ defmodule Pleroma.Web.ActivityPub.ActivityPubControllerTest do      test "with the relay disabled, it returns 404", %{conn: conn} do        Pleroma.Config.put([:instance, :allow_relay], false) -      res = -        conn -        |> get(activity_pub_path(conn, :relay)) -        |> json_response(404) +      conn +      |> get(activity_pub_path(conn, :relay)) +      |> json_response(404) +      |> assert        Pleroma.Config.put([:instance, :allow_relay], true)      end    end    describe "/users/:nickname" do -    test "it returns a json representation of the user", %{conn: conn} do +    test "it returns a json representation of the user with accept application/json", %{ +      conn: conn +    } do +      user = insert(:user) + +      conn = +        conn +        |> put_req_header("accept", "application/json") +        |> get("/users/#{user.nickname}") + +      user = User.get_by_id(user.id) + +      assert json_response(conn, 200) == UserView.render("user.json", %{user: user}) +    end + +    test "it returns a json representation of the user with accept application/activity+json", %{ +      conn: conn +    } do        user = insert(:user)        conn = @@ -36,14 +65,47 @@ defmodule Pleroma.Web.ActivityPub.ActivityPubControllerTest do          |> put_req_header("accept", "application/activity+json")          |> get("/users/#{user.nickname}") -      user = Repo.get(User, user.id) +      user = User.get_by_id(user.id) + +      assert json_response(conn, 200) == UserView.render("user.json", %{user: user}) +    end + +    test "it returns a json representation of the user with accept application/ld+json", %{ +      conn: conn +    } do +      user = insert(:user) + +      conn = +        conn +        |> put_req_header( +          "accept", +          "application/ld+json; profile=\"https://www.w3.org/ns/activitystreams\"" +        ) +        |> get("/users/#{user.nickname}") + +      user = User.get_by_id(user.id)        assert json_response(conn, 200) == UserView.render("user.json", %{user: user})      end    end    describe "/object/:uuid" do -    test "it returns a json representation of the object", %{conn: conn} do +    test "it returns a json representation of the object with accept application/json", %{ +      conn: conn +    } do +      note = insert(:note) +      uuid = String.split(note.data["id"], "/") |> List.last() + +      conn = +        conn +        |> put_req_header("accept", "application/json") +        |> get("/objects/#{uuid}") + +      assert json_response(conn, 200) == ObjectView.render("object.json", %{object: note}) +    end + +    test "it returns a json representation of the object with accept application/activity+json", +         %{conn: conn} do        note = insert(:note)        uuid = String.split(note.data["id"], "/") |> List.last() @@ -55,6 +117,23 @@ defmodule Pleroma.Web.ActivityPub.ActivityPubControllerTest do        assert json_response(conn, 200) == ObjectView.render("object.json", %{object: note})      end +    test "it returns a json representation of the object with accept application/ld+json", %{ +      conn: conn +    } do +      note = insert(:note) +      uuid = String.split(note.data["id"], "/") |> List.last() + +      conn = +        conn +        |> put_req_header( +          "accept", +          "application/ld+json; profile=\"https://www.w3.org/ns/activitystreams\"" +        ) +        |> get("/objects/#{uuid}") + +      assert json_response(conn, 200) == ObjectView.render("object.json", %{object: note}) +    end +      test "it returns 404 for non-public messages", %{conn: conn} do        note = insert(:direct_note)        uuid = String.split(note.data["id"], "/") |> List.last() @@ -66,6 +145,59 @@ defmodule Pleroma.Web.ActivityPub.ActivityPubControllerTest do        assert json_response(conn, 404)      end + +    test "it returns 404 for tombstone objects", %{conn: conn} do +      tombstone = insert(:tombstone) +      uuid = String.split(tombstone.data["id"], "/") |> List.last() + +      conn = +        conn +        |> put_req_header("accept", "application/activity+json") +        |> get("/objects/#{uuid}") + +      assert json_response(conn, 404) +    end +  end + +  describe "/object/:uuid/likes" do +    test "it returns the like activities in a collection", %{conn: conn} do +      like = insert(:like_activity) +      uuid = String.split(like.data["object"], "/") |> List.last() + +      result = +        conn +        |> put_req_header("accept", "application/activity+json") +        |> get("/objects/#{uuid}/likes") +        |> json_response(200) + +      assert List.first(result["first"]["orderedItems"])["id"] == like.data["id"] +    end +  end + +  describe "/activities/:uuid" do +    test "it returns a json representation of the activity", %{conn: conn} do +      activity = insert(:note_activity) +      uuid = String.split(activity.data["id"], "/") |> List.last() + +      conn = +        conn +        |> put_req_header("accept", "application/activity+json") +        |> get("/activities/#{uuid}") + +      assert json_response(conn, 200) == ObjectView.render("object.json", %{object: activity}) +    end + +    test "it returns 404 for non-public activities", %{conn: conn} do +      activity = insert(:direct_note_activity) +      uuid = String.split(activity.data["id"], "/") |> List.last() + +      conn = +        conn +        |> put_req_header("accept", "application/activity+json") +        |> get("/activities/#{uuid}") + +      assert json_response(conn, 404) +    end    end    describe "/inbox" do @@ -82,6 +214,23 @@ defmodule Pleroma.Web.ActivityPub.ActivityPubControllerTest do        :timer.sleep(500)        assert Activity.get_by_ap_id(data["id"])      end + +    test "it clears `unreachable` federation status of the sender", %{conn: conn} do +      data = File.read!("test/fixtures/mastodon-post-activity.json") |> Poison.decode!() + +      sender_url = data["actor"] +      Instances.set_consistently_unreachable(sender_url) +      refute Instances.reachable?(sender_url) + +      conn = +        conn +        |> assign(:valid_signature, true) +        |> put_req_header("content-type", "application/activity+json") +        |> post("/inbox", data) + +      assert "ok" == json_response(conn, 200) +      assert Instances.reachable?(sender_url) +    end    end    describe "/users/:nickname/inbox" do @@ -103,9 +252,99 @@ defmodule Pleroma.Web.ActivityPub.ActivityPubControllerTest do        :timer.sleep(500)        assert Activity.get_by_ap_id(data["id"])      end + +    test "it accepts messages from actors that are followed by the user", %{conn: conn} do +      recipient = insert(:user) +      actor = insert(:user, %{ap_id: "http://mastodon.example.org/users/actor"}) + +      {:ok, recipient} = User.follow(recipient, actor) + +      data = +        File.read!("test/fixtures/mastodon-post-activity.json") +        |> Poison.decode!() + +      object = +        data["object"] +        |> Map.put("attributedTo", actor.ap_id) + +      data = +        data +        |> Map.put("actor", actor.ap_id) +        |> Map.put("object", object) + +      conn = +        conn +        |> assign(:valid_signature, true) +        |> put_req_header("content-type", "application/activity+json") +        |> post("/users/#{recipient.nickname}/inbox", data) + +      assert "ok" == json_response(conn, 200) +      :timer.sleep(500) +      assert Activity.get_by_ap_id(data["id"]) +    end + +    test "it rejects reads from other users", %{conn: conn} do +      user = insert(:user) +      otheruser = insert(:user) + +      conn = +        conn +        |> assign(:user, otheruser) +        |> put_req_header("accept", "application/activity+json") +        |> get("/users/#{user.nickname}/inbox") + +      assert json_response(conn, 403) +    end + +    test "it returns a note activity in a collection", %{conn: conn} do +      note_activity = insert(:direct_note_activity) +      user = User.get_cached_by_ap_id(hd(note_activity.data["to"])) + +      conn = +        conn +        |> assign(:user, user) +        |> put_req_header("accept", "application/activity+json") +        |> get("/users/#{user.nickname}/inbox") + +      assert response(conn, 200) =~ note_activity.data["object"]["content"] +    end + +    test "it clears `unreachable` federation status of the sender", %{conn: conn} do +      user = insert(:user) + +      data = +        File.read!("test/fixtures/mastodon-post-activity.json") +        |> Poison.decode!() +        |> Map.put("bcc", [user.ap_id]) + +      sender_host = URI.parse(data["actor"]).host +      Instances.set_consistently_unreachable(sender_host) +      refute Instances.reachable?(sender_host) + +      conn = +        conn +        |> assign(:valid_signature, true) +        |> put_req_header("content-type", "application/activity+json") +        |> post("/users/#{user.nickname}/inbox", data) + +      assert "ok" == json_response(conn, 200) +      assert Instances.reachable?(sender_host) +    end    end    describe "/users/:nickname/outbox" do +    test "it will not bomb when there is no activity", %{conn: conn} do +      user = insert(:user) + +      conn = +        conn +        |> put_req_header("accept", "application/activity+json") +        |> get("/users/#{user.nickname}/outbox") + +      result = json_response(conn, 200) +      assert user.ap_id <> "/outbox" == result["id"] +    end +      test "it returns a note activity in a collection", %{conn: conn} do        note_activity = insert(:note_activity)        user = User.get_cached_by_ap_id(note_activity.data["actor"]) @@ -129,6 +368,121 @@ defmodule Pleroma.Web.ActivityPub.ActivityPubControllerTest do        assert response(conn, 200) =~ announce_activity.data["object"]      end + +    test "it rejects posts from other users", %{conn: conn} do +      data = File.read!("test/fixtures/activitypub-client-post-activity.json") |> Poison.decode!() +      user = insert(:user) +      otheruser = insert(:user) + +      conn = +        conn +        |> assign(:user, otheruser) +        |> put_req_header("content-type", "application/activity+json") +        |> post("/users/#{user.nickname}/outbox", data) + +      assert json_response(conn, 403) +    end + +    test "it inserts an incoming create activity into the database", %{conn: conn} do +      data = File.read!("test/fixtures/activitypub-client-post-activity.json") |> Poison.decode!() +      user = insert(:user) + +      conn = +        conn +        |> assign(:user, user) +        |> put_req_header("content-type", "application/activity+json") +        |> post("/users/#{user.nickname}/outbox", data) + +      result = json_response(conn, 201) +      assert Activity.get_by_ap_id(result["id"]) +    end + +    test "it rejects an incoming activity with bogus type", %{conn: conn} do +      data = File.read!("test/fixtures/activitypub-client-post-activity.json") |> Poison.decode!() +      user = insert(:user) + +      data = +        data +        |> Map.put("type", "BadType") + +      conn = +        conn +        |> assign(:user, user) +        |> put_req_header("content-type", "application/activity+json") +        |> post("/users/#{user.nickname}/outbox", data) + +      assert json_response(conn, 400) +    end + +    test "it erects a tombstone when receiving a delete activity", %{conn: conn} do +      note_activity = insert(:note_activity) +      user = User.get_cached_by_ap_id(note_activity.data["actor"]) + +      data = %{ +        type: "Delete", +        object: %{ +          id: note_activity.data["object"]["id"] +        } +      } + +      conn = +        conn +        |> assign(:user, user) +        |> put_req_header("content-type", "application/activity+json") +        |> post("/users/#{user.nickname}/outbox", data) + +      result = json_response(conn, 201) +      assert Activity.get_by_ap_id(result["id"]) + +      object = Object.get_by_ap_id(note_activity.data["object"]["id"]) +      assert object +      assert object.data["type"] == "Tombstone" +    end + +    test "it rejects delete activity of object from other actor", %{conn: conn} do +      note_activity = insert(:note_activity) +      user = insert(:user) + +      data = %{ +        type: "Delete", +        object: %{ +          id: note_activity.data["object"]["id"] +        } +      } + +      conn = +        conn +        |> assign(:user, user) +        |> put_req_header("content-type", "application/activity+json") +        |> post("/users/#{user.nickname}/outbox", data) + +      assert json_response(conn, 400) +    end + +    test "it increases like count when receiving a like action", %{conn: conn} do +      note_activity = insert(:note_activity) +      user = User.get_cached_by_ap_id(note_activity.data["actor"]) + +      data = %{ +        type: "Like", +        object: %{ +          id: note_activity.data["object"]["id"] +        } +      } + +      conn = +        conn +        |> assign(:user, user) +        |> put_req_header("content-type", "application/activity+json") +        |> post("/users/#{user.nickname}/outbox", data) + +      result = json_response(conn, 201) +      assert Activity.get_by_ap_id(result["id"]) + +      object = Object.get_by_ap_id(note_activity.data["object"]["id"]) +      assert object +      assert object.data["like_count"] == 1 +    end    end    describe "/users/:nickname/followers" do @@ -145,6 +499,20 @@ defmodule Pleroma.Web.ActivityPub.ActivityPubControllerTest do        assert result["first"]["orderedItems"] == [user.ap_id]      end +    test "it returns returns empty if the user has 'hide_followers' set", %{conn: conn} do +      user = insert(:user) +      user_two = insert(:user, %{info: %{hide_followers: true}}) +      User.follow(user, user_two) + +      result = +        conn +        |> get("/users/#{user_two.nickname}/followers") +        |> json_response(200) + +      assert result["first"]["orderedItems"] == [] +      assert result["totalItems"] == 0 +    end +      test "it works for more than 10 users", %{conn: conn} do        user = insert(:user) @@ -186,11 +554,25 @@ defmodule Pleroma.Web.ActivityPub.ActivityPubControllerTest do        assert result["first"]["orderedItems"] == [user_two.ap_id]      end +    test "it returns returns empty if the user has 'hide_follows' set", %{conn: conn} do +      user = insert(:user, %{info: %{hide_follows: true}}) +      user_two = insert(:user) +      User.follow(user, user_two) + +      result = +        conn +        |> get("/users/#{user.nickname}/following") +        |> json_response(200) + +      assert result["first"]["orderedItems"] == [] +      assert result["totalItems"] == 0 +    end +      test "it works for more than 10 users", %{conn: conn} do        user = insert(:user)        Enum.each(1..15, fn _ -> -        user = Repo.get(User, user.id) +        user = User.get_by_id(user.id)          other_user = insert(:user)          User.follow(user, other_user)        end) | 
