cqm-reports 2.1.1 → 3.0.0.pre.alpha.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (45) hide show
  1. checksums.yaml +5 -5
  2. data/Gemfile +1 -2
  3. data/README.md +0 -27
  4. data/lib/{cqm_report.rb → cqm-reports.rb} +4 -2
  5. data/lib/ext/code.rb +11 -0
  6. data/lib/ext/data_element.rb +24 -0
  7. data/lib/html-export/qdm-patient/qdm_patient.rb +3 -3
  8. data/lib/qrda-export/catI-r5/_header.mustache +2 -2
  9. data/lib/qrda-export/catI-r5/qrda1_r5.mustache +2 -6
  10. data/lib/qrda-export/catI-r5/qrda1_r5.rb +2 -28
  11. data/lib/qrda-export/catI-r5/qrda_header/_record_target.mustache +11 -24
  12. data/lib/qrda-export/catI-r5/qrda_templates/adverse_event.mustache +4 -4
  13. data/lib/qrda-export/catI-r5/qrda_templates/allergy_intolerance.mustache +6 -1
  14. data/lib/qrda-export/catI-r5/qrda_templates/communication_performed.mustache +2 -2
  15. data/lib/qrda-export/catI-r5/qrda_templates/diagnosis.mustache +6 -1
  16. data/lib/qrda-export/catI-r5/qrda_templates/encounter_performed.mustache +0 -4
  17. data/lib/qrda-export/catI-r5/qrda_templates/immunization_administered.mustache +2 -7
  18. data/lib/qrda-export/catI-r5/qrda_templates/medication_discharge.mustache +2 -0
  19. data/lib/qrda-export/catI-r5/qrda_templates/procedure_order.mustache +0 -4
  20. data/lib/qrda-export/catI-r5/qrda_templates/procedure_performed.mustache +0 -4
  21. data/lib/qrda-export/catI-r5/qrda_templates/procedure_recommended.mustache +0 -4
  22. data/lib/qrda-export/catI-r5/qrda_templates/substance_recommended.mustache +0 -1
  23. data/lib/qrda-export/catI-r5/qrda_templates/symptom.mustache +6 -1
  24. data/lib/qrda-export/catI-r5/qrda_templates/template_partials/_encounter_diagnosis.mustache +3 -1
  25. data/lib/qrda-export/catI-r5/qrda_templates/template_partials/_medication_supply_request.mustache +1 -1
  26. data/lib/qrda-export/catI-r5/qrda_templates/template_partials/_results.mustache +12 -0
  27. data/lib/qrda-export/helper/cat1_view_helper.rb +4 -6
  28. data/lib/qrda-export/helper/date_helper.rb +4 -0
  29. data/lib/qrda-import/base-importers/demographics_importer.rb +4 -4
  30. data/lib/qrda-import/base-importers/section_importer.rb +14 -58
  31. data/lib/qrda-import/data-element-importers/adverse_event_importer.rb +1 -1
  32. data/lib/qrda-import/data-element-importers/communication_performed_importer.rb +4 -4
  33. data/lib/qrda-import/data-element-importers/diagnostic_study_performed_importer.rb +1 -1
  34. data/lib/qrda-import/data-element-importers/encounter_performed_importer.rb +0 -12
  35. data/lib/qrda-import/data-element-importers/immunization_order_importer.rb +1 -1
  36. data/lib/qrda-import/data-element-importers/medication_dispensed_importer.rb +2 -2
  37. data/lib/qrda-import/data-element-importers/medication_order_importer.rb +1 -1
  38. data/lib/qrda-import/data-element-importers/procedure_order_importer.rb +0 -2
  39. data/lib/qrda-import/data-element-importers/procedure_performed_importer.rb +0 -2
  40. data/lib/qrda-import/data-element-importers/procedure_recommended_importer.rb +0 -2
  41. data/lib/qrda-import/entry_package.rb +16 -0
  42. data/lib/qrda-import/patient_importer.rb +62 -85
  43. metadata +15 -29
  44. data/lib/qrda-export/catI-r5/qrda_templates/provider_characteristic.mustache +0 -15
  45. data/lib/qrda-import/data-element-importers/provider_characteristic_importer.rb +0 -19
@@ -7,7 +7,6 @@ module QRDA
7
7
  @code_xpath = "./cda:code"
8
8
  @author_datetime_xpath = "./cda:author/cda:time"
9
9
  @anatomical_location_site_xpath = "./cda:targetSiteCode"
10
- @ordinality_xpath = "./cda:priorityCode"
11
10
  @reason_xpath = "./cda:entryRelationship[@typeCode='RSON']/cda:observation[cda:templateId/@root='2.16.840.1.113883.10.20.24.3.88']/cda:value"
12
11
  @entry_class = QDM::ProcedureRecommended
13
12
  end
@@ -15,7 +14,6 @@ module QRDA
15
14
  def create_entry(entry_element, nrh = NarrativeReferenceHandler.new)
16
15
  procedure_recommended = super
17
16
  procedure_recommended.anatomicalLocationSite = code_if_present(entry_element.at_xpath(@anatomical_location_site_xpath))
18
- procedure_recommended.ordinality = code_if_present(entry_element.at_xpath(@ordinality_xpath))
19
17
  procedure_recommended.reason = extract_reason(entry_element)
20
18
  procedure_recommended
21
19
  end
@@ -0,0 +1,16 @@
1
+ module QRDA
2
+ module Cat1
3
+ class EntryPackage
4
+
5
+ attr_accessor :importer_type
6
+
7
+ def initialize(type)
8
+ self.importer_type = type
9
+ end
10
+
11
+ def package_entries(doc, nrh)
12
+ importer_type.create_entries(doc, nrh)
13
+ end
14
+ end
15
+ end
16
+ end
@@ -12,117 +12,88 @@ module QRDA
12
12
  def initialize
13
13
  # This differs from other HDS patient importers in that sections can have multiple importers
14
14
  @data_element_importers = []
15
- @data_element_importers << AdverseEventImporter.new
16
- @data_element_importers << AllergyIntoleranceImporter.new
17
- @data_element_importers << AssessmentOrderImporter.new
18
- @data_element_importers << AssessmentPerformedImporter.new
19
- @data_element_importers << AssessmentRecommendedImporter.new
20
- @data_element_importers << CommunicationPerformedImporter.new
21
- @data_element_importers << DeviceAppliedImporter.new
22
- @data_element_importers << DeviceOrderImporter.new
23
- @data_element_importers << DeviceRecommendedImporter.new
24
- @data_element_importers << DiagnosisImporter.new
25
- @data_element_importers << DiagnosticStudyOrderImporter.new
26
- @data_element_importers << DiagnosticStudyPerformedImporter.new
27
- @data_element_importers << DiagnosticStudyRecommendedImporter.new
28
- @data_element_importers << EncounterOrderImporter.new
29
- @data_element_importers << EncounterPerformedImporter.new
30
- @data_element_importers << EncounterRecommendedImporter.new
31
- @data_element_importers << FamilyHistoryImporter.new
32
- @data_element_importers << ImmunizationAdministeredImporter.new
33
- @data_element_importers << ImmunizationOrderImporter.new
34
- @data_element_importers << InterventionOrderImporter.new
35
- @data_element_importers << InterventionPerformedImporter.new
36
- @data_element_importers << InterventionRecommendedImporter.new
37
- @data_element_importers << LaboratoryTestOrderImporter.new
38
- @data_element_importers << LaboratoryTestPerformedImporter.new
39
- @data_element_importers << LaboratoryTestRecommendedImporter.new
40
- @data_element_importers << MedicationActiveImporter.new
41
- @data_element_importers << MedicationAdministeredImporter.new
42
- @data_element_importers << MedicationDischargeImporter.new
43
- @data_element_importers << MedicationDispensedImporter.new
44
- @data_element_importers << MedicationOrderImporter.new
45
- @data_element_importers << PatientCareExperienceImporter.new
46
- @data_element_importers << PatientCharacteristicClinicalTrialParticipantImporter.new
47
- @data_element_importers << PatientCharacteristicExpiredImporter.new
48
- @data_element_importers << PatientCharacteristicPayerImporter.new
49
- @data_element_importers << PhysicalExamOrderImporter.new
50
- @data_element_importers << PhysicalExamPerformedImporter.new
51
- @data_element_importers << PhysicalExamRecommendedImporter.new
52
- @data_element_importers << ProcedureOrderImporter.new
53
- @data_element_importers << ProcedurePerformedImporter.new
54
- @data_element_importers << ProcedureRecommendedImporter.new
55
- @data_element_importers << ProviderCareExperienceImporter.new
56
- @data_element_importers << ProviderCharacteristicImporter.new
57
- @data_element_importers << SubstanceAdministeredImporter.new
58
- @data_element_importers << SubstanceOrderImporter.new
59
- @data_element_importers << SubstanceRecommendedImporter.new
60
- @data_element_importers << SymptomImporter.new
15
+ @data_element_importers << generate_importer(AdverseEventImporter)
16
+ @data_element_importers << generate_importer(AllergyIntoleranceImporter)
17
+ @data_element_importers << generate_importer(AssessmentOrderImporter)
18
+ @data_element_importers << generate_importer(AssessmentPerformedImporter)
19
+ @data_element_importers << generate_importer(AssessmentRecommendedImporter)
20
+ @data_element_importers << generate_importer(CommunicationPerformedImporter)
21
+ @data_element_importers << generate_importer(DeviceAppliedImporter)
22
+ @data_element_importers << generate_importer(DeviceOrderImporter)
23
+ @data_element_importers << generate_importer(DeviceRecommendedImporter)
24
+ @data_element_importers << generate_importer(DiagnosisImporter)
25
+ @data_element_importers << generate_importer(DiagnosticStudyOrderImporter)
26
+ @data_element_importers << generate_importer(DiagnosticStudyPerformedImporter)
27
+ @data_element_importers << generate_importer(DiagnosticStudyRecommendedImporter)
28
+ @data_element_importers << generate_importer(EncounterOrderImporter)
29
+ @data_element_importers << generate_importer(EncounterPerformedImporter)
30
+ @data_element_importers << generate_importer(EncounterRecommendedImporter)
31
+ @data_element_importers << generate_importer(FamilyHistoryImporter)
32
+ @data_element_importers << generate_importer(ImmunizationAdministeredImporter)
33
+ @data_element_importers << generate_importer(ImmunizationOrderImporter)
34
+ @data_element_importers << generate_importer(InterventionOrderImporter)
35
+ @data_element_importers << generate_importer(InterventionPerformedImporter)
36
+ @data_element_importers << generate_importer(InterventionRecommendedImporter)
37
+ @data_element_importers << generate_importer(LaboratoryTestOrderImporter)
38
+ @data_element_importers << generate_importer(LaboratoryTestPerformedImporter)
39
+ @data_element_importers << generate_importer(LaboratoryTestRecommendedImporter)
40
+ @data_element_importers << generate_importer(MedicationActiveImporter)
41
+ @data_element_importers << generate_importer(MedicationAdministeredImporter)
42
+ @data_element_importers << generate_importer(MedicationDischargeImporter)
43
+ @data_element_importers << generate_importer(MedicationDispensedImporter)
44
+ @data_element_importers << generate_importer(MedicationOrderImporter)
45
+ @data_element_importers << generate_importer(PatientCareExperienceImporter)
46
+ @data_element_importers << generate_importer(PatientCharacteristicClinicalTrialParticipantImporter)
47
+ @data_element_importers << generate_importer(PatientCharacteristicExpiredImporter)
48
+ @data_element_importers << generate_importer(PatientCharacteristicPayerImporter)
49
+ @data_element_importers << generate_importer(PhysicalExamOrderImporter)
50
+ @data_element_importers << generate_importer(PhysicalExamPerformedImporter)
51
+ @data_element_importers << generate_importer(PhysicalExamRecommendedImporter)
52
+ @data_element_importers << generate_importer(ProcedureOrderImporter)
53
+ @data_element_importers << generate_importer(ProcedurePerformedImporter)
54
+ @data_element_importers << generate_importer(ProcedureRecommendedImporter)
55
+ @data_element_importers << generate_importer(ProviderCareExperienceImporter)
56
+ @data_element_importers << generate_importer(SubstanceAdministeredImporter)
57
+ @data_element_importers << generate_importer(SubstanceOrderImporter)
58
+ @data_element_importers << generate_importer(SubstanceRecommendedImporter)
59
+ @data_element_importers << generate_importer(SymptomImporter)
61
60
  end
62
61
 
63
62
  def parse_cat1(doc)
64
63
  patient = CQM::Patient.new
65
- warnings = []
66
- codes_modifiers = {}
67
64
  entry_id_map = {}
68
- import_data_elements(patient, doc, entry_id_map, codes_modifiers, warnings)
65
+ import_data_elements(patient, doc, entry_id_map)
69
66
  normalize_references(patient, entry_id_map)
70
67
  get_demographics(patient, doc)
71
- [patient, warnings, codes_modifiers]
68
+ patient
72
69
  end
73
70
 
74
- def import_data_elements(patient, doc, entry_id_map, codes_modifiers, warnings = [])
71
+ def import_data_elements(patient, doc, entry_id_map)
75
72
  context = doc.xpath("/cda:ClinicalDocument/cda:component/cda:structuredBody/cda:component/cda:section[cda:templateId/@root = '2.16.840.1.113883.10.20.24.2.1']")
76
73
  nrh = NarrativeReferenceHandler.new
77
74
  nrh.build_id_map(doc)
78
- @data_element_importers.each do |importer|
79
- data_elements, id_map = importer.create_entries(context, nrh)
75
+ @data_element_importers.each do |entry_package|
76
+ data_elements, id_map = entry_package.package_entries(context, nrh)
80
77
  new_data_elements = []
81
78
 
82
79
  id_map.each_value do |elem_ids|
80
+
83
81
  elem_id = elem_ids.first
84
82
  data_element = data_elements.find { |de| de.id == elem_id }
85
- # Keep the first element with a shared ID
86
- new_data_elements << data_element
87
-
88
- # Encounters require elements beyond id for uniqueness
89
- next unless data_element._type == 'QDM::EncounterPerformed'
90
- unique_element_keys = []
91
- # Add key_elements_for_determining_encounter_uniqueness to array, this is used to determine if other
92
- # elements with the same ID should be considered as unique
93
- unique_element_keys << key_elements_for_determining_encounter_uniqueness(data_element)
94
83
 
95
- # Loop through all other data elements with the same id
96
- elem_ids[1,elem_ids.length].each do |dup_id|
97
- dup_element = data_elements.find { |de| de.id == dup_id }
98
- dup_element_keys = key_elements_for_determining_encounter_uniqueness(dup_element)
99
- # See if a previously selected data element shared all of the keys files
100
- # If all key fields match, move on.
101
- next if unique_element_keys.include?(dup_element_keys)
102
- # If all key fields don't match, keep element
103
- new_data_elements << dup_element
104
- # Add to list of unique element keys
105
- unique_element_keys << dup_element_keys
84
+ elem_ids[1,elem_ids.length].each do |merge_id|
85
+ merge_element = data_elements.find { |de| de.id == merge_id }
86
+ data_element.merge!(merge_element)
106
87
  end
88
+
89
+ new_data_elements << data_element
107
90
  end
108
91
 
109
92
  patient.qdmPatient.dataElements << new_data_elements
110
93
  entry_id_map.merge!(id_map)
111
- warnings.concat(importer.warnings)
112
- codes_modifiers.merge!(importer.codes_modifiers)
113
- # reset warnings after they're captured so that the importer can be re-used
114
- importer.warnings = []
115
- importer.codes_modifiers = {}
116
94
  end
117
95
  end
118
96
 
119
- def key_elements_for_determining_encounter_uniqueness(encounter)
120
- codes = encounter.codes.collect { |dec| "#{dec.code}_#{dec.codeSystemOid}" }.sort.to_s
121
- admission_date_time = encounter&.relevantPeriod&.low.to_s
122
- discharge_date_time = encounter&.relevantPeriod&.high.to_s
123
- "#{codes}#{admission_date_time}#{discharge_date_time}"
124
- end
125
-
126
97
  def get_patient_expired(record, doc)
127
98
  entry_elements = doc.xpath("/cda:ClinicalDocument/cda:component/cda:structuredBody/cda:component/cda:section[cda:templateId/@root = '2.16.840.1.113883.10.20.24.2.1']/cda:entry/cda:observation[cda:templateId/@root = '2.16.840.1.113883.10.20.24.3.54']")
128
99
  return unless entry_elements.empty?
@@ -145,6 +116,12 @@ module QRDA
145
116
  end
146
117
  end
147
118
  end
119
+
120
+ private
121
+
122
+ def generate_importer(importer_class)
123
+ EntryPackage.new(importer_class.new)
124
+ end
148
125
  end
149
126
  end
150
127
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: cqm-reports
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.1.1
4
+ version: 3.0.0.pre.alpha.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - The MITRE Corporation
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2020-09-11 00:00:00.000000000 Z
11
+ date: 2019-08-23 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: cqm-models
@@ -16,28 +16,14 @@ dependencies:
16
16
  requirements:
17
17
  - - "~>"
18
18
  - !ruby/object:Gem::Version
19
- version: 2.0.0
19
+ version: 3.0.0
20
20
  type: :runtime
21
21
  prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
24
  - - "~>"
25
25
  - !ruby/object:Gem::Version
26
- version: 2.0.0
27
- - !ruby/object:Gem::Dependency
28
- name: cqm-validators
29
- requirement: !ruby/object:Gem::Requirement
30
- requirements:
31
- - - "~>"
32
- - !ruby/object:Gem::Version
33
- version: 2.0.0
34
- type: :runtime
35
- prerelease: false
36
- version_requirements: !ruby/object:Gem::Requirement
37
- requirements:
38
- - - "~>"
39
- - !ruby/object:Gem::Version
40
- version: 2.0.0
26
+ version: 3.0.0
41
27
  - !ruby/object:Gem::Dependency
42
28
  name: mustache
43
29
  requirement: !ruby/object:Gem::Requirement
@@ -70,16 +56,16 @@ dependencies:
70
56
  name: mongoid-tree
71
57
  requirement: !ruby/object:Gem::Requirement
72
58
  requirements:
73
- - - "~>"
59
+ - - ">"
74
60
  - !ruby/object:Gem::Version
75
- version: '2.1'
61
+ version: '2.0'
76
62
  type: :runtime
77
63
  prerelease: false
78
64
  version_requirements: !ruby/object:Gem::Requirement
79
65
  requirements:
80
- - - "~>"
66
+ - - ">"
81
67
  - !ruby/object:Gem::Version
82
- version: '2.1'
68
+ version: '2.0'
83
69
  - !ruby/object:Gem::Dependency
84
70
  name: nokogiri
85
71
  requirement: !ruby/object:Gem::Requirement
@@ -160,7 +146,9 @@ files:
160
146
  - Gemfile
161
147
  - README.md
162
148
  - Rakefile
163
- - lib/cqm_report.rb
149
+ - lib/cqm-reports.rb
150
+ - lib/ext/code.rb
151
+ - lib/ext/data_element.rb
164
152
  - lib/html-export/qdm-patient/_header_css.mustache
165
153
  - lib/html-export/qdm-patient/_javascript.mustache
166
154
  - lib/html-export/qdm-patient/data_element/_data_element.mustache
@@ -224,7 +212,6 @@ files:
224
212
  - lib/qrda-export/catI-r5/qrda_templates/procedure_performed.mustache
225
213
  - lib/qrda-export/catI-r5/qrda_templates/procedure_recommended.mustache
226
214
  - lib/qrda-export/catI-r5/qrda_templates/provider_care_experience.mustache
227
- - lib/qrda-export/catI-r5/qrda_templates/provider_characteristic.mustache
228
215
  - lib/qrda-export/catI-r5/qrda_templates/substance_recommended.mustache
229
216
  - lib/qrda-export/catI-r5/qrda_templates/symptom.mustache
230
217
  - lib/qrda-export/catI-r5/qrda_templates/template_partials/_admission_source.mustache
@@ -314,12 +301,12 @@ files:
314
301
  - lib/qrda-import/data-element-importers/procedure_performed_importer.rb
315
302
  - lib/qrda-import/data-element-importers/procedure_recommended_importer.rb
316
303
  - lib/qrda-import/data-element-importers/provider_care_experience_importer.rb
317
- - lib/qrda-import/data-element-importers/provider_characteristic_importer.rb
318
304
  - lib/qrda-import/data-element-importers/substance_administered_importer.rb
319
305
  - lib/qrda-import/data-element-importers/substance_order_importer.rb
320
306
  - lib/qrda-import/data-element-importers/substance_recommended_importer.rb
321
307
  - lib/qrda-import/data-element-importers/symptom_importer.rb
322
308
  - lib/qrda-import/entry_finder.rb
309
+ - lib/qrda-import/entry_package.rb
323
310
  - lib/qrda-import/narrative_reference_handler.rb
324
311
  - lib/qrda-import/patient_importer.rb
325
312
  - lib/util/code_system_helper.rb
@@ -345,12 +332,11 @@ required_ruby_version: !ruby/object:Gem::Requirement
345
332
  version: '0'
346
333
  required_rubygems_version: !ruby/object:Gem::Requirement
347
334
  requirements:
348
- - - ">="
335
+ - - ">"
349
336
  - !ruby/object:Gem::Version
350
- version: '0'
337
+ version: 1.3.1
351
338
  requirements: []
352
- rubyforge_project:
353
- rubygems_version: 2.6.14
339
+ rubygems_version: 3.0.3
354
340
  signing_key:
355
341
  specification_version: 4
356
342
  summary: A library for import and export of reports for use with electronic Clinical
@@ -1,15 +0,0 @@
1
- <entry>
2
- <observation classCode="OBS" moodCode="EVN">
3
- <!-- Provider Characteristic Observation Assertion (V3) -->
4
- <templateId root="2.16.840.1.113883.10.20.24.3.114" extension="2017-08-01"/>
5
- <id root="1.3.6.1.4.1.115" extension="{{object_id}}"/>
6
- <code code="ASSERTION" codeSystem="2.16.840.1.113883.5.4" codeSystemName="HL7ActCode" />
7
- <statusCode code="completed" />
8
- <!-- Provider Characteristic -->
9
- {{> qrda_templates/template_partials/_data_element_codes_as_values}}
10
- {{#authorDatetime}}
11
- <!-- QDM Attribute: Author dateTime -->
12
- {{> qrda_templates/template_partials/_author}}
13
- {{/authorDatetime}}
14
- </observation>
15
- </entry>
@@ -1,19 +0,0 @@
1
- module QRDA
2
- module Cat1
3
- class ProviderCharacteristicImporter < SectionImporter
4
- def initialize(entry_finder = QRDA::Cat1::EntryFinder.new("./cda:entry/cda:observation[cda:templateId/@root = '2.16.840.1.113883.10.20.24.3.114']"))
5
- super(entry_finder)
6
- @id_xpath = './cda:id'
7
- @code_xpath = "./cda:value"
8
- @author_datetime_xpath = "./cda:author/cda:time"
9
- @entry_class = QDM::ProviderCharacteristic
10
- end
11
-
12
- def create_entry(entry_element, nrh = NarrativeReferenceHandler.new)
13
- provider_characteristic = super
14
- provider_characteristic
15
- end
16
-
17
- end
18
- end
19
- end