artirix_data_models 0.6.2 → 0.6.3.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +13 -0
- data/lib/artirix_data_models.rb +1 -1
- data/lib/artirix_data_models/aggregations_factory.rb +59 -0
- data/lib/artirix_data_models/raw_aggregation_data_normaliser.rb +21 -12
- data/lib/artirix_data_models/version.rb +1 -1
- data/spec/artirix_data_models/es_collection_spec.rb +55 -0
- data/spec/fixtures/articles_search_multiple_nested_raw_es.json +187 -0
- metadata +4 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 6bf75f8fabe2f1161d1306a0c1d1da33abc2e178
|
4
|
+
data.tar.gz: 033a3edd3d4ec0c2cb5158ec3fda73a05e9a6c7f
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 8957ef6dae32230c8dd3c7223f8b2473fba7f70f969cd0585d53bf0008d62b9164d158b1e2fd0c30e19c0c4c5a77e1ff3f71b0c2b060de137725e695faf81e35
|
7
|
+
data.tar.gz: f26f34e27de7508872b7b5ca6a6f8d0a36f740848b6bd900aa6449d21738e975b67a66e1970eb39a25504152fbc92b6074adfce1fc64ca49f85715cff59ac80a
|
data/README.md
CHANGED
@@ -224,6 +224,11 @@ end
|
|
224
224
|
|
225
225
|
## Changes
|
226
226
|
|
227
|
+
### 0.6.3.1
|
228
|
+
|
229
|
+
- Fix in EsCollection's aggregation parsing (nested + single from RAW now work ok)
|
230
|
+
- `SortedBucketAggregationBase` introduced. now `ArtirixDataModels::AggregationsFactory.sorted_aggregation_class_based_on_index_on(index_array)` available to create a class for Aggregations which will sort the buckets based on the position of the elements on a given array.
|
231
|
+
|
227
232
|
### 0.6.2
|
228
233
|
|
229
234
|
*Fixed Breaking Change*: removal of `Aggregation.from_json` static method. Now back but delegating to default factory method is `aggregation_factory.aggregation_from_json` in the Aggregation Factory *instance*.
|
@@ -239,6 +244,14 @@ end
|
|
239
244
|
|
240
245
|
## Yanked versions
|
241
246
|
|
247
|
+
### ~0.6.3~
|
248
|
+
|
249
|
+
Yanked because of typo bug on SortedBucketAggregationBase. Released 0.6.3.1 with the fix.
|
250
|
+
|
251
|
+
|
252
|
+
- Fix in EsCollection's aggregation parsing (nested + single from RAW now work ok)
|
253
|
+
- `SortedBucketAggregationBase` introduced. now `ArtirixDataModels::AggregationsFactory.sorted_aggregation_class_based_on_index_on(index_array)` available to create a class for Aggregations which will sort the buckets based on the position of the elements on a given array.
|
254
|
+
|
242
255
|
|
243
256
|
### ~0.6.1~
|
244
257
|
|
data/lib/artirix_data_models.rb
CHANGED
@@ -14,10 +14,10 @@ require 'hashie'
|
|
14
14
|
|
15
15
|
# loading features
|
16
16
|
require 'artirix_data_models/es_collection'
|
17
|
+
require 'artirix_data_models/aggregation'
|
17
18
|
require 'artirix_data_models/aggregations_factory'
|
18
19
|
require 'artirix_data_models/raw_aggregation_data_normaliser'
|
19
20
|
require 'artirix_data_models/aggregation_builder'
|
20
|
-
require 'artirix_data_models/aggregation'
|
21
21
|
require 'artirix_data_models/model'
|
22
22
|
require 'artirix_data_models/gateways/data_gateway'
|
23
23
|
require 'artirix_data_models/gateway_response_adaptors/model_adaptor'
|
@@ -2,6 +2,14 @@ module ArtirixDataModels
|
|
2
2
|
class AggregationsFactory
|
3
3
|
DEFAULT_COLLECTION_CLASS_NAME = ''.freeze
|
4
4
|
|
5
|
+
# AGGREGATION CLASS BUILDING
|
6
|
+
|
7
|
+
def self.sorted_aggregation_class_based_on_index_on(index_array)
|
8
|
+
SortedBucketsAggregationClassFactory.build_class_based_on_index_on(index_array)
|
9
|
+
end
|
10
|
+
|
11
|
+
# FACTORY INSTANCE
|
12
|
+
|
5
13
|
def initialize
|
6
14
|
@_loaders = Hash.new { |h, k| h[k] = {} }
|
7
15
|
setup_config
|
@@ -61,5 +69,56 @@ module ArtirixDataModels
|
|
61
69
|
RawAggregationDataNormaliser.new(self, raw_aggs).normalise
|
62
70
|
end
|
63
71
|
|
72
|
+
module SortedBucketsAggregationClassFactory
|
73
|
+
def self.build_class_based_on_index_on(index_array)
|
74
|
+
prepared_index_array = index_array.map { |key| SortedBucketsAggregationClassFactory.prepare_key(key) }
|
75
|
+
sort_by_proc = sort_by_index_on(prepared_index_array)
|
76
|
+
|
77
|
+
Class.new(SortedBucketAggregationBase).tap do |klass|
|
78
|
+
klass.sort_by_callable = sort_by_proc
|
79
|
+
end
|
80
|
+
end
|
81
|
+
|
82
|
+
def self.prepare_key(key)
|
83
|
+
key.to_s.strip.downcase
|
84
|
+
end
|
85
|
+
|
86
|
+
def self.sort_by_index_on(index_array)
|
87
|
+
proc do |bucket|
|
88
|
+
name = SortedBucketsAggregationClassFactory.prepare_key(bucket.name)
|
89
|
+
|
90
|
+
found_index = index_array.index(name)
|
91
|
+
|
92
|
+
if found_index.present?
|
93
|
+
[0, found_index]
|
94
|
+
else
|
95
|
+
[1, 0]
|
96
|
+
end
|
97
|
+
end
|
98
|
+
end
|
99
|
+
|
100
|
+
class SortedBucketAggregationBase < ArtirixDataModels::Aggregation
|
101
|
+
alias_method :unordered_buckets, :buckets
|
102
|
+
|
103
|
+
def buckets
|
104
|
+
@sorted_buckets ||= sort_buckets
|
105
|
+
end
|
106
|
+
|
107
|
+
def sort_buckets
|
108
|
+
unordered_buckets.sort_by { |bucket| self.class.sort_by_callable.call(bucket) }
|
109
|
+
end
|
110
|
+
|
111
|
+
def self.sort_by_callable
|
112
|
+
@sort_by_callable
|
113
|
+
end
|
114
|
+
|
115
|
+
def self.sort_by_callable=(callable = nil, &block)
|
116
|
+
raise ArgumentError unless callable || block
|
117
|
+
|
118
|
+
@sort_by_callable = callable || block
|
119
|
+
end
|
120
|
+
end
|
121
|
+
|
122
|
+
end
|
64
123
|
end
|
65
124
|
end
|
@@ -3,44 +3,53 @@ module ArtirixDataModels
|
|
3
3
|
|
4
4
|
FIND_BUCKETS = ->(_k, v, _o) { v.respond_to?(:key?) && v.key?(:buckets) }
|
5
5
|
|
6
|
-
attr_reader :raw_aggs, :aggregations_factory
|
6
|
+
attr_reader :raw_aggs, :aggregations_factory, :list
|
7
7
|
|
8
8
|
def initialize(aggregations_factory, raw_aggs)
|
9
9
|
@aggregations_factory = aggregations_factory
|
10
10
|
@raw_aggs = raw_aggs
|
11
|
+
@list = []
|
11
12
|
end
|
12
13
|
|
13
14
|
def normalise
|
14
15
|
return [] unless raw_aggs.present?
|
15
16
|
return raw_aggs if Array === raw_aggs
|
16
17
|
|
17
|
-
normalise_hash
|
18
|
+
normalise_hash(raw_aggs)
|
19
|
+
|
20
|
+
list
|
18
21
|
end
|
19
22
|
|
20
23
|
alias_method :call, :normalise
|
21
24
|
|
22
25
|
private
|
23
26
|
|
24
|
-
def normalise_hash
|
25
|
-
with_buckets_list = deep_locate
|
27
|
+
def normalise_hash(hash)
|
28
|
+
with_buckets_list = deep_locate hash, FIND_BUCKETS
|
26
29
|
|
27
|
-
with_buckets_list.
|
30
|
+
with_buckets_list.each do |with_buckets|
|
28
31
|
with_buckets.each do |name, value|
|
29
|
-
|
32
|
+
normalise_element(name, value)
|
30
33
|
end
|
31
|
-
|
32
|
-
list
|
33
34
|
end
|
34
35
|
end
|
35
36
|
|
36
|
-
def
|
37
|
-
return unless Hash ===
|
37
|
+
def normalise_element(name, value)
|
38
|
+
return unless Hash === value
|
39
|
+
|
40
|
+
if value.key?(:buckets)
|
41
|
+
add_normalised_element_to_list(name, value)
|
42
|
+
else
|
43
|
+
normalise_hash(value)
|
44
|
+
end
|
45
|
+
end
|
38
46
|
|
39
|
-
|
47
|
+
def add_normalised_element_to_list(name, value)
|
48
|
+
buckets = value[:buckets].map do |raw_bucket|
|
40
49
|
normalise_bucket(raw_bucket)
|
41
50
|
end
|
42
51
|
|
43
|
-
list << { name:
|
52
|
+
list << { name: name, buckets: buckets }
|
44
53
|
end
|
45
54
|
|
46
55
|
def normalise_bucket(raw_bucket)
|
@@ -169,6 +169,61 @@ RSpec.describe ArtirixDataModels::EsCollection, type: :model do
|
|
169
169
|
Then { es_collection.aggregations.first.buckets.last.aggregations.first.buckets.last.name == 'Cognitive Impact' }
|
170
170
|
Then { es_collection.aggregations.first.buckets.last.aggregations.first.buckets.last.count == 3 }
|
171
171
|
end
|
172
|
+
|
173
|
+
context 'with Raw ES with multiple nested aggregations' do
|
174
|
+
Given(:fixture_file) { fixture_pathname('articles_search_multiple_nested_raw_es.json') }
|
175
|
+
|
176
|
+
Given(:model_class) {
|
177
|
+
Class.new do
|
178
|
+
attr_reader :data
|
179
|
+
|
180
|
+
def initialize(data)
|
181
|
+
@data = { given: data }
|
182
|
+
end
|
183
|
+
end
|
184
|
+
}
|
185
|
+
Given(:es_response) { Oj.load(File.read(fixture_file), symbol_keys: true) }
|
186
|
+
|
187
|
+
When(:es_collection) { ArtirixDataModels::EsCollection.new(model_class, response: es_response) }
|
188
|
+
|
189
|
+
Then { es_collection.total == 1234 }
|
190
|
+
Then { es_collection.results == [] }
|
191
|
+
|
192
|
+
Then { es_collection.aggregations.size == 2 }
|
193
|
+
|
194
|
+
Then { es_collection.aggregations.first.name == :publication_types }
|
195
|
+
Then { es_collection.aggregations.first.buckets.size == 8 }
|
196
|
+
|
197
|
+
Then { es_collection.aggregations.first.buckets.first.name == 'Expert Opinion' }
|
198
|
+
Then { es_collection.aggregations.first.buckets.first.count == 1798 }
|
199
|
+
Then { es_collection.aggregations.first.buckets.last.name == 'Guidelines' }
|
200
|
+
Then { es_collection.aggregations.first.buckets.last.count == 33 }
|
201
|
+
|
202
|
+
|
203
|
+
Then { es_collection.aggregations.last.name == :taxonomy_level_1 }
|
204
|
+
Then { es_collection.aggregations.last.buckets.size == 4 }
|
205
|
+
|
206
|
+
Then { es_collection.aggregations.last.buckets.first.name == 'Treatment' }
|
207
|
+
Then { es_collection.aggregations.last.buckets.first.count == 2404 }
|
208
|
+
Then { es_collection.aggregations.last.buckets.first.aggregations.size == 1 }
|
209
|
+
Then { es_collection.aggregations.last.buckets.first.aggregations.first.name == :taxonomy_level_2 }
|
210
|
+
Then { es_collection.aggregations.last.buckets.first.aggregations.first.buckets.size == 7 }
|
211
|
+
Then { es_collection.aggregations.last.buckets.first.aggregations.first.buckets.first.name == 'Drug Treatments' }
|
212
|
+
Then { es_collection.aggregations.last.buckets.first.aggregations.first.buckets.first.count == 977 }
|
213
|
+
Then { es_collection.aggregations.last.buckets.first.aggregations.first.buckets.last.name == 'Complementary and Alternative Therapies' }
|
214
|
+
Then { es_collection.aggregations.last.buckets.first.aggregations.first.buckets.last.count == 14 }
|
215
|
+
|
216
|
+
|
217
|
+
Then { es_collection.aggregations.last.buckets.last.name == 'Living' }
|
218
|
+
Then { es_collection.aggregations.last.buckets.last.count == 365 }
|
219
|
+
Then { es_collection.aggregations.last.buckets.last.aggregations.size == 1 }
|
220
|
+
Then { es_collection.aggregations.last.buckets.last.aggregations.first.name == :taxonomy_level_2 }
|
221
|
+
Then { es_collection.aggregations.last.buckets.last.aggregations.first.buckets.size == 8 }
|
222
|
+
Then { es_collection.aggregations.last.buckets.last.aggregations.first.buckets.first.name == 'Emotional Impact' }
|
223
|
+
Then { es_collection.aggregations.last.buckets.last.aggregations.first.buckets.first.count == 104 }
|
224
|
+
Then { es_collection.aggregations.last.buckets.last.aggregations.first.buckets.last.name == 'Cognitive Impact' }
|
225
|
+
Then { es_collection.aggregations.last.buckets.last.aggregations.first.buckets.last.count == 3 }
|
226
|
+
end
|
172
227
|
end
|
173
228
|
|
174
229
|
end
|
@@ -0,0 +1,187 @@
|
|
1
|
+
{
|
2
|
+
"took": 40,
|
3
|
+
"timed_out": false,
|
4
|
+
"_shards": {
|
5
|
+
"total": 5,
|
6
|
+
"successful": 5,
|
7
|
+
"failed": 0
|
8
|
+
},
|
9
|
+
"hits": {
|
10
|
+
"total": 1234,
|
11
|
+
"max_score": 0,
|
12
|
+
"hits": []
|
13
|
+
},
|
14
|
+
"aggregations": {
|
15
|
+
"publication_types": {
|
16
|
+
"doc_count_error_upper_bound": 0,
|
17
|
+
"sum_other_doc_count": 0,
|
18
|
+
"buckets": [
|
19
|
+
{
|
20
|
+
"key": "Expert Opinion",
|
21
|
+
"doc_count": 1798
|
22
|
+
},
|
23
|
+
{
|
24
|
+
"key": "Observational Studies",
|
25
|
+
"doc_count": 777
|
26
|
+
},
|
27
|
+
{
|
28
|
+
"key": "Clinical Observations",
|
29
|
+
"doc_count": 627
|
30
|
+
},
|
31
|
+
{
|
32
|
+
"key": "Controlled Studies",
|
33
|
+
"doc_count": 303
|
34
|
+
},
|
35
|
+
{
|
36
|
+
"key": "Randomised Controlled Trials",
|
37
|
+
"doc_count": 299
|
38
|
+
},
|
39
|
+
{
|
40
|
+
"key": "Systematic Reviews",
|
41
|
+
"doc_count": 220
|
42
|
+
},
|
43
|
+
{
|
44
|
+
"key": "Meta-Analysis",
|
45
|
+
"doc_count": 49
|
46
|
+
},
|
47
|
+
{
|
48
|
+
"key": "Guidelines",
|
49
|
+
"doc_count": 33
|
50
|
+
}
|
51
|
+
]
|
52
|
+
},
|
53
|
+
"taxonomy": {
|
54
|
+
"doc_count": 4674,
|
55
|
+
"taxonomy_level_1": {
|
56
|
+
"doc_count_error_upper_bound": 0,
|
57
|
+
"sum_other_doc_count": 0,
|
58
|
+
"buckets": [
|
59
|
+
{
|
60
|
+
"key": "Treatment",
|
61
|
+
"doc_count": 2404,
|
62
|
+
"taxonomy_level_2": {
|
63
|
+
"doc_count_error_upper_bound": 0,
|
64
|
+
"sum_other_doc_count": 0,
|
65
|
+
"buckets": [
|
66
|
+
{
|
67
|
+
"key": "Drug Treatments",
|
68
|
+
"doc_count": 977
|
69
|
+
},
|
70
|
+
{
|
71
|
+
"key": "Drug Development",
|
72
|
+
"doc_count": 731
|
73
|
+
},
|
74
|
+
{
|
75
|
+
"key": "Other Treatments",
|
76
|
+
"doc_count": 358
|
77
|
+
},
|
78
|
+
{
|
79
|
+
"key": "Surgical Treatments",
|
80
|
+
"doc_count": 264
|
81
|
+
},
|
82
|
+
{
|
83
|
+
"key": "Assistive Devices",
|
84
|
+
"doc_count": 43
|
85
|
+
},
|
86
|
+
{
|
87
|
+
"key": "Palliative Care",
|
88
|
+
"doc_count": 17
|
89
|
+
},
|
90
|
+
{
|
91
|
+
"key": "Complementary and Alternative Therapies",
|
92
|
+
"doc_count": 14
|
93
|
+
}
|
94
|
+
]
|
95
|
+
}
|
96
|
+
},
|
97
|
+
{
|
98
|
+
"key": "Understand",
|
99
|
+
"doc_count": 1356,
|
100
|
+
"taxonomy_level_2": {
|
101
|
+
"doc_count_error_upper_bound": 0,
|
102
|
+
"sum_other_doc_count": 0,
|
103
|
+
"buckets": [
|
104
|
+
{
|
105
|
+
"key": "Symptoms",
|
106
|
+
"doc_count": 1066
|
107
|
+
},
|
108
|
+
{
|
109
|
+
"key": "Outlook",
|
110
|
+
"doc_count": 143
|
111
|
+
},
|
112
|
+
{
|
113
|
+
"key": "Causes",
|
114
|
+
"doc_count": 123
|
115
|
+
},
|
116
|
+
{
|
117
|
+
"key": "Ethics",
|
118
|
+
"doc_count": 24
|
119
|
+
}
|
120
|
+
]
|
121
|
+
}
|
122
|
+
},
|
123
|
+
{
|
124
|
+
"key": "Diagnosis",
|
125
|
+
"doc_count": 549,
|
126
|
+
"taxonomy_level_2": {
|
127
|
+
"doc_count_error_upper_bound": 0,
|
128
|
+
"sum_other_doc_count": 0,
|
129
|
+
"buckets": [
|
130
|
+
{
|
131
|
+
"key": "Diagnostic Techniques",
|
132
|
+
"doc_count": 525
|
133
|
+
},
|
134
|
+
{
|
135
|
+
"key": "Diagnostic Challenges",
|
136
|
+
"doc_count": 24
|
137
|
+
}
|
138
|
+
]
|
139
|
+
}
|
140
|
+
},
|
141
|
+
{
|
142
|
+
"key": "Living",
|
143
|
+
"doc_count": 365,
|
144
|
+
"taxonomy_level_2": {
|
145
|
+
"doc_count_error_upper_bound": 0,
|
146
|
+
"sum_other_doc_count": 0,
|
147
|
+
"buckets": [
|
148
|
+
{
|
149
|
+
"key": "Emotional Impact",
|
150
|
+
"doc_count": 104
|
151
|
+
},
|
152
|
+
{
|
153
|
+
"key": "Genetic Counseling",
|
154
|
+
"doc_count": 63
|
155
|
+
},
|
156
|
+
{
|
157
|
+
"key": "Diet",
|
158
|
+
"doc_count": 59
|
159
|
+
},
|
160
|
+
{
|
161
|
+
"key": "Fertility/Sex",
|
162
|
+
"doc_count": 56
|
163
|
+
},
|
164
|
+
{
|
165
|
+
"key": "Exercise",
|
166
|
+
"doc_count": 48
|
167
|
+
},
|
168
|
+
{
|
169
|
+
"key": "Physical Impact",
|
170
|
+
"doc_count": 26
|
171
|
+
},
|
172
|
+
{
|
173
|
+
"key": "Sleep",
|
174
|
+
"doc_count": 6
|
175
|
+
},
|
176
|
+
{
|
177
|
+
"key": "Cognitive Impact",
|
178
|
+
"doc_count": 3
|
179
|
+
}
|
180
|
+
]
|
181
|
+
}
|
182
|
+
}
|
183
|
+
]
|
184
|
+
}
|
185
|
+
}
|
186
|
+
}
|
187
|
+
}
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: artirix_data_models
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.6.
|
4
|
+
version: 0.6.3.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Eduardo Turiño
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-08-
|
11
|
+
date: 2015-08-13 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activesupport
|
@@ -259,6 +259,7 @@ files:
|
|
259
259
|
- spec/artirix_data_models/gateways/gateway_response_adaptors/model_adaptor_spec.rb
|
260
260
|
- spec/artirix_data_models/model_fields_dao_spec.rb
|
261
261
|
- spec/fixtures/articles_search_dl.json
|
262
|
+
- spec/fixtures/articles_search_multiple_nested_raw_es.json
|
262
263
|
- spec/fixtures/articles_search_nested_raw_es.json
|
263
264
|
- spec/fixtures/articles_search_nested_single_raw_es.json
|
264
265
|
- spec/fixtures/articles_search_raw_es.json
|
@@ -299,6 +300,7 @@ test_files:
|
|
299
300
|
- spec/artirix_data_models/gateways/gateway_response_adaptors/model_adaptor_spec.rb
|
300
301
|
- spec/artirix_data_models/model_fields_dao_spec.rb
|
301
302
|
- spec/fixtures/articles_search_dl.json
|
303
|
+
- spec/fixtures/articles_search_multiple_nested_raw_es.json
|
302
304
|
- spec/fixtures/articles_search_nested_raw_es.json
|
303
305
|
- spec/fixtures/articles_search_nested_single_raw_es.json
|
304
306
|
- spec/fixtures/articles_search_raw_es.json
|