his_emr_api_lab 1.1.1 → 1.1.5
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/app/jobs/lab/update_patient_orders_job.rb +16 -3
- data/app/services/lab/lims/api/couchdb_api.rb +3 -0
- data/app/services/lab/lims/api/rest_api.rb +92 -28
- data/app/services/lab/lims/config.rb +11 -11
- data/app/services/lab/lims/order_dto.rb +8 -3
- data/app/services/lab/lims/order_serializer.rb +3 -4
- data/app/services/lab/lims/pull_worker.rb +2 -2
- data/app/services/lab/lims/push_worker.rb +8 -2
- data/app/services/lab/lims/worker.rb +13 -6
- data/app/services/lab/metadata.rb +1 -0
- data/app/services/lab/orders_search_service.rb +4 -2
- data/app/services/lab/orders_service.rb +31 -17
- data/lib/lab/version.rb +1 -1
- data/lib/tasks/loaders/data/reasons-for-test.csv +1 -0
- data/lib/tasks/loaders/data/tests.csv +0 -2
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 960dc05ef6fbcddc4538762d7c7f3369e77d2f24b879e14a110ffa4ab2141d22
|
4
|
+
data.tar.gz: 666ea51bb7ff2938b6d4fd733a619a49cf600aed37c330c8be3f9680bdc4e94e
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 3ba9d9cb6d59d656b8d72190d6ecb1bcf6c193fdeb22121608ec39fb2fbb77e1b11e2b53d45d8937f6969cb1212e1adb045bb4a53e76f1eefa825731c2abcb98
|
7
|
+
data.tar.gz: 6e27abac8e38b86238adecf6eec31e3cad2503b5d46e534b498b47cad563cf15ebacf74fdc66c552338ebc584e3f08c331480cb57be14df5951c297ce642a44a
|
@@ -12,9 +12,22 @@ module Lab
|
|
12
12
|
User.current = Lab::Lims::Utils.lab_user
|
13
13
|
Location.current = Location.find_by_name('ART clinic')
|
14
14
|
|
15
|
-
|
16
|
-
|
17
|
-
|
15
|
+
lockfile = Rails.root.join('tmp', "update-patient-orders-#{patient_id}.lock")
|
16
|
+
|
17
|
+
done = File.open(lockfile, File::RDWR | File::CREAT) do |lock|
|
18
|
+
unless lock.flock(File::LOCK_NB | File::LOCK_EX)
|
19
|
+
Rails.logger.info('Another update patient job is already running...')
|
20
|
+
break false
|
21
|
+
end
|
22
|
+
|
23
|
+
lims_api = Lab::Lims::Api::RestApi.new(Lab::Lims::Config.rest_api)
|
24
|
+
worker = Lab::Lims::PullWorker.new(lims_api)
|
25
|
+
worker.pull_orders(patient_id: patient_id)
|
26
|
+
|
27
|
+
true
|
28
|
+
end
|
29
|
+
|
30
|
+
File.unlink(lockfile) if done
|
18
31
|
end
|
19
32
|
end
|
20
33
|
end
|
@@ -22,14 +22,13 @@ class Lab::Lims::Api::RestApi
|
|
22
22
|
end
|
23
23
|
end
|
24
24
|
|
25
|
-
|
26
|
-
|
27
|
-
data = JSON.parse(response.body)['data']
|
25
|
+
data = JSON.parse(response.body)
|
26
|
+
update_order_results(order_dto) unless data['message'].casecmp?('Order already available')
|
28
27
|
|
29
28
|
ActiveSupport::HashWithIndifferentAccess.new(
|
30
|
-
id:
|
29
|
+
id: order_dto.fetch(:_id, order_dto[:tracking_number]),
|
31
30
|
rev: 0,
|
32
|
-
tracking_number:
|
31
|
+
tracking_number: order_dto[:tracking_number]
|
33
32
|
)
|
34
33
|
end
|
35
34
|
|
@@ -44,21 +43,25 @@ class Lab::Lims::Api::RestApi
|
|
44
43
|
end
|
45
44
|
|
46
45
|
def consume_orders(*_args, patient_id: nil, **_kwargs)
|
47
|
-
|
48
|
-
|
46
|
+
orders_pending_updates(patient_id).each do |order|
|
47
|
+
order_dto = Lab::Lims::OrderSerializer.serialize_order(order)
|
49
48
|
|
50
|
-
|
51
|
-
|
52
|
-
Rails.logger.info("Fetching results for order ##{order.accession_number}")
|
53
|
-
RestClient.get(expand_uri("query_results_by_tracking_number/#{order.accession_number}"), headers)
|
49
|
+
if order_dto['priority'].nil? || order_dto['sample_type'].casecmp?('not_specified')
|
50
|
+
patch_order_dto_with_lims_order!(order_dto, find_lims_order(order.accession_number))
|
54
51
|
end
|
55
52
|
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
53
|
+
if order_dto['test_results'].empty?
|
54
|
+
begin
|
55
|
+
patch_order_dto_with_lims_results!(order_dto, find_lims_results(order.accession_number))
|
56
|
+
rescue InvalidParameters => e # LIMS responds with a 401 when a result is not found :(
|
57
|
+
Rails.logger.error("Failed to fetch results for ##{order.accession_number}: #{e.message}")
|
58
|
+
end
|
59
|
+
end
|
60
|
+
|
61
|
+
yield order_dto, OpenStruct.new(last_seq: 0)
|
62
|
+
rescue LimsApiError => e
|
63
|
+
Rails.logger.error("Failed to fetch updates for ##{order.accession_number}: #{e.class} - #{e.message}")
|
64
|
+
sleep(1)
|
62
65
|
end
|
63
66
|
end
|
64
67
|
|
@@ -105,8 +108,8 @@ class Lab::Lims::Api::RestApi
|
|
105
108
|
self.authentication_token = nil
|
106
109
|
retry if (retries -= 1).positive?
|
107
110
|
rescue RestClient::ExceptionWithResponse => e
|
108
|
-
Rails.logger.error("LIMS Error: #{e.response
|
109
|
-
raise e unless e.response
|
111
|
+
Rails.logger.error("LIMS Error: #{e.response&.code} - #{e.response&.body}")
|
112
|
+
raise e unless e.response&.code == 401
|
110
113
|
|
111
114
|
self.authentication_token = nil
|
112
115
|
retry if (retries -= 1).positive?
|
@@ -117,7 +120,8 @@ class Lab::Lims::Api::RestApi
|
|
117
120
|
password = config.fetch(:password)
|
118
121
|
|
119
122
|
Rails.logger.debug("Authenticating with LIMS as: #{username}")
|
120
|
-
response = RestClient.get(expand_uri("re_authenticate/#{username}/#{password}"),
|
123
|
+
response = RestClient.get(expand_uri("re_authenticate/#{username}/#{password}"),
|
124
|
+
headers: { 'Content-type' => 'application/json' })
|
121
125
|
response_body = JSON.parse(response.body)
|
122
126
|
|
123
127
|
if response_body['status'] == 401
|
@@ -153,9 +157,7 @@ class Lab::Lims::Api::RestApi
|
|
153
157
|
|
154
158
|
Rails.logger.error("Lims Api Error: #{response.body}")
|
155
159
|
|
156
|
-
if body['status'] != 401
|
157
|
-
raise LimsApiError, "#{body['status']} - #{body['message']}"
|
158
|
-
end
|
160
|
+
raise LimsApiError, "#{body['status']} - #{body['message']}" if body['status'] != 401
|
159
161
|
|
160
162
|
if body['message'].match?(/token expired/i)
|
161
163
|
raise AuthenticationTokenExpired, "Authentication token expired: #{body['message']}"
|
@@ -255,11 +257,31 @@ class Lab::Lims::Api::RestApi
|
|
255
257
|
"#{orderer[:first_name]} #{orderer[:last_name]}"
|
256
258
|
end
|
257
259
|
|
260
|
+
def find_lims_order(tracking_number)
|
261
|
+
response = in_authenticated_session do |headers|
|
262
|
+
Rails.logger.info("Fetching order ##{tracking_number}")
|
263
|
+
RestClient.get(expand_uri("query_order_by_tracking_number/#{tracking_number}"), headers)
|
264
|
+
end
|
265
|
+
|
266
|
+
Rails.logger.info("Order ##{tracking_number} found... Parsing...")
|
267
|
+
JSON.parse(response).fetch('data')
|
268
|
+
end
|
269
|
+
|
270
|
+
def find_lims_results(tracking_number)
|
271
|
+
response = in_authenticated_session do |headers|
|
272
|
+
Rails.logger.info("Fetching results for order ##{tracking_number}")
|
273
|
+
RestClient.get(expand_uri("query_results_by_tracking_number/#{tracking_number}"), headers)
|
274
|
+
end
|
275
|
+
|
276
|
+
Rails.logger.info("Result for order ##{tracking_number} found... Parsing...")
|
277
|
+
JSON.parse(response).fetch('data').fetch('results')
|
278
|
+
end
|
279
|
+
|
258
280
|
##
|
259
281
|
# Make a copy of the order_dto with the results from LIMS parsed
|
260
282
|
# and appended to it.
|
261
|
-
def
|
262
|
-
order_dto.merge(
|
283
|
+
def patch_order_dto_with_lims_results!(order_dto, results)
|
284
|
+
order_dto.merge!(
|
263
285
|
'_id' => order_dto[:tracking_number],
|
264
286
|
'_rev' => 0,
|
265
287
|
'test_results' => results.each_with_object({}) do |result, formatted_results|
|
@@ -277,10 +299,16 @@ class Lab::Lims::Api::RestApi
|
|
277
299
|
)
|
278
300
|
end
|
279
301
|
|
302
|
+
def patch_order_dto_with_lims_order!(order_dto, lims_order)
|
303
|
+
order_dto.merge!(
|
304
|
+
'sample_type' => lims_order['other']['sample_type'],
|
305
|
+
'sample_status' => lims_order['other']['specimen_status'],
|
306
|
+
'priority' => lims_order['other']['priority']
|
307
|
+
)
|
308
|
+
end
|
309
|
+
|
280
310
|
def update_order_results(order_dto)
|
281
|
-
if order_dto['test_results'].nil? || order_dto['test_results'].empty?
|
282
|
-
return nil
|
283
|
-
end
|
311
|
+
return nil if order_dto['test_results'].nil? || order_dto['test_results'].empty?
|
284
312
|
|
285
313
|
order_dto['test_results'].each do |test_name, results|
|
286
314
|
Rails.logger.info("Pushing result for order ##{order_dto['tracking_number']}")
|
@@ -341,4 +369,40 @@ class Lab::Lims::Api::RestApi
|
|
341
369
|
test_status: 'voided'
|
342
370
|
}
|
343
371
|
end
|
372
|
+
|
373
|
+
def orders_pending_updates(patient_id = nil)
|
374
|
+
Rails.logger.info('Looking for orders that need to be updated...')
|
375
|
+
orders = {}
|
376
|
+
|
377
|
+
orders_without_specimen(patient_id).each { |order| orders[order.order_id] = order }
|
378
|
+
orders_without_results(patient_id).each { |order| orders[order.order_id] = order }
|
379
|
+
orders_without_reason(patient_id).each { |order| orders[order.order_id] = order }
|
380
|
+
|
381
|
+
orders.values
|
382
|
+
end
|
383
|
+
|
384
|
+
def orders_without_specimen(patient_id = nil)
|
385
|
+
Rails.logger.debug('Looking for orders without a specimen')
|
386
|
+
unknown_specimen = ConceptName.where(name: Lab::Metadata::UNKNOWN_SPECIMEN)
|
387
|
+
.select(:concept_id)
|
388
|
+
orders = Lab::LabOrder.where(concept_id: unknown_specimen)
|
389
|
+
orders = orders.where(patient_id: patient_id) if patient_id
|
390
|
+
|
391
|
+
orders
|
392
|
+
end
|
393
|
+
|
394
|
+
def orders_without_results(patient_id = nil)
|
395
|
+
Rails.logger.debug('Looking for orders without a result')
|
396
|
+
Lab::OrdersSearchService.find_orders_without_results(patient_id: patient_id)
|
397
|
+
end
|
398
|
+
|
399
|
+
def orders_without_reason(patient_id = nil)
|
400
|
+
Rails.logger.debug('Looking for orders without a reason for test')
|
401
|
+
orders = Lab::LabOrder.joins(:reason_for_test)
|
402
|
+
.merge(Observation.where(value_coded: nil, value_text: nil))
|
403
|
+
.limit(1000)
|
404
|
+
orders = orders.where(patient_id: patient_id) if patient_id
|
405
|
+
|
406
|
+
orders
|
407
|
+
end
|
344
408
|
end
|
@@ -11,15 +11,19 @@ module Lab
|
|
11
11
|
class ConfigNotFound < RuntimeError; end
|
12
12
|
|
13
13
|
class << self
|
14
|
+
def preferred_api
|
15
|
+
emr_api_application('lims_api', 'couchdb')
|
16
|
+
end
|
17
|
+
|
14
18
|
##
|
15
19
|
# Returns LIMS' couchdb configuration file for the current environment (Rails.env)
|
16
20
|
def couchdb
|
17
21
|
config_path = begin
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
22
|
+
find_config_path('couchdb.yml')
|
23
|
+
rescue ConfigNotFound => e
|
24
|
+
Rails.logger.error("Failed to find default LIMS couchdb config: #{e.message}")
|
25
|
+
find_config_path('couchdb-lims.yml') # This can be placed in HIS-EMR-API/config
|
26
|
+
end
|
23
27
|
|
24
28
|
Rails.logger.debug("Using LIMS couchdb config: #{config_path}")
|
25
29
|
|
@@ -64,9 +68,7 @@ module Lab
|
|
64
68
|
@emr_api_application ||= YAML.load_file(Rails.root.join('config', 'application.yml'))
|
65
69
|
|
66
70
|
@emr_api_application.fetch(param) do
|
67
|
-
unless fallback
|
68
|
-
raise ConfigNotFound, "Missing config param: #{param}"
|
69
|
-
end
|
71
|
+
raise ConfigNotFound, "Missing config param: #{param}" unless fallback
|
70
72
|
|
71
73
|
fallback
|
72
74
|
end
|
@@ -83,9 +85,7 @@ module Lab
|
|
83
85
|
Rails.root.parent.join("nlims_controller/config/#{filename}")
|
84
86
|
]
|
85
87
|
|
86
|
-
if filename == 'couchdb.yml'
|
87
|
-
paths = [Rails.root.join('config/lims-couchdb.yml'), *paths]
|
88
|
-
end
|
88
|
+
paths = [Rails.root.join('config/lims-couchdb.yml'), *paths] if filename == 'couchdb.yml'
|
89
89
|
|
90
90
|
paths.each do |path|
|
91
91
|
Rails.logger.debug("Looking for LIMS couchdb config at: #{path}")
|
@@ -22,7 +22,7 @@ module Lab
|
|
22
22
|
date: start_date,
|
23
23
|
target_lab: facility_name(self['receiving_facility']),
|
24
24
|
order_location: facility_name(self['sending_facility']),
|
25
|
-
|
25
|
+
reason_for_test_id: reason_for_test
|
26
26
|
)
|
27
27
|
end
|
28
28
|
|
@@ -83,9 +83,14 @@ module Lab
|
|
83
83
|
|
84
84
|
# Translates a LIMS sample priority to a concept_id
|
85
85
|
def reason_for_test
|
86
|
-
return
|
86
|
+
return nil unless self['priority']
|
87
87
|
|
88
|
-
|
88
|
+
name = case self['priority']
|
89
|
+
when %r{Reapet / Missing}i then 'Repeat / Missing'
|
90
|
+
else self['priority']
|
91
|
+
end
|
92
|
+
|
93
|
+
ConceptName.find_by_name!(name).concept_id
|
89
94
|
end
|
90
95
|
|
91
96
|
def lab_program
|
@@ -16,6 +16,7 @@ module Lab
|
|
16
16
|
serialized_order = Lims::Utils.structify(Lab::LabOrderSerializer.serialize_order(order))
|
17
17
|
|
18
18
|
Lims::OrderDTO.new(
|
19
|
+
_id: Lab::LimsOrderMapping.find_by(order: order)&.lims_id || serialized_order.accession_number,
|
19
20
|
tracking_number: serialized_order.accession_number,
|
20
21
|
sending_facility: current_facility_name,
|
21
22
|
receiving_facility: serialized_order.target_lab,
|
@@ -63,7 +64,7 @@ module Lab
|
|
63
64
|
first_name: name&.given_name,
|
64
65
|
last_name: name&.family_name,
|
65
66
|
id: national_id&.identifier,
|
66
|
-
phone_number: phone_number&.value,
|
67
|
+
phone_number: phone_number&.value || 'Unknown',
|
67
68
|
gender: person.gender,
|
68
69
|
email: nil
|
69
70
|
}
|
@@ -82,9 +83,7 @@ module Lab
|
|
82
83
|
end
|
83
84
|
|
84
85
|
def format_sample_status_trail(order)
|
85
|
-
if order.concept_id == ConceptName.find_by_name!('Unknown').concept_id
|
86
|
-
return []
|
87
|
-
end
|
86
|
+
return [] if order.concept_id == ConceptName.find_by_name!('Unknown').concept_id
|
88
87
|
|
89
88
|
user = User.find(order.discontinued_by || order.creator)
|
90
89
|
drawn_by = PersonName.find_by_person_id(user.user_id)
|
@@ -176,7 +176,7 @@ module Lab
|
|
176
176
|
def update_order(patient, order_id, order_dto)
|
177
177
|
logger.debug("Updating order ##{order_dto['_id']}")
|
178
178
|
order = OrdersService.update_order(order_id, order_dto.to_order_service_params(patient_id: patient.patient_id)
|
179
|
-
.merge(force_update: true))
|
179
|
+
.merge(force_update: 'true'))
|
180
180
|
unless order_dto['test_results'].empty?
|
181
181
|
update_results(order, order_dto['test_results'])
|
182
182
|
end
|
@@ -194,7 +194,7 @@ module Lab
|
|
194
194
|
next
|
195
195
|
end
|
196
196
|
|
197
|
-
next
|
197
|
+
next if test.result || test_results['results'].blank?
|
198
198
|
|
199
199
|
measures = test_results['results'].map do |indicator, value|
|
200
200
|
measure = find_measure(order, indicator, value)
|
@@ -17,7 +17,12 @@ module Lab
|
|
17
17
|
loop do
|
18
18
|
logger.info('Looking for new orders to push to LIMS...')
|
19
19
|
orders = orders_pending_sync(batch_size).all
|
20
|
-
orders.each
|
20
|
+
orders.each do |order|
|
21
|
+
push_order(order)
|
22
|
+
rescue GatewayError => e
|
23
|
+
logger.error("Failed to push order ##{order.accession_number}: #{e.class} - #{e.message}")
|
24
|
+
sleep(Lab::Lims::Config.updates_poll_frequency)
|
25
|
+
end
|
21
26
|
|
22
27
|
# Doing this after .each above to stop ActiveRecord from executing
|
23
28
|
# an extra request to the database (ActiveRecord's lazy evaluation
|
@@ -56,7 +61,8 @@ module Lab
|
|
56
61
|
else
|
57
62
|
Rails.logger.info("Creating order ##{order_dto['accession_number']} in LIMS")
|
58
63
|
update = lims_api.create_order(order_dto)
|
59
|
-
Lab::LimsOrderMapping.create!(order: order, lims_id: update['id'], revision: update['rev'],
|
64
|
+
Lab::LimsOrderMapping.create!(order: order, lims_id: update['id'], revision: update['rev'],
|
65
|
+
pushed_at: Time.now)
|
60
66
|
end
|
61
67
|
end
|
62
68
|
|
@@ -2,6 +2,8 @@
|
|
2
2
|
|
3
3
|
require 'logger_multiplexor'
|
4
4
|
|
5
|
+
require_relative './api/couchdb_api'
|
6
|
+
|
5
7
|
module Lab
|
6
8
|
module Lims
|
7
9
|
##
|
@@ -19,8 +21,7 @@ module Lab
|
|
19
21
|
|
20
22
|
def self.start_push_worker
|
21
23
|
start_worker('push_worker') do
|
22
|
-
|
23
|
-
worker = PushWorker.new(api)
|
24
|
+
worker = PushWorker.new(lims_api)
|
24
25
|
|
25
26
|
worker.push_orders # (wait: true)
|
26
27
|
end
|
@@ -28,8 +29,7 @@ module Lab
|
|
28
29
|
|
29
30
|
def self.start_pull_worker
|
30
31
|
start_worker('pull_worker') do
|
31
|
-
|
32
|
-
worker = PullWorker.new(api)
|
32
|
+
worker = PullWorker.new(lims_api)
|
33
33
|
|
34
34
|
worker.pull_orders
|
35
35
|
end
|
@@ -37,8 +37,7 @@ module Lab
|
|
37
37
|
|
38
38
|
def self.start_realtime_pull_worker
|
39
39
|
start_worker('realtime_pull_worker') do
|
40
|
-
|
41
|
-
worker = PullWorker.new(api)
|
40
|
+
worker = PullWorker.new(Lims::Api::WsApi.new(Lab::Lims::Config.updates_socket))
|
42
41
|
|
43
42
|
worker.pull_orders
|
44
43
|
end
|
@@ -71,6 +70,14 @@ module Lab
|
|
71
70
|
Rails.logger.warn("Check for realtime updates failed: #{e.message}")
|
72
71
|
false
|
73
72
|
end
|
73
|
+
|
74
|
+
def self.lims_api
|
75
|
+
case Lims::Config.preferred_api
|
76
|
+
when /couchdb/i then Api::CouchDbApi.new(config: Lab::Lims::Config.couchdb)
|
77
|
+
when /rest/i then Api::RestApi.new(Lab::Lims::Config.rest_api)
|
78
|
+
else raise "Invalid LIMS API in application.yml, expected 'rest' or 'couchdb'"
|
79
|
+
end
|
80
|
+
end
|
74
81
|
end
|
75
82
|
end
|
76
83
|
end
|
@@ -26,8 +26,10 @@ module Lab
|
|
26
26
|
end
|
27
27
|
|
28
28
|
def find_orders_without_results(patient_id: nil)
|
29
|
-
|
30
|
-
|
29
|
+
results_query = Lab::LabResult.all
|
30
|
+
results_query = results_query.where(person_id: patient_id) if patient_id
|
31
|
+
|
32
|
+
query = Lab::LabOrder.where.not(order_id: results_query.select(:order_id))
|
31
33
|
query = query.where(patient_id: patient_id) if patient_id
|
32
34
|
|
33
35
|
query
|
@@ -66,20 +66,27 @@ module Lab
|
|
66
66
|
|
67
67
|
def update_order(order_id, params)
|
68
68
|
specimen_id = params.dig(:specimen, :concept_id)
|
69
|
-
unless specimen_id
|
70
|
-
raise ::InvalidParameterError, 'Specimen concept_id is required'
|
71
|
-
end
|
69
|
+
raise ::InvalidParameterError, 'Specimen concept_id is required' unless specimen_id
|
72
70
|
|
73
71
|
order = Lab::LabOrder.find(order_id)
|
74
|
-
|
75
|
-
raise ::UnprocessableEntityError
|
72
|
+
if order.concept_id != unknown_concept_id && !params[:force_update]&.casecmp?('true')
|
73
|
+
raise ::UnprocessableEntityError, "Can't change order specimen once set"
|
74
|
+
end
|
75
|
+
|
76
|
+
if specimen_id.to_i != order.concept_id
|
77
|
+
Rails.logger.debug("Updating order ##{order.order_id}")
|
78
|
+
order.update!(concept_id: specimen_id,
|
79
|
+
discontinued: true,
|
80
|
+
discontinued_by: User.current.user_id,
|
81
|
+
discontinued_date: params[:date]&.to_date || Time.now,
|
82
|
+
discontinued_reason_non_coded: 'Sample drawn/updated')
|
83
|
+
end
|
84
|
+
|
85
|
+
if params[:reason_for_test_id]
|
86
|
+
Rails.logger.debug("Updating reason for test on order ##{order.order_id}")
|
87
|
+
update_reason_for_test(order, params[:reason_for_test_id])
|
76
88
|
end
|
77
89
|
|
78
|
-
order.update!(concept_id: specimen_id,
|
79
|
-
discontinued: true,
|
80
|
-
discontinued_by: User.current.user_id,
|
81
|
-
discontinued_date: params[:date]&.to_date || Time.now,
|
82
|
-
discontinued_reason_non_coded: 'Sample drawn/updated')
|
83
90
|
Lab::LabOrderSerializer.serialize_order(order)
|
84
91
|
end
|
85
92
|
|
@@ -107,13 +114,9 @@ module Lab
|
|
107
114
|
# a 'Lab' encounter is created using the provided program_id and
|
108
115
|
# patient_id.
|
109
116
|
def find_encounter(order_params)
|
110
|
-
if order_params[:encounter_id]
|
111
|
-
return Encounter.find(order_params[:encounter_id])
|
112
|
-
end
|
117
|
+
return Encounter.find(order_params[:encounter_id]) if order_params[:encounter_id]
|
113
118
|
|
114
|
-
unless order_params[:patient_id]
|
115
|
-
raise InvalidParameterError, 'encounter_id or patient_id required'
|
116
|
-
end
|
119
|
+
raise InvalidParameterError, 'encounter_id or patient_id required' unless order_params[:patient_id]
|
117
120
|
|
118
121
|
program_id = order_params[:program_id] || Program.find_by_name!(Lab::Metadata::LAB_PROGRAM_NAME).program_id
|
119
122
|
|
@@ -159,7 +162,7 @@ module Lab
|
|
159
162
|
order,
|
160
163
|
Lab::Metadata::REASON_FOR_TEST_CONCEPT_NAME,
|
161
164
|
params[:date],
|
162
|
-
value_coded: params[
|
165
|
+
value_coded: params[:reason_for_test_id]
|
163
166
|
)
|
164
167
|
end
|
165
168
|
|
@@ -192,6 +195,17 @@ module Lab
|
|
192
195
|
def unknown_concept_id
|
193
196
|
ConceptName.find_by_name!('Unknown').concept_id
|
194
197
|
end
|
198
|
+
|
199
|
+
def update_reason_for_test(order, concept_id)
|
200
|
+
raise InvalidParameterError, "Reason for test can't be blank" if concept_id.blank?
|
201
|
+
|
202
|
+
return if order.reason_for_test&.value_coded == concept_id
|
203
|
+
|
204
|
+
raise InvalidParameterError, "Can't change reason for test once set" if order.reason_for_test&.value_coded
|
205
|
+
|
206
|
+
order.reason_for_test&.delete
|
207
|
+
add_reason_for_test(order, date: order.start_date, reason_for_test_id: concept_id)
|
208
|
+
end
|
195
209
|
end
|
196
210
|
end
|
197
211
|
end
|
data/lib/lab/version.rb
CHANGED
@@ -86,8 +86,6 @@ Blood,HbA1c,"2019-11-19 14:05:31"
|
|
86
86
|
Blood,Microalbumin,"2019-11-19 14:05:31"
|
87
87
|
Blood,Microprotein,"2019-11-19 14:05:31"
|
88
88
|
Blood,"Von Willebrand Factor","2019-11-19 14:05:31"
|
89
|
-
Blood,"HIV_viral_load","2021-04-13 00:00:00"
|
90
|
-
Blood,"Viral laod","2021-04-11 00:00:00"
|
91
89
|
Blood,"Viral Load","2019-11-19 14:05:31"
|
92
90
|
Blood,"Urine Lam","2019-11-19 14:05:31"
|
93
91
|
Blood,"Protein and Sugar","2021-04-16"
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: his_emr_api_lab
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.1.
|
4
|
+
version: 1.1.5
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Elizabeth Glaser Pediatric Foundation Malawi
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2021-07-
|
11
|
+
date: 2021-07-21 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: couchrest
|