Merge remote-tracking branch 'remotes/origin/develop' into 2168-media-preview-proxy
[akkoma] / test / user_test.exs
index a00b1b5e21ef19330077cf0423ecdd2e70682d51..9788e09d9b24f5d74bace103993e53c6c6d5797a 100644 (file)
@@ -15,7 +15,6 @@ defmodule Pleroma.UserTest do
   use Pleroma.DataCase
   use Oban.Testing, repo: Pleroma.Repo
 
-  import Mock
   import Pleroma.Factory
   import ExUnit.CaptureLog
 
@@ -200,6 +199,16 @@ defmodule Pleroma.UserTest do
     assert [^pending_follower] = User.get_follow_requests(locked)
   end
 
+  test "doesn't return follow requests for deactivated accounts" do
+    locked = insert(:user, locked: true)
+    pending_follower = insert(:user, %{deactivated: true})
+
+    CommonAPI.follow(pending_follower, locked)
+
+    assert true == pending_follower.deactivated
+    assert [] = User.get_follow_requests(locked)
+  end
+
   test "clears follow requests when requester is blocked" do
     followed = insert(:user, locked: true)
     follower = insert(:user)
@@ -477,6 +486,15 @@ defmodule Pleroma.UserTest do
     }
     setup do: clear_config([:instance, :account_activation_required], true)
 
+    test "it sets the 'accepts_chat_messages' set to true" do
+      changeset = User.register_changeset(%User{}, @full_user_data)
+      assert changeset.valid?
+
+      {:ok, user} = Repo.insert(changeset)
+
+      assert user.accepts_chat_messages
+    end
+
     test "it creates unconfirmed user" do
       changeset = User.register_changeset(%User{}, @full_user_data)
       assert changeset.valid?
@@ -556,6 +574,7 @@ defmodule Pleroma.UserTest do
       assert user == fetched_user
     end
 
+    @tag capture_log: true
     test "returns nil if no user could be fetched" do
       {:error, fetched_user} = User.get_or_fetch_by_nickname("nonexistant@social.heldscal.la")
       assert fetched_user == "not found nonexistant@social.heldscal.la"
@@ -582,10 +601,55 @@ defmodule Pleroma.UserTest do
 
       {:ok, user} = User.get_or_fetch_by_ap_id("http://mastodon.example.org/users/admin")
 
-      assert user.source_data["endpoints"]
+      assert user.inbox
 
       refute user.last_refreshed_at == orig_user.last_refreshed_at
     end
+
+    test "if nicknames clash, the old user gets a prefix with the old id to the nickname" do
+      a_week_ago = NaiveDateTime.add(NaiveDateTime.utc_now(), -604_800)
+
+      orig_user =
+        insert(
+          :user,
+          local: false,
+          nickname: "admin@mastodon.example.org",
+          ap_id: "http://mastodon.example.org/users/harinezumigari",
+          last_refreshed_at: a_week_ago
+        )
+
+      assert orig_user.last_refreshed_at == a_week_ago
+
+      {:ok, user} = User.get_or_fetch_by_ap_id("http://mastodon.example.org/users/admin")
+
+      assert user.inbox
+
+      refute user.id == orig_user.id
+
+      orig_user = User.get_by_id(orig_user.id)
+
+      assert orig_user.nickname == "#{orig_user.id}.admin@mastodon.example.org"
+    end
+
+    @tag capture_log: true
+    test "it returns the old user if stale, but unfetchable" do
+      a_week_ago = NaiveDateTime.add(NaiveDateTime.utc_now(), -604_800)
+
+      orig_user =
+        insert(
+          :user,
+          local: false,
+          nickname: "admin@mastodon.example.org",
+          ap_id: "http://mastodon.example.org/users/raymoo",
+          last_refreshed_at: a_week_ago
+        )
+
+      assert orig_user.last_refreshed_at == a_week_ago
+
+      {:ok, user} = User.get_or_fetch_by_ap_id("http://mastodon.example.org/users/raymoo")
+
+      assert user.last_refreshed_at == orig_user.last_refreshed_at
+    end
   end
 
   test "returns an ap_id for a user" do
@@ -610,7 +674,7 @@ defmodule Pleroma.UserTest do
              ) <> "/followers"
   end
 
-  describe "remote user creation changeset" do
+  describe "remote user changeset" do
     @valid_remote %{
       bio: "hello",
       name: "Someone",
@@ -622,28 +686,28 @@ defmodule Pleroma.UserTest do
     setup do: clear_config([:instance, :user_name_length])
 
     test "it confirms validity" do
-      cs = User.remote_user_creation(@valid_remote)
+      cs = User.remote_user_changeset(@valid_remote)
       assert cs.valid?
     end
 
     test "it sets the follower_adress" do
-      cs = User.remote_user_creation(@valid_remote)
+      cs = User.remote_user_changeset(@valid_remote)
       # remote users get a fake local follower address
       assert cs.changes.follower_address ==
                User.ap_followers(%User{nickname: @valid_remote[:nickname]})
     end
 
     test "it enforces the fqn format for nicknames" do
-      cs = User.remote_user_creation(%{@valid_remote | nickname: "bla"})
+      cs = User.remote_user_changeset(%{@valid_remote | nickname: "bla"})
       assert Ecto.Changeset.get_field(cs, :local) == false
       assert cs.changes.avatar
       refute cs.valid?
     end
 
     test "it has required fields" do
-      [:name, :ap_id]
+      [:ap_id]
       |> Enum.each(fn field ->
-        cs = User.remote_user_creation(Map.delete(@valid_remote, field))
+        cs = User.remote_user_changeset(Map.delete(@valid_remote, field))
         refute cs.valid?
       end)
     end
@@ -756,8 +820,8 @@ defmodule Pleroma.UserTest do
       ]
 
       {:ok, job} = User.follow_import(user1, identifiers)
-      result = ObanHelpers.perform(job)
 
+      assert {:ok, result} = ObanHelpers.perform(job)
       assert is_list(result)
       assert result == [user2, user3]
     end
@@ -979,14 +1043,26 @@ defmodule Pleroma.UserTest do
       ]
 
       {:ok, job} = User.blocks_import(user1, identifiers)
-      result = ObanHelpers.perform(job)
 
+      assert {:ok, result} = ObanHelpers.perform(job)
       assert is_list(result)
       assert result == [user2, user3]
     end
   end
 
   describe "get_recipients_from_activity" do
+    test "works for announces" do
+      actor = insert(:user)
+      user = insert(:user, local: true)
+
+      {:ok, activity} = CommonAPI.post(actor, %{status: "hello"})
+      {:ok, announce} = CommonAPI.repeat(activity.id, user)
+
+      recipients = User.get_recipients_from_activity(announce)
+
+      assert user in recipients
+    end
+
     test "get recipients" do
       actor = insert(:user)
       user = insert(:user, local: true)
@@ -996,7 +1072,7 @@ defmodule Pleroma.UserTest do
 
       {:ok, activity} =
         CommonAPI.post(actor, %{
-          "status" => "hey @#{addressed.nickname} @#{addressed_remote.nickname}"
+          status: "hey @#{addressed.nickname} @#{addressed_remote.nickname}"
         })
 
       assert Enum.map([actor, addressed], & &1.ap_id) --
@@ -1018,7 +1094,7 @@ defmodule Pleroma.UserTest do
 
       {:ok, activity} =
         CommonAPI.post(actor, %{
-          "status" => "hey @#{addressed.nickname}"
+          status: "hey @#{addressed.nickname}"
         })
 
       assert Enum.map([actor, addressed], & &1.ap_id) --
@@ -1079,7 +1155,7 @@ defmodule Pleroma.UserTest do
 
       {:ok, user2} = User.follow(user2, user)
 
-      {:ok, activity} = CommonAPI.post(user, %{"status" => "hey @#{user2.nickname}"})
+      {:ok, activity} = CommonAPI.post(user, %{status: "hey @#{user2.nickname}"})
 
       activity = Repo.preload(activity, :bookmark)
 
@@ -1090,7 +1166,7 @@ defmodule Pleroma.UserTest do
 
       assert [%{activity | thread_muted?: CommonAPI.thread_muted?(user2, activity)}] ==
                ActivityPub.fetch_activities([user2.ap_id | User.following(user2)], %{
-                 "user" => user2
+                 user: user2
                })
 
       {:ok, _user} = User.deactivate(user)
@@ -1100,7 +1176,7 @@ defmodule Pleroma.UserTest do
 
       assert [] ==
                ActivityPub.fetch_activities([user2.ap_id | User.following(user2)], %{
-                 "user" => user2
+                 user: user2
                })
     end
   end
@@ -1115,27 +1191,21 @@ defmodule Pleroma.UserTest do
     setup do: clear_config([:instance, :federating])
 
     test ".delete_user_activities deletes all create activities", %{user: user} do
-      {:ok, activity} = CommonAPI.post(user, %{"status" => "2hu"})
+      {:ok, activity} = CommonAPI.post(user, %{status: "2hu"})
 
       User.delete_user_activities(user)
 
-      # TODO: Remove favorites, repeats, delete activities.
+      # TODO: Test removal favorites, repeats, delete activities.
       refute Activity.get_by_id(activity.id)
     end
 
-    test "it deletes deactivated user" do
-      {:ok, user} = insert(:user, deactivated: true) |> User.set_cache()
-
-      {:ok, job} = User.delete(user)
-      {:ok, _user} = ObanHelpers.perform(job)
-
-      refute User.get_by_id(user.id)
-    end
-
-    test "it deletes a user, all follow relationships and all activities", %{user: user} do
+    test "it deactivates a user, all follow relationships and all activities", %{user: user} do
       follower = insert(:user)
       {:ok, follower} = User.follow(follower, user)
 
+      locked_user = insert(:user, name: "locked", locked: true)
+      {:ok, _} = User.follow(user, locked_user, :follow_pending)
+
       object = insert(:note, user: user)
       activity = insert(:note_activity, user: user, note: object)
 
@@ -1144,7 +1214,7 @@ defmodule Pleroma.UserTest do
 
       {:ok, like} = CommonAPI.favorite(user, activity_two.id)
       {:ok, like_two} = CommonAPI.favorite(follower, activity.id)
-      {:ok, repeat, _} = CommonAPI.repeat(activity_two.id, user)
+      {:ok, repeat} = CommonAPI.repeat(activity_two.id, user)
 
       {:ok, job} = User.delete(user)
       {:ok, _user} = ObanHelpers.perform(job)
@@ -1152,8 +1222,9 @@ defmodule Pleroma.UserTest do
       follower = User.get_cached_by_id(follower.id)
 
       refute User.following?(follower, user)
-      refute User.get_by_id(user.id)
-      assert {:ok, nil} == Cachex.get(:user_cache, "ap_id:#{user.ap_id}")
+      assert %{deactivated: true} = User.get_by_id(user.id)
+
+      assert [] == User.get_follow_requests(locked_user)
 
       user_activities =
         user.ap_id
@@ -1168,87 +1239,37 @@ defmodule Pleroma.UserTest do
       refute Activity.get_by_id(like_two.id)
       refute Activity.get_by_id(repeat.id)
     end
-
-    test_with_mock "it sends out User Delete activity",
-                   %{user: user},
-                   Pleroma.Web.ActivityPub.Publisher,
-                   [:passthrough],
-                   [] do
-      Pleroma.Config.put([:instance, :federating], true)
-
-      {:ok, follower} = User.get_or_fetch_by_ap_id("http://mastodon.example.org/users/admin")
-      {:ok, _} = User.follow(follower, user)
-
-      {:ok, job} = User.delete(user)
-      {:ok, _user} = ObanHelpers.perform(job)
-
-      assert ObanHelpers.member?(
-               %{
-                 "op" => "publish_one",
-                 "params" => %{
-                   "inbox" => "http://mastodon.example.org/inbox",
-                   "id" => "pleroma:fakeid"
-                 }
-               },
-               all_enqueued(worker: Pleroma.Workers.PublisherWorker)
-             )
-    end
   end
 
-  test "get_public_key_for_ap_id fetches a user that's not in the db" do
-    assert {:ok, _key} = User.get_public_key_for_ap_id("http://mastodon.example.org/users/admin")
-  end
-
-  describe "insert or update a user from given data" do
-    test "with normal data" do
-      user = insert(:user, %{nickname: "nick@name.de"})
-      data = %{ap_id: user.ap_id <> "xxx", name: user.name, nickname: user.nickname}
-
-      assert {:ok, %User{}} = User.insert_or_update_user(data)
+  describe "delete/1 when confirmation is pending" do
+    setup do
+      user = insert(:user, confirmation_pending: true)
+      {:ok, user: user}
     end
 
-    test "with overly long fields" do
-      current_max_length = Pleroma.Config.get([:instance, :account_field_value_length], 255)
-      user = insert(:user, nickname: "nickname@supergood.domain")
+    test "deletes user from database when activation required", %{user: user} do
+      clear_config([:instance, :account_activation_required], true)
 
-      data = %{
-        ap_id: user.ap_id,
-        name: user.name,
-        nickname: user.nickname,
-        fields: [
-          %{"name" => "myfield", "value" => String.duplicate("h", current_max_length + 1)}
-        ]
-      }
+      {:ok, job} = User.delete(user)
+      {:ok, _} = ObanHelpers.perform(job)
 
-      assert {:ok, %User{}} = User.insert_or_update_user(data)
+      refute User.get_cached_by_id(user.id)
+      refute User.get_by_id(user.id)
     end
 
-    test "with an overly long bio" do
-      current_max_length = Pleroma.Config.get([:instance, :user_bio_length], 5000)
-      user = insert(:user, nickname: "nickname@supergood.domain")
+    test "deactivates user when activation is not required", %{user: user} do
+      clear_config([:instance, :account_activation_required], false)
 
-      data = %{
-        ap_id: user.ap_id,
-        name: user.name,
-        nickname: user.nickname,
-        bio: String.duplicate("h", current_max_length + 1)
-      }
+      {:ok, job} = User.delete(user)
+      {:ok, _} = ObanHelpers.perform(job)
 
-      assert {:ok, %User{}} = User.insert_or_update_user(data)
+      assert %{deactivated: true} = User.get_cached_by_id(user.id)
+      assert %{deactivated: true} = User.get_by_id(user.id)
     end
+  end
 
-    test "with an overly long display name" do
-      current_max_length = Pleroma.Config.get([:instance, :user_name_length], 100)
-      user = insert(:user, nickname: "nickname@supergood.domain")
-
-      data = %{
-        ap_id: user.ap_id,
-        name: String.duplicate("h", current_max_length + 1),
-        nickname: user.nickname
-      }
-
-      assert {:ok, %User{}} = User.insert_or_update_user(data)
-    end
+  test "get_public_key_for_ap_id fetches a user that's not in the db" do
+    assert {:ok, _key} = User.get_public_key_for_ap_id("http://mastodon.example.org/users/admin")
   end
 
   describe "per-user rich-text filtering" do
@@ -1365,11 +1386,11 @@ defmodule Pleroma.UserTest do
     end
   end
 
-  describe "visible_for?/2" do
+  describe "visible_for/2" do
     test "returns true when the account is itself" do
       user = insert(:user, local: true)
 
-      assert User.visible_for?(user, user)
+      assert User.visible_for(user, user) == :visible
     end
 
     test "returns false when the account is unauthenticated and auth is required" do
@@ -1378,14 +1399,14 @@ defmodule Pleroma.UserTest do
       user = insert(:user, local: true, confirmation_pending: true)
       other_user = insert(:user, local: true)
 
-      refute User.visible_for?(user, other_user)
+      refute User.visible_for(user, other_user) == :visible
     end
 
     test "returns true when the account is unauthenticated and auth is not required" do
       user = insert(:user, local: true, confirmation_pending: true)
       other_user = insert(:user, local: true)
 
-      assert User.visible_for?(user, other_user)
+      assert User.visible_for(user, other_user) == :visible
     end
 
     test "returns true when the account is unauthenticated and being viewed by a privileged account (auth required)" do
@@ -1394,7 +1415,7 @@ defmodule Pleroma.UserTest do
       user = insert(:user, local: true, confirmation_pending: true)
       other_user = insert(:user, local: true, is_admin: true)
 
-      assert User.visible_for?(user, other_user)
+      assert User.visible_for(user, other_user) == :visible
     end
   end
 
@@ -1487,7 +1508,7 @@ defmodule Pleroma.UserTest do
 
         {:ok, _} =
           CommonAPI.post(user, %{
-            "status" => "hey @#{to.nickname}"
+            status: "hey @#{to.nickname}"
           })
       end)
 
@@ -1519,12 +1540,12 @@ defmodule Pleroma.UserTest do
       Enum.each(recipients, fn to ->
         {:ok, _} =
           CommonAPI.post(sender, %{
-            "status" => "hey @#{to.nickname}"
+            status: "hey @#{to.nickname}"
           })
 
         {:ok, _} =
           CommonAPI.post(sender, %{
-            "status" => "hey again @#{to.nickname}"
+            status: "hey again @#{to.nickname}"
           })
       end)
 
@@ -1825,4 +1846,16 @@ defmodule Pleroma.UserTest do
       assert result.email_notifications["digest"] == false
     end
   end
+
+  test "avatar fallback" do
+    user = insert(:user)
+    assert User.avatar_url(user) =~ "/images/avi.png"
+
+    clear_config([:assets, :default_user_avatar], "avatar.png")
+
+    user = User.get_cached_by_nickname_or_id(user.nickname)
+    assert User.avatar_url(user) =~ "avatar.png"
+
+    assert User.avatar_url(user, no_default: true) == nil
+  end
 end