2019-04-30 10:27:42 +10:00
# frozen_string_literal: true
2022-07-28 05:27:38 +03:00
RSpec . describe SearchController do
2020-07-17 16:27:30 +08:00
fab! ( :awesome_topic ) do
topic = Fabricate ( :topic )
tag = Fabricate ( :tag )
topic . tags << tag
Fabricate ( :tag , target_tag_id : tag . id )
topic
end
2019-07-02 11:21:52 +10:00
fab! ( :awesome_post ) do
2023-05-04 09:20:52 +08:00
with_search_indexer_enabled do
Fabricate ( :post , topic : awesome_topic , raw : "this is my really awesome post" )
end
2020-07-17 16:27:30 +08:00
end
fab! ( :awesome_post_2 ) do
2023-05-04 09:20:52 +08:00
with_search_indexer_enabled { Fabricate ( :post , raw : "this is my really awesome post 2" ) }
2019-07-02 11:21:52 +10:00
end
2023-05-04 09:20:52 +08:00
fab! ( :user ) { with_search_indexer_enabled { Fabricate ( :user ) } }
2019-07-02 11:21:52 +10:00
fab! ( :user_post ) do
2023-05-04 09:20:52 +08:00
with_search_indexer_enabled { Fabricate ( :post , raw : " #{ user . username } is a cool person" ) }
2019-07-02 11:21:52 +10:00
end
2022-07-27 18:14:14 +02:00
context "with integration" do
2016-12-22 13:13:14 +11:00
before { SearchIndexer . enable }
2014-09-02 19:15:08 +10:00
2018-06-14 18:31:07 +10:00
before do
# TODO be a bit more strategic here instead of junking
# all of redis
2020-05-23 00:56:13 -04:00
Discourse . redis . flushdb
2018-06-14 18:31:07 +10:00
end
2020-05-23 00:56:13 -04:00
after { Discourse . redis . flushdb }
2018-06-05 10:07:05 +08:00
2019-07-02 11:21:52 +10:00
context "when overloaded" do
before { global_setting :disable_search_queue_threshold , 0 . 2 }
let! :start_time do
freeze_time
Time . now
end
let! :current_time do
freeze_time 0 . 3 . seconds . from_now
end
it "errors on #query" do
get "/search/query.json" ,
headers : {
"HTTP_X_REQUEST_START" => "t= #{ start_time . to_f } " ,
},
params : {
2020-07-14 11:05:57 +08:00
term : "hi there" ,
2019-07-02 11:21:52 +10:00
}
expect ( response . status ) . to eq ( 409 )
end
it "no results and error on #index" do
get "/search.json" ,
headers : {
"HTTP_X_REQUEST_START" => "t= #{ start_time . to_f } " ,
},
params : {
q : "awesome" ,
}
expect ( response . status ) . to eq ( 200 )
2020-05-07 17:04:12 +02:00
data = response . parsed_body
2019-07-02 11:21:52 +10:00
expect ( data [ "posts" ] ) . to be_empty
expect ( data [ "grouped_search_result" ][ "error" ] ) . not_to be_empty
end
end
2018-09-04 12:11:42 +10:00
it "returns a 400 error if you search for null bytes" do
term = "hello \0 hello"
get "/search/query.json" , params : { term : term }
expect ( response . status ) . to eq ( 400 )
end
2014-09-02 19:15:08 +10:00
it "can search correctly" do
2020-08-06 14:15:31 +08:00
SiteSetting . use_pg_headlines_for_excerpt = true
2020-08-07 12:43:09 +08:00
awesome_post_3 = Fabricate ( :post , topic : Fabricate ( :topic , title : "this is an awesome title" ))
2018-06-04 06:12:38 +03:00
get "/search/query.json" , params : { term : "awesome" }
2014-09-02 19:15:08 +10:00
2018-06-07 16:11:09 +08:00
expect ( response . status ) . to eq ( 200 )
2019-07-02 11:21:52 +10:00
2020-05-07 17:04:12 +02:00
data = response . parsed_body
2019-07-02 11:21:52 +10:00
2020-08-07 12:43:09 +08:00
expect ( data [ "posts" ]. length ) . to eq ( 3 )
expect ( data [ "posts" ][ 0 ][ "id" ] ) . to eq ( awesome_post_3 . id )
expect ( data [ "posts" ][ 0 ][ "blurb" ] ) . to eq ( awesome_post_3 . raw )
expect ( data [ "posts" ][ 0 ][ "topic_title_headline" ] ) . to eq (
"This is an <span class= \" #{ Search :: HIGHLIGHT_CSS_CLASS } \" >awesome</span> title" ,
)
expect ( data [ "topics" ][ 0 ][ "id" ] ) . to eq ( awesome_post_3 . topic_id )
2020-07-17 16:27:30 +08:00
2020-08-07 12:43:09 +08:00
expect ( data [ "posts" ][ 1 ][ "id" ] ) . to eq ( awesome_post_2 . id )
expect ( data [ "posts" ][ 1 ][ "blurb" ] ) . to eq (
2020-08-12 15:55:22 +08:00
" #{ Search :: GroupedSearchResults :: OMISSION } this is my really <span class= \" #{ Search :: HIGHLIGHT_CSS_CLASS } \" >awesome</span> post #{ Search :: GroupedSearchResults :: OMISSION } " ,
2020-08-07 12:43:09 +08:00
)
expect ( data [ "topics" ][ 1 ][ "id" ] ) . to eq ( awesome_post_2 . topic_id )
expect ( data [ "posts" ][ 2 ][ "id" ] ) . to eq ( awesome_post . id )
expect ( data [ "posts" ][ 2 ][ "blurb" ] ) . to eq (
"this is my really <span class= \" #{ Search :: HIGHLIGHT_CSS_CLASS } \" >awesome</span> post" ,
)
expect ( data [ "topics" ][ 2 ][ "id" ] ) . to eq ( awesome_post . topic_id )
2014-09-02 19:15:08 +10:00
end
2017-07-14 13:56:58 -04:00
2020-07-14 11:05:57 +08:00
it "can search correctly with advanced search filters" do
awesome_post . update! ( raw : " #{ "a" * Search :: GroupedSearchResults :: BLURB_LENGTH } elephant" )
get "/search/query.json" , params : { term : "order:views elephant" }
expect ( response . status ) . to eq ( 200 )
data = response . parsed_body
expect ( data . dig ( "grouped_search_result" , "term" )) . to eq ( "order:views elephant" )
expect ( data [ "posts" ]. length ) . to eq ( 1 )
expect ( data [ "posts" ][ 0 ][ "id" ] ) . to eq ( awesome_post . id )
expect ( data [ "posts" ][ 0 ][ "blurb" ] ) . to include ( "elephant" )
expect ( data [ "topics" ][ 0 ][ "id" ] ) . to eq ( awesome_post . topic_id )
end
2017-07-14 13:56:58 -04:00
it "performs the query with a type filter" do
2017-08-31 12:06:56 +08:00
get "/search/query.json" , params : { term : user . username , type_filter : "topic" }
2017-07-14 13:56:58 -04:00
2018-06-07 16:11:09 +08:00
expect ( response . status ) . to eq ( 200 )
2020-05-07 17:04:12 +02:00
data = response . parsed_body
2017-07-14 13:56:58 -04:00
2019-07-02 11:21:52 +10:00
expect ( data [ "posts" ][ 0 ][ "id" ] ) . to eq ( user_post . id )
2017-07-14 13:56:58 -04:00
expect ( data [ "users" ] ) . to be_blank
2017-08-31 12:06:56 +08:00
get "/search/query.json" , params : { term : user . username , type_filter : "user" }
2018-06-07 16:11:09 +08:00
expect ( response . status ) . to eq ( 200 )
2020-05-07 17:04:12 +02:00
data = response . parsed_body
2017-07-14 13:56:58 -04:00
expect ( data [ "posts" ] ) . to be_blank
expect ( data [ "users" ][ 0 ][ "id" ] ) . to eq ( user . id )
end
2022-07-27 18:14:14 +02:00
context "when searching by topic id" do
2017-07-26 09:51:44 +09:00
it "should not be restricted by minimum search term length" do
SiteSetting . min_search_term_length = 20_000
2018-06-04 06:12:38 +03:00
get "/search/query.json" ,
params : {
2019-07-02 11:21:52 +10:00
term : awesome_post . topic_id ,
2017-07-26 09:51:44 +09:00
type_filter : "topic" ,
search_for_id : true ,
2018-06-04 06:12:38 +03:00
}
2017-07-26 09:51:44 +09:00
2018-06-07 16:11:09 +08:00
expect ( response . status ) . to eq ( 200 )
2020-05-07 17:04:12 +02:00
data = response . parsed_body
2017-07-26 09:51:44 +09:00
2019-07-02 11:21:52 +10:00
expect ( data [ "topics" ][ 0 ][ "id" ] ) . to eq ( awesome_post . topic_id )
2017-07-26 09:51:44 +09:00
end
it "should return the right result" do
2018-06-04 06:12:38 +03:00
get "/search/query.json" ,
params : {
2019-07-02 11:21:52 +10:00
term : user_post . topic_id ,
2017-07-26 09:51:44 +09:00
type_filter : "topic" ,
search_for_id : true ,
2018-06-04 06:12:38 +03:00
}
2017-07-26 09:51:44 +09:00
2018-06-07 16:11:09 +08:00
expect ( response . status ) . to eq ( 200 )
2020-05-07 17:04:12 +02:00
data = response . parsed_body
2017-07-26 09:51:44 +09:00
2019-07-02 11:21:52 +10:00
expect ( data [ "topics" ][ 0 ][ "id" ] ) . to eq ( user_post . topic_id )
2017-07-25 17:09:13 -04:00
end
2017-07-14 13:56:58 -04:00
end
2014-09-02 19:15:08 +10:00
end
2022-07-27 12:21:10 +02:00
describe "#query" do
2017-07-13 13:34:31 -04:00
it "logs the search term" do
SiteSetting . log_search_queries = true
2018-06-04 06:12:38 +03:00
get "/search/query.json" , params : { term : "wookie" }
2017-07-17 11:57:13 -04:00
2018-06-07 16:11:09 +08:00
expect ( response . status ) . to eq ( 200 )
2017-07-13 13:34:31 -04:00
expect ( SearchLog . where ( term : "wookie" )) . to be_present
2017-07-17 11:57:13 -04:00
2020-05-07 17:04:12 +02:00
json = response . parsed_body
2017-07-17 11:57:13 -04:00
search_log_id = json [ "grouped_search_result" ][ "search_log_id" ]
expect ( search_log_id ) . to be_present
log = SearchLog . where ( id : search_log_id ) . first
expect ( log ) . to be_present
expect ( log . term ) . to eq ( "wookie" )
2017-07-13 13:34:31 -04:00
end
it "doesn't log when disabled" do
SiteSetting . log_search_queries = false
2018-06-04 06:12:38 +03:00
get "/search/query.json" , params : { term : "wookie" }
2018-06-07 16:11:09 +08:00
expect ( response . status ) . to eq ( 200 )
2017-07-13 13:34:31 -04:00
expect ( SearchLog . where ( term : "wookie" )) . to be_blank
end
2020-06-04 06:26:08 -10:00
2021-11-17 20:21:12 -05:00
it "doesn't log when filtering by exclude_topics" do
SiteSetting . log_search_queries = true
get "/search/query.json" , params : { term : "boop" , type_filter : "exclude_topics" }
expect ( response . status ) . to eq ( 200 )
expect ( SearchLog . where ( term : "boop" )) . to be_blank
end
2020-11-20 11:28:14 +02:00
it "does not raise 500 with an empty term" do
get "/search/query.json" ,
params : {
term : "in:first" ,
type_filter : "topic" ,
search_for_id : true ,
}
expect ( response . status ) . to eq ( 200 )
end
2022-07-27 18:14:14 +02:00
context "when rate limited" do
2023-06-16 12:44:35 +10:00
before { RateLimiter . enable }
use_redis_snapshotting
2023-01-28 05:05:27 +11:00
def unlimited_request ( ip_address = "1.2.3.4" )
get "/search/query.json" , params : { term : "wookie" }, env : { REMOTE_ADDR : ip_address }
expect ( response . status ) . to eq ( 200 )
json = response . parsed_body
expect ( json [ "grouped_search_result" ][ "error" ] ) . to eq ( nil )
end
def limited_request ( ip_address = "1.2.3.4" )
get "/search/query.json" , params : { term : "wookie" }, env : { REMOTE_ADDR : ip_address }
expect ( response . status ) . to eq ( 429 )
json = response . parsed_body
expect ( json [ "message" ] ) . to eq ( I18n . t ( "rate_limiter.slow_down" ))
end
2020-07-09 20:44:17 -03:00
it "rate limits anon searches per user" do
2023-01-28 05:05:27 +11:00
SiteSetting . rate_limit_search_anon_user_per_second = 2
SiteSetting . rate_limit_search_anon_user_per_minute = 3
2020-07-09 20:44:17 -03:00
2023-01-28 05:05:27 +11:00
start = Time . now
freeze_time start
2020-07-09 20:44:17 -03:00
2023-01-28 05:05:27 +11:00
unlimited_request
unlimited_request
limited_request
2020-07-09 20:44:17 -03:00
2023-01-28 05:05:27 +11:00
freeze_time start + 2
unlimited_request
limited_request
# cause it is a diff IP
unlimited_request ( "100.0.0.0" )
2020-06-04 06:26:08 -10:00
end
2020-07-09 20:44:17 -03:00
it "rate limits anon searches globally" do
2023-01-28 05:05:27 +11:00
SiteSetting . rate_limit_search_anon_global_per_second = 2
SiteSetting . rate_limit_search_anon_global_per_minute = 3
2020-06-04 06:26:08 -10:00
2023-01-28 05:05:27 +11:00
t = Time . now
freeze_time t
2020-06-04 06:26:08 -10:00
2023-01-28 05:05:27 +11:00
unlimited_request ( "1.2.3.4" )
unlimited_request ( "1.2.3.5" )
limited_request ( "1.2.3.6" )
2020-06-04 06:26:08 -10:00
2023-01-28 05:05:27 +11:00
freeze_time t + 2
unlimited_request ( "1.2.3.7" )
limited_request ( "1.2.3.8" )
2020-06-04 06:26:08 -10:00
end
2022-07-27 18:14:14 +02:00
context "with a logged in user" do
2020-06-04 06:26:08 -10:00
before { sign_in ( user ) }
it "rate limits logged in searches" do
2020-07-09 20:44:17 -03:00
SiteSetting . rate_limit_search_user = 3
2020-06-04 06:26:08 -10:00
3 . times do
get "/search/query.json" , params : { term : "wookie" }
expect ( response . status ) . to eq ( 200 )
json = response . parsed_body
expect ( json [ "grouped_search_result" ][ "error" ] ) . to eq ( nil )
end
get "/search/query.json" , params : { term : "wookie" }
2023-01-28 05:05:27 +11:00
expect ( response . status ) . to eq ( 429 )
2020-06-04 06:26:08 -10:00
json = response . parsed_body
2023-01-28 05:05:27 +11:00
expect ( json [ "message" ] ) . to eq ( I18n . t ( "rate_limiter.slow_down" ))
2020-06-04 06:26:08 -10:00
end
end
end
2017-07-13 13:34:31 -04:00
end
2022-07-27 12:21:10 +02:00
describe "#show" do
2018-12-20 21:43:14 +05:30
it "doesn't raise an error when search term not specified" do
get "/search"
expect ( response . status ) . to eq ( 200 )
end
2018-12-18 20:06:59 +05:30
it "raises an error when the search term length is less than required" do
get "/search.json" , params : { q : "ba" }
expect ( response . status ) . to eq ( 400 )
end
2019-04-29 09:09:25 +02:00
it "raises an error when search term is a hash" do
get "/search.json?q[foo]"
expect ( response . status ) . to eq ( 400 )
end
2019-10-22 08:44:52 -06:00
it "returns a 400 error if you search for null bytes" do
term = "hello \0 hello"
get "/search.json" , params : { q : term }
expect ( response . status ) . to eq ( 400 )
end
2020-11-02 12:40:54 -05:00
it "doesn't raise an error if the page is a string number" do
get "/search.json" , params : { q : "kittens" , page : "3" }
expect ( response . status ) . to eq ( 200 )
end
it "doesn't raise an error if the page is a integer number" do
get "/search.json" , params : { q : "kittens" , page : 3 }
expect ( response . status ) . to eq ( 200 )
end
it "returns a 400 error if the page parameter is invalid" do
get "/search.json?page=xawesome%27 \" </a\&"
expect ( response . status ) . to eq ( 400 )
end
2020-11-04 11:05:31 -05:00
it "returns a 400 error if the page parameter is padded with spaces" do
get "/search.json" , params : { q : "kittens" , page : " 3 " }
expect ( response . status ) . to eq ( 400 )
end
2017-07-13 13:34:31 -04:00
it "logs the search term" do
SiteSetting . log_search_queries = true
2018-06-04 06:12:38 +03:00
get "/search.json" , params : { q : "bantha" }
2018-06-07 16:11:09 +08:00
expect ( response . status ) . to eq ( 200 )
2017-07-13 13:34:31 -04:00
expect ( SearchLog . where ( term : "bantha" )) . to be_present
end
it "doesn't log when disabled" do
SiteSetting . log_search_queries = false
2018-06-04 06:12:38 +03:00
get "/search.json" , params : { q : "bantha" }
2018-06-07 16:11:09 +08:00
expect ( response . status ) . to eq ( 200 )
2017-07-13 13:34:31 -04:00
expect ( SearchLog . where ( term : "bantha" )) . to be_blank
end
2020-06-04 06:26:08 -10:00
2023-08-08 15:15:34 -04:00
it "works when using a tag context" do
tag = Fabricate ( :tag , name : "awesome" )
awesome_topic . tags << tag
SearchIndexer . index ( awesome_topic , force : true )
get "/search.json" ,
params : {
q : "awesome" ,
context : "tag" ,
context_id : "awesome" ,
skip_context : false ,
}
expect ( response . status ) . to eq ( 200 )
expect ( response . parsed_body [ "posts" ]. length ) . to eq ( 1 )
expect ( response . parsed_body [ "posts" ][ 0 ][ "id" ] ) . to eq ( awesome_post . id )
end
context "with restricted tags" do
let ( :restricted_tag ) { Fabricate ( :tag ) }
let ( :admin ) { Fabricate ( :admin ) }
before do
tag_group =
Fabricate ( :tag_group , permissions : { "staff" => 1 }, tag_names : [ restricted_tag . name ] )
awesome_topic . tags << restricted_tag
SearchIndexer . index ( awesome_topic , force : true )
end
it "works for user with tag group permision" do
sign_in ( admin )
get "/search.json" ,
params : {
q : "awesome" ,
context : "tag" ,
context_id : restricted_tag . name ,
skip_context : false ,
}
expect ( response . status ) . to eq ( 200 )
end
it "doesn’ t work for user without tag group permission" do
get "/search.json" ,
params : {
q : "awesome" ,
context : "tag" ,
context_id : restricted_tag . name ,
skip_context : false ,
}
expect ( response . status ) . to eq ( 403 )
end
end
2022-07-27 18:14:14 +02:00
context "when rate limited" do
2023-06-16 12:44:35 +10:00
before { RateLimiter . enable }
use_redis_snapshotting
2023-01-28 05:05:27 +11:00
def unlimited_request ( ip_address = "1.2.3.4" )
get "/search.json" , params : { q : "wookie" }, env : { REMOTE_ADDR : ip_address }
expect ( response . status ) . to eq ( 200 )
json = response . parsed_body
expect ( json [ "grouped_search_result" ][ "error" ] ) . to eq ( nil )
end
def limited_request ( ip_address = "1.2.3.4" )
get "/search.json" , params : { q : "wookie" }, env : { REMOTE_ADDR : ip_address }
expect ( response . status ) . to eq ( 429 )
json = response . parsed_body
expect ( json [ "message" ] ) . to eq ( I18n . t ( "rate_limiter.slow_down" ))
end
2020-07-09 20:44:17 -03:00
it "rate limits anon searches per user" do
2023-01-28 05:05:27 +11:00
SiteSetting . rate_limit_search_anon_user_per_second = 2
SiteSetting . rate_limit_search_anon_user_per_minute = 3
2020-07-09 20:44:17 -03:00
2023-01-28 05:05:27 +11:00
t = Time . now
freeze_time t
2020-07-09 20:44:17 -03:00
2023-01-28 05:05:27 +11:00
unlimited_request
unlimited_request
limited_request
2020-07-09 20:44:17 -03:00
2023-01-28 05:05:27 +11:00
freeze_time ( t + 2 )
unlimited_request
limited_request
unlimited_request ( "1.2.3.100" )
2020-06-04 06:26:08 -10:00
end
2020-07-09 20:44:17 -03:00
it "rate limits anon searches globally" do
2023-01-28 05:05:27 +11:00
SiteSetting . rate_limit_search_anon_global_per_second = 2
SiteSetting . rate_limit_search_anon_global_per_minute = 3
2020-06-04 06:26:08 -10:00
2023-02-06 14:35:05 -05:00
t = Time . now
freeze_time t
2023-01-28 05:05:27 +11:00
unlimited_request ( "1.1.1.1" )
unlimited_request ( "2.2.2.2" )
limited_request ( "3.3.3.3" )
2020-06-04 06:26:08 -10:00
2023-01-28 05:05:27 +11:00
freeze_time ( t + 2 )
2020-06-04 06:26:08 -10:00
2023-01-28 05:05:27 +11:00
unlimited_request ( "4.4.4.4" )
limited_request ( "5.5.5.5" )
2020-06-04 06:26:08 -10:00
end
2022-07-27 18:14:14 +02:00
context "with a logged in user" do
2020-06-04 06:26:08 -10:00
before { sign_in ( user ) }
it "rate limits searches" do
2020-07-09 20:44:17 -03:00
SiteSetting . rate_limit_search_user = 3
2020-06-04 06:26:08 -10:00
3 . times do
get "/search.json" , params : { q : "bantha" }
expect ( response . status ) . to eq ( 200 )
json = response . parsed_body
expect ( json [ "grouped_search_result" ][ "error" ] ) . to eq ( nil )
end
get "/search.json" , params : { q : "bantha" }
2023-01-28 05:05:27 +11:00
expect ( response . status ) . to eq ( 429 )
2020-06-04 06:26:08 -10:00
json = response . parsed_body
2023-01-28 05:05:27 +11:00
expect ( json [ "message" ] ) . to eq ( I18n . t ( "rate_limiter.slow_down" ))
2020-06-04 06:26:08 -10:00
end
end
end
2024-02-21 17:29:47 +02:00
context "with lazy loaded categories" do
fab! ( :parent_category ) { Fabricate ( :category ) }
fab! ( :category ) { Fabricate ( :category , parent_category : parent_category ) }
fab! ( :other_category ) { Fabricate ( :category , parent_category : parent_category ) }
fab! ( :post ) do
with_search_indexer_enabled do
topic = Fabricate ( :topic , category : category )
Fabricate ( :post , topic : topic , raw : "hello world. first topic" )
end
end
fab! ( :other_post ) do
with_search_indexer_enabled do
topic = Fabricate ( :topic , category : other_category )
Fabricate ( :post , topic : topic , raw : "hello world. second topic" )
end
end
before { SiteSetting . lazy_load_categories_groups = " #{ Group :: AUTO_GROUPS [ :everyone ] } " }
it "returns extra categories and parent categories" do
get "/search.json" , params : { q : "hello" }
categories = response . parsed_body [ "grouped_search_result" ][ "extra" ][ "categories" ]
expect ( categories . map { | c | c [ "id" ] }) . to contain_exactly (
parent_category . id ,
category . id ,
other_category . id ,
)
end
end
2017-07-13 13:34:31 -04:00
end
2022-07-27 18:14:14 +02:00
context "with search priority" do
2020-12-23 15:14:41 +08:00
fab! ( :very_low_priority_category ) do
2020-04-27 22:35:27 +08:00
Fabricate ( :category , search_priority : Searchable :: PRIORITIES [ :very_low ] )
end
2020-12-23 15:14:41 +08:00
fab! ( :low_priority_category ) do
Fabricate ( :category , search_priority : Searchable :: PRIORITIES [ :low ] )
end
2020-04-27 22:35:27 +08:00
fab! ( :high_priority_category ) do
Fabricate ( :category , search_priority : Searchable :: PRIORITIES [ :high ] )
end
2020-12-23 15:14:41 +08:00
2020-04-27 22:35:27 +08:00
fab! ( :very_high_priority_category ) do
Fabricate ( :category , search_priority : Searchable :: PRIORITIES [ :very_high ] )
end
2020-12-23 15:14:41 +08:00
fab! ( :very_low_priority_topic ) { Fabricate ( :topic , category : very_low_priority_category ) }
2020-04-27 22:35:27 +08:00
fab! ( :low_priority_topic ) { Fabricate ( :topic , category : low_priority_category ) }
fab! ( :high_priority_topic ) { Fabricate ( :topic , category : high_priority_category ) }
fab! ( :very_high_priority_topic ) { Fabricate ( :topic , category : very_high_priority_category ) }
2020-12-23 15:14:41 +08:00
fab! ( :very_low_priority_post ) do
2023-05-04 09:20:52 +08:00
with_search_indexer_enabled do
Fabricate ( :post , topic : very_low_priority_topic , raw : "This is a very Low Priority Post" )
end
2020-12-23 15:14:41 +08:00
end
2020-04-27 22:35:27 +08:00
fab! ( :low_priority_post ) do
2023-05-04 09:20:52 +08:00
with_search_indexer_enabled do
Fabricate (
:post ,
topic : low_priority_topic ,
raw : "This is a Low Priority Post" ,
created_at : 1 . day . ago ,
)
end
2020-04-27 22:35:27 +08:00
end
2020-12-23 15:14:41 +08:00
fab! ( :high_priority_post ) do
2023-05-04 09:20:52 +08:00
with_search_indexer_enabled do
Fabricate ( :post , topic : high_priority_topic , raw : "This is a High Priority Post" )
end
2020-04-27 22:35:27 +08:00
end
2020-12-23 15:14:41 +08:00
fab! ( :very_high_priority_post ) do
2023-05-04 09:20:52 +08:00
with_search_indexer_enabled do
Fabricate (
:post ,
topic : very_high_priority_topic ,
raw : "This is a Old but Very High Priority Post" ,
created_at : 2 . days . ago ,
)
end
2020-04-27 22:35:27 +08:00
end
it "sort posts with search priority when search term is empty" do
get "/search.json" , params : { q : "status:open" }
expect ( response . status ) . to eq ( 200 )
2020-05-07 17:04:12 +02:00
data = response . parsed_body
2020-12-23 15:14:41 +08:00
post1 = data [ "posts" ]. find { | e | e [ "id" ] == very_high_priority_post . id }
post2 = data [ "posts" ]. find { | e | e [ "id" ] == very_low_priority_post . id }
expect ( data [ "posts" ][ 0 ][ "id" ] ) . to eq ( very_high_priority_post . id )
2020-04-27 22:35:27 +08:00
expect ( post1 [ "id" ] ) . to be > post2 [ "id" ]
end
it "sort posts with search priority when no order query" do
2020-12-23 15:14:41 +08:00
SiteSetting . category_search_priority_high_weight = 999_999
SiteSetting . category_search_priority_low_weight = 0
2020-04-27 22:35:27 +08:00
get "/search.json" , params : { q : "status:open Priority Post" }
expect ( response . status ) . to eq ( 200 )
2020-05-07 17:04:12 +02:00
data = response . parsed_body
2020-12-23 15:14:41 +08:00
expect ( data [ "posts" ][ 0 ][ "id" ] ) . to eq ( very_high_priority_post . id )
expect ( data [ "posts" ][ 1 ][ "id" ] ) . to eq ( high_priority_post . id )
2020-04-27 22:35:27 +08:00
expect ( data [ "posts" ][ 2 ][ "id" ] ) . to eq ( low_priority_post . id )
2020-12-23 15:14:41 +08:00
expect ( data [ "posts" ][ 3 ][ "id" ] ) . to eq ( very_low_priority_post . id )
2020-04-27 22:35:27 +08:00
end
2021-05-20 21:43:47 -04:00
it "doesn't sort posts with search priority when query with order" do
2020-04-27 22:35:27 +08:00
get "/search.json" , params : { q : "status:open order:latest Priority Post" }
expect ( response . status ) . to eq ( 200 )
2020-05-07 17:04:12 +02:00
data = response . parsed_body
2020-12-23 15:14:41 +08:00
expect ( data [ "posts" ][ 0 ][ "id" ] ) . to eq ( high_priority_post . id )
expect ( data [ "posts" ][ 1 ][ "id" ] ) . to eq ( very_low_priority_post . id )
expect ( data [ "posts" ][ 2 ][ "id" ] ) . to eq ( low_priority_post . id )
expect ( data [ "posts" ][ 3 ][ "id" ] ) . to eq ( very_high_priority_post . id )
2020-04-27 22:35:27 +08:00
end
end
2022-07-27 18:14:14 +02:00
context "with search context" do
2013-05-24 14:03:45 -04:00
it "raises an error with an invalid context type" do
2018-06-04 06:12:38 +03:00
get "/search/query.json" ,
params : {
2018-01-12 14:15:10 +11:00
term : "test" ,
search_context : {
type : "security" ,
id : "hole" ,
},
2018-06-04 06:12:38 +03:00
}
2018-01-12 14:15:10 +11:00
expect ( response . status ) . to eq ( 400 )
2013-05-24 14:03:45 -04:00
end
it "raises an error with a missing id" do
2018-06-04 06:12:38 +03:00
get "/search/query.json" , params : { term : "test" , search_context : { type : "user" } }
2018-01-12 14:15:10 +11:00
expect ( response . status ) . to eq ( 400 )
2013-05-24 14:03:45 -04:00
end
context "with a user" do
it "raises an error if the user can't see the context" do
2018-06-04 06:12:38 +03:00
get "/search/query.json" ,
params : {
term : "test" ,
search_context : {
type : "private_messages" ,
id : user . username ,
},
}
expect ( response ) . to be_forbidden
2013-05-24 14:03:45 -04:00
end
it "performs the query with a search context" do
2018-06-04 06:12:38 +03:00
get "/search/query.json" ,
params : {
2017-08-31 12:06:56 +08:00
term : "test" ,
search_context : {
type : "user" ,
id : user . username ,
},
2018-06-04 06:12:38 +03:00
}
2017-08-31 12:06:56 +08:00
2018-06-07 16:11:09 +08:00
expect ( response . status ) . to eq ( 200 )
2013-05-24 14:03:45 -04:00
end
end
2019-11-14 10:40:26 +10:00
context "with a tag" do
it "raises an error if the tag does not exist" do
get "/search/query.json" ,
params : {
term : "test" ,
search_context : {
type : "tag" ,
id : "important-tag" ,
name : "important-tag" ,
},
}
expect ( response ) . to be_forbidden
end
it "performs the query with a search context" do
Fabricate ( :tag , name : "important-tag" )
get "/search/query.json" ,
params : {
term : "test" ,
search_context : {
type : "tag" ,
id : "important-tag" ,
name : "important-tag" ,
},
}
expect ( response . status ) . to eq ( 200 )
end
end
2017-07-14 13:56:58 -04:00
end
2013-05-24 14:03:45 -04:00
2022-07-27 12:21:10 +02:00
describe "#click" do
2018-01-15 15:29:54 +11:00
after { SearchLog . clear_debounce_cache! }
2021-05-20 21:43:47 -04:00
it "doesn't work without the necessary parameters" do
2018-06-04 06:12:38 +03:00
post "/search/click.json"
expect ( response . status ) . to eq ( 400 )
2017-07-17 15:42:32 -04:00
end
it "doesn't record the click for a different user" do
2019-07-02 11:21:52 +10:00
sign_in ( user )
2017-07-17 15:42:32 -04:00
_ , search_log_id =
SearchLog . log (
2018-06-14 18:31:07 +10:00
term : SecureRandom . hex ,
2017-07-17 15:42:32 -04:00
search_type : :header ,
user_id : - 10 ,
ip_address : "127.0.0.1" ,
)
2023-01-09 11:18:21 +00:00
2020-07-24 10:52:13 +08:00
post "/search/click.json" ,
params : {
2017-08-31 12:06:56 +08:00
search_log_id : search_log_id ,
search_result_id : 12_345 ,
search_result_type : "topic" ,
}
2017-07-17 15:42:32 -04:00
2018-06-07 16:11:09 +08:00
expect ( response . status ) . to eq ( 200 )
2020-07-24 10:52:13 +08:00
expect ( response . parsed_body [ "success" ] ) . to be_present
2017-11-28 23:24:27 +05:30
expect ( SearchLog . find ( search_log_id ) . search_result_id ) . to be_blank
2017-07-17 15:42:32 -04:00
end
it "records the click for a logged in user" do
2019-07-02 11:21:52 +10:00
sign_in ( user )
2017-07-17 15:42:32 -04:00
_ , search_log_id =
SearchLog . log (
2018-06-14 18:31:07 +10:00
term : SecureRandom . hex ,
2017-07-17 15:42:32 -04:00
search_type : :header ,
user_id : user . id ,
ip_address : "127.0.0.1" ,
)
2023-01-09 11:18:21 +00:00
2018-06-04 06:12:38 +03:00
post "/search/click.json" ,
params : {
2017-08-31 12:06:56 +08:00
search_log_id : search_log_id ,
search_result_id : 12_345 ,
2017-11-28 23:24:27 +05:30
search_result_type : "user" ,
2018-06-04 06:12:38 +03:00
}
2017-07-17 15:42:32 -04:00
2018-06-07 16:11:09 +08:00
expect ( response . status ) . to eq ( 200 )
2017-11-28 23:24:27 +05:30
expect ( SearchLog . find ( search_log_id ) . search_result_id ) . to eq ( 12_345 )
expect ( SearchLog . find ( search_log_id ) . search_result_type ) . to eq (
SearchLog . search_result_types [ :user ] ,
)
2017-07-17 15:42:32 -04:00
end
it "records the click for an anonymous user" do
2018-06-04 06:12:38 +03:00
get "/"
ip_address = request . remote_ip
2017-07-17 15:42:32 -04:00
_ , search_log_id =
2018-06-14 18:31:07 +10:00
SearchLog . log ( term : SecureRandom . hex , search_type : :header , ip_address : ip_address )
2017-07-17 15:42:32 -04:00
2018-06-04 06:12:38 +03:00
post "/search/click.json" ,
params : {
2017-08-31 12:06:56 +08:00
search_log_id : search_log_id ,
search_result_id : 22_222 ,
search_result_type : "topic" ,
2018-06-04 06:12:38 +03:00
}
2017-07-17 15:42:32 -04:00
2018-06-07 16:11:09 +08:00
expect ( response . status ) . to eq ( 200 )
2017-11-28 23:24:27 +05:30
expect ( SearchLog . find ( search_log_id ) . search_result_id ) . to eq ( 22_222 )
expect ( SearchLog . find ( search_log_id ) . search_result_type ) . to eq (
SearchLog . search_result_types [ :topic ] ,
)
2017-07-17 15:42:32 -04:00
end
it "doesn't record the click for a different IP" do
_ , search_log_id =
2018-06-04 06:12:38 +03:00
SearchLog . log ( term : SecureRandom . hex , search_type : :header , ip_address : "192.168.0.19" )
2017-07-17 15:42:32 -04:00
2020-07-24 10:52:13 +08:00
post "/search/click.json" ,
params : {
2017-08-31 12:06:56 +08:00
search_log_id : search_log_id ,
search_result_id : 22_222 ,
search_result_type : "topic" ,
}
2017-07-17 15:42:32 -04:00
2018-06-07 16:11:09 +08:00
expect ( response . status ) . to eq ( 200 )
2020-07-24 10:52:13 +08:00
expect ( response . parsed_body [ "success" ] ) . to be_present
2017-11-28 23:24:27 +05:30
expect ( SearchLog . find ( search_log_id ) . search_result_id ) . to be_blank
end
it "records the click for search result type category" do
2018-06-04 06:12:38 +03:00
get "/"
ip_address = request . remote_ip
2017-11-28 23:24:27 +05:30
_ , search_log_id =
2018-06-14 18:31:07 +10:00
SearchLog . log ( term : SecureRandom . hex , search_type : :header , ip_address : ip_address )
2017-11-28 23:24:27 +05:30
2018-06-04 06:12:38 +03:00
post "/search/click.json" ,
params : {
2017-11-28 23:24:27 +05:30
search_log_id : search_log_id ,
search_result_id : 23_456 ,
search_result_type : "category" ,
2018-06-04 06:12:38 +03:00
}
2017-11-28 23:24:27 +05:30
2018-06-07 16:11:09 +08:00
expect ( response . status ) . to eq ( 200 )
2017-11-28 23:24:27 +05:30
expect ( SearchLog . find ( search_log_id ) . search_result_id ) . to eq ( 23_456 )
expect ( SearchLog . find ( search_log_id ) . search_result_type ) . to eq (
SearchLog . search_result_types [ :category ] ,
)
end
it "records the click for search result type tag" do
2018-06-04 06:12:38 +03:00
get "/"
ip_address = request . remote_ip
tag = Fabricate ( :tag , name : "test" )
2017-11-28 23:24:27 +05:30
_ , search_log_id =
2018-06-14 18:31:07 +10:00
SearchLog . log ( term : SecureRandom . hex , search_type : :header , ip_address : ip_address )
2017-11-28 23:24:27 +05:30
2018-06-04 06:12:38 +03:00
post "/search/click.json" ,
params : {
2017-11-28 23:24:27 +05:30
search_log_id : search_log_id ,
search_result_id : tag . name ,
search_result_type : "tag" ,
2018-06-04 06:12:38 +03:00
}
2017-11-28 23:24:27 +05:30
2018-06-07 16:11:09 +08:00
expect ( response . status ) . to eq ( 200 )
2017-11-28 23:24:27 +05:30
expect ( SearchLog . find ( search_log_id ) . search_result_id ) . to eq ( tag . id )
expect ( SearchLog . find ( search_log_id ) . search_result_type ) . to eq (
SearchLog . search_result_types [ :tag ] ,
)
2017-07-17 15:42:32 -04:00
end
end
2013-02-05 14:16:51 -05:00
end