algolia 2.0.4 → 2.1.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.circleci/config.yml +9 -0
- data/CHANGELOG.md +14 -1
- data/lib/algolia.rb +1 -0
- data/lib/algolia/helpers.rb +49 -0
- data/lib/algolia/http/http_requester.rb +4 -4
- data/lib/algolia/responses/dictionary_response.rb +33 -0
- data/lib/algolia/search_client.rb +175 -2
- data/lib/algolia/search_index.rb +9 -50
- data/lib/algolia/version.rb +1 -1
- data/test/algolia/integration/analytics_client_test.rb +6 -2
- data/test/algolia/integration/search_client_test.rb +106 -12
- data/test/algolia/integration/search_index_test.rb +3 -0
- data/test/test_helper.rb +12 -0
- metadata +4 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: dc743bd03ca6ebc94d2ae61eec22670ccbaa3531d2a9b66c44858280c644a938
|
4
|
+
data.tar.gz: 9e5fb85f9d474d266de360c25b7ef3efafa0fe0b78765aa1cae32b402a0865ac
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: b343a5a32c22f73fd18b33235e9dfd4adcc4c6f3236bac881ad37160dce5af9a7b79e836643ba126e3c0f2943d0187ffb804fe1688fdd6f9599966d39950fa48
|
7
|
+
data.tar.gz: 98fea72cc28767839cead8d54d75f9d2ac262999bb92b5ba446d81abfb9d43ef7986c99bccc523c892916df6cf605b3e5fcf305935161bf9bdf371ab24e44196
|
data/.circleci/config.yml
CHANGED
@@ -23,6 +23,13 @@ aliases:
|
|
23
23
|
name: Run linting tool
|
24
24
|
command: bundle exec rake rubocop
|
25
25
|
|
26
|
+
- &credentials
|
27
|
+
name: Retrieve temporary Algolia credentials if needed
|
28
|
+
command: |
|
29
|
+
if [ "$CIRCLE_PR_REPONAME" ]; then
|
30
|
+
curl -s https://algoliasearch-client-keygen.herokuapp.com | sh >> $BASH_ENV
|
31
|
+
fi
|
32
|
+
|
26
33
|
- &run_tests
|
27
34
|
name: Run unit and integration tests
|
28
35
|
command: |
|
@@ -73,6 +80,7 @@ jobs:
|
|
73
80
|
- restore_cache: *restore_cache
|
74
81
|
- run: *install_bundler
|
75
82
|
- save_cache: *save_cache
|
83
|
+
- run: *credentials
|
76
84
|
- run: *run_tests
|
77
85
|
|
78
86
|
test_jruby:
|
@@ -88,6 +96,7 @@ jobs:
|
|
88
96
|
- restore_cache: *restore_cache
|
89
97
|
- run: *install_bundler
|
90
98
|
- save_cache: *save_cache
|
99
|
+
- run: *credentials
|
91
100
|
- run: *run_tests
|
92
101
|
|
93
102
|
release:
|
data/CHANGELOG.md
CHANGED
@@ -1,6 +1,19 @@
|
|
1
1
|
# ChangeLog
|
2
2
|
|
3
|
-
## [Unreleased](https://github.com/algolia/algoliasearch-client-ruby/compare/2.
|
3
|
+
## [Unreleased](https://github.com/algolia/algoliasearch-client-ruby/compare/2.1.1..master)
|
4
|
+
|
5
|
+
## [2.1.1](https://github.com/algolia/algoliasearch-client-ruby/compare/2.1.0...2.1.1) (2021-05-27)
|
6
|
+
|
7
|
+
### Fix
|
8
|
+
- Bug with read/write nodes caching ([`#455`](https://github.com/algolia/algoliasearch-client-ruby/pull/455))
|
9
|
+
|
10
|
+
## [2.1.0](https://github.com/algolia/algoliasearch-client-ruby/compare/2.0.4...2.1.0) (2021-03-30)
|
11
|
+
|
12
|
+
### Feat
|
13
|
+
- Custom dictionaries methods
|
14
|
+
|
15
|
+
### Fix
|
16
|
+
- The parameter `forwardToReplicas` should be handled independently in the `set_settings` method
|
4
17
|
|
5
18
|
## [2.0.4](https://github.com/algolia/algoliasearch-client-ruby/compare/2.0.3...2.0.4) (2021-01-05)
|
6
19
|
|
data/lib/algolia.rb
CHANGED
@@ -20,6 +20,7 @@ require 'algolia/responses/indexing_response'
|
|
20
20
|
require 'algolia/responses/add_api_key_response'
|
21
21
|
require 'algolia/responses/update_api_key_response'
|
22
22
|
require 'algolia/responses/delete_api_key_response'
|
23
|
+
require 'algolia/responses/dictionary_response'
|
23
24
|
require 'algolia/responses/restore_api_key_response'
|
24
25
|
require 'algolia/responses/multiple_batch_indexing_response'
|
25
26
|
require 'algolia/responses/multiple_response'
|
data/lib/algolia/helpers.rb
CHANGED
@@ -82,4 +82,53 @@ module Helpers
|
|
82
82
|
end
|
83
83
|
res
|
84
84
|
end
|
85
|
+
|
86
|
+
# Check the passed object to determine if it's an array
|
87
|
+
#
|
88
|
+
# @param object [Object]
|
89
|
+
#
|
90
|
+
def check_array(object)
|
91
|
+
raise Algolia::AlgoliaError, 'argument must be an array of objects' unless object.is_a?(Array)
|
92
|
+
end
|
93
|
+
|
94
|
+
# Check the passed object
|
95
|
+
#
|
96
|
+
# @param object [Object]
|
97
|
+
# @param in_array [Boolean] whether the object is an array or not
|
98
|
+
#
|
99
|
+
def check_object(object, in_array = false)
|
100
|
+
case object
|
101
|
+
when Array
|
102
|
+
raise Algolia::AlgoliaError, in_array ? 'argument must be an array of objects' : 'argument must not be an array'
|
103
|
+
when String, Integer, Float, TrueClass, FalseClass, NilClass
|
104
|
+
raise Algolia::AlgoliaError, "argument must be an #{'array of' if in_array} object, got: #{object.inspect}"
|
105
|
+
end
|
106
|
+
end
|
107
|
+
|
108
|
+
# Check if passed object has a objectID
|
109
|
+
#
|
110
|
+
# @param object [Object]
|
111
|
+
# @param object_id [String]
|
112
|
+
#
|
113
|
+
def get_object_id(object, object_id = nil)
|
114
|
+
check_object(object)
|
115
|
+
object_id ||= object[:objectID] || object['objectID']
|
116
|
+
raise Algolia::AlgoliaError, "Missing 'objectID'" if object_id.nil?
|
117
|
+
object_id
|
118
|
+
end
|
119
|
+
|
120
|
+
# Build a batch request
|
121
|
+
#
|
122
|
+
# @param action [String] action to perform on the engine
|
123
|
+
# @param objects [Array] objects on which build the action
|
124
|
+
# @param with_object_id [Boolean] if set to true, check if each object has an objectID set
|
125
|
+
#
|
126
|
+
def chunk(action, objects, with_object_id = false)
|
127
|
+
objects.map do |object|
|
128
|
+
check_object(object, true)
|
129
|
+
request = { action: action, body: object }
|
130
|
+
request[:objectID] = get_object_id(object).to_s if with_object_id
|
131
|
+
request
|
132
|
+
end
|
133
|
+
end
|
85
134
|
end
|
@@ -9,9 +9,9 @@ module Algolia
|
|
9
9
|
# @param logger [Object] logger used to log requests. Defaults to Algolia::LoggerHelper
|
10
10
|
#
|
11
11
|
def initialize(adapter, logger)
|
12
|
-
@adapter
|
13
|
-
@logger
|
14
|
-
@
|
12
|
+
@adapter = adapter
|
13
|
+
@logger = logger
|
14
|
+
@connections = {}
|
15
15
|
end
|
16
16
|
|
17
17
|
# Sends request to the engine
|
@@ -65,7 +65,7 @@ module Algolia
|
|
65
65
|
# @return [Faraday::Connection]
|
66
66
|
#
|
67
67
|
def connection(host)
|
68
|
-
@
|
68
|
+
@connections[host.accept] ||= Faraday.new(build_url(host)) do |f|
|
69
69
|
f.adapter @adapter.to_sym
|
70
70
|
end
|
71
71
|
end
|
@@ -0,0 +1,33 @@
|
|
1
|
+
module Algolia
|
2
|
+
class DictionaryResponse < BaseResponse
|
3
|
+
include CallType
|
4
|
+
|
5
|
+
attr_reader :raw_response
|
6
|
+
|
7
|
+
# @param client [Search::Client] Algolia Search Client used for verification
|
8
|
+
# @param response [Hash] Raw response from the client
|
9
|
+
#
|
10
|
+
def initialize(client, response)
|
11
|
+
@client = client
|
12
|
+
@raw_response = response
|
13
|
+
@done = false
|
14
|
+
end
|
15
|
+
|
16
|
+
# Wait for the task to complete
|
17
|
+
#
|
18
|
+
# @param opts [Hash] contains extra parameters to send with your query
|
19
|
+
#
|
20
|
+
def wait(_opts = {})
|
21
|
+
until @done
|
22
|
+
res = @client.custom_request({}, path_encode('/1/task/%s', @raw_response[:taskID]), :GET, READ)
|
23
|
+
status = get_option(res, 'status')
|
24
|
+
if status == 'published'
|
25
|
+
@done = true
|
26
|
+
end
|
27
|
+
sleep(Defaults::WAIT_TASK_DEFAULT_TIME_BEFORE_RETRY / 1000)
|
28
|
+
end
|
29
|
+
|
30
|
+
self
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
@@ -80,7 +80,7 @@ module Algolia
|
|
80
80
|
end
|
81
81
|
|
82
82
|
# # # # # # # # # # # # # # # # # # # # #
|
83
|
-
#
|
83
|
+
# INDEX METHODS
|
84
84
|
# # # # # # # # # # # # # # # # # # # # #
|
85
85
|
|
86
86
|
# Initialize an index with a given name
|
@@ -594,12 +594,185 @@ module Algolia
|
|
594
594
|
@transporter.read(:GET, '/1/clusters/mapping/pending' + handle_params({ getClusters: retrieve_mappings }), {}, request_options)
|
595
595
|
end
|
596
596
|
|
597
|
-
#
|
598
597
|
# Aliases the pending_mappings? method
|
599
598
|
#
|
600
599
|
alias_method :has_pending_mappings, :pending_mappings?
|
601
600
|
|
601
|
+
# # # # # # # # # # # # # # # # # # # # #
|
602
|
+
# CUSTOM DICTIONARIES METHODS
|
603
|
+
# # # # # # # # # # # # # # # # # # # # #
|
604
|
+
|
605
|
+
# Save entries for a given dictionary
|
606
|
+
#
|
607
|
+
# @param dictionary [String] dictionary name. Can be either 'stopwords', 'plurals' or 'compounds'
|
608
|
+
# @param dictionary_entries [Array<Hash>] array of dictionary entries
|
609
|
+
# @param opts [Hash] contains extra parameters to send with your query
|
610
|
+
#
|
611
|
+
# @return DictionaryResponse
|
612
|
+
#
|
613
|
+
def save_dictionary_entries(dictionary, dictionary_entries, opts = {})
|
614
|
+
response = @transporter.write(
|
615
|
+
:POST,
|
616
|
+
path_encode('/1/dictionaries/%s/batch', dictionary),
|
617
|
+
{ clearExistingDictionaryEntries: false, requests: chunk('addEntry', dictionary_entries) },
|
618
|
+
opts
|
619
|
+
)
|
620
|
+
|
621
|
+
DictionaryResponse.new(self, response)
|
622
|
+
end
|
623
|
+
|
624
|
+
# Save entries for a given dictionary and wait for the task to finish
|
625
|
+
#
|
626
|
+
# @param dictionary [String] dictionary name. Can be either 'stopwords', 'plurals' or 'compounds'
|
627
|
+
# @param dictionary_entries [Array<Hash>] array of dictionary entries
|
628
|
+
# @param opts [Hash] contains extra parameters to send with your query
|
629
|
+
#
|
630
|
+
def save_dictionary_entries!(dictionary, dictionary_entries, opts = {})
|
631
|
+
response = save_dictionary_entries(dictionary, dictionary_entries, opts)
|
632
|
+
|
633
|
+
response.wait(opts)
|
634
|
+
end
|
635
|
+
|
636
|
+
# Replace entries for a given dictionary
|
637
|
+
#
|
638
|
+
# @param dictionary [String] dictionary name. Can be either 'stopwords', 'plurals' or 'compounds'
|
639
|
+
# @param dictionary_entries [Array<Hash>] array of dictionary entries
|
640
|
+
# @param opts [Hash] contains extra parameters to send with your query
|
641
|
+
#
|
642
|
+
# @return DictionaryResponse
|
643
|
+
#
|
644
|
+
def replace_dictionary_entries(dictionary, dictionary_entries, opts = {})
|
645
|
+
response = @transporter.write(
|
646
|
+
:POST,
|
647
|
+
path_encode('/1/dictionaries/%s/batch', dictionary),
|
648
|
+
{ clearExistingDictionaryEntries: true, requests: chunk('addEntry', dictionary_entries) },
|
649
|
+
opts
|
650
|
+
)
|
651
|
+
|
652
|
+
DictionaryResponse.new(self, response)
|
653
|
+
end
|
654
|
+
|
655
|
+
# Replace entries for a given dictionary and wait for the task to finish
|
656
|
+
#
|
657
|
+
# @param dictionary [String] dictionary name. Can be either 'stopwords', 'plurals' or 'compounds'
|
658
|
+
# @param dictionary_entries [Array<Hash>] array of dictionary entries
|
659
|
+
# @param opts [Hash] contains extra parameters to send with your query
|
660
|
+
#
|
661
|
+
def replace_dictionary_entries!(dictionary, dictionary_entries, opts = {})
|
662
|
+
response = replace_dictionary_entries(dictionary, dictionary_entries, opts)
|
663
|
+
|
664
|
+
response.wait(opts)
|
665
|
+
end
|
666
|
+
|
667
|
+
# Delete entries for a given dictionary
|
668
|
+
#
|
669
|
+
# @param dictionary [String] dictionary name. Can be either 'stopwords', 'plurals' or 'compounds'
|
670
|
+
# @param object_ids [Array<Hash>] array of object ids
|
671
|
+
# @param opts [Hash] contains extra parameters to send with your query
|
672
|
+
#
|
673
|
+
# @return DictionaryResponse
|
674
|
+
#
|
675
|
+
def delete_dictionary_entries(dictionary, object_ids, opts = {})
|
676
|
+
request = object_ids.map do |object_id|
|
677
|
+
{ objectID: object_id }
|
678
|
+
end
|
679
|
+
response = @transporter.write(
|
680
|
+
:POST,
|
681
|
+
path_encode('/1/dictionaries/%s/batch', dictionary),
|
682
|
+
{ clearExistingDictionaryEntries: false, requests: chunk('deleteEntry', request) },
|
683
|
+
opts
|
684
|
+
)
|
685
|
+
|
686
|
+
DictionaryResponse.new(self, response)
|
687
|
+
end
|
688
|
+
|
689
|
+
# Delete entries for a given dictionary and wait for the task to finish
|
690
|
+
#
|
691
|
+
# @param dictionary [String] dictionary name. Can be either 'stopwords', 'plurals' or 'compounds'
|
692
|
+
# @param object_ids [Array<Hash>] array of object ids
|
693
|
+
# @param opts [Hash] contains extra parameters to send with your query
|
602
694
|
#
|
695
|
+
def delete_dictionary_entries!(dictionary, object_ids, opts = {})
|
696
|
+
response = delete_dictionary_entries(dictionary, object_ids, opts)
|
697
|
+
|
698
|
+
response.wait(opts)
|
699
|
+
end
|
700
|
+
|
701
|
+
# Clear all entries for a given dictionary
|
702
|
+
#
|
703
|
+
# @param dictionary [String] dictionary name. Can be either 'stopwords', 'plurals' or 'compounds'
|
704
|
+
# @param opts [Hash] contains extra parameters to send with your query
|
705
|
+
#
|
706
|
+
# @return DictionaryResponse
|
707
|
+
#
|
708
|
+
def clear_dictionary_entries(dictionary, opts = {})
|
709
|
+
replace_dictionary_entries(dictionary, [], opts)
|
710
|
+
end
|
711
|
+
|
712
|
+
# Clear all entries for a given dictionary and wait for the task to finish
|
713
|
+
#
|
714
|
+
# @param dictionary [String] dictionary name. Can be either 'stopwords', 'plurals' or 'compounds'
|
715
|
+
# @param opts [Hash] contains extra parameters to send with your query
|
716
|
+
#
|
717
|
+
def clear_dictionary_entries!(dictionary, opts = {})
|
718
|
+
response = replace_dictionary_entries(dictionary, [], opts)
|
719
|
+
|
720
|
+
response.wait(opts)
|
721
|
+
end
|
722
|
+
|
723
|
+
# Search entries for a given dictionary
|
724
|
+
#
|
725
|
+
# @param dictionary [String] dictionary name. Can be either 'stopwords', 'plurals' or 'compounds'
|
726
|
+
# @param query [String] query to send
|
727
|
+
# @param opts [Hash] contains extra parameters to send with your query
|
728
|
+
#
|
729
|
+
def search_dictionary_entries(dictionary, query, opts = {})
|
730
|
+
@transporter.read(
|
731
|
+
:POST,
|
732
|
+
path_encode('/1/dictionaries/%s/search', dictionary),
|
733
|
+
{ query: query },
|
734
|
+
opts
|
735
|
+
)
|
736
|
+
end
|
737
|
+
|
738
|
+
# Set settings for all the dictionaries
|
739
|
+
#
|
740
|
+
# @param dictionary_settings [Hash]
|
741
|
+
# @param opts [Hash] contains extra parameters to send with your query
|
742
|
+
#
|
743
|
+
# @return DictionaryResponse
|
744
|
+
#
|
745
|
+
def set_dictionary_settings(dictionary_settings, opts = {})
|
746
|
+
response = @transporter.write(:PUT, '/1/dictionaries/*/settings', dictionary_settings, opts)
|
747
|
+
|
748
|
+
DictionaryResponse.new(self, response)
|
749
|
+
end
|
750
|
+
|
751
|
+
# Set settings for all the dictionaries and wait for the task to finish
|
752
|
+
#
|
753
|
+
# @param dictionary_settings [Hash]
|
754
|
+
# @param opts [Hash] contains extra parameters to send with your query
|
755
|
+
#
|
756
|
+
# @return DictionaryResponse
|
757
|
+
#
|
758
|
+
def set_dictionary_settings!(dictionary_settings, opts = {})
|
759
|
+
response = set_dictionary_settings(dictionary_settings, opts)
|
760
|
+
|
761
|
+
response.wait(opts)
|
762
|
+
end
|
763
|
+
|
764
|
+
# Retrieve settings for all the dictionaries
|
765
|
+
#
|
766
|
+
# @param opts [Hash] contains extra parameters to send with your query
|
767
|
+
#
|
768
|
+
def get_dictionary_settings(opts = {})
|
769
|
+
@transporter.read(:GET, '/1/dictionaries/*/settings', {}, opts)
|
770
|
+
end
|
771
|
+
|
772
|
+
# # # # # # # # # # # # # # # # # # # # #
|
773
|
+
# MISC METHODS
|
774
|
+
# # # # # # # # # # # # # # # # # # # # #
|
775
|
+
|
603
776
|
# Method available to make custom requests to the API
|
604
777
|
#
|
605
778
|
def custom_request(data, uri, method, call_type, opts = {})
|
data/lib/algolia/search_index.rb
CHANGED
@@ -987,7 +987,15 @@ module Algolia
|
|
987
987
|
# @return [IndexingResponse]
|
988
988
|
#
|
989
989
|
def set_settings(settings, opts = {})
|
990
|
-
|
990
|
+
request_options = symbolize_hash(opts)
|
991
|
+
forward_to_replicas = request_options.delete(:forwardToReplicas) || false
|
992
|
+
|
993
|
+
response = @transporter.write(
|
994
|
+
:PUT,
|
995
|
+
path_encode('/1/indexes/%s/settings', @name) + handle_params({ forwardToReplicas: forward_to_replicas }),
|
996
|
+
settings,
|
997
|
+
request_options
|
998
|
+
)
|
991
999
|
|
992
1000
|
IndexingResponse.new(self, response)
|
993
1001
|
end
|
@@ -1037,55 +1045,6 @@ module Algolia
|
|
1037
1045
|
|
1038
1046
|
private
|
1039
1047
|
|
1040
|
-
# Check the passed object to determine if it's an array
|
1041
|
-
#
|
1042
|
-
# @param object [Object]
|
1043
|
-
#
|
1044
|
-
def check_array(object)
|
1045
|
-
raise AlgoliaError, 'argument must be an array of objects' unless object.is_a?(Array)
|
1046
|
-
end
|
1047
|
-
|
1048
|
-
# Check the passed object
|
1049
|
-
#
|
1050
|
-
# @param object [Object]
|
1051
|
-
# @param in_array [Boolean] whether the object is an array or not
|
1052
|
-
#
|
1053
|
-
def check_object(object, in_array = false)
|
1054
|
-
case object
|
1055
|
-
when Array
|
1056
|
-
raise AlgoliaError, in_array ? 'argument must be an array of objects' : 'argument must not be an array'
|
1057
|
-
when String, Integer, Float, TrueClass, FalseClass, NilClass
|
1058
|
-
raise AlgoliaError, "argument must be an #{'array of' if in_array} object, got: #{object.inspect}"
|
1059
|
-
end
|
1060
|
-
end
|
1061
|
-
|
1062
|
-
# Check if passed object has a objectID
|
1063
|
-
#
|
1064
|
-
# @param object [Object]
|
1065
|
-
# @param object_id [String]
|
1066
|
-
#
|
1067
|
-
def get_object_id(object, object_id = nil)
|
1068
|
-
check_object(object)
|
1069
|
-
object_id ||= object[:objectID] || object['objectID']
|
1070
|
-
raise AlgoliaError, "Missing 'objectID'" if object_id.nil?
|
1071
|
-
object_id
|
1072
|
-
end
|
1073
|
-
|
1074
|
-
# Build a batch request
|
1075
|
-
#
|
1076
|
-
# @param action [String] action to perform on the engine
|
1077
|
-
# @param objects [Array] objects on which build the action
|
1078
|
-
# @param with_object_id [Boolean] if set to true, check if each object has an objectID set
|
1079
|
-
#
|
1080
|
-
def chunk(action, objects, with_object_id = false)
|
1081
|
-
objects.map do |object|
|
1082
|
-
check_object(object, true)
|
1083
|
-
request = { action: action, body: object }
|
1084
|
-
request[:objectID] = get_object_id(object).to_s if with_object_id
|
1085
|
-
request
|
1086
|
-
end
|
1087
|
-
end
|
1088
|
-
|
1089
1048
|
def raw_batch(requests, opts)
|
1090
1049
|
@transporter.write(:POST, path_encode('/1/indexes/%s/batch', @name), { requests: requests }, opts)
|
1091
1050
|
end
|
data/lib/algolia/version.rb
CHANGED
@@ -23,7 +23,9 @@ class AnalyticsClientTest < BaseTest
|
|
23
23
|
endAt: tomorrow.strftime('%Y-%m-%dT%H:%M:%SZ')
|
24
24
|
}
|
25
25
|
|
26
|
-
response =
|
26
|
+
response = retry_test do
|
27
|
+
client.add_ab_test(ab_test)
|
28
|
+
end
|
27
29
|
ab_test_id = response[:abTestID]
|
28
30
|
|
29
31
|
index1.wait_task(response[:taskID])
|
@@ -86,7 +88,9 @@ class AnalyticsClientTest < BaseTest
|
|
86
88
|
endAt: tomorrow.strftime('%Y-%m-%dT%H:%M:%SZ')
|
87
89
|
}
|
88
90
|
|
89
|
-
response =
|
91
|
+
response = retry_test do
|
92
|
+
client.add_ab_test(ab_test)
|
93
|
+
end
|
90
94
|
ab_test_id = response[:abTestID]
|
91
95
|
|
92
96
|
index.wait_task(response[:taskID])
|
@@ -1,3 +1,4 @@
|
|
1
|
+
require 'securerandom'
|
1
2
|
require_relative 'base_test'
|
2
3
|
|
3
4
|
class SearchClientTest < BaseTest
|
@@ -223,7 +224,9 @@ class SearchClientTest < BaseTest
|
|
223
224
|
assert_includes api_keys, @api_key[:value]
|
224
225
|
|
225
226
|
@@search_client.update_api_key!(@api_key[:value], { maxHitsPerQuery: 42 })
|
226
|
-
updated_api_key =
|
227
|
+
updated_api_key = retry_test do
|
228
|
+
@@search_client.get_api_key(@api_key[:value], test: 'test')
|
229
|
+
end
|
227
230
|
assert_equal 42, updated_api_key[:maxHitsPerQuery]
|
228
231
|
|
229
232
|
@@search_client.delete_api_key!(@api_key[:value])
|
@@ -234,18 +237,13 @@ class SearchClientTest < BaseTest
|
|
234
237
|
|
235
238
|
assert_equal 'Key does not exist', exception.message
|
236
239
|
|
237
|
-
|
238
|
-
|
239
|
-
@@search_client.restore_api_key!(@api_key[:value])
|
240
|
-
break
|
241
|
-
rescue Algolia::AlgoliaHttpError => e
|
242
|
-
if e.code != 404
|
243
|
-
raise StandardError
|
244
|
-
end
|
245
|
-
end
|
240
|
+
retry_test do
|
241
|
+
@@search_client.restore_api_key!(@api_key[:value])
|
246
242
|
end
|
247
243
|
|
248
|
-
restored_key =
|
244
|
+
restored_key = retry_test do
|
245
|
+
@@search_client.get_api_key(@api_key[:value])
|
246
|
+
end
|
249
247
|
|
250
248
|
refute_nil restored_key
|
251
249
|
end
|
@@ -334,7 +332,12 @@ class SearchClientTest < BaseTest
|
|
334
332
|
secured_index1 = secured_client.init_index(@index1.name)
|
335
333
|
secured_index2 = secured_client.init_index(@index2.name)
|
336
334
|
|
337
|
-
|
335
|
+
res = retry_test do
|
336
|
+
secured_index1.search('')
|
337
|
+
end
|
338
|
+
|
339
|
+
assert_equal 1, res[:hits].length
|
340
|
+
|
338
341
|
exception = assert_raises Algolia::AlgoliaHttpError do
|
339
342
|
secured_index2.search('')
|
340
343
|
end
|
@@ -367,5 +370,96 @@ class SearchClientTest < BaseTest
|
|
367
370
|
assert_equal 'The SecuredAPIKey doesn\'t have a validUntil parameter.', exception.message
|
368
371
|
end
|
369
372
|
end
|
373
|
+
|
374
|
+
describe 'Custom Dictionaries' do
|
375
|
+
def before_all
|
376
|
+
@client = Algolia::Search::Client.create(APPLICATION_ID_2, ADMIN_KEY_2)
|
377
|
+
end
|
378
|
+
|
379
|
+
def test_stopwords_dictionaries
|
380
|
+
entry_id = SecureRandom.hex
|
381
|
+
assert_equal 0, @client.search_dictionary_entries('stopwords', entry_id)[:nbHits]
|
382
|
+
|
383
|
+
entry = {
|
384
|
+
objectID: entry_id,
|
385
|
+
language: 'en',
|
386
|
+
word: 'down'
|
387
|
+
}
|
388
|
+
@client.save_dictionary_entries!('stopwords', [entry])
|
389
|
+
|
390
|
+
stopwords = @client.search_dictionary_entries('stopwords', entry_id)
|
391
|
+
assert_equal 1, stopwords[:nbHits]
|
392
|
+
assert_equal stopwords[:hits][0][:objectID], entry[:objectID]
|
393
|
+
assert_equal stopwords[:hits][0][:word], entry[:word]
|
394
|
+
|
395
|
+
@client.delete_dictionary_entries!('stopwords', [entry_id])
|
396
|
+
assert_equal 0, @client.search_dictionary_entries('stopwords', entry_id)[:nbHits]
|
397
|
+
|
398
|
+
old_dictionary_state = @client.search_dictionary_entries('stopwords', '')
|
399
|
+
old_dictionary_entries = old_dictionary_state[:hits].map do |hit|
|
400
|
+
hit.reject { |key| key == :type }
|
401
|
+
end
|
402
|
+
|
403
|
+
@client.save_dictionary_entries!('stopwords', [entry])
|
404
|
+
assert_equal 1, @client.search_dictionary_entries('stopwords', entry_id)[:nbHits]
|
405
|
+
|
406
|
+
@client.replace_dictionary_entries!('stopwords', old_dictionary_entries)
|
407
|
+
assert_equal 0, @client.search_dictionary_entries('stopwords', entry_id)[:nbHits]
|
408
|
+
|
409
|
+
stopwords_settings = {
|
410
|
+
disableStandardEntries: {
|
411
|
+
stopwords: {
|
412
|
+
en: true
|
413
|
+
}
|
414
|
+
}
|
415
|
+
}
|
416
|
+
|
417
|
+
@client.set_dictionary_settings!(stopwords_settings)
|
418
|
+
|
419
|
+
assert_equal @client.get_dictionary_settings, stopwords_settings
|
420
|
+
end
|
421
|
+
|
422
|
+
def test_plurals_dictionaries
|
423
|
+
entry_id = SecureRandom.hex
|
424
|
+
assert_equal 0, @client.search_dictionary_entries('plurals', entry_id)[:nbHits]
|
425
|
+
|
426
|
+
entry = {
|
427
|
+
objectID: entry_id,
|
428
|
+
language: 'fr',
|
429
|
+
words: %w(cheval chevaux)
|
430
|
+
}
|
431
|
+
@client.save_dictionary_entries!('plurals', [entry])
|
432
|
+
|
433
|
+
plurals = @client.search_dictionary_entries('plurals', entry_id)
|
434
|
+
assert_equal 1, plurals[:nbHits]
|
435
|
+
assert_equal plurals[:hits][0][:objectID], entry[:objectID]
|
436
|
+
assert_equal plurals[:hits][0][:words], entry[:words]
|
437
|
+
|
438
|
+
@client.delete_dictionary_entries!('plurals', [entry_id])
|
439
|
+
assert_equal 0, @client.search_dictionary_entries('plurals', entry_id)[:nbHits]
|
440
|
+
end
|
441
|
+
|
442
|
+
def test_compounds_dictionaries
|
443
|
+
entry_id = SecureRandom.hex
|
444
|
+
assert_equal 0, @client.search_dictionary_entries('compounds', entry_id)[:nbHits]
|
445
|
+
|
446
|
+
entry = {
|
447
|
+
objectID: entry_id,
|
448
|
+
language: 'de',
|
449
|
+
word: 'kopfschmerztablette',
|
450
|
+
decomposition: %w(kopf schmerz tablette)
|
451
|
+
}
|
452
|
+
@client.save_dictionary_entries!('compounds', [entry])
|
453
|
+
|
454
|
+
compounds = @client.search_dictionary_entries('compounds', entry_id)
|
455
|
+
assert_equal 1, compounds[:nbHits]
|
456
|
+
assert_equal compounds[:hits][0][:objectID], entry[:objectID]
|
457
|
+
assert_equal compounds[:hits][0][:word], entry[:word]
|
458
|
+
assert_equal compounds[:hits][0][:decomposition], entry[:decomposition]
|
459
|
+
|
460
|
+
@client.delete_dictionary_entries!('compounds', [entry_id])
|
461
|
+
assert_equal 0, @client.search_dictionary_entries('compounds', entry_id)[:nbHits]
|
462
|
+
end
|
463
|
+
end
|
370
464
|
end
|
371
465
|
end
|
@@ -274,6 +274,9 @@ class SearchIndexTest < BaseTest
|
|
274
274
|
@index.set_settings!(settings)
|
275
275
|
|
276
276
|
assert_equal @index.get_settings, settings
|
277
|
+
|
278
|
+
# check that the forwardToReplicas parameter is passed correctly
|
279
|
+
assert @index.set_settings!(settings, { forwardToReplicas: true })
|
277
280
|
end
|
278
281
|
end
|
279
282
|
|
data/test/test_helper.rb
CHANGED
@@ -87,3 +87,15 @@ def rule_without_metadata(rule)
|
|
87
87
|
rule.delete(:_metadata)
|
88
88
|
rule
|
89
89
|
end
|
90
|
+
|
91
|
+
def retry_test(delay = 0.1, max_retries = 30)
|
92
|
+
(1...max_retries).each do |i|
|
93
|
+
begin
|
94
|
+
return yield
|
95
|
+
rescue Algolia::AlgoliaHttpError
|
96
|
+
sleep delay * i
|
97
|
+
end
|
98
|
+
end
|
99
|
+
|
100
|
+
raise StandardError, 'reached the maximum number of retries'
|
101
|
+
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: algolia
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 2.
|
4
|
+
version: 2.1.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Algolia
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2021-
|
11
|
+
date: 2021-05-27 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|
@@ -238,6 +238,7 @@ files:
|
|
238
238
|
- lib/algolia/responses/add_api_key_response.rb
|
239
239
|
- lib/algolia/responses/base_response.rb
|
240
240
|
- lib/algolia/responses/delete_api_key_response.rb
|
241
|
+
- lib/algolia/responses/dictionary_response.rb
|
241
242
|
- lib/algolia/responses/indexing_response.rb
|
242
243
|
- lib/algolia/responses/multiple_batch_indexing_response.rb
|
243
244
|
- lib/algolia/responses/multiple_response.rb
|
@@ -304,7 +305,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
304
305
|
- !ruby/object:Gem::Version
|
305
306
|
version: '0'
|
306
307
|
requirements: []
|
307
|
-
rubygems_version: 3.
|
308
|
+
rubygems_version: 3.0.6
|
308
309
|
signing_key:
|
309
310
|
specification_version: 4
|
310
311
|
summary: A simple Ruby client for the algolia.com REST API
|