Browse Source

add test for search_controller/ 100% coverage

tags/v1.1.4
Maksim kaniini 5 years ago
parent
commit
008c55e4e9
3 changed files with 168 additions and 94 deletions
  1. +18
    -17
      lib/pleroma/web/mastodon_api/search_controller.ex
  2. +2
    -0
      lib/pleroma/web/mastodon_api/views/status_view.ex
  3. +148
    -77
      test/web/mastodon_api/search_controller_test.exs

+ 18
- 17
lib/pleroma/web/mastodon_api/search_controller.ex View File

@@ -4,29 +4,27 @@


defmodule Pleroma.Web.MastodonAPI.SearchController do defmodule Pleroma.Web.MastodonAPI.SearchController do
use Pleroma.Web, :controller use Pleroma.Web, :controller

alias Pleroma.Activity alias Pleroma.Activity
alias Pleroma.Plugs.RateLimiter
alias Pleroma.User alias Pleroma.User
alias Pleroma.Web alias Pleroma.Web
alias Pleroma.Web.ControllerHelper
alias Pleroma.Web.MastodonAPI.AccountView alias Pleroma.Web.MastodonAPI.AccountView
alias Pleroma.Web.MastodonAPI.StatusView alias Pleroma.Web.MastodonAPI.StatusView


alias Pleroma.Web.ControllerHelper

require Logger require Logger

plug(Pleroma.Plugs.RateLimiter, :search when action in [:search, :search2, :account_search])
plug(RateLimiter, :search when action in [:search, :search2, :account_search])


def search2(%{assigns: %{user: user}} = conn, %{"q" => query} = params) do def search2(%{assigns: %{user: user}} = conn, %{"q" => query} = params) do
accounts = with_fallback(fn -> User.search(query, search_options(params, user)) end, []) accounts = with_fallback(fn -> User.search(query, search_options(params, user)) end, [])
statuses = with_fallback(fn -> Activity.search(user, query) end, []) statuses = with_fallback(fn -> Activity.search(user, query) end, [])

tags_path = Web.base_url() <> "/tag/" tags_path = Web.base_url() <> "/tag/"


tags = tags =
query query
|> String.split()
|> Enum.uniq()
|> Enum.filter(fn tag -> String.starts_with?(tag, "#") end)
|> Enum.map(fn tag -> String.slice(tag, 1..-1) end)
|> prepare_tags
|> Enum.map(fn tag -> %{name: tag, url: tags_path <> tag} end) |> Enum.map(fn tag -> %{name: tag, url: tags_path <> tag} end)


res = %{ res = %{
@@ -40,15 +38,10 @@ defmodule Pleroma.Web.MastodonAPI.SearchController do
end end


def search(%{assigns: %{user: user}} = conn, %{"q" => query} = params) do def search(%{assigns: %{user: user}} = conn, %{"q" => query} = params) do
accounts = with_fallback(fn -> User.search(query, search_options(params, user)) end, [])
statuses = with_fallback(fn -> Activity.search(user, query) end, [])
accounts = with_fallback(fn -> User.search(query, search_options(params, user)) end)
statuses = with_fallback(fn -> Activity.search(user, query) end)


tags =
query
|> String.split()
|> Enum.uniq()
|> Enum.filter(fn tag -> String.starts_with?(tag, "#") end)
|> Enum.map(fn tag -> String.slice(tag, 1..-1) end)
tags = prepare_tags(query)


res = %{ res = %{
"accounts" => AccountView.render("accounts.json", users: accounts, for: user, as: :user), "accounts" => AccountView.render("accounts.json", users: accounts, for: user, as: :user),
@@ -67,6 +60,14 @@ defmodule Pleroma.Web.MastodonAPI.SearchController do
json(conn, res) json(conn, res)
end end


defp prepare_tags(query) do
query
|> String.split()
|> Enum.uniq()
|> Enum.filter(fn tag -> String.starts_with?(tag, "#") end)
|> Enum.map(fn tag -> String.slice(tag, 1..-1) end)
end

defp search_options(params, user) do defp search_options(params, user) do
[ [
resolve: params["resolve"] == "true", resolve: params["resolve"] == "true",
@@ -77,7 +78,7 @@ defmodule Pleroma.Web.MastodonAPI.SearchController do
] ]
end end


defp with_fallback(f, fallback) do
defp with_fallback(f, fallback \\ []) do
try do try do
f.() f.()
rescue rescue


+ 2
- 0
lib/pleroma/web/mastodon_api/views/status_view.ex View File

@@ -19,6 +19,8 @@ defmodule Pleroma.Web.MastodonAPI.StatusView do
import Pleroma.Web.ActivityPub.Visibility, only: [get_visibility: 1] import Pleroma.Web.ActivityPub.Visibility, only: [get_visibility: 1]


# TODO: Add cached version. # TODO: Add cached version.
defp get_replied_to_activities([]), do: %{}

defp get_replied_to_activities(activities) do defp get_replied_to_activities(activities) do
activities activities
|> Enum.map(fn |> Enum.map(fn


+ 148
- 77
test/web/mastodon_api/search_controller_test.exs View File

@@ -6,123 +6,194 @@ defmodule Pleroma.Web.MastodonAPI.SearchControllerTest do
use Pleroma.Web.ConnCase use Pleroma.Web.ConnCase


alias Pleroma.Object alias Pleroma.Object
alias Pleroma.Web
alias Pleroma.Web.CommonAPI alias Pleroma.Web.CommonAPI
import Pleroma.Factory import Pleroma.Factory
import ExUnit.CaptureLog import ExUnit.CaptureLog
import Tesla.Mock import Tesla.Mock
import Mock


setup do setup do
mock(fn env -> apply(HttpRequestMock, :request, [env]) end)
mock_global(fn env -> apply(HttpRequestMock, :request, [env]) end)
:ok :ok
end end


test "account search", %{conn: conn} do
user = insert(:user)
user_two = insert(:user, %{nickname: "shp@shitposter.club"})
user_three = insert(:user, %{nickname: "shp@heldscal.la", name: "I love 2hu"})
describe ".search2" do
test "it returns empty result if user or status search return undefined error", %{conn: conn} do
with_mocks [
{Pleroma.User, [], [search: fn _q, _o -> raise "Oops" end]},
{Pleroma.Activity, [], [search: fn _u, _q -> raise "Oops" end]}
] do
conn = get(conn, "/api/v2/search", %{"q" => "2hu"})


results =
conn
|> assign(:user, user)
|> get("/api/v1/accounts/search", %{"q" => "shp"})
|> json_response(200)
assert results = json_response(conn, 200)


result_ids = for result <- results, do: result["acct"]
assert results["accounts"] == []
assert results["statuses"] == []
end
end


assert user_two.nickname in result_ids
assert user_three.nickname in result_ids
test "search", %{conn: conn} do
user = insert(:user)
user_two = insert(:user, %{nickname: "shp@shitposter.club"})
user_three = insert(:user, %{nickname: "shp@heldscal.la", name: "I love 2hu"})


results =
conn
|> assign(:user, user)
|> get("/api/v1/accounts/search", %{"q" => "2hu"})
|> json_response(200)
{:ok, activity} = CommonAPI.post(user, %{"status" => "This is about 2hu private"})


result_ids = for result <- results, do: result["acct"]
{:ok, _activity} =
CommonAPI.post(user, %{
"status" => "This is about 2hu, but private",
"visibility" => "private"
})


assert user_three.nickname in result_ids
end
{:ok, _} = CommonAPI.post(user_two, %{"status" => "This isn't"})


test "search", %{conn: conn} do
user = insert(:user)
user_two = insert(:user, %{nickname: "shp@shitposter.club"})
user_three = insert(:user, %{nickname: "shp@heldscal.la", name: "I love 2hu"})
conn = get(conn, "/api/v2/search", %{"q" => "2hu #private"})


{:ok, activity} = CommonAPI.post(user, %{"status" => "This is about 2hu"})
assert results = json_response(conn, 200)
# IO.inspect results


{:ok, _activity} =
CommonAPI.post(user, %{
"status" => "This is about 2hu, but private",
"visibility" => "private"
})
[account | _] = results["accounts"]
assert account["id"] == to_string(user_three.id)


{:ok, _} = CommonAPI.post(user_two, %{"status" => "This isn't"})
assert results["hashtags"] == [
%{"name" => "private", "url" => "#{Web.base_url()}/tag/private"}
]


conn =
conn
|> get("/api/v1/search", %{"q" => "2hu"})
[status] = results["statuses"]
assert status["id"] == to_string(activity.id)
end
end


assert results = json_response(conn, 200)
describe ".account_search" do
test "account search", %{conn: conn} do
user = insert(:user)
user_two = insert(:user, %{nickname: "shp@shitposter.club"})
user_three = insert(:user, %{nickname: "shp@heldscal.la", name: "I love 2hu"})


[account | _] = results["accounts"]
assert account["id"] == to_string(user_three.id)
results =
conn
|> assign(:user, user)
|> get("/api/v1/accounts/search", %{"q" => "shp"})
|> json_response(200)


assert results["hashtags"] == []
result_ids = for result <- results, do: result["acct"]


[status] = results["statuses"]
assert status["id"] == to_string(activity.id)
end
assert user_two.nickname in result_ids
assert user_three.nickname in result_ids


test "search fetches remote statuses", %{conn: conn} do
capture_log(fn ->
conn =
results =
conn conn
|> get("/api/v1/search", %{"q" => "https://shitposter.club/notice/2827873"})
|> assign(:user, user)
|> get("/api/v1/accounts/search", %{"q" => "2hu"})
|> json_response(200)


assert results = json_response(conn, 200)
result_ids = for result <- results, do: result["acct"]


[status] = results["statuses"]
assert status["uri"] == "tag:shitposter.club,2017-05-05:noticeId=2827873:objectType=comment"
end)
assert user_three.nickname in result_ids
end
end end


test "search doesn't show statuses that it shouldn't", %{conn: conn} do
{:ok, activity} =
CommonAPI.post(insert(:user), %{
"status" => "This is about 2hu, but private",
"visibility" => "private"
})
describe ".search" do
test "it returns empty result if user or status search return undefined error", %{conn: conn} do
with_mocks [
{Pleroma.User, [], [search: fn _q, _o -> raise "Oops" end]},
{Pleroma.Activity, [], [search: fn _u, _q -> raise "Oops" end]}
] do
conn =
conn
|> get("/api/v1/search", %{"q" => "2hu"})

assert results = json_response(conn, 200)

assert results["accounts"] == []
assert results["statuses"] == []
end
end

test "search", %{conn: conn} do
user = insert(:user)
user_two = insert(:user, %{nickname: "shp@shitposter.club"})
user_three = insert(:user, %{nickname: "shp@heldscal.la", name: "I love 2hu"})

{:ok, activity} = CommonAPI.post(user, %{"status" => "This is about 2hu"})

{:ok, _activity} =
CommonAPI.post(user, %{
"status" => "This is about 2hu, but private",
"visibility" => "private"
})

{:ok, _} = CommonAPI.post(user_two, %{"status" => "This isn't"})


capture_log(fn ->
conn = conn =
conn conn
|> get("/api/v1/search", %{"q" => Object.normalize(activity).data["id"]})
|> get("/api/v1/search", %{"q" => "2hu"})


assert results = json_response(conn, 200) assert results = json_response(conn, 200)


[] = results["statuses"]
end)
end
[account | _] = results["accounts"]
assert account["id"] == to_string(user_three.id)

assert results["hashtags"] == []


test "search fetches remote accounts", %{conn: conn} do
user = insert(:user)
[status] = results["statuses"]
assert status["id"] == to_string(activity.id)
end


conn =
conn
|> assign(:user, user)
|> get("/api/v1/search", %{"q" => "shp@social.heldscal.la", "resolve" => "true"})
test "search fetches remote statuses", %{conn: conn} do
capture_log(fn ->
conn =
conn
|> get("/api/v1/search", %{"q" => "https://shitposter.club/notice/2827873"})


assert results = json_response(conn, 200)
[account] = results["accounts"]
assert account["acct"] == "shp@social.heldscal.la"
end
assert results = json_response(conn, 200)

[status] = results["statuses"]

assert status["uri"] ==
"tag:shitposter.club,2017-05-05:noticeId=2827873:objectType=comment"
end)
end

test "search doesn't show statuses that it shouldn't", %{conn: conn} do
{:ok, activity} =
CommonAPI.post(insert(:user), %{
"status" => "This is about 2hu, but private",
"visibility" => "private"
})


test "search doesn't fetch remote accounts if resolve is false", %{conn: conn} do
conn =
conn
|> get("/api/v1/search", %{"q" => "shp@social.heldscal.la", "resolve" => "false"})
capture_log(fn ->
conn =
conn
|> get("/api/v1/search", %{"q" => Object.normalize(activity).data["id"]})


assert results = json_response(conn, 200)
assert [] == results["accounts"]
assert results = json_response(conn, 200)

[] = results["statuses"]
end)
end

test "search fetches remote accounts", %{conn: conn} do
user = insert(:user)

conn =
conn
|> assign(:user, user)
|> get("/api/v1/search", %{"q" => "shp@social.heldscal.la", "resolve" => "true"})

assert results = json_response(conn, 200)
[account] = results["accounts"]
assert account["acct"] == "shp@social.heldscal.la"
end

test "search doesn't fetch remote accounts if resolve is false", %{conn: conn} do
conn =
conn
|> get("/api/v1/search", %{"q" => "shp@social.heldscal.la", "resolve" => "false"})

assert results = json_response(conn, 200)
assert [] == results["accounts"]
end
end end
end end

Loading…
Cancel
Save