labimotion 1.4.1 → 2.0.0.rc2
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/labimotion/apis/generic_element_api.rb +1 -0
- data/lib/labimotion/apis/generic_klass_api.rb +3 -2
- data/lib/labimotion/apis/labimotion_api.rb +13 -0
- data/lib/labimotion/apis/standard_api.rb +26 -0
- data/lib/labimotion/apis/standard_layer_api.rb +100 -0
- data/lib/labimotion/apis/vocabulary_api.rb +107 -0
- data/lib/labimotion/entities/dataset_entity.rb +2 -1
- data/lib/labimotion/entities/properties_entity.rb +167 -55
- data/lib/labimotion/entities/segment_entity.rb +1 -0
- data/lib/labimotion/entities/vocabulary_entity.rb +39 -0
- data/lib/labimotion/helpers/element_helpers.rb +8 -6
- data/lib/labimotion/helpers/param_helpers.rb +137 -82
- data/lib/labimotion/helpers/segment_helpers.rb +1 -1
- data/lib/labimotion/helpers/vocabulary_helpers.rb +16 -0
- data/lib/labimotion/libs/converter.rb +13 -33
- data/lib/labimotion/libs/data/vocab/Standard.json +385 -0
- data/lib/labimotion/libs/data/vocab/System.json +131 -0
- data/lib/labimotion/libs/nmr_mapper.rb +2 -1
- data/lib/labimotion/libs/sample_association.rb +4 -0
- data/lib/labimotion/libs/vocabulary_handler.rb +118 -0
- data/lib/labimotion/models/concerns/attachment_converter.rb +5 -4
- data/lib/labimotion/models/concerns/datasetable.rb +1 -0
- data/lib/labimotion/models/concerns/segmentable.rb +2 -0
- data/lib/labimotion/models/std_layer.rb +9 -0
- data/lib/labimotion/models/std_layers_revision.rb +9 -0
- data/lib/labimotion/models/vocabulary.rb +12 -0
- data/lib/labimotion/version.rb +1 -1
- data/lib/labimotion.rb +10 -0
- metadata +20 -5
@@ -6,94 +6,149 @@ module Labimotion
|
|
6
6
|
## Generic Helpers
|
7
7
|
module ParamHelpers
|
8
8
|
extend Grape::API::Helpers
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
9
|
+
## Element Klass Params
|
10
|
+
params :upload_element_klass_params do
|
11
|
+
requires :name, type: String, desc: 'Klass Name'
|
12
|
+
optional :label, type: String, desc: 'Klass label'
|
13
|
+
optional :desc, type: String, desc: 'Klass desc'
|
14
|
+
optional :klass_prefix, type: String, desc: 'Klass klass_prefix'
|
15
|
+
optional :icon_name, type: String, desc: 'Klass icon_name'
|
16
|
+
requires :properties_template, type: Hash, desc: 'Klass template'
|
17
|
+
optional :properties_release, type: Hash, desc: 'Klass release'
|
18
|
+
optional :released_at, type: DateTime, desc: 'Klass released_at'
|
19
|
+
requires :uuid, type: String, desc: 'Klass uuid'
|
20
|
+
requires :place, type: Integer, desc: 'Klass place'
|
21
|
+
requires :identifier, type: String, desc: 'Klass identifier'
|
22
|
+
optional :sync_time, type: DateTime, desc: 'Klass sync_time'
|
23
|
+
optional :version, type: String, desc: 'Klass version'
|
24
|
+
end
|
25
25
|
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
26
|
+
params :create_element_klass_params do
|
27
|
+
requires :name, type: String, desc: 'Element Klass Name'
|
28
|
+
requires :label, type: String, desc: 'Element Klass Label'
|
29
|
+
requires :klass_prefix, type: String, desc: 'Element Klass Short Label Prefix'
|
30
|
+
optional :icon_name, type: String, desc: 'Element Klass Icon Name'
|
31
|
+
optional :desc, type: String, desc: 'Element Klass Desc'
|
32
|
+
optional :properties_template, type: Hash, desc: 'Element Klass properties template'
|
33
|
+
end
|
34
34
|
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
35
|
+
params :update_element_klass_params do
|
36
|
+
requires :id, type: Integer, desc: 'Element Klass ID'
|
37
|
+
optional :label, type: String, desc: 'Element Klass Label'
|
38
|
+
optional :klass_prefix, type: String, desc: 'Element Klass Short Label Prefix'
|
39
|
+
optional :icon_name, type: String, desc: 'Element Klass Icon Name'
|
40
|
+
optional :desc, type: String, desc: 'Element Klass Desc'
|
41
|
+
optional :place, type: String, desc: 'Element Klass Place'
|
42
|
+
end
|
43
43
|
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
44
|
+
## Element Params
|
45
|
+
params :create_element_params do
|
46
|
+
requires :element_klass, type: Hash
|
47
|
+
requires :name, type: String
|
48
|
+
optional :properties, type: Hash
|
49
|
+
optional :properties_release, type: Hash
|
50
|
+
optional :collection_id, type: Integer
|
51
|
+
requires :container, type: Hash
|
52
|
+
optional :user_labels, type: Array
|
53
|
+
optional :segments, type: Array, desc: 'Segments'
|
54
|
+
end
|
55
55
|
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
56
|
+
params :update_element_params do
|
57
|
+
requires :id, type: Integer, desc: 'element id'
|
58
|
+
optional :name, type: String
|
59
|
+
requires :properties, type: Hash
|
60
|
+
optional :properties_release, type: Hash
|
61
|
+
requires :container, type: Hash
|
62
|
+
optional :user_labels, type: Array
|
63
|
+
optional :segments, type: Array, desc: 'Segments'
|
64
|
+
end
|
65
65
|
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
|
78
|
-
|
79
|
-
|
80
|
-
end
|
66
|
+
## Segment Klass Params
|
67
|
+
params :upload_segment_klass_params do
|
68
|
+
requires :label, type: String, desc: 'Klass label'
|
69
|
+
optional :desc, type: String, desc: 'Klass desc'
|
70
|
+
requires :properties_template, type: Hash, desc: 'Klass template'
|
71
|
+
optional :properties_release, type: Hash, desc: 'Klass release'
|
72
|
+
optional :released_at, type: DateTime, desc: 'Klass released_at'
|
73
|
+
requires :uuid, type: String, desc: 'Klass uuid'
|
74
|
+
requires :place, type: Integer, desc: 'Klass place'
|
75
|
+
requires :identifier, type: String, desc: 'Klass identifier'
|
76
|
+
optional :sync_time, type: DateTime, desc: 'Klass sync_time'
|
77
|
+
optional :version, type: String, desc: 'Klass version'
|
78
|
+
requires :element_klass, type: Hash do
|
79
|
+
use :upload_element_klass_params
|
81
80
|
end
|
81
|
+
end
|
82
82
|
|
83
|
-
|
84
|
-
|
85
|
-
|
86
|
-
|
87
|
-
|
88
|
-
|
89
|
-
|
83
|
+
params :update_segment_klass_params do
|
84
|
+
requires :id, type: Integer, desc: 'Segment Klass ID'
|
85
|
+
optional :label, type: String, desc: 'Segment Klass Label'
|
86
|
+
optional :desc, type: String, desc: 'Segment Klass Desc'
|
87
|
+
optional :place, type: String, desc: 'Segment Klass Place', default: '100'
|
88
|
+
optional :identifier, type: String, desc: 'Segment Identifier'
|
89
|
+
end
|
90
90
|
|
91
|
-
|
92
|
-
|
93
|
-
|
94
|
-
|
95
|
-
|
96
|
-
|
97
|
-
|
91
|
+
params :create_segment_klass_params do
|
92
|
+
requires :label, type: String, desc: 'Segment Klass Label'
|
93
|
+
requires :element_klass, type: Integer, desc: 'Element Klass Id'
|
94
|
+
optional :desc, type: String, desc: 'Segment Klass Desc'
|
95
|
+
optional :place, type: String, desc: 'Segment Klass Place', default: '100'
|
96
|
+
optional :properties_template, type: Hash, desc: 'Element Klass properties template'
|
97
|
+
end
|
98
|
+
|
99
|
+
params :create_std_layer_params do
|
100
|
+
requires :name, type: String, desc: 'Element Klass Name'
|
101
|
+
requires :label, type: String, desc: 'Element Klass Label'
|
102
|
+
requires :klass_prefix, type: String, desc: 'Element Klass Short Label Prefix'
|
103
|
+
optional :icon_name, type: String, desc: 'Element Klass Icon Name'
|
104
|
+
optional :desc, type: String, desc: 'Element Klass Desc'
|
105
|
+
optional :properties_template, type: Hash, desc: 'Element Klass properties template'
|
106
|
+
end
|
107
|
+
|
108
|
+
params :std_layer_save do
|
109
|
+
requires :key, type: String, desc: 'key'
|
110
|
+
requires :cols, type: Integer, desc: 'key'
|
111
|
+
requires :label, type: String, desc: 'Label'
|
112
|
+
optional :position, type: Integer, desc: 'position'
|
113
|
+
optional :wf_position, type: Integer, desc: 'wf position'
|
114
|
+
optional :fields, type: Array, desc: 'fields'
|
115
|
+
optional :select_options, type: Hash, desc: 'selections'
|
116
|
+
end
|
117
|
+
|
118
|
+
params :std_layer_criteria do
|
119
|
+
requires :name, type: String, desc: 'Layer name'
|
120
|
+
end
|
121
|
+
|
122
|
+
params :vocab_save do
|
123
|
+
optional :name, type: String, desc: 'field'
|
124
|
+
optional :label, type: String, desc: 'Label'
|
125
|
+
optional :term_id, type: String, desc: 'ontology term_id'
|
126
|
+
requires :ontology, type: Hash, desc: 'ontology'
|
127
|
+
optional :source, type: String, desc: 'source'
|
128
|
+
optional :source_id, type: String, desc: 'source_id'
|
129
|
+
optional :layer_id, type: String, desc: 'layer_id'
|
130
|
+
optional :sub_fields, type: Array, desc: 'sub_fields'
|
131
|
+
optional :text_sub_fields, type: Array, desc: 'text_sub_fields'
|
132
|
+
requires :field_type, type: String, desc: 'field type'
|
133
|
+
requires :voc, type: Hash, desc: 'vocabulary references'
|
134
|
+
optional :select_options, type: Hash, desc: 'selections'
|
135
|
+
optional :option_layers, type: String, desc: 'option'
|
136
|
+
end
|
137
|
+
|
138
|
+
# params :vocabulary_save do
|
139
|
+
# requires :type, type: String, desc: 'type'
|
140
|
+
# requires :field, type: String, desc: 'field'
|
141
|
+
# optional :default, type: String, desc: 'default'
|
142
|
+
# optional :description, type: String, desc: 'description'
|
143
|
+
# optional :label, type: String, desc: 'label'
|
144
|
+
# optional :position, type: Integer, desc: 'position'
|
145
|
+
# optional :ontology, type: Hash, desc: 'ontology'
|
146
|
+
# optional :required, type: Boolean, desc: 'is required?'
|
147
|
+
# optional :sub_fields, type: Array, desc: 'sub_fields'
|
148
|
+
# optional :text_sub_fields, type: Array, desc: 'text_sub_fields'
|
149
|
+
# optional :source_type, type: String, desc: 'source type'
|
150
|
+
# optional :source_id, type: String, desc: 'source id'
|
151
|
+
# optional :layer_id, type: String, desc: 'layer id'
|
152
|
+
# end
|
98
153
|
end
|
99
|
-
end
|
154
|
+
end
|
@@ -72,7 +72,7 @@ module Labimotion
|
|
72
72
|
# el_attributes['properties_template'] = response['element_klass']['properties_release']
|
73
73
|
# Labimotion::ElementKlass.create!(el_attributes)
|
74
74
|
attributes['element_klass_id'] = element_klass.id
|
75
|
-
segment_klass = Labimotion::SegmentKlass.find_by(identifier: attributes['identifier'])
|
75
|
+
segment_klass = Labimotion::SegmentKlass.find_by(identifier: attributes['identifier']) if attributes['identifier'].present?
|
76
76
|
if segment_klass.present?
|
77
77
|
if segment_klass['uuid'] == attributes['uuid'] && segment_klass['version'] == attributes['version']
|
78
78
|
return { status: 'success', message: "This segment: #{attributes['label']} has the latest version!" }
|
@@ -0,0 +1,16 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module Labimotion
|
4
|
+
# Helper for associated sample
|
5
|
+
module VocabularyHelpers
|
6
|
+
extend Grape::API::Helpers
|
7
|
+
|
8
|
+
def update_vocabularies(properties, current_user, element)
|
9
|
+
Labimotion::VocabularyHandler.update_vocabularies(properties, current_user, element)
|
10
|
+
rescue StandardError => e
|
11
|
+
Labimotion.log_exception(e, current_user)
|
12
|
+
properties
|
13
|
+
end
|
14
|
+
|
15
|
+
end
|
16
|
+
end
|
@@ -28,7 +28,7 @@ module Labimotion
|
|
28
28
|
dsr = []
|
29
29
|
ols = nil
|
30
30
|
Zip::File.open(att.attachment_attacher.file.url) do |zip_file|
|
31
|
-
res = Labimotion::Converter.collect_metadata(zip_file) if att.filename.split('.')&.last == 'zip'
|
31
|
+
res = Labimotion::Converter.collect_metadata(zip_file, current_user) if att.filename.split('.')&.last == 'zip'
|
32
32
|
ols = res[:o] unless res&.dig(:o).nil?
|
33
33
|
dsr.push(res[:d]) unless res&.dig(:d).nil?
|
34
34
|
end
|
@@ -92,7 +92,7 @@ module Labimotion
|
|
92
92
|
{ a: oa, f: folder }
|
93
93
|
end
|
94
94
|
|
95
|
-
def self.collect_metadata(zip_file) # rubocop: disable Metrics/PerceivedComplexity
|
95
|
+
def self.collect_metadata(zip_file, current_user = {}) # rubocop: disable Metrics/PerceivedComplexity
|
96
96
|
dsr = []
|
97
97
|
ols = nil
|
98
98
|
zip_file.each do |entry|
|
@@ -114,7 +114,7 @@ module Labimotion
|
|
114
114
|
{ d: dsr, o: ols }
|
115
115
|
end
|
116
116
|
|
117
|
-
def self.handle_response(oat, response) # rubocop: disable Metrics/PerceivedComplexity
|
117
|
+
def self.handle_response(oat, response, current_user = {}) # rubocop: disable Metrics/PerceivedComplexity
|
118
118
|
dsr = []
|
119
119
|
ols = nil
|
120
120
|
|
@@ -123,10 +123,9 @@ module Labimotion
|
|
123
123
|
tmp_file.write(response.parsed_response)
|
124
124
|
tmp_file.rewind
|
125
125
|
|
126
|
-
name = response&.headers && response&.headers['content-disposition']&.split('=')&.last
|
126
|
+
# name = response&.headers && response&.headers['content-disposition']&.split('=')&.last
|
127
127
|
filename = oat.filename
|
128
128
|
name = "#{File.basename(filename, '.*')}.zip"
|
129
|
-
|
130
129
|
att = Attachment.new(
|
131
130
|
filename: name,
|
132
131
|
file_path: tmp_file.path,
|
@@ -140,7 +139,7 @@ module Labimotion
|
|
140
139
|
|
141
140
|
att.save! if att.valid?
|
142
141
|
|
143
|
-
process_ds(att.id)
|
142
|
+
process_ds(att.id, current_user)
|
144
143
|
rescue StandardError => e
|
145
144
|
raise e
|
146
145
|
ensure
|
@@ -148,7 +147,7 @@ module Labimotion
|
|
148
147
|
end
|
149
148
|
end
|
150
149
|
|
151
|
-
def self.process(data)
|
150
|
+
def self.process(data, current_user = {}) # rubocop: disable Metrics/PerceivedComplexity
|
152
151
|
return data[:a].con_state if data[:a]&.attachable_type != 'Container'
|
153
152
|
response = nil
|
154
153
|
begin
|
@@ -165,25 +164,25 @@ module Labimotion
|
|
165
164
|
)
|
166
165
|
end
|
167
166
|
if response.ok?
|
168
|
-
Labimotion::Converter.handle_response(data[:a], response)
|
167
|
+
Labimotion::Converter.handle_response(data[:a], response, current_user)
|
169
168
|
Labimotion::ConState::PROCESSED
|
170
169
|
else
|
171
170
|
Labimotion::Converter.logger.error ["Converter Response Error: id: [#{data[:a]&.id}], filename: [#{data[:a]&.filename}], response: #{response}"].join($INPUT_RECORD_SEPARATOR)
|
172
171
|
Labimotion::ConState::ERROR
|
173
172
|
end
|
174
173
|
rescue StandardError => e
|
175
|
-
Labimotion::Converter.logger.error ["process fail:
|
174
|
+
Labimotion::Converter.logger.error ["process fail: #{data[:a]&.id}", e.message, *e.backtrace].join($INPUT_RECORD_SEPARATOR)
|
176
175
|
Labimotion::ConState::ERROR
|
177
176
|
ensure
|
178
177
|
FileUtils.rm_f(ofile)
|
179
178
|
end
|
180
179
|
end
|
181
180
|
|
182
|
-
def self.jcamp_converter(id)
|
181
|
+
def self.jcamp_converter(id, current_user = {})
|
183
182
|
data = Labimotion::Converter.vor_conv(id)
|
184
183
|
return if data.nil?
|
185
184
|
|
186
|
-
Labimotion::Converter.process(data)
|
185
|
+
Labimotion::Converter.process(data, current_user)
|
187
186
|
rescue StandardError => e
|
188
187
|
Labimotion::Converter.logger.error ["jcamp_converter fail: #{id}", e.message, *e.backtrace].join($INPUT_RECORD_SEPARATOR)
|
189
188
|
Labimotion::ConState::ERROR
|
@@ -243,27 +242,8 @@ module Labimotion
|
|
243
242
|
fi['device'] = ds[:device] || ds[:value]
|
244
243
|
new_prop[Labimotion::Prop::LAYERS][ds[:layer]][Labimotion::Prop::FIELDS][idx] = fi
|
245
244
|
end
|
246
|
-
new_prop.dig(Labimotion::Prop::LAYERS, 'general', Labimotion::Prop::FIELDS)&.each_with_index do |fi, idx|
|
247
|
-
if fi['field'] == 'creator' && current_user.present?
|
248
|
-
fi['value'] = current_user.name
|
249
|
-
fi['system'] = current_user.name
|
250
|
-
new_prop[Labimotion::Prop::LAYERS]['general'][Labimotion::Prop::FIELDS][idx] = fi
|
251
|
-
end
|
252
|
-
end
|
253
245
|
element = Container.find(dataset.element_id)&.root_element
|
254
|
-
|
255
|
-
if fi['field'] == 'id'
|
256
|
-
fi['value'] = element.id
|
257
|
-
fi['system'] = element.id
|
258
|
-
new_prop[Labimotion::Prop::LAYERS]['sample_details'][Labimotion::Prop::FIELDS][idx] = fi
|
259
|
-
end
|
260
|
-
|
261
|
-
if fi['field'] == 'label'
|
262
|
-
fi['value'] = element.short_label
|
263
|
-
fi['system'] = element.short_label
|
264
|
-
new_prop[Labimotion::Prop::LAYERS]['sample_details'][Labimotion::Prop::FIELDS][idx] = fi
|
265
|
-
end
|
266
|
-
end
|
246
|
+
new_prop = Labimotion::VocabularyHandler.update_vocabularies(new_prop, current_user, element)
|
267
247
|
dataset.properties = new_prop
|
268
248
|
dataset.save!
|
269
249
|
end
|
@@ -325,13 +305,13 @@ module Labimotion
|
|
325
305
|
res
|
326
306
|
end
|
327
307
|
|
328
|
-
def self.metadata(id)
|
308
|
+
def self.metadata(id, current_user)
|
329
309
|
att = Attachment.find(id)
|
330
310
|
return if att.nil? || att.attachable_id.nil? || att.attachable_type != Labimotion::Prop::CONTAINER
|
331
311
|
|
332
312
|
ds = Labimotion::Dataset.find_by(element_type: Labimotion::Prop::CONTAINER, element_id: att.attachable_id)
|
333
313
|
att.update_column(:con_state, Labimotion::ConState::COMPLETED) if ds.present?
|
334
|
-
process_ds(att.id) if ds.nil?
|
314
|
+
process_ds(att.id, current_user) if ds.nil?
|
335
315
|
end
|
336
316
|
end
|
337
317
|
end
|