Merge branch 'fix/failed-legacy-test' into 'develop'
[akkoma] / test / web / mastodon_api / mastodon_api_controller_test.exs
1 # Pleroma: A lightweight social networking server
2 # Copyright © 2017-2019 Pleroma Authors <https://pleroma.social/>
3 # SPDX-License-Identifier: AGPL-3.0-only
4
5 defmodule Pleroma.Web.MastodonAPI.MastodonAPIControllerTest do
6 use Pleroma.Web.ConnCase
7
8 alias Ecto.Changeset
9 alias Pleroma.Activity
10 alias Pleroma.Notification
11 alias Pleroma.Object
12 alias Pleroma.Repo
13 alias Pleroma.User
14 alias Pleroma.Web.ActivityPub.ActivityPub
15 alias Pleroma.Web.CommonAPI
16 alias Pleroma.Web.MastodonAPI.FilterView
17 alias Pleroma.Web.OAuth.App
18 alias Pleroma.Web.OStatus
19 alias Pleroma.Web.Push
20 alias Pleroma.Web.TwitterAPI.TwitterAPI
21 import Pleroma.Factory
22 import ExUnit.CaptureLog
23 import Tesla.Mock
24
25 setup do
26 mock(fn env -> apply(HttpRequestMock, :request, [env]) end)
27 :ok
28 end
29
30 test "the home timeline", %{conn: conn} do
31 user = insert(:user)
32 following = insert(:user)
33
34 {:ok, _activity} = TwitterAPI.create_status(following, %{"status" => "test"})
35
36 conn =
37 conn
38 |> assign(:user, user)
39 |> get("/api/v1/timelines/home")
40
41 assert Enum.empty?(json_response(conn, 200))
42
43 {:ok, user} = User.follow(user, following)
44
45 conn =
46 build_conn()
47 |> assign(:user, user)
48 |> get("/api/v1/timelines/home")
49
50 assert [%{"content" => "test"}] = json_response(conn, 200)
51 end
52
53 test "the public timeline", %{conn: conn} do
54 following = insert(:user)
55
56 capture_log(fn ->
57 {:ok, _activity} = TwitterAPI.create_status(following, %{"status" => "test"})
58
59 {:ok, [_activity]} =
60 OStatus.fetch_activity_from_url("https://shitposter.club/notice/2827873")
61
62 conn =
63 conn
64 |> get("/api/v1/timelines/public", %{"local" => "False"})
65
66 assert length(json_response(conn, 200)) == 2
67
68 conn =
69 build_conn()
70 |> get("/api/v1/timelines/public", %{"local" => "True"})
71
72 assert [%{"content" => "test"}] = json_response(conn, 200)
73
74 conn =
75 build_conn()
76 |> get("/api/v1/timelines/public", %{"local" => "1"})
77
78 assert [%{"content" => "test"}] = json_response(conn, 200)
79 end)
80 end
81
82 test "posting a status", %{conn: conn} do
83 user = insert(:user)
84
85 idempotency_key = "Pikachu rocks!"
86
87 conn_one =
88 conn
89 |> assign(:user, user)
90 |> put_req_header("idempotency-key", idempotency_key)
91 |> post("/api/v1/statuses", %{
92 "status" => "cofe",
93 "spoiler_text" => "2hu",
94 "sensitive" => "false"
95 })
96
97 {:ok, ttl} = Cachex.ttl(:idempotency_cache, idempotency_key)
98 # Six hours
99 assert ttl > :timer.seconds(6 * 60 * 60 - 1)
100
101 assert %{"content" => "cofe", "id" => id, "spoiler_text" => "2hu", "sensitive" => false} =
102 json_response(conn_one, 200)
103
104 assert Activity.get_by_id(id)
105
106 conn_two =
107 conn
108 |> assign(:user, user)
109 |> put_req_header("idempotency-key", idempotency_key)
110 |> post("/api/v1/statuses", %{
111 "status" => "cofe",
112 "spoiler_text" => "2hu",
113 "sensitive" => "false"
114 })
115
116 assert %{"id" => second_id} = json_response(conn_two, 200)
117
118 assert id == second_id
119
120 conn_three =
121 conn
122 |> assign(:user, user)
123 |> post("/api/v1/statuses", %{
124 "status" => "cofe",
125 "spoiler_text" => "2hu",
126 "sensitive" => "false"
127 })
128
129 assert %{"id" => third_id} = json_response(conn_three, 200)
130
131 refute id == third_id
132 end
133
134 test "posting a sensitive status", %{conn: conn} do
135 user = insert(:user)
136
137 conn =
138 conn
139 |> assign(:user, user)
140 |> post("/api/v1/statuses", %{"status" => "cofe", "sensitive" => true})
141
142 assert %{"content" => "cofe", "id" => id, "sensitive" => true} = json_response(conn, 200)
143 assert Activity.get_by_id(id)
144 end
145
146 test "posting a fake status", %{conn: conn} do
147 user = insert(:user)
148
149 real_conn =
150 conn
151 |> assign(:user, user)
152 |> post("/api/v1/statuses", %{
153 "status" =>
154 "\"Tenshi Eating a Corndog\" is a much discussed concept on /jp/. The significance of it is disputed, so I will focus on one core concept: the symbolism behind it"
155 })
156
157 real_status = json_response(real_conn, 200)
158
159 assert real_status
160 assert Object.get_by_ap_id(real_status["uri"])
161
162 real_status =
163 real_status
164 |> Map.put("id", nil)
165 |> Map.put("url", nil)
166 |> Map.put("uri", nil)
167 |> Map.put("created_at", nil)
168 |> Kernel.put_in(["pleroma", "conversation_id"], nil)
169
170 fake_conn =
171 conn
172 |> assign(:user, user)
173 |> post("/api/v1/statuses", %{
174 "status" =>
175 "\"Tenshi Eating a Corndog\" is a much discussed concept on /jp/. The significance of it is disputed, so I will focus on one core concept: the symbolism behind it",
176 "preview" => true
177 })
178
179 fake_status = json_response(fake_conn, 200)
180
181 assert fake_status
182 refute Object.get_by_ap_id(fake_status["uri"])
183
184 fake_status =
185 fake_status
186 |> Map.put("id", nil)
187 |> Map.put("url", nil)
188 |> Map.put("uri", nil)
189 |> Map.put("created_at", nil)
190 |> Kernel.put_in(["pleroma", "conversation_id"], nil)
191
192 assert real_status == fake_status
193 end
194
195 test "posting a status with OGP link preview", %{conn: conn} do
196 Pleroma.Config.put([:rich_media, :enabled], true)
197 user = insert(:user)
198
199 conn =
200 conn
201 |> assign(:user, user)
202 |> post("/api/v1/statuses", %{
203 "status" => "http://example.com/ogp"
204 })
205
206 assert %{"id" => id, "card" => %{"title" => "The Rock"}} = json_response(conn, 200)
207 assert Activity.get_by_id(id)
208 Pleroma.Config.put([:rich_media, :enabled], false)
209 end
210
211 test "posting a direct status", %{conn: conn} do
212 user1 = insert(:user)
213 user2 = insert(:user)
214 content = "direct cofe @#{user2.nickname}"
215
216 conn =
217 conn
218 |> assign(:user, user1)
219 |> post("api/v1/statuses", %{"status" => content, "visibility" => "direct"})
220
221 assert %{"id" => id, "visibility" => "direct"} = json_response(conn, 200)
222 assert activity = Activity.get_by_id(id)
223 assert activity.recipients == [user2.ap_id, user1.ap_id]
224 assert activity.data["to"] == [user2.ap_id]
225 assert activity.data["cc"] == []
226 end
227
228 test "direct timeline", %{conn: conn} do
229 user_one = insert(:user)
230 user_two = insert(:user)
231
232 {:ok, user_two} = User.follow(user_two, user_one)
233
234 {:ok, direct} =
235 CommonAPI.post(user_one, %{
236 "status" => "Hi @#{user_two.nickname}!",
237 "visibility" => "direct"
238 })
239
240 {:ok, _follower_only} =
241 CommonAPI.post(user_one, %{
242 "status" => "Hi @#{user_two.nickname}!",
243 "visibility" => "private"
244 })
245
246 # Only direct should be visible here
247 res_conn =
248 conn
249 |> assign(:user, user_two)
250 |> get("api/v1/timelines/direct")
251
252 [status] = json_response(res_conn, 200)
253
254 assert %{"visibility" => "direct"} = status
255 assert status["url"] != direct.data["id"]
256
257 # User should be able to see his own direct message
258 res_conn =
259 build_conn()
260 |> assign(:user, user_one)
261 |> get("api/v1/timelines/direct")
262
263 [status] = json_response(res_conn, 200)
264
265 assert %{"visibility" => "direct"} = status
266
267 # Both should be visible here
268 res_conn =
269 conn
270 |> assign(:user, user_two)
271 |> get("api/v1/timelines/home")
272
273 [_s1, _s2] = json_response(res_conn, 200)
274
275 # Test pagination
276 Enum.each(1..20, fn _ ->
277 {:ok, _} =
278 CommonAPI.post(user_one, %{
279 "status" => "Hi @#{user_two.nickname}!",
280 "visibility" => "direct"
281 })
282 end)
283
284 res_conn =
285 conn
286 |> assign(:user, user_two)
287 |> get("api/v1/timelines/direct")
288
289 statuses = json_response(res_conn, 200)
290 assert length(statuses) == 20
291
292 res_conn =
293 conn
294 |> assign(:user, user_two)
295 |> get("api/v1/timelines/direct", %{max_id: List.last(statuses)["id"]})
296
297 [status] = json_response(res_conn, 200)
298
299 assert status["url"] != direct.data["id"]
300 end
301
302 test "doesn't include DMs from blocked users", %{conn: conn} do
303 blocker = insert(:user)
304 blocked = insert(:user)
305 user = insert(:user)
306 {:ok, blocker} = User.block(blocker, blocked)
307
308 {:ok, _blocked_direct} =
309 CommonAPI.post(blocked, %{
310 "status" => "Hi @#{blocker.nickname}!",
311 "visibility" => "direct"
312 })
313
314 {:ok, direct} =
315 CommonAPI.post(user, %{
316 "status" => "Hi @#{blocker.nickname}!",
317 "visibility" => "direct"
318 })
319
320 res_conn =
321 conn
322 |> assign(:user, user)
323 |> get("api/v1/timelines/direct")
324
325 [status] = json_response(res_conn, 200)
326 assert status["id"] == direct.id
327 end
328
329 test "replying to a status", %{conn: conn} do
330 user = insert(:user)
331
332 {:ok, replied_to} = TwitterAPI.create_status(user, %{"status" => "cofe"})
333
334 conn =
335 conn
336 |> assign(:user, user)
337 |> post("/api/v1/statuses", %{"status" => "xD", "in_reply_to_id" => replied_to.id})
338
339 assert %{"content" => "xD", "id" => id} = json_response(conn, 200)
340
341 activity = Activity.get_by_id(id)
342
343 assert activity.data["context"] == replied_to.data["context"]
344 assert activity.data["object"]["inReplyToStatusId"] == replied_to.id
345 end
346
347 test "posting a status with an invalid in_reply_to_id", %{conn: conn} do
348 user = insert(:user)
349
350 conn =
351 conn
352 |> assign(:user, user)
353 |> post("/api/v1/statuses", %{"status" => "xD", "in_reply_to_id" => ""})
354
355 assert %{"content" => "xD", "id" => id} = json_response(conn, 200)
356
357 activity = Activity.get_by_id(id)
358
359 assert activity
360 end
361
362 test "verify_credentials", %{conn: conn} do
363 user = insert(:user)
364
365 conn =
366 conn
367 |> assign(:user, user)
368 |> get("/api/v1/accounts/verify_credentials")
369
370 assert %{"id" => id, "source" => %{"privacy" => "public"}} = json_response(conn, 200)
371 assert id == to_string(user.id)
372 end
373
374 test "verify_credentials default scope unlisted", %{conn: conn} do
375 user = insert(:user, %{info: %Pleroma.User.Info{default_scope: "unlisted"}})
376
377 conn =
378 conn
379 |> assign(:user, user)
380 |> get("/api/v1/accounts/verify_credentials")
381
382 assert %{"id" => id, "source" => %{"privacy" => "unlisted"}} = json_response(conn, 200)
383 assert id == to_string(user.id)
384 end
385
386 test "apps/verify_credentials", %{conn: conn} do
387 token = insert(:oauth_token)
388
389 conn =
390 conn
391 |> assign(:user, token.user)
392 |> assign(:token, token)
393 |> get("/api/v1/apps/verify_credentials")
394
395 app = Repo.preload(token, :app).app
396
397 expected = %{
398 "name" => app.client_name,
399 "website" => app.website,
400 "vapid_key" => Push.vapid_config() |> Keyword.get(:public_key)
401 }
402
403 assert expected == json_response(conn, 200)
404 end
405
406 test "creates an oauth app", %{conn: conn} do
407 user = insert(:user)
408 app_attrs = build(:oauth_app)
409
410 conn =
411 conn
412 |> assign(:user, user)
413 |> post("/api/v1/apps", %{
414 client_name: app_attrs.client_name,
415 redirect_uris: app_attrs.redirect_uris
416 })
417
418 [app] = Repo.all(App)
419
420 expected = %{
421 "name" => app.client_name,
422 "website" => app.website,
423 "client_id" => app.client_id,
424 "client_secret" => app.client_secret,
425 "id" => app.id |> to_string(),
426 "redirect_uri" => app.redirect_uris,
427 "vapid_key" => Push.vapid_config() |> Keyword.get(:public_key)
428 }
429
430 assert expected == json_response(conn, 200)
431 end
432
433 test "get a status", %{conn: conn} do
434 activity = insert(:note_activity)
435
436 conn =
437 conn
438 |> get("/api/v1/statuses/#{activity.id}")
439
440 assert %{"id" => id} = json_response(conn, 200)
441 assert id == to_string(activity.id)
442 end
443
444 describe "deleting a status" do
445 test "when you created it", %{conn: conn} do
446 activity = insert(:note_activity)
447 author = User.get_by_ap_id(activity.data["actor"])
448
449 conn =
450 conn
451 |> assign(:user, author)
452 |> delete("/api/v1/statuses/#{activity.id}")
453
454 assert %{} = json_response(conn, 200)
455
456 refute Activity.get_by_id(activity.id)
457 end
458
459 test "when you didn't create it", %{conn: conn} do
460 activity = insert(:note_activity)
461 user = insert(:user)
462
463 conn =
464 conn
465 |> assign(:user, user)
466 |> delete("/api/v1/statuses/#{activity.id}")
467
468 assert %{"error" => _} = json_response(conn, 403)
469
470 assert Activity.get_by_id(activity.id) == activity
471 end
472
473 test "when you're an admin or moderator", %{conn: conn} do
474 activity1 = insert(:note_activity)
475 activity2 = insert(:note_activity)
476 admin = insert(:user, info: %{is_admin: true})
477 moderator = insert(:user, info: %{is_moderator: true})
478
479 res_conn =
480 conn
481 |> assign(:user, admin)
482 |> delete("/api/v1/statuses/#{activity1.id}")
483
484 assert %{} = json_response(res_conn, 200)
485
486 res_conn =
487 conn
488 |> assign(:user, moderator)
489 |> delete("/api/v1/statuses/#{activity2.id}")
490
491 assert %{} = json_response(res_conn, 200)
492
493 refute Activity.get_by_id(activity1.id)
494 refute Activity.get_by_id(activity2.id)
495 end
496 end
497
498 describe "filters" do
499 test "creating a filter", %{conn: conn} do
500 user = insert(:user)
501
502 filter = %Pleroma.Filter{
503 phrase: "knights",
504 context: ["home"]
505 }
506
507 conn =
508 conn
509 |> assign(:user, user)
510 |> post("/api/v1/filters", %{"phrase" => filter.phrase, context: filter.context})
511
512 assert response = json_response(conn, 200)
513 assert response["phrase"] == filter.phrase
514 assert response["context"] == filter.context
515 assert response["id"] != nil
516 assert response["id"] != ""
517 end
518
519 test "fetching a list of filters", %{conn: conn} do
520 user = insert(:user)
521
522 query_one = %Pleroma.Filter{
523 user_id: user.id,
524 filter_id: 1,
525 phrase: "knights",
526 context: ["home"]
527 }
528
529 query_two = %Pleroma.Filter{
530 user_id: user.id,
531 filter_id: 2,
532 phrase: "who",
533 context: ["home"]
534 }
535
536 {:ok, filter_one} = Pleroma.Filter.create(query_one)
537 {:ok, filter_two} = Pleroma.Filter.create(query_two)
538
539 response =
540 conn
541 |> assign(:user, user)
542 |> get("/api/v1/filters")
543 |> json_response(200)
544
545 assert response ==
546 render_json(
547 FilterView,
548 "filters.json",
549 filters: [filter_two, filter_one]
550 )
551 end
552
553 test "get a filter", %{conn: conn} do
554 user = insert(:user)
555
556 query = %Pleroma.Filter{
557 user_id: user.id,
558 filter_id: 2,
559 phrase: "knight",
560 context: ["home"]
561 }
562
563 {:ok, filter} = Pleroma.Filter.create(query)
564
565 conn =
566 conn
567 |> assign(:user, user)
568 |> get("/api/v1/filters/#{filter.filter_id}")
569
570 assert _response = json_response(conn, 200)
571 end
572
573 test "update a filter", %{conn: conn} do
574 user = insert(:user)
575
576 query = %Pleroma.Filter{
577 user_id: user.id,
578 filter_id: 2,
579 phrase: "knight",
580 context: ["home"]
581 }
582
583 {:ok, _filter} = Pleroma.Filter.create(query)
584
585 new = %Pleroma.Filter{
586 phrase: "nii",
587 context: ["home"]
588 }
589
590 conn =
591 conn
592 |> assign(:user, user)
593 |> put("/api/v1/filters/#{query.filter_id}", %{
594 phrase: new.phrase,
595 context: new.context
596 })
597
598 assert response = json_response(conn, 200)
599 assert response["phrase"] == new.phrase
600 assert response["context"] == new.context
601 end
602
603 test "delete a filter", %{conn: conn} do
604 user = insert(:user)
605
606 query = %Pleroma.Filter{
607 user_id: user.id,
608 filter_id: 2,
609 phrase: "knight",
610 context: ["home"]
611 }
612
613 {:ok, filter} = Pleroma.Filter.create(query)
614
615 conn =
616 conn
617 |> assign(:user, user)
618 |> delete("/api/v1/filters/#{filter.filter_id}")
619
620 assert response = json_response(conn, 200)
621 assert response == %{}
622 end
623 end
624
625 describe "lists" do
626 test "creating a list", %{conn: conn} do
627 user = insert(:user)
628
629 conn =
630 conn
631 |> assign(:user, user)
632 |> post("/api/v1/lists", %{"title" => "cuties"})
633
634 assert %{"title" => title} = json_response(conn, 200)
635 assert title == "cuties"
636 end
637
638 test "adding users to a list", %{conn: conn} do
639 user = insert(:user)
640 other_user = insert(:user)
641 {:ok, list} = Pleroma.List.create("name", user)
642
643 conn =
644 conn
645 |> assign(:user, user)
646 |> post("/api/v1/lists/#{list.id}/accounts", %{"account_ids" => [other_user.id]})
647
648 assert %{} == json_response(conn, 200)
649 %Pleroma.List{following: following} = Pleroma.List.get(list.id, user)
650 assert following == [other_user.follower_address]
651 end
652
653 test "removing users from a list", %{conn: conn} do
654 user = insert(:user)
655 other_user = insert(:user)
656 third_user = insert(:user)
657 {:ok, list} = Pleroma.List.create("name", user)
658 {:ok, list} = Pleroma.List.follow(list, other_user)
659 {:ok, list} = Pleroma.List.follow(list, third_user)
660
661 conn =
662 conn
663 |> assign(:user, user)
664 |> delete("/api/v1/lists/#{list.id}/accounts", %{"account_ids" => [other_user.id]})
665
666 assert %{} == json_response(conn, 200)
667 %Pleroma.List{following: following} = Pleroma.List.get(list.id, user)
668 assert following == [third_user.follower_address]
669 end
670
671 test "listing users in a list", %{conn: conn} do
672 user = insert(:user)
673 other_user = insert(:user)
674 {:ok, list} = Pleroma.List.create("name", user)
675 {:ok, list} = Pleroma.List.follow(list, other_user)
676
677 conn =
678 conn
679 |> assign(:user, user)
680 |> get("/api/v1/lists/#{list.id}/accounts", %{"account_ids" => [other_user.id]})
681
682 assert [%{"id" => id}] = json_response(conn, 200)
683 assert id == to_string(other_user.id)
684 end
685
686 test "retrieving a list", %{conn: conn} do
687 user = insert(:user)
688 {:ok, list} = Pleroma.List.create("name", user)
689
690 conn =
691 conn
692 |> assign(:user, user)
693 |> get("/api/v1/lists/#{list.id}")
694
695 assert %{"id" => id} = json_response(conn, 200)
696 assert id == to_string(list.id)
697 end
698
699 test "renaming a list", %{conn: conn} do
700 user = insert(:user)
701 {:ok, list} = Pleroma.List.create("name", user)
702
703 conn =
704 conn
705 |> assign(:user, user)
706 |> put("/api/v1/lists/#{list.id}", %{"title" => "newname"})
707
708 assert %{"title" => name} = json_response(conn, 200)
709 assert name == "newname"
710 end
711
712 test "deleting a list", %{conn: conn} do
713 user = insert(:user)
714 {:ok, list} = Pleroma.List.create("name", user)
715
716 conn =
717 conn
718 |> assign(:user, user)
719 |> delete("/api/v1/lists/#{list.id}")
720
721 assert %{} = json_response(conn, 200)
722 assert is_nil(Repo.get(Pleroma.List, list.id))
723 end
724
725 test "list timeline", %{conn: conn} do
726 user = insert(:user)
727 other_user = insert(:user)
728 {:ok, _activity_one} = TwitterAPI.create_status(user, %{"status" => "Marisa is cute."})
729 {:ok, activity_two} = TwitterAPI.create_status(other_user, %{"status" => "Marisa is cute."})
730 {:ok, list} = Pleroma.List.create("name", user)
731 {:ok, list} = Pleroma.List.follow(list, other_user)
732
733 conn =
734 conn
735 |> assign(:user, user)
736 |> get("/api/v1/timelines/list/#{list.id}")
737
738 assert [%{"id" => id}] = json_response(conn, 200)
739
740 assert id == to_string(activity_two.id)
741 end
742
743 test "list timeline does not leak non-public statuses for unfollowed users", %{conn: conn} do
744 user = insert(:user)
745 other_user = insert(:user)
746 {:ok, activity_one} = TwitterAPI.create_status(other_user, %{"status" => "Marisa is cute."})
747
748 {:ok, _activity_two} =
749 TwitterAPI.create_status(other_user, %{
750 "status" => "Marisa is cute.",
751 "visibility" => "private"
752 })
753
754 {:ok, list} = Pleroma.List.create("name", user)
755 {:ok, list} = Pleroma.List.follow(list, other_user)
756
757 conn =
758 conn
759 |> assign(:user, user)
760 |> get("/api/v1/timelines/list/#{list.id}")
761
762 assert [%{"id" => id}] = json_response(conn, 200)
763
764 assert id == to_string(activity_one.id)
765 end
766 end
767
768 describe "notifications" do
769 test "list of notifications", %{conn: conn} do
770 user = insert(:user)
771 other_user = insert(:user)
772
773 {:ok, activity} =
774 TwitterAPI.create_status(other_user, %{"status" => "hi @#{user.nickname}"})
775
776 {:ok, [_notification]} = Notification.create_notifications(activity)
777
778 conn =
779 conn
780 |> assign(:user, user)
781 |> get("/api/v1/notifications")
782
783 expected_response =
784 "hi <span class=\"h-card\"><a data-user=\"#{user.id}\" class=\"u-url mention\" href=\"#{
785 user.ap_id
786 }\">@<span>#{user.nickname}</span></a></span>"
787
788 assert [%{"status" => %{"content" => response}} | _rest] = json_response(conn, 200)
789 assert response == expected_response
790 end
791
792 test "getting a single notification", %{conn: conn} do
793 user = insert(:user)
794 other_user = insert(:user)
795
796 {:ok, activity} =
797 TwitterAPI.create_status(other_user, %{"status" => "hi @#{user.nickname}"})
798
799 {:ok, [notification]} = Notification.create_notifications(activity)
800
801 conn =
802 conn
803 |> assign(:user, user)
804 |> get("/api/v1/notifications/#{notification.id}")
805
806 expected_response =
807 "hi <span class=\"h-card\"><a data-user=\"#{user.id}\" class=\"u-url mention\" href=\"#{
808 user.ap_id
809 }\">@<span>#{user.nickname}</span></a></span>"
810
811 assert %{"status" => %{"content" => response}} = json_response(conn, 200)
812 assert response == expected_response
813 end
814
815 test "dismissing a single notification", %{conn: conn} do
816 user = insert(:user)
817 other_user = insert(:user)
818
819 {:ok, activity} =
820 TwitterAPI.create_status(other_user, %{"status" => "hi @#{user.nickname}"})
821
822 {:ok, [notification]} = Notification.create_notifications(activity)
823
824 conn =
825 conn
826 |> assign(:user, user)
827 |> post("/api/v1/notifications/dismiss", %{"id" => notification.id})
828
829 assert %{} = json_response(conn, 200)
830 end
831
832 test "clearing all notifications", %{conn: conn} do
833 user = insert(:user)
834 other_user = insert(:user)
835
836 {:ok, activity} =
837 TwitterAPI.create_status(other_user, %{"status" => "hi @#{user.nickname}"})
838
839 {:ok, [_notification]} = Notification.create_notifications(activity)
840
841 conn =
842 conn
843 |> assign(:user, user)
844 |> post("/api/v1/notifications/clear")
845
846 assert %{} = json_response(conn, 200)
847
848 conn =
849 build_conn()
850 |> assign(:user, user)
851 |> get("/api/v1/notifications")
852
853 assert all = json_response(conn, 200)
854 assert all == []
855 end
856
857 test "paginates notifications using min_id, since_id, max_id, and limit", %{conn: conn} do
858 user = insert(:user)
859 other_user = insert(:user)
860
861 {:ok, activity1} = CommonAPI.post(other_user, %{"status" => "hi @#{user.nickname}"})
862 {:ok, activity2} = CommonAPI.post(other_user, %{"status" => "hi @#{user.nickname}"})
863 {:ok, activity3} = CommonAPI.post(other_user, %{"status" => "hi @#{user.nickname}"})
864 {:ok, activity4} = CommonAPI.post(other_user, %{"status" => "hi @#{user.nickname}"})
865
866 notification1_id = Repo.get_by(Notification, activity_id: activity1.id).id |> to_string()
867 notification2_id = Repo.get_by(Notification, activity_id: activity2.id).id |> to_string()
868 notification3_id = Repo.get_by(Notification, activity_id: activity3.id).id |> to_string()
869 notification4_id = Repo.get_by(Notification, activity_id: activity4.id).id |> to_string()
870
871 conn =
872 conn
873 |> assign(:user, user)
874
875 # min_id
876 conn_res =
877 conn
878 |> get("/api/v1/notifications?limit=2&min_id=#{notification1_id}")
879
880 result = json_response(conn_res, 200)
881 assert [%{"id" => ^notification3_id}, %{"id" => ^notification2_id}] = result
882
883 # since_id
884 conn_res =
885 conn
886 |> get("/api/v1/notifications?limit=2&since_id=#{notification1_id}")
887
888 result = json_response(conn_res, 200)
889 assert [%{"id" => ^notification4_id}, %{"id" => ^notification3_id}] = result
890
891 # max_id
892 conn_res =
893 conn
894 |> get("/api/v1/notifications?limit=2&max_id=#{notification4_id}")
895
896 result = json_response(conn_res, 200)
897 assert [%{"id" => ^notification3_id}, %{"id" => ^notification2_id}] = result
898 end
899
900 test "filters notifications using exclude_types", %{conn: conn} do
901 user = insert(:user)
902 other_user = insert(:user)
903
904 {:ok, mention_activity} = CommonAPI.post(other_user, %{"status" => "hey @#{user.nickname}"})
905 {:ok, create_activity} = CommonAPI.post(user, %{"status" => "hey"})
906 {:ok, favorite_activity, _} = CommonAPI.favorite(create_activity.id, other_user)
907 {:ok, reblog_activity, _} = CommonAPI.repeat(create_activity.id, other_user)
908 {:ok, _, _, follow_activity} = CommonAPI.follow(other_user, user)
909
910 mention_notification_id =
911 Repo.get_by(Notification, activity_id: mention_activity.id).id |> to_string()
912
913 favorite_notification_id =
914 Repo.get_by(Notification, activity_id: favorite_activity.id).id |> to_string()
915
916 reblog_notification_id =
917 Repo.get_by(Notification, activity_id: reblog_activity.id).id |> to_string()
918
919 follow_notification_id =
920 Repo.get_by(Notification, activity_id: follow_activity.id).id |> to_string()
921
922 conn =
923 conn
924 |> assign(:user, user)
925
926 conn_res =
927 get(conn, "/api/v1/notifications", %{exclude_types: ["mention", "favourite", "reblog"]})
928
929 assert [%{"id" => ^follow_notification_id}] = json_response(conn_res, 200)
930
931 conn_res =
932 get(conn, "/api/v1/notifications", %{exclude_types: ["favourite", "reblog", "follow"]})
933
934 assert [%{"id" => ^mention_notification_id}] = json_response(conn_res, 200)
935
936 conn_res =
937 get(conn, "/api/v1/notifications", %{exclude_types: ["reblog", "follow", "mention"]})
938
939 assert [%{"id" => ^favorite_notification_id}] = json_response(conn_res, 200)
940
941 conn_res =
942 get(conn, "/api/v1/notifications", %{exclude_types: ["follow", "mention", "favourite"]})
943
944 assert [%{"id" => ^reblog_notification_id}] = json_response(conn_res, 200)
945 end
946 end
947
948 describe "reblogging" do
949 test "reblogs and returns the reblogged status", %{conn: conn} do
950 activity = insert(:note_activity)
951 user = insert(:user)
952
953 conn =
954 conn
955 |> assign(:user, user)
956 |> post("/api/v1/statuses/#{activity.id}/reblog")
957
958 assert %{"reblog" => %{"id" => id, "reblogged" => true, "reblogs_count" => 1}} =
959 json_response(conn, 200)
960
961 assert to_string(activity.id) == id
962 end
963 end
964
965 describe "unreblogging" do
966 test "unreblogs and returns the unreblogged status", %{conn: conn} do
967 activity = insert(:note_activity)
968 user = insert(:user)
969
970 {:ok, _, _} = CommonAPI.repeat(activity.id, user)
971
972 conn =
973 conn
974 |> assign(:user, user)
975 |> post("/api/v1/statuses/#{activity.id}/unreblog")
976
977 assert %{"id" => id, "reblogged" => false, "reblogs_count" => 0} = json_response(conn, 200)
978
979 assert to_string(activity.id) == id
980 end
981 end
982
983 describe "favoriting" do
984 test "favs a status and returns it", %{conn: conn} do
985 activity = insert(:note_activity)
986 user = insert(:user)
987
988 conn =
989 conn
990 |> assign(:user, user)
991 |> post("/api/v1/statuses/#{activity.id}/favourite")
992
993 assert %{"id" => id, "favourites_count" => 1, "favourited" => true} =
994 json_response(conn, 200)
995
996 assert to_string(activity.id) == id
997 end
998
999 test "returns 500 for a wrong id", %{conn: conn} do
1000 user = insert(:user)
1001
1002 resp =
1003 conn
1004 |> assign(:user, user)
1005 |> post("/api/v1/statuses/1/favourite")
1006 |> json_response(500)
1007
1008 assert resp == "Something went wrong"
1009 end
1010 end
1011
1012 describe "unfavoriting" do
1013 test "unfavorites a status and returns it", %{conn: conn} do
1014 activity = insert(:note_activity)
1015 user = insert(:user)
1016
1017 {:ok, _, _} = CommonAPI.favorite(activity.id, user)
1018
1019 conn =
1020 conn
1021 |> assign(:user, user)
1022 |> post("/api/v1/statuses/#{activity.id}/unfavourite")
1023
1024 assert %{"id" => id, "favourites_count" => 0, "favourited" => false} =
1025 json_response(conn, 200)
1026
1027 assert to_string(activity.id) == id
1028 end
1029 end
1030
1031 describe "user timelines" do
1032 test "gets a users statuses", %{conn: conn} do
1033 user_one = insert(:user)
1034 user_two = insert(:user)
1035 user_three = insert(:user)
1036
1037 {:ok, user_three} = User.follow(user_three, user_one)
1038
1039 {:ok, activity} = CommonAPI.post(user_one, %{"status" => "HI!!!"})
1040
1041 {:ok, direct_activity} =
1042 CommonAPI.post(user_one, %{
1043 "status" => "Hi, @#{user_two.nickname}.",
1044 "visibility" => "direct"
1045 })
1046
1047 {:ok, private_activity} =
1048 CommonAPI.post(user_one, %{"status" => "private", "visibility" => "private"})
1049
1050 resp =
1051 conn
1052 |> get("/api/v1/accounts/#{user_one.id}/statuses")
1053
1054 assert [%{"id" => id}] = json_response(resp, 200)
1055 assert id == to_string(activity.id)
1056
1057 resp =
1058 conn
1059 |> assign(:user, user_two)
1060 |> get("/api/v1/accounts/#{user_one.id}/statuses")
1061
1062 assert [%{"id" => id_one}, %{"id" => id_two}] = json_response(resp, 200)
1063 assert id_one == to_string(direct_activity.id)
1064 assert id_two == to_string(activity.id)
1065
1066 resp =
1067 conn
1068 |> assign(:user, user_three)
1069 |> get("/api/v1/accounts/#{user_one.id}/statuses")
1070
1071 assert [%{"id" => id_one}, %{"id" => id_two}] = json_response(resp, 200)
1072 assert id_one == to_string(private_activity.id)
1073 assert id_two == to_string(activity.id)
1074 end
1075
1076 test "unimplemented pinned statuses feature", %{conn: conn} do
1077 note = insert(:note_activity)
1078 user = User.get_by_ap_id(note.data["actor"])
1079
1080 conn =
1081 conn
1082 |> get("/api/v1/accounts/#{user.id}/statuses?pinned=true")
1083
1084 assert json_response(conn, 200) == []
1085 end
1086
1087 test "gets an users media", %{conn: conn} do
1088 note = insert(:note_activity)
1089 user = User.get_by_ap_id(note.data["actor"])
1090
1091 file = %Plug.Upload{
1092 content_type: "image/jpg",
1093 path: Path.absname("test/fixtures/image.jpg"),
1094 filename: "an_image.jpg"
1095 }
1096
1097 media =
1098 TwitterAPI.upload(file, user, "json")
1099 |> Poison.decode!()
1100
1101 {:ok, image_post} =
1102 TwitterAPI.create_status(user, %{"status" => "cofe", "media_ids" => [media["media_id"]]})
1103
1104 conn =
1105 conn
1106 |> get("/api/v1/accounts/#{user.id}/statuses", %{"only_media" => "true"})
1107
1108 assert [%{"id" => id}] = json_response(conn, 200)
1109 assert id == to_string(image_post.id)
1110
1111 conn =
1112 build_conn()
1113 |> get("/api/v1/accounts/#{user.id}/statuses", %{"only_media" => "1"})
1114
1115 assert [%{"id" => id}] = json_response(conn, 200)
1116 assert id == to_string(image_post.id)
1117 end
1118
1119 test "gets a user's statuses without reblogs", %{conn: conn} do
1120 user = insert(:user)
1121 {:ok, post} = CommonAPI.post(user, %{"status" => "HI!!!"})
1122 {:ok, _, _} = CommonAPI.repeat(post.id, user)
1123
1124 conn =
1125 conn
1126 |> get("/api/v1/accounts/#{user.id}/statuses", %{"exclude_reblogs" => "true"})
1127
1128 assert [%{"id" => id}] = json_response(conn, 200)
1129 assert id == to_string(post.id)
1130
1131 conn =
1132 conn
1133 |> get("/api/v1/accounts/#{user.id}/statuses", %{"exclude_reblogs" => "1"})
1134
1135 assert [%{"id" => id}] = json_response(conn, 200)
1136 assert id == to_string(post.id)
1137 end
1138 end
1139
1140 describe "user relationships" do
1141 test "returns the relationships for the current user", %{conn: conn} do
1142 user = insert(:user)
1143 other_user = insert(:user)
1144 {:ok, user} = User.follow(user, other_user)
1145
1146 conn =
1147 conn
1148 |> assign(:user, user)
1149 |> get("/api/v1/accounts/relationships", %{"id" => [other_user.id]})
1150
1151 assert [relationship] = json_response(conn, 200)
1152
1153 assert to_string(other_user.id) == relationship["id"]
1154 end
1155 end
1156
1157 describe "locked accounts" do
1158 test "/api/v1/follow_requests works" do
1159 user = insert(:user, %{info: %Pleroma.User.Info{locked: true}})
1160 other_user = insert(:user)
1161
1162 {:ok, _activity} = ActivityPub.follow(other_user, user)
1163
1164 user = User.get_by_id(user.id)
1165 other_user = User.get_by_id(other_user.id)
1166
1167 assert User.following?(other_user, user) == false
1168
1169 conn =
1170 build_conn()
1171 |> assign(:user, user)
1172 |> get("/api/v1/follow_requests")
1173
1174 assert [relationship] = json_response(conn, 200)
1175 assert to_string(other_user.id) == relationship["id"]
1176 end
1177
1178 test "/api/v1/follow_requests/:id/authorize works" do
1179 user = insert(:user, %{info: %User.Info{locked: true}})
1180 other_user = insert(:user)
1181
1182 {:ok, _activity} = ActivityPub.follow(other_user, user)
1183
1184 user = User.get_by_id(user.id)
1185 other_user = User.get_by_id(other_user.id)
1186
1187 assert User.following?(other_user, user) == false
1188
1189 conn =
1190 build_conn()
1191 |> assign(:user, user)
1192 |> post("/api/v1/follow_requests/#{other_user.id}/authorize")
1193
1194 assert relationship = json_response(conn, 200)
1195 assert to_string(other_user.id) == relationship["id"]
1196
1197 user = User.get_by_id(user.id)
1198 other_user = User.get_by_id(other_user.id)
1199
1200 assert User.following?(other_user, user) == true
1201 end
1202
1203 test "verify_credentials", %{conn: conn} do
1204 user = insert(:user, %{info: %Pleroma.User.Info{default_scope: "private"}})
1205
1206 conn =
1207 conn
1208 |> assign(:user, user)
1209 |> get("/api/v1/accounts/verify_credentials")
1210
1211 assert %{"id" => id, "source" => %{"privacy" => "private"}} = json_response(conn, 200)
1212 assert id == to_string(user.id)
1213 end
1214
1215 test "/api/v1/follow_requests/:id/reject works" do
1216 user = insert(:user, %{info: %Pleroma.User.Info{locked: true}})
1217 other_user = insert(:user)
1218
1219 {:ok, _activity} = ActivityPub.follow(other_user, user)
1220
1221 user = User.get_by_id(user.id)
1222
1223 conn =
1224 build_conn()
1225 |> assign(:user, user)
1226 |> post("/api/v1/follow_requests/#{other_user.id}/reject")
1227
1228 assert relationship = json_response(conn, 200)
1229 assert to_string(other_user.id) == relationship["id"]
1230
1231 user = User.get_by_id(user.id)
1232 other_user = User.get_by_id(other_user.id)
1233
1234 assert User.following?(other_user, user) == false
1235 end
1236 end
1237
1238 test "account fetching", %{conn: conn} do
1239 user = insert(:user)
1240
1241 conn =
1242 conn
1243 |> get("/api/v1/accounts/#{user.id}")
1244
1245 assert %{"id" => id} = json_response(conn, 200)
1246 assert id == to_string(user.id)
1247
1248 conn =
1249 build_conn()
1250 |> get("/api/v1/accounts/-1")
1251
1252 assert %{"error" => "Can't find user"} = json_response(conn, 404)
1253 end
1254
1255 test "account fetching also works nickname", %{conn: conn} do
1256 user = insert(:user)
1257
1258 conn =
1259 conn
1260 |> get("/api/v1/accounts/#{user.nickname}")
1261
1262 assert %{"id" => id} = json_response(conn, 200)
1263 assert id == user.id
1264 end
1265
1266 test "media upload", %{conn: conn} do
1267 file = %Plug.Upload{
1268 content_type: "image/jpg",
1269 path: Path.absname("test/fixtures/image.jpg"),
1270 filename: "an_image.jpg"
1271 }
1272
1273 desc = "Description of the image"
1274
1275 user = insert(:user)
1276
1277 conn =
1278 conn
1279 |> assign(:user, user)
1280 |> post("/api/v1/media", %{"file" => file, "description" => desc})
1281
1282 assert media = json_response(conn, 200)
1283
1284 assert media["type"] == "image"
1285 assert media["description"] == desc
1286 assert media["id"]
1287
1288 object = Repo.get(Object, media["id"])
1289 assert object.data["actor"] == User.ap_id(user)
1290 end
1291
1292 test "hashtag timeline", %{conn: conn} do
1293 following = insert(:user)
1294
1295 capture_log(fn ->
1296 {:ok, activity} = TwitterAPI.create_status(following, %{"status" => "test #2hu"})
1297
1298 {:ok, [_activity]} =
1299 OStatus.fetch_activity_from_url("https://shitposter.club/notice/2827873")
1300
1301 nconn =
1302 conn
1303 |> get("/api/v1/timelines/tag/2hu")
1304
1305 assert [%{"id" => id}] = json_response(nconn, 200)
1306
1307 assert id == to_string(activity.id)
1308
1309 # works for different capitalization too
1310 nconn =
1311 conn
1312 |> get("/api/v1/timelines/tag/2HU")
1313
1314 assert [%{"id" => id}] = json_response(nconn, 200)
1315
1316 assert id == to_string(activity.id)
1317 end)
1318 end
1319
1320 test "multi-hashtag timeline", %{conn: conn} do
1321 user = insert(:user)
1322
1323 {:ok, activity_test} = CommonAPI.post(user, %{"status" => "#test"})
1324 {:ok, activity_test1} = CommonAPI.post(user, %{"status" => "#test #test1"})
1325 {:ok, activity_none} = CommonAPI.post(user, %{"status" => "#test #none"})
1326
1327 any_test =
1328 conn
1329 |> get("/api/v1/timelines/tag/test", %{"any" => ["test1"]})
1330
1331 [status_none, status_test1, status_test] = json_response(any_test, 200)
1332
1333 assert to_string(activity_test.id) == status_test["id"]
1334 assert to_string(activity_test1.id) == status_test1["id"]
1335 assert to_string(activity_none.id) == status_none["id"]
1336
1337 restricted_test =
1338 conn
1339 |> get("/api/v1/timelines/tag/test", %{"all" => ["test1"], "none" => ["none"]})
1340
1341 assert [status_test1] == json_response(restricted_test, 200)
1342
1343 all_test = conn |> get("/api/v1/timelines/tag/test", %{"all" => ["none"]})
1344
1345 assert [status_none] == json_response(all_test, 200)
1346 end
1347
1348 test "getting followers", %{conn: conn} do
1349 user = insert(:user)
1350 other_user = insert(:user)
1351 {:ok, user} = User.follow(user, other_user)
1352
1353 conn =
1354 conn
1355 |> get("/api/v1/accounts/#{other_user.id}/followers")
1356
1357 assert [%{"id" => id}] = json_response(conn, 200)
1358 assert id == to_string(user.id)
1359 end
1360
1361 test "getting followers, hide_followers", %{conn: conn} do
1362 user = insert(:user)
1363 other_user = insert(:user, %{info: %{hide_followers: true}})
1364 {:ok, _user} = User.follow(user, other_user)
1365
1366 conn =
1367 conn
1368 |> get("/api/v1/accounts/#{other_user.id}/followers")
1369
1370 assert [] == json_response(conn, 200)
1371 end
1372
1373 test "getting followers, hide_followers, same user requesting", %{conn: conn} do
1374 user = insert(:user)
1375 other_user = insert(:user, %{info: %{hide_followers: true}})
1376 {:ok, _user} = User.follow(user, other_user)
1377
1378 conn =
1379 conn
1380 |> assign(:user, other_user)
1381 |> get("/api/v1/accounts/#{other_user.id}/followers")
1382
1383 refute [] == json_response(conn, 200)
1384 end
1385
1386 test "getting followers, pagination", %{conn: conn} do
1387 user = insert(:user)
1388 follower1 = insert(:user)
1389 follower2 = insert(:user)
1390 follower3 = insert(:user)
1391 {:ok, _} = User.follow(follower1, user)
1392 {:ok, _} = User.follow(follower2, user)
1393 {:ok, _} = User.follow(follower3, user)
1394
1395 conn =
1396 conn
1397 |> assign(:user, user)
1398
1399 res_conn =
1400 conn
1401 |> get("/api/v1/accounts/#{user.id}/followers?since_id=#{follower1.id}")
1402
1403 assert [%{"id" => id3}, %{"id" => id2}] = json_response(res_conn, 200)
1404 assert id3 == follower3.id
1405 assert id2 == follower2.id
1406
1407 res_conn =
1408 conn
1409 |> get("/api/v1/accounts/#{user.id}/followers?max_id=#{follower3.id}")
1410
1411 assert [%{"id" => id2}, %{"id" => id1}] = json_response(res_conn, 200)
1412 assert id2 == follower2.id
1413 assert id1 == follower1.id
1414
1415 res_conn =
1416 conn
1417 |> get("/api/v1/accounts/#{user.id}/followers?limit=1&max_id=#{follower3.id}")
1418
1419 assert [%{"id" => id2}] = json_response(res_conn, 200)
1420 assert id2 == follower2.id
1421
1422 assert [link_header] = get_resp_header(res_conn, "link")
1423 assert link_header =~ ~r/since_id=#{follower2.id}/
1424 assert link_header =~ ~r/max_id=#{follower2.id}/
1425 end
1426
1427 test "getting following", %{conn: conn} do
1428 user = insert(:user)
1429 other_user = insert(:user)
1430 {:ok, user} = User.follow(user, other_user)
1431
1432 conn =
1433 conn
1434 |> get("/api/v1/accounts/#{user.id}/following")
1435
1436 assert [%{"id" => id}] = json_response(conn, 200)
1437 assert id == to_string(other_user.id)
1438 end
1439
1440 test "getting following, hide_follows", %{conn: conn} do
1441 user = insert(:user, %{info: %{hide_follows: true}})
1442 other_user = insert(:user)
1443 {:ok, user} = User.follow(user, other_user)
1444
1445 conn =
1446 conn
1447 |> get("/api/v1/accounts/#{user.id}/following")
1448
1449 assert [] == json_response(conn, 200)
1450 end
1451
1452 test "getting following, hide_follows, same user requesting", %{conn: conn} do
1453 user = insert(:user, %{info: %{hide_follows: true}})
1454 other_user = insert(:user)
1455 {:ok, user} = User.follow(user, other_user)
1456
1457 conn =
1458 conn
1459 |> assign(:user, user)
1460 |> get("/api/v1/accounts/#{user.id}/following")
1461
1462 refute [] == json_response(conn, 200)
1463 end
1464
1465 test "getting following, pagination", %{conn: conn} do
1466 user = insert(:user)
1467 following1 = insert(:user)
1468 following2 = insert(:user)
1469 following3 = insert(:user)
1470 {:ok, _} = User.follow(user, following1)
1471 {:ok, _} = User.follow(user, following2)
1472 {:ok, _} = User.follow(user, following3)
1473
1474 conn =
1475 conn
1476 |> assign(:user, user)
1477
1478 res_conn =
1479 conn
1480 |> get("/api/v1/accounts/#{user.id}/following?since_id=#{following1.id}")
1481
1482 assert [%{"id" => id3}, %{"id" => id2}] = json_response(res_conn, 200)
1483 assert id3 == following3.id
1484 assert id2 == following2.id
1485
1486 res_conn =
1487 conn
1488 |> get("/api/v1/accounts/#{user.id}/following?max_id=#{following3.id}")
1489
1490 assert [%{"id" => id2}, %{"id" => id1}] = json_response(res_conn, 200)
1491 assert id2 == following2.id
1492 assert id1 == following1.id
1493
1494 res_conn =
1495 conn
1496 |> get("/api/v1/accounts/#{user.id}/following?limit=1&max_id=#{following3.id}")
1497
1498 assert [%{"id" => id2}] = json_response(res_conn, 200)
1499 assert id2 == following2.id
1500
1501 assert [link_header] = get_resp_header(res_conn, "link")
1502 assert link_header =~ ~r/since_id=#{following2.id}/
1503 assert link_header =~ ~r/max_id=#{following2.id}/
1504 end
1505
1506 test "following / unfollowing a user", %{conn: conn} do
1507 user = insert(:user)
1508 other_user = insert(:user)
1509
1510 conn =
1511 conn
1512 |> assign(:user, user)
1513 |> post("/api/v1/accounts/#{other_user.id}/follow")
1514
1515 assert %{"id" => _id, "following" => true} = json_response(conn, 200)
1516
1517 user = User.get_by_id(user.id)
1518
1519 conn =
1520 build_conn()
1521 |> assign(:user, user)
1522 |> post("/api/v1/accounts/#{other_user.id}/unfollow")
1523
1524 assert %{"id" => _id, "following" => false} = json_response(conn, 200)
1525
1526 user = User.get_by_id(user.id)
1527
1528 conn =
1529 build_conn()
1530 |> assign(:user, user)
1531 |> post("/api/v1/follows", %{"uri" => other_user.nickname})
1532
1533 assert %{"id" => id} = json_response(conn, 200)
1534 assert id == to_string(other_user.id)
1535 end
1536
1537 test "muting / unmuting a user", %{conn: conn} do
1538 user = insert(:user)
1539 other_user = insert(:user)
1540
1541 conn =
1542 conn
1543 |> assign(:user, user)
1544 |> post("/api/v1/accounts/#{other_user.id}/mute")
1545
1546 assert %{"id" => _id, "muting" => true} = json_response(conn, 200)
1547
1548 user = User.get_by_id(user.id)
1549
1550 conn =
1551 build_conn()
1552 |> assign(:user, user)
1553 |> post("/api/v1/accounts/#{other_user.id}/unmute")
1554
1555 assert %{"id" => _id, "muting" => false} = json_response(conn, 200)
1556 end
1557
1558 test "getting a list of mutes", %{conn: conn} do
1559 user = insert(:user)
1560 other_user = insert(:user)
1561
1562 {:ok, user} = User.mute(user, other_user)
1563
1564 conn =
1565 conn
1566 |> assign(:user, user)
1567 |> get("/api/v1/mutes")
1568
1569 other_user_id = to_string(other_user.id)
1570 assert [%{"id" => ^other_user_id}] = json_response(conn, 200)
1571 end
1572
1573 test "blocking / unblocking a user", %{conn: conn} do
1574 user = insert(:user)
1575 other_user = insert(:user)
1576
1577 conn =
1578 conn
1579 |> assign(:user, user)
1580 |> post("/api/v1/accounts/#{other_user.id}/block")
1581
1582 assert %{"id" => _id, "blocking" => true} = json_response(conn, 200)
1583
1584 user = User.get_by_id(user.id)
1585
1586 conn =
1587 build_conn()
1588 |> assign(:user, user)
1589 |> post("/api/v1/accounts/#{other_user.id}/unblock")
1590
1591 assert %{"id" => _id, "blocking" => false} = json_response(conn, 200)
1592 end
1593
1594 test "getting a list of blocks", %{conn: conn} do
1595 user = insert(:user)
1596 other_user = insert(:user)
1597
1598 {:ok, user} = User.block(user, other_user)
1599
1600 conn =
1601 conn
1602 |> assign(:user, user)
1603 |> get("/api/v1/blocks")
1604
1605 other_user_id = to_string(other_user.id)
1606 assert [%{"id" => ^other_user_id}] = json_response(conn, 200)
1607 end
1608
1609 test "blocking / unblocking a domain", %{conn: conn} do
1610 user = insert(:user)
1611 other_user = insert(:user, %{ap_id: "https://dogwhistle.zone/@pundit"})
1612
1613 conn =
1614 conn
1615 |> assign(:user, user)
1616 |> post("/api/v1/domain_blocks", %{"domain" => "dogwhistle.zone"})
1617
1618 assert %{} = json_response(conn, 200)
1619 user = User.get_cached_by_ap_id(user.ap_id)
1620 assert User.blocks?(user, other_user)
1621
1622 conn =
1623 build_conn()
1624 |> assign(:user, user)
1625 |> delete("/api/v1/domain_blocks", %{"domain" => "dogwhistle.zone"})
1626
1627 assert %{} = json_response(conn, 200)
1628 user = User.get_cached_by_ap_id(user.ap_id)
1629 refute User.blocks?(user, other_user)
1630 end
1631
1632 test "getting a list of domain blocks", %{conn: conn} do
1633 user = insert(:user)
1634
1635 {:ok, user} = User.block_domain(user, "bad.site")
1636 {:ok, user} = User.block_domain(user, "even.worse.site")
1637
1638 conn =
1639 conn
1640 |> assign(:user, user)
1641 |> get("/api/v1/domain_blocks")
1642
1643 domain_blocks = json_response(conn, 200)
1644
1645 assert "bad.site" in domain_blocks
1646 assert "even.worse.site" in domain_blocks
1647 end
1648
1649 test "unimplemented follow_requests, blocks, domain blocks" do
1650 user = insert(:user)
1651
1652 ["blocks", "domain_blocks", "follow_requests"]
1653 |> Enum.each(fn endpoint ->
1654 conn =
1655 build_conn()
1656 |> assign(:user, user)
1657 |> get("/api/v1/#{endpoint}")
1658
1659 assert [] = json_response(conn, 200)
1660 end)
1661 end
1662
1663 test "account search", %{conn: conn} do
1664 user = insert(:user)
1665 user_two = insert(:user, %{nickname: "shp@shitposter.club"})
1666 user_three = insert(:user, %{nickname: "shp@heldscal.la", name: "I love 2hu"})
1667
1668 results =
1669 conn
1670 |> assign(:user, user)
1671 |> get("/api/v1/accounts/search", %{"q" => "shp"})
1672 |> json_response(200)
1673
1674 result_ids = for result <- results, do: result["acct"]
1675
1676 assert user_two.nickname in result_ids
1677 assert user_three.nickname in result_ids
1678
1679 results =
1680 conn
1681 |> assign(:user, user)
1682 |> get("/api/v1/accounts/search", %{"q" => "2hu"})
1683 |> json_response(200)
1684
1685 result_ids = for result <- results, do: result["acct"]
1686
1687 assert user_three.nickname in result_ids
1688 end
1689
1690 test "search", %{conn: conn} do
1691 user = insert(:user)
1692 user_two = insert(:user, %{nickname: "shp@shitposter.club"})
1693 user_three = insert(:user, %{nickname: "shp@heldscal.la", name: "I love 2hu"})
1694
1695 {:ok, activity} = CommonAPI.post(user, %{"status" => "This is about 2hu"})
1696
1697 {:ok, _activity} =
1698 CommonAPI.post(user, %{
1699 "status" => "This is about 2hu, but private",
1700 "visibility" => "private"
1701 })
1702
1703 {:ok, _} = CommonAPI.post(user_two, %{"status" => "This isn't"})
1704
1705 conn =
1706 conn
1707 |> get("/api/v1/search", %{"q" => "2hu"})
1708
1709 assert results = json_response(conn, 200)
1710
1711 [account | _] = results["accounts"]
1712 assert account["id"] == to_string(user_three.id)
1713
1714 assert results["hashtags"] == []
1715
1716 [status] = results["statuses"]
1717 assert status["id"] == to_string(activity.id)
1718 end
1719
1720 test "search fetches remote statuses", %{conn: conn} do
1721 capture_log(fn ->
1722 conn =
1723 conn
1724 |> get("/api/v1/search", %{"q" => "https://shitposter.club/notice/2827873"})
1725
1726 assert results = json_response(conn, 200)
1727
1728 [status] = results["statuses"]
1729 assert status["uri"] == "tag:shitposter.club,2017-05-05:noticeId=2827873:objectType=comment"
1730 end)
1731 end
1732
1733 test "search doesn't show statuses that it shouldn't", %{conn: conn} do
1734 {:ok, activity} =
1735 CommonAPI.post(insert(:user), %{
1736 "status" => "This is about 2hu, but private",
1737 "visibility" => "private"
1738 })
1739
1740 capture_log(fn ->
1741 conn =
1742 conn
1743 |> get("/api/v1/search", %{"q" => activity.data["object"]["id"]})
1744
1745 assert results = json_response(conn, 200)
1746
1747 [] = results["statuses"]
1748 end)
1749 end
1750
1751 test "search fetches remote accounts", %{conn: conn} do
1752 conn =
1753 conn
1754 |> get("/api/v1/search", %{"q" => "shp@social.heldscal.la", "resolve" => "true"})
1755
1756 assert results = json_response(conn, 200)
1757 [account] = results["accounts"]
1758 assert account["acct"] == "shp@social.heldscal.la"
1759 end
1760
1761 test "returns the favorites of a user", %{conn: conn} do
1762 user = insert(:user)
1763 other_user = insert(:user)
1764
1765 {:ok, _} = CommonAPI.post(other_user, %{"status" => "bla"})
1766 {:ok, activity} = CommonAPI.post(other_user, %{"status" => "traps are happy"})
1767
1768 {:ok, _, _} = CommonAPI.favorite(activity.id, user)
1769
1770 first_conn =
1771 conn
1772 |> assign(:user, user)
1773 |> get("/api/v1/favourites")
1774
1775 assert [status] = json_response(first_conn, 200)
1776 assert status["id"] == to_string(activity.id)
1777
1778 assert [{"link", _link_header}] =
1779 Enum.filter(first_conn.resp_headers, fn element -> match?({"link", _}, element) end)
1780
1781 # Honours query params
1782 {:ok, second_activity} =
1783 CommonAPI.post(other_user, %{
1784 "status" =>
1785 "Trees Are Never Sad Look At Them Every Once In Awhile They're Quite Beautiful."
1786 })
1787
1788 {:ok, _, _} = CommonAPI.favorite(second_activity.id, user)
1789
1790 last_like = status["id"]
1791
1792 second_conn =
1793 conn
1794 |> assign(:user, user)
1795 |> get("/api/v1/favourites?since_id=#{last_like}")
1796
1797 assert [second_status] = json_response(second_conn, 200)
1798 assert second_status["id"] == to_string(second_activity.id)
1799
1800 third_conn =
1801 conn
1802 |> assign(:user, user)
1803 |> get("/api/v1/favourites?limit=0")
1804
1805 assert [] = json_response(third_conn, 200)
1806 end
1807
1808 describe "updating credentials" do
1809 test "updates the user's bio", %{conn: conn} do
1810 user = insert(:user)
1811 user2 = insert(:user)
1812
1813 conn =
1814 conn
1815 |> assign(:user, user)
1816 |> patch("/api/v1/accounts/update_credentials", %{
1817 "note" => "I drink #cofe with @#{user2.nickname}"
1818 })
1819
1820 assert user = json_response(conn, 200)
1821
1822 assert user["note"] ==
1823 ~s(I drink <a class="hashtag" data-tag="cofe" href="http://localhost:4001/tag/cofe" rel="tag">#cofe</a> with <span class="h-card"><a data-user=") <>
1824 user2.id <>
1825 ~s(" class="u-url mention" href=") <>
1826 user2.ap_id <> ~s(">@<span>) <> user2.nickname <> ~s(</span></a></span>)
1827 end
1828
1829 test "updates the user's locking status", %{conn: conn} do
1830 user = insert(:user)
1831
1832 conn =
1833 conn
1834 |> assign(:user, user)
1835 |> patch("/api/v1/accounts/update_credentials", %{locked: "true"})
1836
1837 assert user = json_response(conn, 200)
1838 assert user["locked"] == true
1839 end
1840
1841 test "updates the user's name", %{conn: conn} do
1842 user = insert(:user)
1843
1844 conn =
1845 conn
1846 |> assign(:user, user)
1847 |> patch("/api/v1/accounts/update_credentials", %{"display_name" => "markorepairs"})
1848
1849 assert user = json_response(conn, 200)
1850 assert user["display_name"] == "markorepairs"
1851 end
1852
1853 test "updates the user's avatar", %{conn: conn} do
1854 user = insert(:user)
1855
1856 new_avatar = %Plug.Upload{
1857 content_type: "image/jpg",
1858 path: Path.absname("test/fixtures/image.jpg"),
1859 filename: "an_image.jpg"
1860 }
1861
1862 conn =
1863 conn
1864 |> assign(:user, user)
1865 |> patch("/api/v1/accounts/update_credentials", %{"avatar" => new_avatar})
1866
1867 assert user_response = json_response(conn, 200)
1868 assert user_response["avatar"] != User.avatar_url(user)
1869 end
1870
1871 test "updates the user's banner", %{conn: conn} do
1872 user = insert(:user)
1873
1874 new_header = %Plug.Upload{
1875 content_type: "image/jpg",
1876 path: Path.absname("test/fixtures/image.jpg"),
1877 filename: "an_image.jpg"
1878 }
1879
1880 conn =
1881 conn
1882 |> assign(:user, user)
1883 |> patch("/api/v1/accounts/update_credentials", %{"header" => new_header})
1884
1885 assert user_response = json_response(conn, 200)
1886 assert user_response["header"] != User.banner_url(user)
1887 end
1888
1889 test "requires 'write' permission", %{conn: conn} do
1890 token1 = insert(:oauth_token, scopes: ["read"])
1891 token2 = insert(:oauth_token, scopes: ["write", "follow"])
1892
1893 for token <- [token1, token2] do
1894 conn =
1895 conn
1896 |> put_req_header("authorization", "Bearer #{token.token}")
1897 |> patch("/api/v1/accounts/update_credentials", %{})
1898
1899 if token == token1 do
1900 assert %{"error" => "Insufficient permissions: write."} == json_response(conn, 403)
1901 else
1902 assert json_response(conn, 200)
1903 end
1904 end
1905 end
1906 end
1907
1908 test "get instance information", %{conn: conn} do
1909 conn = get(conn, "/api/v1/instance")
1910 assert result = json_response(conn, 200)
1911
1912 # Note: not checking for "max_toot_chars" since it's optional
1913 assert %{
1914 "uri" => _,
1915 "title" => _,
1916 "description" => _,
1917 "version" => _,
1918 "email" => _,
1919 "urls" => %{
1920 "streaming_api" => _
1921 },
1922 "stats" => _,
1923 "thumbnail" => _,
1924 "languages" => _,
1925 "registrations" => _
1926 } = result
1927 end
1928
1929 test "get instance stats", %{conn: conn} do
1930 user = insert(:user, %{local: true})
1931
1932 user2 = insert(:user, %{local: true})
1933 {:ok, _user2} = User.deactivate(user2, !user2.info.deactivated)
1934
1935 insert(:user, %{local: false, nickname: "u@peer1.com"})
1936 insert(:user, %{local: false, nickname: "u@peer2.com"})
1937
1938 {:ok, _} = TwitterAPI.create_status(user, %{"status" => "cofe"})
1939
1940 # Stats should count users with missing or nil `info.deactivated` value
1941 user = User.get_by_id(user.id)
1942 info_change = Changeset.change(user.info, %{deactivated: nil})
1943
1944 {:ok, _user} =
1945 user
1946 |> Changeset.change()
1947 |> Changeset.put_embed(:info, info_change)
1948 |> User.update_and_set_cache()
1949
1950 Pleroma.Stats.update_stats()
1951
1952 conn = get(conn, "/api/v1/instance")
1953
1954 assert result = json_response(conn, 200)
1955
1956 stats = result["stats"]
1957
1958 assert stats
1959 assert stats["user_count"] == 1
1960 assert stats["status_count"] == 1
1961 assert stats["domain_count"] == 2
1962 end
1963
1964 test "get peers", %{conn: conn} do
1965 insert(:user, %{local: false, nickname: "u@peer1.com"})
1966 insert(:user, %{local: false, nickname: "u@peer2.com"})
1967
1968 Pleroma.Stats.update_stats()
1969
1970 conn = get(conn, "/api/v1/instance/peers")
1971
1972 assert result = json_response(conn, 200)
1973
1974 assert ["peer1.com", "peer2.com"] == Enum.sort(result)
1975 end
1976
1977 test "put settings", %{conn: conn} do
1978 user = insert(:user)
1979
1980 conn =
1981 conn
1982 |> assign(:user, user)
1983 |> put("/api/web/settings", %{"data" => %{"programming" => "socks"}})
1984
1985 assert _result = json_response(conn, 200)
1986
1987 user = User.get_cached_by_ap_id(user.ap_id)
1988 assert user.info.settings == %{"programming" => "socks"}
1989 end
1990
1991 describe "pinned statuses" do
1992 setup do
1993 Pleroma.Config.put([:instance, :max_pinned_statuses], 1)
1994
1995 user = insert(:user)
1996 {:ok, activity} = CommonAPI.post(user, %{"status" => "HI!!!"})
1997
1998 [user: user, activity: activity]
1999 end
2000
2001 test "returns pinned statuses", %{conn: conn, user: user, activity: activity} do
2002 {:ok, _} = CommonAPI.pin(activity.id, user)
2003
2004 result =
2005 conn
2006 |> assign(:user, user)
2007 |> get("/api/v1/accounts/#{user.id}/statuses?pinned=true")
2008 |> json_response(200)
2009
2010 id_str = to_string(activity.id)
2011
2012 assert [%{"id" => ^id_str, "pinned" => true}] = result
2013 end
2014
2015 test "pin status", %{conn: conn, user: user, activity: activity} do
2016 id_str = to_string(activity.id)
2017
2018 assert %{"id" => ^id_str, "pinned" => true} =
2019 conn
2020 |> assign(:user, user)
2021 |> post("/api/v1/statuses/#{activity.id}/pin")
2022 |> json_response(200)
2023
2024 assert [%{"id" => ^id_str, "pinned" => true}] =
2025 conn
2026 |> assign(:user, user)
2027 |> get("/api/v1/accounts/#{user.id}/statuses?pinned=true")
2028 |> json_response(200)
2029 end
2030
2031 test "unpin status", %{conn: conn, user: user, activity: activity} do
2032 {:ok, _} = CommonAPI.pin(activity.id, user)
2033
2034 id_str = to_string(activity.id)
2035 user = refresh_record(user)
2036
2037 assert %{"id" => ^id_str, "pinned" => false} =
2038 conn
2039 |> assign(:user, user)
2040 |> post("/api/v1/statuses/#{activity.id}/unpin")
2041 |> json_response(200)
2042
2043 assert [] =
2044 conn
2045 |> assign(:user, user)
2046 |> get("/api/v1/accounts/#{user.id}/statuses?pinned=true")
2047 |> json_response(200)
2048 end
2049
2050 test "max pinned statuses", %{conn: conn, user: user, activity: activity_one} do
2051 {:ok, activity_two} = CommonAPI.post(user, %{"status" => "HI!!!"})
2052
2053 id_str_one = to_string(activity_one.id)
2054
2055 assert %{"id" => ^id_str_one, "pinned" => true} =
2056 conn
2057 |> assign(:user, user)
2058 |> post("/api/v1/statuses/#{id_str_one}/pin")
2059 |> json_response(200)
2060
2061 user = refresh_record(user)
2062
2063 assert %{"error" => "You have already pinned the maximum number of statuses"} =
2064 conn
2065 |> assign(:user, user)
2066 |> post("/api/v1/statuses/#{activity_two.id}/pin")
2067 |> json_response(400)
2068 end
2069
2070 test "Status rich-media Card", %{conn: conn, user: user} do
2071 Pleroma.Config.put([:rich_media, :enabled], true)
2072 {:ok, activity} = CommonAPI.post(user, %{"status" => "http://example.com/ogp"})
2073
2074 response =
2075 conn
2076 |> get("/api/v1/statuses/#{activity.id}/card")
2077 |> json_response(200)
2078
2079 assert response == %{
2080 "image" => "http://ia.media-imdb.com/images/rock.jpg",
2081 "provider_name" => "www.imdb.com",
2082 "provider_url" => "http://www.imdb.com",
2083 "title" => "The Rock",
2084 "type" => "link",
2085 "url" => "http://www.imdb.com/title/tt0117500/",
2086 "description" => nil,
2087 "pleroma" => %{
2088 "opengraph" => %{
2089 "image" => "http://ia.media-imdb.com/images/rock.jpg",
2090 "title" => "The Rock",
2091 "type" => "video.movie",
2092 "url" => "http://www.imdb.com/title/tt0117500/"
2093 }
2094 }
2095 }
2096
2097 # works with private posts
2098 {:ok, activity} =
2099 CommonAPI.post(user, %{"status" => "http://example.com/ogp", "visibility" => "direct"})
2100
2101 response_two =
2102 conn
2103 |> assign(:user, user)
2104 |> get("/api/v1/statuses/#{activity.id}/card")
2105 |> json_response(200)
2106
2107 assert response_two == response
2108
2109 Pleroma.Config.put([:rich_media, :enabled], false)
2110 end
2111 end
2112
2113 test "bookmarks" do
2114 user = insert(:user)
2115 for_user = insert(:user)
2116
2117 {:ok, activity1} =
2118 CommonAPI.post(user, %{
2119 "status" => "heweoo?"
2120 })
2121
2122 {:ok, activity2} =
2123 CommonAPI.post(user, %{
2124 "status" => "heweoo!"
2125 })
2126
2127 response1 =
2128 build_conn()
2129 |> assign(:user, for_user)
2130 |> post("/api/v1/statuses/#{activity1.id}/bookmark")
2131
2132 assert json_response(response1, 200)["bookmarked"] == true
2133
2134 response2 =
2135 build_conn()
2136 |> assign(:user, for_user)
2137 |> post("/api/v1/statuses/#{activity2.id}/bookmark")
2138
2139 assert json_response(response2, 200)["bookmarked"] == true
2140
2141 bookmarks =
2142 build_conn()
2143 |> assign(:user, for_user)
2144 |> get("/api/v1/bookmarks")
2145
2146 assert [json_response(response2, 200), json_response(response1, 200)] ==
2147 json_response(bookmarks, 200)
2148
2149 response1 =
2150 build_conn()
2151 |> assign(:user, for_user)
2152 |> post("/api/v1/statuses/#{activity1.id}/unbookmark")
2153
2154 assert json_response(response1, 200)["bookmarked"] == false
2155
2156 bookmarks =
2157 build_conn()
2158 |> assign(:user, for_user)
2159 |> get("/api/v1/bookmarks")
2160
2161 assert [json_response(response2, 200)] == json_response(bookmarks, 200)
2162 end
2163
2164 describe "conversation muting" do
2165 setup do
2166 user = insert(:user)
2167 {:ok, activity} = CommonAPI.post(user, %{"status" => "HIE"})
2168
2169 [user: user, activity: activity]
2170 end
2171
2172 test "mute conversation", %{conn: conn, user: user, activity: activity} do
2173 id_str = to_string(activity.id)
2174
2175 assert %{"id" => ^id_str, "muted" => true} =
2176 conn
2177 |> assign(:user, user)
2178 |> post("/api/v1/statuses/#{activity.id}/mute")
2179 |> json_response(200)
2180 end
2181
2182 test "unmute conversation", %{conn: conn, user: user, activity: activity} do
2183 {:ok, _} = CommonAPI.add_mute(user, activity)
2184
2185 id_str = to_string(activity.id)
2186 user = refresh_record(user)
2187
2188 assert %{"id" => ^id_str, "muted" => false} =
2189 conn
2190 |> assign(:user, user)
2191 |> post("/api/v1/statuses/#{activity.id}/unmute")
2192 |> json_response(200)
2193 end
2194 end
2195
2196 test "flavours switching (Pleroma Extension)", %{conn: conn} do
2197 user = insert(:user)
2198
2199 get_old_flavour =
2200 conn
2201 |> assign(:user, user)
2202 |> get("/api/v1/pleroma/flavour")
2203
2204 assert "glitch" == json_response(get_old_flavour, 200)
2205
2206 set_flavour =
2207 conn
2208 |> assign(:user, user)
2209 |> post("/api/v1/pleroma/flavour/vanilla")
2210
2211 assert "vanilla" == json_response(set_flavour, 200)
2212
2213 get_new_flavour =
2214 conn
2215 |> assign(:user, user)
2216 |> post("/api/v1/pleroma/flavour/vanilla")
2217
2218 assert json_response(set_flavour, 200) == json_response(get_new_flavour, 200)
2219 end
2220
2221 describe "reports" do
2222 setup do
2223 reporter = insert(:user)
2224 target_user = insert(:user)
2225
2226 {:ok, activity} = CommonAPI.post(target_user, %{"status" => "foobar"})
2227
2228 [reporter: reporter, target_user: target_user, activity: activity]
2229 end
2230
2231 test "submit a basic report", %{conn: conn, reporter: reporter, target_user: target_user} do
2232 assert %{"action_taken" => false, "id" => _} =
2233 conn
2234 |> assign(:user, reporter)
2235 |> post("/api/v1/reports", %{"account_id" => target_user.id})
2236 |> json_response(200)
2237 end
2238
2239 test "submit a report with statuses and comment", %{
2240 conn: conn,
2241 reporter: reporter,
2242 target_user: target_user,
2243 activity: activity
2244 } do
2245 assert %{"action_taken" => false, "id" => _} =
2246 conn
2247 |> assign(:user, reporter)
2248 |> post("/api/v1/reports", %{
2249 "account_id" => target_user.id,
2250 "status_ids" => [activity.id],
2251 "comment" => "bad status!"
2252 })
2253 |> json_response(200)
2254 end
2255
2256 test "account_id is required", %{
2257 conn: conn,
2258 reporter: reporter,
2259 activity: activity
2260 } do
2261 assert %{"error" => "Valid `account_id` required"} =
2262 conn
2263 |> assign(:user, reporter)
2264 |> post("/api/v1/reports", %{"status_ids" => [activity.id]})
2265 |> json_response(400)
2266 end
2267
2268 test "comment must be up to the size specified in the config", %{
2269 conn: conn,
2270 reporter: reporter,
2271 target_user: target_user
2272 } do
2273 max_size = Pleroma.Config.get([:instance, :max_report_comment_size], 1000)
2274 comment = String.pad_trailing("a", max_size + 1, "a")
2275
2276 error = %{"error" => "Comment must be up to #{max_size} characters"}
2277
2278 assert ^error =
2279 conn
2280 |> assign(:user, reporter)
2281 |> post("/api/v1/reports", %{"account_id" => target_user.id, "comment" => comment})
2282 |> json_response(400)
2283 end
2284 end
2285
2286 describe "link headers" do
2287 test "preserves parameters in link headers", %{conn: conn} do
2288 user = insert(:user)
2289 other_user = insert(:user)
2290
2291 {:ok, activity1} =
2292 CommonAPI.post(other_user, %{
2293 "status" => "hi @#{user.nickname}",
2294 "visibility" => "public"
2295 })
2296
2297 {:ok, activity2} =
2298 CommonAPI.post(other_user, %{
2299 "status" => "hi @#{user.nickname}",
2300 "visibility" => "public"
2301 })
2302
2303 notification1 = Repo.get_by(Notification, activity_id: activity1.id)
2304 notification2 = Repo.get_by(Notification, activity_id: activity2.id)
2305
2306 conn =
2307 conn
2308 |> assign(:user, user)
2309 |> get("/api/v1/notifications", %{media_only: true})
2310
2311 assert [link_header] = get_resp_header(conn, "link")
2312 assert link_header =~ ~r/media_only=true/
2313 assert link_header =~ ~r/since_id=#{notification2.id}/
2314 assert link_header =~ ~r/max_id=#{notification1.id}/
2315 end
2316 end
2317
2318 test "accounts fetches correct account for nicknames beginning with numbers", %{conn: conn} do
2319 # Need to set an old-style integer ID to reproduce the problem
2320 # (these are no longer assigned to new accounts but were preserved
2321 # for existing accounts during the migration to flakeIDs)
2322 user_one = insert(:user, %{id: 1212})
2323 user_two = insert(:user, %{nickname: "#{user_one.id}garbage"})
2324
2325 resp_one =
2326 conn
2327 |> get("/api/v1/accounts/#{user_one.id}")
2328
2329 resp_two =
2330 conn
2331 |> get("/api/v1/accounts/#{user_two.nickname}")
2332
2333 resp_three =
2334 conn
2335 |> get("/api/v1/accounts/#{user_two.id}")
2336
2337 acc_one = json_response(resp_one, 200)
2338 acc_two = json_response(resp_two, 200)
2339 acc_three = json_response(resp_three, 200)
2340 refute acc_one == acc_two
2341 assert acc_two == acc_three
2342 end
2343
2344 describe "index/2 redirections" do
2345 setup %{conn: conn} do
2346 session_opts = [
2347 store: :cookie,
2348 key: "_test",
2349 signing_salt: "cooldude"
2350 ]
2351
2352 conn =
2353 conn
2354 |> Plug.Session.call(Plug.Session.init(session_opts))
2355 |> fetch_session()
2356
2357 test_path = "/web/statuses/test"
2358 %{conn: conn, path: test_path}
2359 end
2360
2361 test "redirects not logged-in users to the login page", %{conn: conn, path: path} do
2362 conn = get(conn, path)
2363
2364 assert conn.status == 302
2365 assert redirected_to(conn) == "/web/login"
2366 end
2367
2368 test "does not redirect logged in users to the login page", %{conn: conn, path: path} do
2369 token = insert(:oauth_token)
2370
2371 conn =
2372 conn
2373 |> assign(:user, token.user)
2374 |> put_session(:oauth_token, token.token)
2375 |> get(path)
2376
2377 assert conn.status == 200
2378 end
2379
2380 test "saves referer path to session", %{conn: conn, path: path} do
2381 conn = get(conn, path)
2382 return_to = Plug.Conn.get_session(conn, :return_to)
2383
2384 assert return_to == path
2385 end
2386
2387 test "redirects to the saved path after log in", %{conn: conn, path: path} do
2388 app = insert(:oauth_app, client_name: "Mastodon-Local", redirect_uris: ".")
2389 auth = insert(:oauth_authorization, app: app)
2390
2391 conn =
2392 conn
2393 |> put_session(:return_to, path)
2394 |> get("/web/login", %{code: auth.token})
2395
2396 assert conn.status == 302
2397 assert redirected_to(conn) == path
2398 end
2399
2400 test "redirects to the getting-started page when referer is not present", %{conn: conn} do
2401 app = insert(:oauth_app, client_name: "Mastodon-Local", redirect_uris: ".")
2402 auth = insert(:oauth_authorization, app: app)
2403
2404 conn = get(conn, "/web/login", %{code: auth.token})
2405
2406 assert conn.status == 302
2407 assert redirected_to(conn) == "/web/getting-started"
2408 end
2409 end
2410 end