1 # Pleroma: A lightweight social networking server
2 # Copyright © 2017-2019 Pleroma Authors <https://pleroma.social/>
3 # SPDX-License-Identifier: AGPL-3.0-only
5 defmodule Pleroma.Web.TwitterAPI.UtilControllerTest do
6 use Pleroma.Web.ConnCase
8 alias Pleroma.Notification
11 alias Pleroma.Web.CommonAPI
12 import Pleroma.Factory
16 Tesla.Mock.mock(fn env -> apply(HttpRequestMock, :request, [env]) end)
20 clear_config([:instance])
21 clear_config([:frontend_configurations, :pleroma_fe])
22 clear_config([:user, :deny_follow_blocked])
24 describe "POST /api/pleroma/follow_import" do
25 test "it returns HTTP 200", %{conn: conn} do
31 |> assign(:user, user1)
32 |> post("/api/pleroma/follow_import", %{"list" => "#{user2.ap_id}"})
35 assert response == "job started"
38 test "it imports follow lists from file", %{conn: conn} do
44 read!: fn "follow_list.txt" ->
45 "Account address,Show boosts\n#{user2.ap_id},true"
47 {PleromaJobQueue, [:passthrough], []}
51 |> assign(:user, user1)
52 |> post("/api/pleroma/follow_import", %{"list" => %Plug.Upload{path: "follow_list.txt"}})
56 PleromaJobQueue.enqueue(
59 [:follow_import, user1, [user2.ap_id]]
63 assert response == "job started"
67 test "it imports new-style mastodon follow lists", %{conn: conn} do
73 |> assign(:user, user1)
74 |> post("/api/pleroma/follow_import", %{
75 "list" => "Account address,Show boosts\n#{user2.ap_id},true"
79 assert response == "job started"
82 test "requires 'follow' permission", %{conn: conn} do
83 token1 = insert(:oauth_token, scopes: ["read", "write"])
84 token2 = insert(:oauth_token, scopes: ["follow"])
85 another_user = insert(:user)
87 for token <- [token1, token2] do
90 |> put_req_header("authorization", "Bearer #{token.token}")
91 |> post("/api/pleroma/follow_import", %{"list" => "#{another_user.ap_id}"})
94 assert %{"error" => "Insufficient permissions: follow."} == json_response(conn, 403)
96 assert json_response(conn, 200)
102 describe "POST /api/pleroma/blocks_import" do
103 test "it returns HTTP 200", %{conn: conn} do
104 user1 = insert(:user)
105 user2 = insert(:user)
109 |> assign(:user, user1)
110 |> post("/api/pleroma/blocks_import", %{"list" => "#{user2.ap_id}"})
111 |> json_response(:ok)
113 assert response == "job started"
116 test "it imports blocks users from file", %{conn: conn} do
117 user1 = insert(:user)
118 user2 = insert(:user)
119 user3 = insert(:user)
122 {File, [], read!: fn "blocks_list.txt" -> "#{user2.ap_id} #{user3.ap_id}" end},
123 {PleromaJobQueue, [:passthrough], []}
127 |> assign(:user, user1)
128 |> post("/api/pleroma/blocks_import", %{"list" => %Plug.Upload{path: "blocks_list.txt"}})
129 |> json_response(:ok)
132 PleromaJobQueue.enqueue(
135 [:blocks_import, user1, [user2.ap_id, user3.ap_id]]
139 assert response == "job started"
144 describe "POST /api/pleroma/notifications/read" do
145 test "it marks a single notification as read", %{conn: conn} do
146 user1 = insert(:user)
147 user2 = insert(:user)
148 {:ok, activity1} = CommonAPI.post(user2, %{"status" => "hi @#{user1.nickname}"})
149 {:ok, activity2} = CommonAPI.post(user2, %{"status" => "hi @#{user1.nickname}"})
150 {:ok, [notification1]} = Notification.create_notifications(activity1)
151 {:ok, [notification2]} = Notification.create_notifications(activity2)
154 |> assign(:user, user1)
155 |> post("/api/pleroma/notifications/read", %{"id" => "#{notification1.id}"})
156 |> json_response(:ok)
158 assert Repo.get(Notification, notification1.id).seen
159 refute Repo.get(Notification, notification2.id).seen
162 test "it returns error when notification not found", %{conn: conn} do
163 user1 = insert(:user)
167 |> assign(:user, user1)
168 |> post("/api/pleroma/notifications/read", %{"id" => "22222222222222"})
169 |> json_response(403)
171 assert response == %{"error" => "Cannot get notification"}
175 describe "PUT /api/pleroma/notification_settings" do
176 test "it updates notification settings", %{conn: conn} do
180 |> assign(:user, user)
181 |> put("/api/pleroma/notification_settings", %{
182 "followers" => false,
185 |> json_response(:ok)
187 user = Repo.get(User, user.id)
190 "followers" => false,
192 "non_follows" => true,
193 "non_followers" => true
194 } == user.info.notification_settings
198 describe "GET /api/statusnet/config" do
199 test "it returns config in xml format", %{conn: conn} do
200 instance = Pleroma.Config.get(:instance)
204 |> put_req_header("accept", "application/xml")
205 |> get("/api/statusnet/config")
209 "<config>\n<site>\n<name>#{Keyword.get(instance, :name)}</name>\n<site>#{
210 Pleroma.Web.base_url()
211 }</site>\n<textlimit>#{Keyword.get(instance, :limit)}</textlimit>\n<closed>#{
212 !Keyword.get(instance, :registrations_open)
213 }</closed>\n</site>\n</config>\n"
216 test "it returns config in json format", %{conn: conn} do
217 instance = Pleroma.Config.get(:instance)
218 Pleroma.Config.put([:instance, :managed_config], true)
219 Pleroma.Config.put([:instance, :registrations_open], false)
220 Pleroma.Config.put([:instance, :invites_enabled], true)
221 Pleroma.Config.put([:instance, :public], false)
222 Pleroma.Config.put([:frontend_configurations, :pleroma_fe], %{theme: "asuka-hospital"})
226 |> put_req_header("accept", "application/json")
227 |> get("/api/statusnet/config")
228 |> json_response(:ok)
232 "accountActivationRequired" => "0",
234 "description" => Keyword.get(instance, :description),
235 "invitesEnabled" => "1",
236 "name" => Keyword.get(instance, :name),
237 "pleromafe" => %{"theme" => "asuka-hospital"},
239 "safeDMMentionsEnabled" => "0",
240 "server" => Pleroma.Web.base_url(),
241 "textlimit" => to_string(Keyword.get(instance, :limit)),
243 "avatarlimit" => to_string(Keyword.get(instance, :avatar_upload_limit)),
244 "backgroundlimit" => to_string(Keyword.get(instance, :background_upload_limit)),
245 "bannerlimit" => to_string(Keyword.get(instance, :banner_upload_limit)),
246 "uploadlimit" => to_string(Keyword.get(instance, :upload_limit))
248 "vapidPublicKey" => Keyword.get(Pleroma.Web.Push.vapid_config(), :public_key)
252 assert response == expected_data
255 test "returns the state of safe_dm_mentions flag", %{conn: conn} do
256 Pleroma.Config.put([:instance, :safe_dm_mentions], true)
260 |> get("/api/statusnet/config.json")
261 |> json_response(:ok)
263 assert response["site"]["safeDMMentionsEnabled"] == "1"
265 Pleroma.Config.put([:instance, :safe_dm_mentions], false)
269 |> get("/api/statusnet/config.json")
270 |> json_response(:ok)
272 assert response["site"]["safeDMMentionsEnabled"] == "0"
275 test "it returns the managed config", %{conn: conn} do
276 Pleroma.Config.put([:instance, :managed_config], false)
277 Pleroma.Config.put([:frontend_configurations, :pleroma_fe], %{theme: "asuka-hospital"})
281 |> get("/api/statusnet/config.json")
282 |> json_response(:ok)
284 refute response["site"]["pleromafe"]
286 Pleroma.Config.put([:instance, :managed_config], true)
290 |> get("/api/statusnet/config.json")
291 |> json_response(:ok)
293 assert response["site"]["pleromafe"] == %{"theme" => "asuka-hospital"}
297 describe "GET /api/pleroma/frontend_configurations" do
298 test "returns everything in :pleroma, :frontend_configurations", %{conn: conn} do
309 Pleroma.Config.put(:frontend_configurations, config)
313 |> get("/api/pleroma/frontend_configurations")
314 |> json_response(:ok)
316 assert response == Jason.encode!(config |> Enum.into(%{})) |> Jason.decode!()
320 describe "/api/pleroma/emoji" do
321 test "returns json with custom emoji with tags", %{conn: conn} do
324 |> get("/api/pleroma/emoji")
325 |> json_response(200)
327 assert Enum.all?(emoji, fn
333 is_binary(url) and is_list(tags)
338 describe "GET /ostatus_subscribe - remote_follow/2" do
339 test "adds status to pleroma instance if the `acct` is a status", %{conn: conn} do
343 "/ostatus_subscribe?acct=https://mastodon.social/users/emelie/statuses/101849165031453009"
346 assert redirected_to(conn) =~ "/notice/"
349 test "show follow account page if the `acct` is a account link", %{conn: conn} do
353 "/ostatus_subscribe?acct=https://mastodon.social/users/emelie"
356 assert html_response(response, 200) =~ "Log in to follow"
359 test "show follow page if the `acct` is a account link", %{conn: conn} do
364 |> assign(:user, user)
365 |> get("/ostatus_subscribe?acct=https://mastodon.social/users/emelie")
367 assert html_response(response, 200) =~ "Remote follow"
370 test "show follow page with error when user cannot fecth by `acct` link", %{conn: conn} do
375 |> assign(:user, user)
376 |> get("/ostatus_subscribe?acct=https://mastodon.social/users/not_found")
378 assert html_response(response, 200) =~ "Error fetching user"
382 describe "POST /ostatus_subscribe - do_remote_follow/2 with assigned user " do
383 test "follows user", %{conn: conn} do
385 user2 = insert(:user)
389 |> assign(:user, user)
390 |> post("/ostatus_subscribe", %{"user" => %{"id" => user2.id}})
393 assert response =~ "Account followed!"
394 assert user2.follower_address in refresh_record(user).following
397 test "returns error when user is deactivated", %{conn: conn} do
398 user = insert(:user, info: %{deactivated: true})
399 user2 = insert(:user)
403 |> assign(:user, user)
404 |> post("/ostatus_subscribe", %{"user" => %{"id" => user2.id}})
407 assert response =~ "Error following account"
410 test "returns error when user is blocked", %{conn: conn} do
411 Pleroma.Config.put([:user, :deny_follow_blocked], true)
413 user2 = insert(:user)
415 {:ok, _user} = Pleroma.User.block(user2, user)
419 |> assign(:user, user)
420 |> post("/ostatus_subscribe", %{"user" => %{"id" => user2.id}})
423 assert response =~ "Error following account"
426 test "returns error when followee not found", %{conn: conn} do
431 |> assign(:user, user)
432 |> post("/ostatus_subscribe", %{"user" => %{"id" => "jimm"}})
435 assert response =~ "Error following account"
438 test "returns success result when user already in followers", %{conn: conn} do
440 user2 = insert(:user)
441 {:ok, _, _, _} = CommonAPI.follow(user, user2)
445 |> assign(:user, refresh_record(user))
446 |> post("/ostatus_subscribe", %{"user" => %{"id" => user2.id}})
449 assert response =~ "Account followed!"
453 describe "POST /ostatus_subscribe - do_remote_follow/2 without assigned user " do
454 test "follows", %{conn: conn} do
456 user2 = insert(:user)
460 |> post("/ostatus_subscribe", %{
461 "authorization" => %{"name" => user.nickname, "password" => "test", "id" => user2.id}
465 assert response =~ "Account followed!"
466 assert user2.follower_address in refresh_record(user).following
469 test "returns error when followee not found", %{conn: conn} do
474 |> post("/ostatus_subscribe", %{
475 "authorization" => %{"name" => user.nickname, "password" => "test", "id" => "jimm"}
479 assert response =~ "Error following account"
482 test "returns error when login invalid", %{conn: conn} do
487 |> post("/ostatus_subscribe", %{
488 "authorization" => %{"name" => "jimm", "password" => "test", "id" => user.id}
492 assert response =~ "Wrong username or password"
495 test "returns error when password invalid", %{conn: conn} do
497 user2 = insert(:user)
501 |> post("/ostatus_subscribe", %{
502 "authorization" => %{"name" => user.nickname, "password" => "42", "id" => user2.id}
506 assert response =~ "Wrong username or password"
509 test "returns error when user is blocked", %{conn: conn} do
510 Pleroma.Config.put([:user, :deny_follow_blocked], true)
512 user2 = insert(:user)
513 {:ok, _user} = Pleroma.User.block(user2, user)
517 |> post("/ostatus_subscribe", %{
518 "authorization" => %{"name" => user.nickname, "password" => "test", "id" => user2.id}
522 assert response =~ "Error following account"
526 describe "GET /api/pleroma/healthcheck" do
527 clear_config([:instance, :healthcheck])
529 test "returns 503 when healthcheck disabled", %{conn: conn} do
530 Pleroma.Config.put([:instance, :healthcheck], false)
534 |> get("/api/pleroma/healthcheck")
535 |> json_response(503)
537 assert response == %{}
540 test "returns 200 when healthcheck enabled and all ok", %{conn: conn} do
541 Pleroma.Config.put([:instance, :healthcheck], true)
543 with_mock Pleroma.Healthcheck,
544 system_info: fn -> %Pleroma.Healthcheck{healthy: true} end do
547 |> get("/api/pleroma/healthcheck")
548 |> json_response(200)
560 test "returns 503 when healthcheck enabled and health is false", %{conn: conn} do
561 Pleroma.Config.put([:instance, :healthcheck], true)
563 with_mock Pleroma.Healthcheck,
564 system_info: fn -> %Pleroma.Healthcheck{healthy: false} end do
567 |> get("/api/pleroma/healthcheck")
568 |> json_response(503)
581 describe "POST /api/pleroma/disable_account" do
582 test "it returns HTTP 200", %{conn: conn} do
587 |> assign(:user, user)
588 |> post("/api/pleroma/disable_account", %{"password" => "test"})
589 |> json_response(:ok)
591 assert response == %{"status" => "success"}
593 user = User.get_cached_by_id(user.id)
595 assert user.info.deactivated == true
598 test "it returns returns when password invalid", %{conn: conn} do
603 |> assign(:user, user)
604 |> post("/api/pleroma/disable_account", %{"password" => "test1"})
605 |> json_response(:ok)
607 assert response == %{"error" => "Invalid password."}
608 user = User.get_cached_by_id(user.id)
610 refute user.info.deactivated
614 describe "GET /api/statusnet/version" do
615 test "it returns version in xml format", %{conn: conn} do
618 |> put_req_header("accept", "application/xml")
619 |> get("/api/statusnet/version")
622 assert response == "<version>#{Pleroma.Application.named_version()}</version>"
625 test "it returns version in json format", %{conn: conn} do
628 |> put_req_header("accept", "application/json")
629 |> get("/api/statusnet/version")
630 |> json_response(:ok)
632 assert response == "#{Pleroma.Application.named_version()}"
636 describe "POST /main/ostatus - remote_subscribe/2" do
637 test "renders subscribe form", %{conn: conn} do
642 |> post("/main/ostatus", %{"nickname" => user.nickname, "profile" => ""})
645 refute response =~ "Could not find user"
646 assert response =~ "Remotely follow #{user.nickname}"
649 test "renders subscribe form with error when user not found", %{conn: conn} do
652 |> post("/main/ostatus", %{"nickname" => "nickname", "profile" => ""})
655 assert response =~ "Could not find user"
656 refute response =~ "Remotely follow"
659 test "it redirect to webfinger url", %{conn: conn} do
661 user2 = insert(:user, ap_id: "shp@social.heldscal.la")
665 |> post("/main/ostatus", %{
666 "user" => %{"nickname" => user.nickname, "profile" => user2.ap_id}
669 assert redirected_to(conn) ==
670 "https://social.heldscal.la/main/ostatussub?profile=#{user.ap_id}"
673 test "it renders form with error when use not found", %{conn: conn} do
674 user2 = insert(:user, ap_id: "shp@social.heldscal.la")
678 |> post("/main/ostatus", %{"user" => %{"nickname" => "jimm", "profile" => user2.ap_id}})
681 assert response =~ "Something went wrong."
685 test "it returns new captcha", %{conn: conn} do
686 with_mock Pleroma.Captcha,
687 new: fn -> "test_captcha" end do
690 |> get("/api/pleroma/captcha")
693 assert resp == "\"test_captcha\""
694 assert called(Pleroma.Captcha.new())