search_flip 3.7.2 → 4.0.0.beta
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.github/workflows/test.yml +3 -5
- data/.rubocop.yml +3 -7
- data/CHANGELOG.md +6 -39
- data/README.md +36 -50
- data/UPDATING.md +40 -0
- data/docker-compose.yml +0 -1
- data/lib/search_flip/aws_sigv4_plugin.rb +1 -0
- data/lib/search_flip/bulk.rb +1 -1
- data/lib/search_flip/config.rb +1 -7
- data/lib/search_flip/connection.rb +19 -77
- data/lib/search_flip/criteria.rb +9 -36
- data/lib/search_flip/filterable.rb +0 -16
- data/lib/search_flip/http_client.rb +7 -46
- data/lib/search_flip/index.rb +9 -15
- data/lib/search_flip/json.rb +3 -3
- data/lib/search_flip/response.rb +6 -7
- data/lib/search_flip/result.rb +45 -19
- data/lib/search_flip/to_json.rb +29 -1
- data/lib/search_flip/version.rb +1 -1
- data/lib/search_flip.rb +3 -10
- data/search_flip.gemspec +1 -2
- data/spec/search_flip/aggregation_spec.rb +17 -17
- data/spec/search_flip/aws_sigv4_plugin_spec.rb +6 -10
- data/spec/search_flip/bulk_spec.rb +8 -5
- data/spec/search_flip/connection_spec.rb +5 -102
- data/spec/search_flip/criteria_spec.rb +10 -57
- data/spec/search_flip/http_client_spec.rb +3 -13
- data/spec/search_flip/index_spec.rb +8 -29
- data/spec/search_flip/json_spec.rb +4 -18
- data/spec/search_flip/null_instrumenter_spec.rb +2 -2
- data/spec/search_flip/result_spec.rb +23 -6
- data/spec/search_flip/to_json_spec.rb +28 -0
- data/spec/spec_helper.rb +3 -5
- metadata +24 -36
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: b023bc6411647eaecfcb8f5b0fe535379974a0824d49699dd74ef867a67c69eb
|
|
4
|
+
data.tar.gz: 5dc4a0439f9442811f3966e86b0c6b09d09c54450a04234c3738ae0ab7935900
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: a5fc637e8c016531df22af678adcae60a4f4169e5f1d2215d52be0a0dff1111b849cb4d79ca36d6cbf315c8516bc51d543852ab5026339d59cb1f5d08ba356f7
|
|
7
|
+
data.tar.gz: 7cf9d55a9aca5d6d63401750d40bc656fcc345101d8ce92a300c24649e38810d399d43ff225611bbdd91a257d6cb15eee26a6c811974b987e92e72e67eded704
|
data/.github/workflows/test.yml
CHANGED
|
@@ -11,18 +11,16 @@ jobs:
|
|
|
11
11
|
- elasticsearch:5.4
|
|
12
12
|
- docker.elastic.co/elasticsearch/elasticsearch:6.7.0
|
|
13
13
|
- docker.elastic.co/elasticsearch/elasticsearch:7.0.0
|
|
14
|
-
- docker.elastic.co/elasticsearch/elasticsearch:7.
|
|
15
|
-
- docker.elastic.co/elasticsearch/elasticsearch:8.1.1
|
|
14
|
+
- docker.elastic.co/elasticsearch/elasticsearch:7.9.0
|
|
16
15
|
ruby:
|
|
16
|
+
- 2.5
|
|
17
17
|
- 2.6
|
|
18
18
|
- 2.7
|
|
19
|
-
- 3.0
|
|
20
19
|
services:
|
|
21
20
|
elasticsearch:
|
|
22
21
|
image: ${{ matrix.elasticsearch }}
|
|
23
22
|
env:
|
|
24
23
|
discovery.type: single-node
|
|
25
|
-
xpack.security.enabled: false
|
|
26
24
|
ports:
|
|
27
25
|
- 9200:9200
|
|
28
26
|
steps:
|
|
@@ -30,7 +28,7 @@ jobs:
|
|
|
30
28
|
- uses: actions/setup-ruby@v1
|
|
31
29
|
with:
|
|
32
30
|
ruby-version: ${{ matrix.ruby }}
|
|
33
|
-
- run: gem install bundler
|
|
34
31
|
- run: bundle
|
|
32
|
+
- run: sleep 10
|
|
35
33
|
- run: bundle exec rspec
|
|
36
34
|
- run: bundle exec rubocop
|
data/.rubocop.yml
CHANGED
|
@@ -1,15 +1,11 @@
|
|
|
1
1
|
AllCops:
|
|
2
2
|
NewCops: enable
|
|
3
|
-
TargetRubyVersion: 2.
|
|
4
|
-
SuggestExtensions: false
|
|
3
|
+
TargetRubyVersion: 2.4
|
|
5
4
|
|
|
6
|
-
Gemspec/
|
|
5
|
+
Gemspec/RequiredRubyVersion:
|
|
7
6
|
Enabled: false
|
|
8
7
|
|
|
9
|
-
|
|
10
|
-
EmptyLineBetweenClassDefs: false
|
|
11
|
-
|
|
12
|
-
Gemspec/RequiredRubyVersion:
|
|
8
|
+
Style/CaseLikeIf:
|
|
13
9
|
Enabled: false
|
|
14
10
|
|
|
15
11
|
Style/ExplicitBlockArgument:
|
data/CHANGELOG.md
CHANGED
|
@@ -1,46 +1,13 @@
|
|
|
1
1
|
|
|
2
2
|
# CHANGELOG
|
|
3
3
|
|
|
4
|
-
##
|
|
4
|
+
## v4.0.0
|
|
5
5
|
|
|
6
|
-
*
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
*
|
|
11
|
-
|
|
12
|
-
## v3.7.0
|
|
13
|
-
|
|
14
|
-
* Add `SearchFlip::Connection#bulk` to allow more clean bulk indexing to
|
|
15
|
-
multiple indices at once
|
|
16
|
-
|
|
17
|
-
## v3.6.0
|
|
18
|
-
|
|
19
|
-
* Support Elasticsearch v8
|
|
20
|
-
|
|
21
|
-
## v3.5.0
|
|
22
|
-
|
|
23
|
-
* Add `SearchFlip::Criteria#http_timeout` to allow specifying timeouts on
|
|
24
|
-
a query level
|
|
25
|
-
|
|
26
|
-
## v3.4.0
|
|
27
|
-
|
|
28
|
-
* Expose `Http#timeout` via `SearchFlip::HTTPClient`
|
|
29
|
-
|
|
30
|
-
## v3.3.0
|
|
31
|
-
|
|
32
|
-
* Update httprb
|
|
33
|
-
* Changed oj default options
|
|
34
|
-
* Allow to set oj json options
|
|
35
|
-
|
|
36
|
-
## v3.2.1
|
|
37
|
-
|
|
38
|
-
* Fix `refresh` having a empty body breaking in elasticsearch 7.11
|
|
39
|
-
|
|
40
|
-
## v3.2.0
|
|
41
|
-
|
|
42
|
-
* Fix `index_scope` not being passed in `each_record` without block
|
|
43
|
-
* Added `SearchFlip::Criteria#match_none`
|
|
6
|
+
* [BREAKING] For performance reasons, `SearchFlip::Result` now no longer
|
|
7
|
+
inherits `Hashie::Mash`
|
|
8
|
+
* It no longer supports symbol based access like `result[:id]`
|
|
9
|
+
* It no longer supports question mark methods like `result.title?`
|
|
10
|
+
* It no longer supports method based assignment like `result.some_key = "value"`
|
|
44
11
|
|
|
45
12
|
## v3.1.2
|
|
46
13
|
|
data/README.md
CHANGED
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
Using SearchFlip it is dead-simple to create index classes that correspond to
|
|
10
10
|
[Elasticsearch](https://www.elastic.co/) indices and to manipulate, query and
|
|
11
11
|
aggregate these indices using a chainable, concise, yet powerful DSL. Finally,
|
|
12
|
-
SearchFlip supports Elasticsearch 2.x, 5.x, 6.x, 7.x
|
|
12
|
+
SearchFlip supports Elasticsearch 2.x, 5.x, 6.x, 7.x. Check section
|
|
13
13
|
[Feature Support](#feature-support) for version dependent features.
|
|
14
14
|
|
|
15
15
|
```ruby
|
|
@@ -51,7 +51,7 @@ CommentIndex.search("hello world").where(available: true).sort(id: "desc").aggre
|
|
|
51
51
|
|
|
52
52
|
```
|
|
53
53
|
|
|
54
|
-
Finally, SearchFlip comes with a minimal set of dependencies.
|
|
54
|
+
Finally, SearchFlip comes with a minimal set of dependencies (http-rb and oj only).
|
|
55
55
|
|
|
56
56
|
## Reference Docs
|
|
57
57
|
|
|
@@ -418,14 +418,6 @@ Simply matches all documents:
|
|
|
418
418
|
CommentIndex.match_all
|
|
419
419
|
```
|
|
420
420
|
|
|
421
|
-
* `match_none`
|
|
422
|
-
|
|
423
|
-
Simply matches none documents at all:
|
|
424
|
-
|
|
425
|
-
```ruby
|
|
426
|
-
CommentIndex.match_none
|
|
427
|
-
```
|
|
428
|
-
|
|
429
421
|
* `all`
|
|
430
422
|
|
|
431
423
|
Simply returns the criteria as is or an empty criteria when called on the index
|
|
@@ -482,8 +474,8 @@ end
|
|
|
482
474
|
```
|
|
483
475
|
|
|
484
476
|
Generally, aggregation results returned by Elasticsearch are returned as a
|
|
485
|
-
`SearchFlip::Result`, which basically is a
|
|
486
|
-
access them via:
|
|
477
|
+
`SearchFlip::Result`, which basically is a Hash with method-like access, such
|
|
478
|
+
that you can access them via:
|
|
487
479
|
|
|
488
480
|
```ruby
|
|
489
481
|
query.aggregations(:username)["mrkamel"].revenue.value
|
|
@@ -698,14 +690,6 @@ Specify a timeout to limit query processing time:
|
|
|
698
690
|
CommentIndex.timeout("3s").execute
|
|
699
691
|
```
|
|
700
692
|
|
|
701
|
-
* `http_timeout`
|
|
702
|
-
|
|
703
|
-
Specify a http timeout for the request which will be send to Elasticsearch:
|
|
704
|
-
|
|
705
|
-
```ruby
|
|
706
|
-
CommentIndex.http_timeout(3).execute
|
|
707
|
-
```
|
|
708
|
-
|
|
709
693
|
* `terminate_after`
|
|
710
694
|
|
|
711
695
|
Activate early query termination to stop query processing after the specified
|
|
@@ -764,7 +748,7 @@ end
|
|
|
764
748
|
This allows to use different clusters per index e.g. when migrating indices to
|
|
765
749
|
new versions of Elasticsearch.
|
|
766
750
|
|
|
767
|
-
You can specify basic auth, additional headers,
|
|
751
|
+
You can specify basic auth, additional headers, etc via:
|
|
768
752
|
|
|
769
753
|
```ruby
|
|
770
754
|
http_client = SearchFlip::HTTPClient.new
|
|
@@ -781,9 +765,6 @@ http_client = http_client.via("proxy.host", 8080)
|
|
|
781
765
|
# Custom headers
|
|
782
766
|
http_client = http_client.headers(key: "value")
|
|
783
767
|
|
|
784
|
-
# Timeouts
|
|
785
|
-
http_client = http_client.timeout(20)
|
|
786
|
-
|
|
787
768
|
SearchFlip::Connection.new(base_url: "...", http_client: http_client)
|
|
788
769
|
```
|
|
789
770
|
|
|
@@ -893,52 +874,57 @@ Thus, if your ORM supports `.find_each`, `#id` and `#where` you are already
|
|
|
893
874
|
good to go. Otherwise, simply add your custom implementation of those methods
|
|
894
875
|
that work with whatever ORM you use.
|
|
895
876
|
|
|
896
|
-
## JSON
|
|
877
|
+
## Date and Timestamps in JSON
|
|
897
878
|
|
|
898
|
-
|
|
899
|
-
|
|
879
|
+
Elasticsearch requires dates and timestamps to have one of the formats listed
|
|
880
|
+
here: [https://www.elastic.co/guide/en/elasticsearch/reference/current/mapping-date-format.html#strict-date-time](https://www.elastic.co/guide/en/elasticsearch/reference/current/mapping-date-format.html#strict-date-time).
|
|
881
|
+
|
|
882
|
+
However, `JSON.generate` in ruby by default outputs something like:
|
|
900
883
|
|
|
901
884
|
```ruby
|
|
902
|
-
|
|
885
|
+
JSON.generate(time: Time.now.utc)
|
|
886
|
+
# => "{\"time\":\"2018-02-22 18:19:33 UTC\"}"
|
|
903
887
|
```
|
|
904
888
|
|
|
905
|
-
|
|
906
|
-
|
|
907
|
-
|
|
908
|
-
|
|
889
|
+
This format is not compatible with Elasticsearch by default. If you're on
|
|
890
|
+
Rails, ActiveSupport adds its own `#to_json` methods to `Time`, `Date`, etc.
|
|
891
|
+
However, ActiveSupport checks whether they are used in combination with
|
|
892
|
+
`JSON.generate` or not and adapt:
|
|
909
893
|
|
|
910
894
|
```ruby
|
|
911
|
-
|
|
912
|
-
|
|
913
|
-
|
|
914
|
-
|
|
915
|
-
|
|
916
|
-
}
|
|
895
|
+
Time.now.utc.to_json
|
|
896
|
+
=> "\"2018-02-22T18:18:22.088Z\""
|
|
897
|
+
|
|
898
|
+
JSON.generate(time: Time.now.utc)
|
|
899
|
+
=> "{\"time\":\"2018-02-22 18:18:59 UTC\"}"
|
|
917
900
|
```
|
|
918
901
|
|
|
919
|
-
|
|
902
|
+
SearchFlip is using the [Oj gem](https://github.com/ohler55/oj) to generate
|
|
903
|
+
JSON. More concretely, SearchFlip is using:
|
|
920
904
|
|
|
921
905
|
```ruby
|
|
922
|
-
|
|
923
|
-
|
|
906
|
+
Oj.dump({ key: "value" }, mode: :custom, use_to_json: true)
|
|
907
|
+
```
|
|
924
908
|
|
|
925
|
-
|
|
926
|
-
{
|
|
927
|
-
# ...
|
|
909
|
+
This mitigates the issues if you're on Rails:
|
|
928
910
|
|
|
929
|
-
|
|
930
|
-
|
|
931
|
-
|
|
932
|
-
end
|
|
911
|
+
```ruby
|
|
912
|
+
Oj.dump(Time.now, mode: :custom, use_to_json: true)
|
|
913
|
+
# => "\"2018-02-22T18:21:21.064Z\""
|
|
933
914
|
```
|
|
934
915
|
|
|
935
|
-
|
|
916
|
+
However, if you're not on Rails, you need to add `#to_json` methods to `Time`,
|
|
917
|
+
`Date` and `DateTime` to get proper serialization. You can either add them on
|
|
918
|
+
your own, via other libraries or by simply using:
|
|
919
|
+
|
|
920
|
+
```ruby
|
|
921
|
+
require "search_flip/to_json"
|
|
922
|
+
```
|
|
936
923
|
|
|
937
924
|
## Feature Support
|
|
938
925
|
|
|
939
926
|
* for Elasticsearch 2.x, the delete-by-query plugin is required to delete
|
|
940
927
|
records via queries
|
|
941
|
-
* `#match_none` is only available with Elasticsearch >= 5
|
|
942
928
|
* `#track_total_hits` is only available with Elasticsearch >= 7
|
|
943
929
|
|
|
944
930
|
## Keeping your Models and Indices in Sync
|
data/UPDATING.md
CHANGED
|
@@ -1,6 +1,46 @@
|
|
|
1
1
|
|
|
2
2
|
# Updating from previous SearchFlip versions
|
|
3
3
|
|
|
4
|
+
## Update 3.x to 4.x
|
|
5
|
+
|
|
6
|
+
**[BREAKING]** For performance reasons, `SearchFlip::Result` no longer
|
|
7
|
+
inherits `Hashie::Mash`
|
|
8
|
+
|
|
9
|
+
* It no longer supports symbol based access like `result[:id]`
|
|
10
|
+
|
|
11
|
+
2.x:
|
|
12
|
+
|
|
13
|
+
```ruby
|
|
14
|
+
CommentIndex.match_all.results.first[:id]
|
|
15
|
+
CommentIndex.aggregate(:tags).aggregations(:tags).values.first[:doc_count]
|
|
16
|
+
```
|
|
17
|
+
|
|
18
|
+
3.x
|
|
19
|
+
|
|
20
|
+
```ruby
|
|
21
|
+
CommentIndex.match_all.results.first["id"] # or .id
|
|
22
|
+
CommentIndex.aggregate(:tags).aggregations(:tags).values.first["doc_count"] # or .doc_count
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
* It no longer supports question mark methods like `result.title?`
|
|
26
|
+
|
|
27
|
+
2.x:
|
|
28
|
+
|
|
29
|
+
```ruby
|
|
30
|
+
CommentIndex.match_all.results.first.is_published?
|
|
31
|
+
```
|
|
32
|
+
|
|
33
|
+
3.x
|
|
34
|
+
|
|
35
|
+
```ruby
|
|
36
|
+
CommentIndex.match_all.results.first.is_published == true
|
|
37
|
+
```
|
|
38
|
+
|
|
39
|
+
* It no longer supports method based assignment like `result.some_key = "value"`.
|
|
40
|
+
|
|
41
|
+
However, this should not have any practical implications, as changing the
|
|
42
|
+
results is not considered to be a common use case.
|
|
43
|
+
|
|
4
44
|
## Update 2.x to 3.x
|
|
5
45
|
|
|
6
46
|
* **[BREAKING]** No longer pass multiple arguments to `#must`, `#must_not`,
|
data/docker-compose.yml
CHANGED
|
@@ -37,6 +37,7 @@ module SearchFlip
|
|
|
37
37
|
}
|
|
38
38
|
|
|
39
39
|
signature_request[:body] = options[:body] if options.key?(:body)
|
|
40
|
+
signature_request[:body] = options[:json].respond_to?(:to_str) ? options[:json] : JSON.generate(options[:json]) if options[:json]
|
|
40
41
|
|
|
41
42
|
signature = signer.sign_request(signature_request)
|
|
42
43
|
|
data/lib/search_flip/bulk.rb
CHANGED
data/lib/search_flip/config.rb
CHANGED
|
@@ -5,12 +5,6 @@ module SearchFlip
|
|
|
5
5
|
bulk_limit: 1_000,
|
|
6
6
|
bulk_max_mb: 100,
|
|
7
7
|
auto_refresh: false,
|
|
8
|
-
instrumenter: NullInstrumenter.new
|
|
9
|
-
json_options: {
|
|
10
|
-
mode: :custom,
|
|
11
|
-
use_to_json: true,
|
|
12
|
-
time_format: :xmlschema,
|
|
13
|
-
bigdecimal_as_decimal: false
|
|
14
|
-
}
|
|
8
|
+
instrumenter: NullInstrumenter.new
|
|
15
9
|
}
|
|
16
10
|
end
|
|
@@ -28,11 +28,7 @@ module SearchFlip
|
|
|
28
28
|
|
|
29
29
|
def version
|
|
30
30
|
@version_mutex.synchronize do
|
|
31
|
-
@version ||=
|
|
32
|
-
response = http_client.headers(accept: "application/json").get("#{base_url}/")
|
|
33
|
-
|
|
34
|
-
SearchFlip::JSON.parse(response.to_s)["version"]["number"]
|
|
35
|
-
end
|
|
31
|
+
@version ||= http_client.headers(accept: "application/json").get("#{base_url}/").parse["version"]["number"]
|
|
36
32
|
end
|
|
37
33
|
end
|
|
38
34
|
|
|
@@ -44,9 +40,7 @@ module SearchFlip
|
|
|
44
40
|
# @return [Hash] The raw response
|
|
45
41
|
|
|
46
42
|
def cluster_health
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
SearchFlip::JSON.parse(response.to_s)
|
|
43
|
+
http_client.headers(accept: "application/json").get("#{base_url}/_cluster/health").parse
|
|
50
44
|
end
|
|
51
45
|
|
|
52
46
|
# Uses the Elasticsearch Multi Search API to execute multiple search requests
|
|
@@ -64,7 +58,7 @@ module SearchFlip
|
|
|
64
58
|
def msearch(criterias)
|
|
65
59
|
payload = criterias.flat_map do |criteria|
|
|
66
60
|
[
|
|
67
|
-
SearchFlip::JSON.generate(index: criteria.target.index_name_with_prefix,
|
|
61
|
+
SearchFlip::JSON.generate(index: criteria.target.index_name_with_prefix, type: criteria.target.type_name),
|
|
68
62
|
SearchFlip::JSON.generate(criteria.request)
|
|
69
63
|
]
|
|
70
64
|
end
|
|
@@ -96,11 +90,10 @@ module SearchFlip
|
|
|
96
90
|
# @return [Hash] The raw response
|
|
97
91
|
|
|
98
92
|
def update_aliases(payload)
|
|
99
|
-
|
|
93
|
+
http_client
|
|
100
94
|
.headers(accept: "application/json", content_type: "application/json")
|
|
101
95
|
.post("#{base_url}/_aliases", body: SearchFlip::JSON.generate(payload))
|
|
102
|
-
|
|
103
|
-
SearchFlip::JSON.parse(response.to_s)
|
|
96
|
+
.parse
|
|
104
97
|
end
|
|
105
98
|
|
|
106
99
|
# Sends an analyze request to Elasticsearch. Raises
|
|
@@ -112,11 +105,10 @@ module SearchFlip
|
|
|
112
105
|
# @return [Hash] The raw response
|
|
113
106
|
|
|
114
107
|
def analyze(request, params = {})
|
|
115
|
-
|
|
108
|
+
http_client
|
|
116
109
|
.headers(accept: "application/json")
|
|
117
110
|
.post("#{base_url}/_analyze", json: request, params: params)
|
|
118
|
-
|
|
119
|
-
SearchFlip::JSON.parse(response.to_s)
|
|
111
|
+
.parse
|
|
120
112
|
end
|
|
121
113
|
|
|
122
114
|
# Fetches information about the specified index aliases. Raises
|
|
@@ -132,11 +124,10 @@ module SearchFlip
|
|
|
132
124
|
# @return [Hash] The raw response
|
|
133
125
|
|
|
134
126
|
def get_aliases(index_name: "*", alias_name: "*")
|
|
135
|
-
|
|
127
|
+
http_client
|
|
136
128
|
.headers(accept: "application/json", content_type: "application/json")
|
|
137
129
|
.get("#{base_url}/#{index_name}/_alias/#{alias_name}")
|
|
138
|
-
|
|
139
|
-
SearchFlip::JSON.parse(response.to_s)
|
|
130
|
+
.parse
|
|
140
131
|
end
|
|
141
132
|
|
|
142
133
|
# Returns whether or not the associated Elasticsearch alias already
|
|
@@ -168,11 +159,10 @@ module SearchFlip
|
|
|
168
159
|
# @return [Array] The raw response
|
|
169
160
|
|
|
170
161
|
def get_indices(name = "*", params: {})
|
|
171
|
-
|
|
162
|
+
http_client
|
|
172
163
|
.headers(accept: "application/json", content_type: "application/json")
|
|
173
164
|
.get("#{base_url}/_cat/indices/#{name}", params: params)
|
|
174
|
-
|
|
175
|
-
SearchFlip::JSON.parse(response.to_s)
|
|
165
|
+
.parse
|
|
176
166
|
end
|
|
177
167
|
|
|
178
168
|
alias_method :cat_indices, :get_indices
|
|
@@ -269,11 +259,10 @@ module SearchFlip
|
|
|
269
259
|
# @return [Hash] The index settings
|
|
270
260
|
|
|
271
261
|
def get_index_settings(index_name)
|
|
272
|
-
|
|
262
|
+
http_client
|
|
273
263
|
.headers(accept: "application/json")
|
|
274
264
|
.get("#{index_url(index_name)}/_settings")
|
|
275
|
-
|
|
276
|
-
SearchFlip::JSON.parse(response.to_s)
|
|
265
|
+
.parse
|
|
277
266
|
end
|
|
278
267
|
|
|
279
268
|
# Sends a refresh request to Elasticsearch. Raises
|
|
@@ -283,7 +272,7 @@ module SearchFlip
|
|
|
283
272
|
# @return [Boolean] Returns true or raises SearchFlip::ResponseError
|
|
284
273
|
|
|
285
274
|
def refresh(index_names = nil)
|
|
286
|
-
http_client.post("#{index_names ? index_url(Array(index_names).join(",")) : base_url}/_refresh")
|
|
275
|
+
http_client.post("#{index_names ? index_url(Array(index_names).join(",")) : base_url}/_refresh", json: {})
|
|
287
276
|
|
|
288
277
|
true
|
|
289
278
|
end
|
|
@@ -300,8 +289,8 @@ module SearchFlip
|
|
|
300
289
|
# @return [Boolean] Returns true or raises SearchFlip::ResponseError
|
|
301
290
|
|
|
302
291
|
def update_mapping(index_name, mapping, type_name: nil)
|
|
303
|
-
url = type_name
|
|
304
|
-
params = type_name && version.to_f >= 6.7
|
|
292
|
+
url = type_name ? type_url(index_name, type_name) : index_url(index_name)
|
|
293
|
+
params = type_name && version.to_f >= 6.7 ? { include_type_name: true } : {}
|
|
305
294
|
|
|
306
295
|
http_client.put("#{url}/_mapping", params: params, json: mapping)
|
|
307
296
|
|
|
@@ -318,12 +307,10 @@ module SearchFlip
|
|
|
318
307
|
# @return [Hash] The current type mapping
|
|
319
308
|
|
|
320
309
|
def get_mapping(index_name, type_name: nil)
|
|
321
|
-
url = type_name
|
|
322
|
-
params = type_name && version.to_f >= 6.7
|
|
323
|
-
|
|
324
|
-
response = http_client.headers(accept: "application/json").get("#{url}/_mapping", params: params)
|
|
310
|
+
url = type_name ? type_url(index_name, type_name) : index_url(index_name)
|
|
311
|
+
params = type_name && version.to_f >= 6.7 ? { include_type_name: true } : {}
|
|
325
312
|
|
|
326
|
-
|
|
313
|
+
http_client.headers(accept: "application/json").get("#{url}/_mapping", params: params).parse
|
|
327
314
|
end
|
|
328
315
|
|
|
329
316
|
# Deletes the specified index from Elasticsearch. Raises
|
|
@@ -355,51 +342,6 @@ module SearchFlip
|
|
|
355
342
|
raise e
|
|
356
343
|
end
|
|
357
344
|
|
|
358
|
-
# Initiates and yields a bulk object, such that index, import, create,
|
|
359
|
-
# update and delete requests can be appended to the bulk request. Please
|
|
360
|
-
# note that you need to manually pass the desired index name as well as
|
|
361
|
-
# type name (depending on the Elasticsearch version) when using #bulk on a
|
|
362
|
-
# connection object or Elasticsearch will return an error. After the bulk
|
|
363
|
-
# requests are successfully processed all existing indices will
|
|
364
|
-
# subsequently be refreshed when auto_refresh is enabled.
|
|
365
|
-
#
|
|
366
|
-
# @see SearchFlip::Config See SearchFlip::Config for auto_refresh
|
|
367
|
-
#
|
|
368
|
-
# @example
|
|
369
|
-
# connection = SearchFlip::Connection.new
|
|
370
|
-
#
|
|
371
|
-
# connection.bulk ignore_errors: [409] do |bulk|
|
|
372
|
-
# bulk.create comment.id, CommentIndex.serialize(comment),
|
|
373
|
-
# _index: CommentIndex.index_name, version: comment.version, version_type: "external_gte"
|
|
374
|
-
#
|
|
375
|
-
# bulk.delete product.id, _index: ProductIndex.index_name, routing: product.user_id
|
|
376
|
-
#
|
|
377
|
-
# # ...
|
|
378
|
-
# end
|
|
379
|
-
#
|
|
380
|
-
# @param options [Hash] Specifies options regarding the bulk indexing
|
|
381
|
-
# @option options ignore_errors [Array] Specifies an array of http status
|
|
382
|
-
# codes that shouldn't raise any exceptions, like eg 409 for conflicts,
|
|
383
|
-
# ie when optimistic concurrency control is used.
|
|
384
|
-
# @option options raise [Boolean] Prevents any exceptions from being
|
|
385
|
-
# raised. Please note that this only applies to the bulk response, not to
|
|
386
|
-
# the request in general, such that connection errors, etc will still
|
|
387
|
-
# raise.
|
|
388
|
-
|
|
389
|
-
def bulk(options = {})
|
|
390
|
-
default_options = {
|
|
391
|
-
http_client: http_client,
|
|
392
|
-
bulk_limit: bulk_limit,
|
|
393
|
-
bulk_max_mb: bulk_max_mb
|
|
394
|
-
}
|
|
395
|
-
|
|
396
|
-
SearchFlip::Bulk.new("#{base_url}/_bulk", default_options.merge(options)) do |indexer|
|
|
397
|
-
yield indexer
|
|
398
|
-
end
|
|
399
|
-
|
|
400
|
-
refresh if SearchFlip::Config[:auto_refresh]
|
|
401
|
-
end
|
|
402
|
-
|
|
403
345
|
# Returns the full Elasticsearch type URL, ie base URL, index name with
|
|
404
346
|
# prefix and type name.
|
|
405
347
|
#
|
data/lib/search_flip/criteria.rb
CHANGED
|
@@ -26,8 +26,7 @@ module SearchFlip
|
|
|
26
26
|
|
|
27
27
|
attr_accessor :target, :profile_value, :source_value, :suggest_values, :includes_values,
|
|
28
28
|
:eager_load_values, :preload_values, :failsafe_value, :scroll_args, :terminate_after_value,
|
|
29
|
-
:timeout_value, :preference_value, :search_type_value, :routing_value, :track_total_hits_value
|
|
30
|
-
:http_timeout_value
|
|
29
|
+
:timeout_value, :preference_value, :search_type_value, :routing_value, :track_total_hits_value
|
|
31
30
|
|
|
32
31
|
# Creates a new criteria while merging the attributes (constraints,
|
|
33
32
|
# settings, etc) of the current criteria with the attributes of another one
|
|
@@ -48,7 +47,7 @@ module SearchFlip
|
|
|
48
47
|
[
|
|
49
48
|
:profile_value, :failsafe_value, :terminate_after_value, :timeout_value, :offset_value,
|
|
50
49
|
:limit_value, :scroll_args, :source_value, :preference_value, :search_type_value,
|
|
51
|
-
:routing_value, :track_total_hits_value, :explain_value
|
|
50
|
+
:routing_value, :track_total_hits_value, :explain_value
|
|
52
51
|
].each do |name|
|
|
53
52
|
criteria.send(:"#{name}=", other.send(name)) unless other.send(name).nil?
|
|
54
53
|
end
|
|
@@ -149,22 +148,6 @@ module SearchFlip
|
|
|
149
148
|
end
|
|
150
149
|
end
|
|
151
150
|
|
|
152
|
-
# Specifies a http timeout, such that a SearchFlip::TimeoutError will be
|
|
153
|
-
# thrown when the request times out.
|
|
154
|
-
#
|
|
155
|
-
# @example
|
|
156
|
-
# ProductIndex.http_timeout(3).search("hello world")
|
|
157
|
-
#
|
|
158
|
-
# @param value [Fixnum] The timeout value
|
|
159
|
-
#
|
|
160
|
-
# @return [SearchFlip::Criteria] A newly created extended criteria
|
|
161
|
-
|
|
162
|
-
def http_timeout(value)
|
|
163
|
-
fresh.tap do |criteria|
|
|
164
|
-
criteria.http_timeout_value = value
|
|
165
|
-
end
|
|
166
|
-
end
|
|
167
|
-
|
|
168
151
|
# Specifies early query termination, such that the processing will be
|
|
169
152
|
# stopped after the specified number of results has been accumulated.
|
|
170
153
|
#
|
|
@@ -347,15 +330,10 @@ module SearchFlip
|
|
|
347
330
|
dupped_request.delete(:from)
|
|
348
331
|
dupped_request.delete(:size)
|
|
349
332
|
|
|
350
|
-
http_request = connection.http_client
|
|
351
|
-
http_request = http_request.timeout(http_timeout_value) if http_timeout_value
|
|
352
|
-
|
|
353
333
|
if connection.version.to_i >= 5
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
http_request.post("#{url}/_delete_by_query", params: request_params.merge(params), json: dupped_request)
|
|
334
|
+
connection.http_client.post("#{target.type_url}/_delete_by_query", params: request_params.merge(params), json: dupped_request)
|
|
357
335
|
else
|
|
358
|
-
|
|
336
|
+
connection.http_client.delete("#{target.type_url}/_query", params: request_params.merge(params), json: dupped_request)
|
|
359
337
|
end
|
|
360
338
|
|
|
361
339
|
target.refresh if SearchFlip::Config[:auto_refresh]
|
|
@@ -523,8 +501,8 @@ module SearchFlip
|
|
|
523
501
|
end
|
|
524
502
|
|
|
525
503
|
# Executes the search request for the current criteria, ie sends the
|
|
526
|
-
# request to Elasticsearch and returns the response. Connection
|
|
527
|
-
#
|
|
504
|
+
# request to Elasticsearch and returns the response. Connection and
|
|
505
|
+
# response errors will be rescued if you specify the criteria to be
|
|
528
506
|
# #failsafe, such that an empty response is returned instead.
|
|
529
507
|
#
|
|
530
508
|
# @example
|
|
@@ -612,7 +590,6 @@ module SearchFlip
|
|
|
612
590
|
|
|
613
591
|
def execute!
|
|
614
592
|
http_request = connection.http_client.headers(accept: "application/json")
|
|
615
|
-
http_request = http_request.timeout(http_timeout_value) if http_timeout_value
|
|
616
593
|
|
|
617
594
|
http_response =
|
|
618
595
|
if scroll_args && scroll_args[:id]
|
|
@@ -622,21 +599,17 @@ module SearchFlip
|
|
|
622
599
|
json: { scroll: scroll_args[:timeout], scroll_id: scroll_args[:id] }
|
|
623
600
|
)
|
|
624
601
|
elsif scroll_args
|
|
625
|
-
url = connection.version.to_i < 8 ? target.type_url : target.index_url
|
|
626
|
-
|
|
627
602
|
http_request.post(
|
|
628
|
-
"#{
|
|
603
|
+
"#{target.type_url}/_search",
|
|
629
604
|
params: request_params.merge(scroll: scroll_args[:timeout]),
|
|
630
605
|
json: request
|
|
631
606
|
)
|
|
632
607
|
else
|
|
633
|
-
|
|
634
|
-
|
|
635
|
-
http_request.post("#{url}/_search", params: request_params, json: request)
|
|
608
|
+
http_request.post("#{target.type_url}/_search", params: request_params, json: request)
|
|
636
609
|
end
|
|
637
610
|
|
|
638
611
|
SearchFlip::Response.new(self, SearchFlip::JSON.parse(http_response.to_s))
|
|
639
|
-
rescue SearchFlip::ConnectionError, SearchFlip::
|
|
612
|
+
rescue SearchFlip::ConnectionError, SearchFlip::ResponseError => e
|
|
640
613
|
raise e unless failsafe_value
|
|
641
614
|
|
|
642
615
|
SearchFlip::Response.new(self, "took" => 0, "hits" => { "total" => 0, "hits" => [] })
|
|
@@ -235,22 +235,6 @@ module SearchFlip
|
|
|
235
235
|
filter(match_all: options)
|
|
236
236
|
end
|
|
237
237
|
|
|
238
|
-
# Adds a match none filter to the criteria, which simply matches none
|
|
239
|
-
# documents at all. Check out the Elasticsearch docs for further details.
|
|
240
|
-
#
|
|
241
|
-
# @example Basic usage
|
|
242
|
-
# CommentIndex.match_none
|
|
243
|
-
#
|
|
244
|
-
# @example Filter chaining
|
|
245
|
-
# query = CommentIndex.search("...")
|
|
246
|
-
# query = query.match_none unless current_user.admin?
|
|
247
|
-
#
|
|
248
|
-
# @return [SearchFlip::Criteria] A newly created extended criteria
|
|
249
|
-
|
|
250
|
-
def match_none
|
|
251
|
-
filter(match_none: {})
|
|
252
|
-
end
|
|
253
|
-
|
|
254
238
|
# Adds an exists filter to the criteria, which selects all documents for
|
|
255
239
|
# which the specified field has a non-null value.
|
|
256
240
|
#
|