quality-measure-engine 2.5.3 → 3.0.0.beta.1
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 +9 -9
- data/Gemfile.lock +4 -4
- data/lib/qme/database_access.rb +2 -22
- data/lib/qme/manual_exclusion.rb +18 -0
- data/lib/qme/map/map_reduce_builder.rb +10 -10
- data/lib/qme/map/map_reduce_executor.rb +33 -33
- data/lib/qme/map/measure_calculation_job.rb +69 -15
- data/lib/qme/patient_cache.rb +31 -0
- data/lib/qme/quality_measure.rb +11 -55
- data/lib/qme/quality_report.rb +98 -74
- data/lib/qme/version.rb +1 -1
- data/lib/quality-measure-engine.rb +2 -3
- data/test/fixtures/library_functions/map_reduce_utils.js +6 -0
- data/test/fixtures/measures/0002.json +1 -1
- data/test/fixtures/measures/measure_metadata.json +1 -0
- data/test/mongoid.yml +6 -0
- data/test/test_helper.rb +3 -7
- data/test/unit/qme/map/map_reduce_builder_test.rb +2 -2
- data/test/unit/qme/map/map_reduce_executor_test.rb +27 -38
- data/test/unit/qme/map/measure_calculation_job_test.rb +2 -2
- data/test/unit/qme/quality_measure_test.rb +3 -39
- data/test/unit/qme/quality_report_test.rb +12 -9
- metadata +9 -11
- data/lib/qme/bundle/eh_measure_sheet.rb +0 -117
- data/lib/qme/bundle/eh_patient_importer.rb +0 -25
- data/test/unit/qme/bundle/eh_measure_sheet_test.rb +0 -37
- data/test/unit/qme/bundle/eh_patient_importer_test.rb +0 -20
checksums.yaml
CHANGED
@@ -1,15 +1,15 @@
|
|
1
1
|
---
|
2
2
|
!binary "U0hBMQ==":
|
3
3
|
metadata.gz: !binary |-
|
4
|
-
|
4
|
+
ODgyZTA5NDU0MGQ0NjZlOTc2YWYwZTYyYmE3OWZlZTUzNDNmYTYzOA==
|
5
5
|
data.tar.gz: !binary |-
|
6
|
-
|
7
|
-
|
6
|
+
ZjIwZDA5NTdkZWNjODBkYTMxNWY3YjA3ZWE3OWI3NTkwZTMwOTQxMQ==
|
7
|
+
!binary "U0hBNTEy":
|
8
8
|
metadata.gz: !binary |-
|
9
|
-
|
10
|
-
|
11
|
-
|
9
|
+
NTkxNTdlMWJiMzJjNDY0MjQxYjc0MjFjMGQyYTc4ZGZlZGU5ODhmNzIyMWI5
|
10
|
+
YWUxZDM0ODc5YzE0ZmI3OWRlMTg3ZWM5MWE5NDkyZGNkOTQ3YzI5ZWViNWUx
|
11
|
+
NzgzNWI0ZGQwZDE3MTk1MTU2N2ZjZjRhMGViMjY4MzIwNTFlZDM=
|
12
12
|
data.tar.gz: !binary |-
|
13
|
-
|
14
|
-
|
15
|
-
|
13
|
+
ZDMwZTJkYTlkMWRmZWM1ZTc2YzZlNjM1ZTdlYTU0YzNlYTlmZThiNzhlN2Zh
|
14
|
+
NTA3NmVjNTk0ZjkyNjZkODZlYTZkYTVhZjYxZGQxMDUzNjMyMTZiZDdiNDRi
|
15
|
+
NWFhMjg1NmY1NzEzMzQ3NDAyOTA2MmVkMDhmYjU5ZjllMzQwZTI=
|
data/Gemfile.lock
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
PATH
|
2
2
|
remote: .
|
3
3
|
specs:
|
4
|
-
quality-measure-engine (
|
4
|
+
quality-measure-engine (3.0.0.beta.1)
|
5
5
|
delayed_job_mongoid (~> 2.0.0)
|
6
6
|
mongoid (~> 3.1.4)
|
7
7
|
moped (~> 1.5.1)
|
@@ -62,7 +62,7 @@ GEM
|
|
62
62
|
treetop (~> 1.4.8)
|
63
63
|
method_source (0.8.2)
|
64
64
|
mime-types (1.24)
|
65
|
-
mini_portile (0.5.
|
65
|
+
mini_portile (0.5.1)
|
66
66
|
minitest (4.7.5)
|
67
67
|
mongoid (3.1.5)
|
68
68
|
activemodel (~> 3.2)
|
@@ -70,7 +70,7 @@ GEM
|
|
70
70
|
origin (~> 1.0)
|
71
71
|
tzinfo (~> 0.3.29)
|
72
72
|
moped (1.5.1)
|
73
|
-
multi_json (1.
|
73
|
+
multi_json (1.8.2)
|
74
74
|
nokogiri (1.6.0)
|
75
75
|
mini_portile (~> 0.5.0)
|
76
76
|
origin (1.1.0)
|
@@ -131,7 +131,7 @@ GEM
|
|
131
131
|
polyglot (>= 0.3.1)
|
132
132
|
turn (0.9.6)
|
133
133
|
ansi
|
134
|
-
tzinfo (0.3.
|
134
|
+
tzinfo (0.3.38)
|
135
135
|
|
136
136
|
PLATFORMS
|
137
137
|
ruby
|
data/lib/qme/database_access.rb
CHANGED
@@ -1,30 +1,10 @@
|
|
1
1
|
module QME
|
2
|
-
module DatabaseAccess
|
3
|
-
|
4
|
-
# Set up the information to connect to the database. Database host
|
5
|
-
# and port may be set using the environment variables TEST_DB_HOST
|
6
|
-
# and TEST_DB_PORT which default to localhost and 27017 respectively.
|
7
|
-
# @param [String] db_name the name of the database to use
|
8
|
-
def determine_connection_information(db_name = nil)
|
9
|
-
@db_name = ENV['DB_NAME'] || db_name || 'test'
|
10
|
-
@db_host = ENV['TEST_DB_HOST'] || 'localhost'
|
11
|
-
@db_port = ENV['TEST_DB_PORT'] ? ENV['TEST_DB_PORT'].to_i : 27017
|
12
|
-
end
|
13
|
-
|
2
|
+
module DatabaseAccess
|
14
3
|
# Lazily creates a connection to the database and initializes the
|
15
4
|
# JavaScript environment
|
16
5
|
# @return [Moped::Session]
|
17
6
|
def get_db
|
18
|
-
|
19
|
-
if @db_name==nil || @db_host==nil || @db_port==nil
|
20
|
-
determine_connection_information()
|
21
|
-
end
|
22
|
-
|
23
|
-
@db = Moped::Session.new(["#{@db_host}:#{@db_port}"])
|
24
|
-
@db.use(@db_name)
|
25
|
-
end
|
26
|
-
|
27
|
-
@db
|
7
|
+
Mongoid.default_session
|
28
8
|
end
|
29
9
|
end
|
30
10
|
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
module QME
|
2
|
+
class ManualExclusion
|
3
|
+
include Mongoid::Document
|
4
|
+
store_in collection: 'manual_exclusions'
|
5
|
+
field :measure_id, type: String
|
6
|
+
field :sub_id, type: String
|
7
|
+
field :medical_record_id, type: String
|
8
|
+
|
9
|
+
|
10
|
+
def self.apply_manual_exclusions(measure_id, sub_id)
|
11
|
+
mids = where({measure_id: measure_id, sub_id: sub_id}).collect {|me| me.medical_record_id}
|
12
|
+
QME::PatientCache.where({'value.measure_id'=>@measure_id, 'value.sub_id'=>@sub_id, 'value.medical_record_id'=>{'$in'=>mids} })
|
13
|
+
.update_all({'$set'=>{'value.manual_exclusion'=>true}})
|
14
|
+
end
|
15
|
+
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
@@ -66,8 +66,8 @@ module QME
|
|
66
66
|
@params[name.to_s] = value
|
67
67
|
end
|
68
68
|
@measure_def = measure_def
|
69
|
-
@measure_def
|
70
|
-
@measure_def
|
69
|
+
@measure_def.parameters ||= {}
|
70
|
+
@measure_def.parameters.each do |parameter, value|
|
71
71
|
if !@params.has_key?(parameter)
|
72
72
|
raise "No value supplied for measure parameter: #{parameter}"
|
73
73
|
end
|
@@ -75,17 +75,17 @@ module QME
|
|
75
75
|
# if the map function is specified then replace any erb templates with their values
|
76
76
|
# taken from the supplied params
|
77
77
|
# always true for actual measures, not always true for unit tests
|
78
|
-
if (@measure_def
|
79
|
-
template = ERB.new(@measure_def
|
78
|
+
if (@measure_def.map_fn)
|
79
|
+
template = ERB.new(@measure_def.map_fn)
|
80
80
|
context = Context.new(@db, @params)
|
81
|
-
@measure_def
|
81
|
+
@measure_def.map_fn = template.result(context.get_binding)
|
82
82
|
end
|
83
83
|
end
|
84
84
|
|
85
85
|
# Get the map function for the measure
|
86
86
|
# @return [String] the map function
|
87
87
|
def map_function
|
88
|
-
@measure_def
|
88
|
+
@measure_def.map_fn
|
89
89
|
end
|
90
90
|
|
91
91
|
# Get the reduce function for the measure, this is a simple
|
@@ -100,11 +100,11 @@ module QME
|
|
100
100
|
if @params['test_id'] && @params['test_id'].class==Moped::BSON::ObjectId
|
101
101
|
reduce += " patient.test_id = new ObjectId(\"#{@params['test_id']}\");\n"
|
102
102
|
end
|
103
|
-
if @measure_def
|
104
|
-
reduce += " patient.sub_id = \"#{@measure_def
|
103
|
+
if @measure_def.sub_id
|
104
|
+
reduce += " patient.sub_id = \"#{@measure_def.sub_id}\";\n"
|
105
105
|
end
|
106
|
-
if @measure_def
|
107
|
-
reduce += " patient.nqf_id = \"#{@measure_def
|
106
|
+
if @measure_def.nqf_id
|
107
|
+
reduce += " patient.nqf_id = \"#{@measure_def.nqf_id}\";\n"
|
108
108
|
end
|
109
109
|
|
110
110
|
reduce += "patient.effective_date = #{@params['effective_date']};
|
@@ -15,18 +15,24 @@ module QME
|
|
15
15
|
# @param [String] measure_id the measure identifier
|
16
16
|
# @param [String] sub_id the measure sub-identifier or null if the measure is single numerator
|
17
17
|
# @param [Hash] parameter_values a hash that may contain the following keys: 'effective_date' the measurement period end date, 'test_id' an identifier for a specific set of patients
|
18
|
-
def initialize(measure_id,
|
18
|
+
def initialize(measure_id,sub_id, parameter_values)
|
19
|
+
|
19
20
|
@measure_id = measure_id
|
20
|
-
@sub_id =
|
21
|
+
@sub_id =sub_id
|
22
|
+
|
21
23
|
@parameter_values = parameter_values
|
22
|
-
|
23
|
-
|
24
|
+
q_filter = {hqmf_id: @measure_id,sub_id: @sub_id}
|
25
|
+
if @parameter_values.keys.index("bundle_id")
|
26
|
+
q_filter["bundle_id"] == @parameter_values['bundle_id']
|
27
|
+
@bundle_id = @parameter_values['bundle_id']
|
28
|
+
end
|
29
|
+
@measure_def = QualityMeasure.where(q_filter).first
|
24
30
|
end
|
25
31
|
|
26
32
|
def build_query
|
27
33
|
pipeline = []
|
28
34
|
|
29
|
-
filters = @parameter_values[
|
35
|
+
filters = @parameter_values["filters"]
|
30
36
|
|
31
37
|
|
32
38
|
match = {'value.measure_id' => @measure_id,
|
@@ -77,7 +83,7 @@ module QME
|
|
77
83
|
'value.test_id' => @parameter_values['test_id'],
|
78
84
|
'value.manual_exclusion' => {'$in' => [nil, false]}}
|
79
85
|
|
80
|
-
keys = @measure_def
|
86
|
+
keys = @measure_def.population_ids.keys - [QME::QualityReport::OBSERVATION, "stratification"]
|
81
87
|
supplemental_data = Hash[*keys.map{|k| [k,{QME::QualityReport::RACE => {},
|
82
88
|
QME::QualityReport::ETHNICITY => {},
|
83
89
|
QME::QualityReport::SEX => {},
|
@@ -131,24 +137,26 @@ module QME
|
|
131
137
|
raise RuntimeError, "Expected one group from patient_cache aggregation, got #{aggregate['result'].size}"
|
132
138
|
end
|
133
139
|
|
134
|
-
nqf_id = @measure_def
|
135
|
-
result =
|
136
|
-
|
137
|
-
|
140
|
+
nqf_id = @measure_def.nqf_id || @measure_def['id']
|
141
|
+
result = QME::QualityReportResult.new
|
142
|
+
result.population_ids=@measure_def.population_ids
|
143
|
+
|
138
144
|
|
139
|
-
if @measure_def
|
145
|
+
if @measure_def.continuous_variable
|
140
146
|
aggregated_value = calculate_cv_aggregation
|
141
147
|
result[QME::QualityReport::OBSERVATION] = aggregated_value
|
142
148
|
end
|
143
149
|
|
144
|
-
|
145
|
-
|
150
|
+
agg_result = aggregate['result'].first
|
151
|
+
agg_result.reject! {|k, v| k == '_id'} # get rid of the group id the Mongo forced us to use
|
146
152
|
# result['exclusions'] += get_db['patient_cache'].find(base_query.merge({'value.manual_exclusion'=>true})).count
|
147
|
-
|
148
|
-
|
149
|
-
|
150
|
-
|
153
|
+
agg_result.merge!(execution_time: (Time.now.to_i - @parameter_values['start_time'].to_i)) if @parameter_values['start_time']
|
154
|
+
agg_result.each_pair do |k,v|
|
155
|
+
result[k]=v
|
156
|
+
end
|
157
|
+
result.supplemental_data = self.calculate_supplemental_data_elements
|
151
158
|
result
|
159
|
+
|
152
160
|
end
|
153
161
|
|
154
162
|
# This method calculates the aggregated value for a CV measure. It extracts all
|
@@ -170,7 +178,7 @@ module QME
|
|
170
178
|
aggregate['result'].each do |freq_count_pair|
|
171
179
|
frequencies[freq_count_pair['_id']] = freq_count_pair['count']
|
172
180
|
end
|
173
|
-
QME::MapReduce::CVAggregator.send(@measure_def
|
181
|
+
QME::MapReduce::CVAggregator.send(@measure_def.aggregator.parameterize, frequencies)
|
174
182
|
end
|
175
183
|
|
176
184
|
|
@@ -185,7 +193,7 @@ module QME
|
|
185
193
|
:out => {:reduce => 'patient_cache'},
|
186
194
|
:finalize => measure.finalize_function,
|
187
195
|
:query => {:test_id => @parameter_values['test_id']})
|
188
|
-
apply_manual_exclusions
|
196
|
+
QME::ManualExclusion.apply_manual_exclusions(@measure_id,@sub_id)
|
189
197
|
end
|
190
198
|
|
191
199
|
# This method runs the MapReduce job for the measure and a specific patient.
|
@@ -198,8 +206,9 @@ module QME
|
|
198
206
|
:reduce => "function(key, values){return values;}",
|
199
207
|
:out => {:reduce => 'patient_cache'},
|
200
208
|
:finalize => measure.finalize_function,
|
201
|
-
:query => {:medical_record_number => patient_id, :test_id => @parameter_values[
|
202
|
-
apply_manual_exclusions
|
209
|
+
:query => {:medical_record_number => patient_id, :test_id => @parameter_values["test_id"]})
|
210
|
+
QME::ManualExclusion.apply_manual_exclusions(@measure_id,@sub_id)
|
211
|
+
|
203
212
|
end
|
204
213
|
|
205
214
|
# This method runs the MapReduce job for the measure and a specific patient.
|
@@ -212,22 +221,13 @@ module QME
|
|
212
221
|
:reduce => "function(key, values){return values;}",
|
213
222
|
:out => {:inline => true},
|
214
223
|
:raw => true,
|
215
|
-
:
|
216
|
-
|
224
|
+
:query => {:medical_record_number => patient_id, :test_id => @parameter_values["test_id"]})
|
225
|
+
|
217
226
|
raise result['err'] if result['ok']!=1
|
218
227
|
result['results'][0]['value']
|
219
228
|
end
|
220
229
|
|
221
|
-
|
222
|
-
# and sets a flag in each cached patient result for patients that have been excluded from the
|
223
|
-
# current measure
|
224
|
-
def apply_manual_exclusions
|
225
|
-
exclusions = get_db()['manual_exclusions'].find({'measure_id'=>@measure_id, 'sub_id'=>@sub_id}).to_a.map do |exclusion|
|
226
|
-
exclusion['medical_record_id']
|
227
|
-
end
|
228
|
-
get_db()['patient_cache'].find({'value.measure_id'=>@measure_id, 'value.sub_id'=>@sub_id, 'value.medical_record_id'=>{'$in'=>exclusions} })
|
229
|
-
.update_all({'$set'=>{'value.manual_exclusion'=>true}})
|
230
|
-
end
|
230
|
+
|
231
231
|
end
|
232
232
|
end
|
233
233
|
end
|
@@ -2,30 +2,27 @@ module QME
|
|
2
2
|
module MapReduce
|
3
3
|
# A delayed_job that allows for measure calculation by a delayed_job worker. Can be created as follows:
|
4
4
|
#
|
5
|
-
# Delayed::Job.enqueue QME::MapRedude::MeasureCalculationJob.new(
|
5
|
+
# Delayed::Job.enqueue QME::MapRedude::MeasureCalculationJob.new(quality_report, :effective_date => 1291352400, :test_id => xyzzy)
|
6
6
|
#
|
7
|
-
# MeasureCalculationJob will check to see if a measure has been calculated before running the calculation. It
|
8
|
-
#
|
9
|
-
# running the MapReduce job.
|
7
|
+
# MeasureCalculationJob will check to see if a measure has been calculated before running the calculation. It will do this by
|
8
|
+
# checking the status of the quality report that this calculation job was created with.
|
10
9
|
#
|
11
10
|
# When a measure needs calculation, the job will create a QME::MapReduce::Executor and interact with it to calculate
|
12
11
|
# the report.
|
13
12
|
class MeasureCalculationJob
|
14
|
-
attr_accessor :
|
13
|
+
attr_accessor :quality_report
|
15
14
|
|
16
15
|
def initialize(options)
|
17
|
-
@
|
18
|
-
@sub_id = options['sub_id']
|
16
|
+
@quality_report = QME::QualityReport.find(options["quality_report_id"])
|
19
17
|
@options = options
|
18
|
+
@options.merge! @quality_report.attributes
|
20
19
|
end
|
21
20
|
|
22
21
|
def perform
|
23
|
-
|
24
|
-
if
|
25
|
-
|
26
|
-
|
27
|
-
map = QME::MapReduce::Executor.new(@measure_id, @sub_id, @options.merge('start_time' => Time.now.to_i))
|
28
|
-
if !qr.patients_cached?
|
22
|
+
|
23
|
+
if !@quality_report.calculated?
|
24
|
+
map = QME::MapReduce::Executor.new(@quality_report.measure_id,@quality_report.sub_id, @options.merge('start_time' => Time.now.to_i))
|
25
|
+
if !@quality_report.patients_cached?
|
29
26
|
tick('Starting MapReduce')
|
30
27
|
map.map_records_into_measure_groups
|
31
28
|
tick('MapReduce complete')
|
@@ -33,17 +30,74 @@ module QME
|
|
33
30
|
|
34
31
|
tick('Calculating group totals')
|
35
32
|
result = map.count_records_in_measure_groups
|
33
|
+
@quality_report.result=result
|
34
|
+
# backwards compatibility with previous q cahce users. Should be reomved going foward
|
35
|
+
# and provide a means to update existing results to the newer format
|
36
|
+
result.attributes.each_pair do |k,v|
|
37
|
+
unless k.to_s == "_id"
|
38
|
+
@quality_report[k]=v
|
39
|
+
end
|
40
|
+
end
|
41
|
+
@quality_report.save
|
36
42
|
completed("#{@measure_id}#{@sub_id}: p#{result[QME::QualityReport::POPULATION]}, d#{result[QME::QualityReport::DENOMINATOR]}, n#{result[QME::QualityReport::NUMERATOR]}, excl#{result[QME::QualityReport::EXCLUSIONS]}, excep#{result[QME::QualityReport::EXCEPTIONS]}")
|
37
43
|
end
|
38
44
|
end
|
39
45
|
|
40
46
|
def completed(message)
|
41
|
-
|
47
|
+
@quality_report.status["state"] = "completed"
|
48
|
+
@quality_report.status["log"] << message
|
49
|
+
@quality_report.calculation_time = Time.now
|
50
|
+
@quality_report.save
|
42
51
|
end
|
43
52
|
|
44
53
|
def tick(message)
|
45
|
-
|
54
|
+
@quality_report.status["state"] = "calculating"
|
55
|
+
@quality_report.status["log"] << message
|
56
|
+
@quality_report.save
|
57
|
+
end
|
58
|
+
|
59
|
+
def enqueue(job)
|
60
|
+
@quality_report.status = {"state" => "queued", "log" => ["Queued at #{Time.now}"], "job_id" => job.id}
|
46
61
|
end
|
62
|
+
|
63
|
+
|
64
|
+
def error(job, exception)
|
65
|
+
@quality_report.status["state"] = "error"
|
66
|
+
@quality_report.status["log"] << exception.to_s
|
67
|
+
@quality_report.save
|
68
|
+
end
|
69
|
+
|
70
|
+
def failure(job)
|
71
|
+
@quality_report.status["state"] = "failed"
|
72
|
+
@quality_report.status["log"] << "Failed at #{Time.now}"
|
73
|
+
@quality_report.save
|
74
|
+
end
|
75
|
+
|
76
|
+
def after(job)
|
77
|
+
@quality_report.status.delete("job_id")
|
78
|
+
@quality_report.save
|
79
|
+
end
|
80
|
+
|
81
|
+
# Returns the status of a measure calculation job
|
82
|
+
# @param job_id the id of the job to check on
|
83
|
+
# @return [Symbol] Will return the status: :complete, :queued, :running, :failed
|
84
|
+
def self.status(job_id)
|
85
|
+
job = Delayed::Job.where(_id: job_id).first
|
86
|
+
if job.nil?
|
87
|
+
# If we can't find the job, we assume that it is complete
|
88
|
+
:complete
|
89
|
+
else
|
90
|
+
if job.locked_at.nil?
|
91
|
+
:queued
|
92
|
+
else
|
93
|
+
if job.failed?
|
94
|
+
:failed
|
95
|
+
else
|
96
|
+
:running
|
97
|
+
end
|
98
|
+
end
|
99
|
+
end
|
100
|
+
end
|
47
101
|
end
|
48
102
|
end
|
49
103
|
end
|
@@ -0,0 +1,31 @@
|
|
1
|
+
module QME
|
2
|
+
class PatientCache
|
3
|
+
include Mongoid::Document
|
4
|
+
include Mongoid::Timestamps
|
5
|
+
store_in collection: 'patient_cache'
|
6
|
+
index "value.last" => 1
|
7
|
+
index "bundle_id" => 1
|
8
|
+
embeds_one :value, class_name: "QME::PatientCacheValue", inverse_of: :patient_cache
|
9
|
+
end
|
10
|
+
|
11
|
+
class PatientCacheValue
|
12
|
+
|
13
|
+
include Mongoid::Document
|
14
|
+
|
15
|
+
embedded_in :patient_cache, inverse_of: :value
|
16
|
+
|
17
|
+
field :filters, type: Hash
|
18
|
+
field :manual_exclusion, type: Boolean, default: false
|
19
|
+
field :DENOM, type: Integer
|
20
|
+
field :NUMER, type: Integer
|
21
|
+
field :DENEX, type: Integer
|
22
|
+
field :DENEXCEP, type: Integer
|
23
|
+
field :MSRPOPL, type: Integer
|
24
|
+
field :OBSERV
|
25
|
+
field :antinumerator, type: Integer
|
26
|
+
field :IPP, type: Integer
|
27
|
+
field :measure_id, type: String
|
28
|
+
field :sub_id, type: String
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
data/lib/qme/quality_measure.rb
CHANGED
@@ -1,61 +1,17 @@
|
|
1
1
|
module QME
|
2
2
|
class QualityMeasure
|
3
|
-
include DatabaseAccess
|
4
|
-
extend DatabaseAccess
|
5
|
-
determine_connection_information
|
6
3
|
|
7
|
-
|
8
|
-
|
9
|
-
def self.all(bundle_id = nil)
|
10
|
-
result = {}
|
11
|
-
measures = query_measures({}, bundle_id)
|
12
|
-
measures.find_all.each do |measure|
|
13
|
-
id = measure['id']
|
14
|
-
sub_id = measure['sub_id']
|
15
|
-
measure_id = "#{id}#{sub_id}.json"
|
16
|
-
result[measure_id] ||= measure
|
17
|
-
end
|
18
|
-
result
|
19
|
-
end
|
20
|
-
|
21
|
-
def self.get_measures(measure_ids, bundle_id = nil)
|
22
|
-
query_measures({'id' => {"$in" => measure_ids}}, bundle_id)
|
23
|
-
end
|
24
|
-
|
25
|
-
def self.get(measure_id, sub_id, bundle_id = nil)
|
26
|
-
query_measures({'id' => measure_id, 'sub_id' => sub_id}, bundle_id)
|
27
|
-
end
|
28
|
-
|
29
|
-
def self.sub_measures(measure_id, bundle_id = nil)
|
30
|
-
query_measures({'id' => measure_id}, bundle_id)
|
31
|
-
end
|
32
|
-
|
33
|
-
# Creates a new QualityMeasure
|
34
|
-
# @param [String] measure_id value of the measure's id field
|
35
|
-
# @param [String] sub_id value of the measure's sub_id field, may be nil for measures with only a single numerator and denominator
|
36
|
-
def initialize(measure_id, sub_id = nil, bundle_id = nil)
|
37
|
-
@measure_id = measure_id
|
38
|
-
@sub_id = sub_id
|
39
|
-
@bundle_id = bundle_id
|
40
|
-
determine_connection_information
|
41
|
-
end
|
42
|
-
|
43
|
-
# Retrieve a measure definition from the database
|
44
|
-
# @return [Hash] a JSON hash of the encoded measure
|
45
|
-
def definition
|
46
|
-
if @sub_id
|
47
|
-
QME::QualityMeasure.query_measures({'id' => @measure_id, 'sub_id' => @sub_id}, @bundle_id).first()
|
48
|
-
else
|
49
|
-
QME::QualityMeasure.query_measures({'id' => @measure_id}, @bundle_id).first()
|
50
|
-
end
|
51
|
-
end
|
4
|
+
include Mongoid::Document
|
5
|
+
store_in collection: 'measures'
|
52
6
|
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
7
|
+
field :id, type: String
|
8
|
+
field :sub_id, type: String
|
9
|
+
field :map_fn, type: String
|
10
|
+
field :nqf_id, type: String
|
11
|
+
field :continuous_variable, type: Boolean, default: false
|
12
|
+
field :aggregator, type: String
|
13
|
+
field :map_fn, type: String
|
14
|
+
field :population_ids, type: Hash
|
15
|
+
field :parameters, type: Hash, default: {}
|
60
16
|
end
|
61
17
|
end
|