class HealthDataStandards::Import::C32::PatientImporter
This class is the central location for taking a HITSP C32
XML document and converting it into the processed form we store in MongoDB. The class does this by running each measure independently on the XML document
This class is a Singleton. It should be accessed by calling PatientImporter.instance
Public Class Methods
Creates a new PatientImporter
with the following XPath expressions used to find content in a HITSP C32:
Encounter
entries
//cda:section[cda:templateId/@root='2.16.840.1.113883.3.88.11.83.127']/cda:entry/cda:encounter
Procedure
entries
//cda:procedure[cda:templateId/@root='2.16.840.1.113883.10.20.1.29']
Result entries - There seems to be some confusion around the correct templateId, so the code checks for both
//cda:observation[cda:templateId/@root='2.16.840.1.113883.3.88.11.83.15.1'] | //cda:observation[cda:templateId/@root='2.16.840.1.113883.3.88.11.83.15']
Vital sign entries
//cda:observation[cda:templateId/@root='2.16.840.1.113883.3.88.11.83.14']
Medication
entries
//cda:section[cda:templateId/@root='2.16.840.1.113883.3.88.11.83.112']/cda:entry/cda:substanceAdministration
Codes for medications are found in the substanceAdministration with the following relative XPath
./cda:consumable/cda:manufacturedProduct/cda:manufacturedMaterial/cda:code
Condition
entries
//cda:section[cda:templateId/@root='2.16.840.1.113883.3.88.11.83.103']/cda:entry/cda:act/cda:entryRelationship/cda:observation
Codes for conditions are determined by examining the value child element as opposed to the code child element
Social History entries (non-C32 section, specified in the HL7 CCD)
//cda:observation[cda:templateId/@root='2.16.840.1.113883.3.88.11.83.19']
Care Goal entries(non-C32 section, specified in the HL7 CCD)
//cda:observation[cda:templateId/@root='2.16.840.1.113883.10.20.1.25']
Allergy
entries
//cda:observation[cda:templateId/@root='2.16.840.1.113883.10.20.1.18']
Immunization
entries
//cda:substanceAdministration[cda:templateId/@root='2.16.840.1.113883.10.20.1.24']
Codes for immunizations are found in the substanceAdministration with the following relative XPath
./cda:consumable/cda:manufacturedProduct/cda:manufacturedMaterial/cda:code
# File lib/health-data-standards/import/c32/patient_importer.rb, line 56 def initialize(check_usable = true) @section_importers = {} @section_importers[:encounters] = CDA::EncounterImporter.new @section_importers[:procedures] = CDA::ProcedureImporter.new @section_importers[:results] = CDA::ResultImporter.new @section_importers[:vital_signs] = CDA::VitalSignImporter.new @section_importers[:medications] = CDA::MedicationImporter.new @section_importers[:conditions] = ConditionImporter.new @section_importers[:social_history] = CDA::SectionImporter.new(CDA::EntryFinder.new("//cda:observation[cda:templateId/@root='2.16.840.1.113883.3.88.11.83.19']")) @section_importers[:care_goals] = CareGoalImporter.new @section_importers[:medical_equipment] = CDA::MedicalEquipmentImporter.new @section_importers[:allergies] = CDA::AllergyImporter.new @section_importers[:immunizations] = ImmunizationImporter.new @section_importers[:insurance_providers] = InsuranceProviderImporter.new end
Public Instance Methods
Checks the conditions to see if any of them have a cause of death set. If they do, it will set the expired field on the Record
. This is done here rather than replacing the expried method on Record
because other formats may actully tell you whether a patient is dead or not. @param [Record] c32_patient to check the conditions on and set the expired
property if applicable
# File lib/health-data-standards/import/c32/patient_importer.rb, line 99 def check_for_cause_of_death(c32_patient) cause_of_death = c32_patient.conditions.detect {|condition| condition.cause_of_death } if cause_of_death c32_patient.expired = true c32_patient.deathdate = cause_of_death.time_of_death end end
@param [boolean] value for check_usable_entries…importer uses true, stats uses false
# File lib/health-data-standards/import/c32/patient_importer.rb, line 73 def check_usable(check_usable_entries) @section_importers.each_pair do |section, importer| importer.check_for_usable = check_usable_entries end end
Create a simple representation of the patient from a HITSP C32
@param [Record] record Mongoid model to append the Entry
objects to @param [Nokogiri::XML::Document] doc It is expected that the root node of this document
will have the "cda" namespace registered to "urn:hl7-org:v3"
@return [Hash] a represnetation of the patient with symbols as keys for each section
# File lib/health-data-standards/import/c32/patient_importer.rb, line 112 def create_c32_hash(record, doc) nrh = CDA::NarrativeReferenceHandler.new nrh.build_id_map(doc) @section_importers.each_pair do |section, importer| record.send(section.to_setter, importer.create_entries(doc, nrh)) end end
Inspects a C32
document and populates the patient Hash with first name, last name birth date, gender and the effectiveTime.
@param [Hash] patient A hash that is used to represent the patient @param [Nokogiri::XML::Node] doc The C32
document parsed by Nokogiri
# File lib/health-data-standards/import/c32/patient_importer.rb, line 125 def get_demographics(patient, doc) effective_date = doc.at_xpath('/cda:ClinicalDocument/cda:effectiveTime')['value'] patient.effective_time = HL7Helper.timestamp_to_integer(effective_date) patient_role_element = doc.at_xpath('/cda:ClinicalDocument/cda:recordTarget/cda:patientRole') patient_element = patient_role_element.at_xpath('./cda:patient') patient.title = patient_element.at_xpath('cda:name/cda:title').try(:text) patient.first = patient_element.at_xpath('cda:name/cda:given').text patient.last = patient_element.at_xpath('cda:name/cda:family').text birthdate_in_hl7ts_node = patient_element.at_xpath('cda:birthTime') birthdate_in_hl7ts = birthdate_in_hl7ts_node['value'] patient.birthdate = HL7Helper.timestamp_to_integer(birthdate_in_hl7ts) gender_node = patient_element.at_xpath('cda:administrativeGenderCode') patient.gender = gender_node['code'] id_node = patient_role_element.at_xpath('./cda:id') patient.medical_record_number = id_node['extension'] # parse race, ethnicity, and spoken language race_node = patient_element.at_xpath('cda:raceCode') patient.race = { code: race_node['code'], code_set: 'CDC-RE' } if race_node ethnicity_node = patient_element.at_xpath('cda:ethnicGroupCode') patient.ethnicity = {code: ethnicity_node['code'], code_set: 'CDC-RE'} if ethnicity_node marital_status_node = patient_element.at_xpath("./cda:maritalStatusCode") patient.marital_status = {code: marital_status_node['code'], code_set: "HL7 Marital Status"} if marital_status_node ra_node = patient_element.at_xpath("./cda:religiousAffiliationCode") patient.religious_affiliation = {code: ra_node['code'], code_set: "Religious Affiliation"} if ra_node languages = patient_element.search('languageCommunication').map {|lc| lc.at_xpath('cda:languageCode')['code'] } patient.languages = languages unless languages.empty? patient.addresses = patient_role_element.xpath("./cda:addr").map { |addr| import_address(addr) } patient.telecoms = patient_role_element.xpath("./cda:telecom").map { |tele| import_telecom(tele) } end
Parses a HITSP C32
document and returns a Hash of of the patient.
@param [Nokogiri::XML::Document] doc It is expected that the root node of this document
will have the "cda" namespace registered to "urn:hl7-org:v3"
@return [Record] a Mongoid model representing the patient
# File lib/health-data-standards/import/c32/patient_importer.rb, line 84 def parse_c32(doc) c32_patient = Record.new get_demographics(c32_patient, doc) create_c32_hash(c32_patient, doc) check_for_cause_of_death(c32_patient) c32_patient end