Healthy Route Implementation Guide
0.2.0 - ci-build
Healthy Route Implementation Guide, published by Savannah Informatics. This guide is not an authorized publication; it is the continuous build for version 0.2.0 built by the FHIR (HL7® FHIR® Standard) CI Build. This version is based on the current content of https://github.com/savannahghi/healthy-route-ig/ and changes regularly. See the Directory of published versions
| Official URL: https://fhir.optimalhealth.org/ig/healthy-route/StructureMap/HRExtractHistory | Version: 0.2.0 | |||
| Draft as of 2026-11-12 | Computable Name: HRExtractHistory | |||
/// url = 'https://fhir.optimalhealth.org/ig/healthy-route/StructureMap/HRExtractHistory' /// version = '0.2.0' /// name = 'HRExtractHistory' /// status = 'draft' uses "http://hl7.org/fhir/StructureDefinition/QuestionnaireResponse" alias QR as source uses "http://hl7.org/fhir/StructureDefinition/Bundle" alias Bundle as target uses "http://hl7.org/fhir/StructureDefinition/Observation" alias Observation as target uses "http://hl7.org/fhir/StructureDefinition/Condition" alias Condition as target group HRExtractHistory(source qr : QR, target bundle : Bundle) { qr -> bundle.type = 'transaction' "type"; qr.item as it where (linkId = 'history-dm') then { it.answer first as a then { a -> bundle.entry as e, e.resource = create('Observation') as obs then { qr -> obs then SurveyObservation(qr, it, obs, e) "base"; qr -> obs.code = create('CodeableConcept') as cv then { qr -> cv.coding = create('Coding') as cd then { qr -> cd.system = 'https://fhir.optimalhealth.org/ig/healthy-route/CodeSystem/hr-measurement' "codeSystem"; qr -> cd.code = 'history-dm' "codeCode"; qr -> cd.display = 'Diabetes, reported' "codeDisplay"; } "codeCoding"; } "code"; a.value as v -> obs.value = v; } "obs"; a where (value = true) -> bundle.entry as e, e.resource = create('Condition') as cond then { qr -> cond then ReportedCondition(qr, it, cond, e) "base"; qr -> cond.code = create('CodeableConcept') as cv then { qr -> cv.coding = create('Coding') as cd then { qr -> cd.system = 'http://id.who.int/icd/release/11/mms' "codeSystem"; qr -> cd.code = '5A14' "codeCode"; qr -> cd.display = 'Diabetes mellitus, type unspecified' "codeDisplay"; } "codeCoding"; } "code"; } "condition"; }; } "dm"; qr.item as it where (linkId = 'history-htn') then { it.answer first as a then { a -> bundle.entry as e, e.resource = create('Observation') as obs then { qr -> obs then SurveyObservation(qr, it, obs, e) "base"; qr -> obs.code = create('CodeableConcept') as cv then { qr -> cv.coding = create('Coding') as cd then { qr -> cd.system = 'https://fhir.optimalhealth.org/ig/healthy-route/CodeSystem/hr-measurement' "codeSystem"; qr -> cd.code = 'history-htn' "codeCode"; qr -> cd.display = 'Hypertension, reported' "codeDisplay"; } "codeCoding"; } "code"; a.value as v -> obs.value = v; } "obs"; a where (value = true) -> bundle.entry as e, e.resource = create('Condition') as cond then { qr -> cond then ReportedCondition(qr, it, cond, e) "base"; qr -> cond.code = create('CodeableConcept') as cv then { qr -> cv.coding = create('Coding') as cd then { qr -> cd.system = 'http://id.who.int/icd/release/11/mms' "codeSystem"; qr -> cd.code = 'BA00' "codeCode"; qr -> cd.display = 'Essential hypertension' "codeDisplay"; } "codeCoding"; } "code"; } "condition"; }; } "htn"; qr.item as it where (linkId = 'history-ckd') then { it.answer first as a then { a -> bundle.entry as e, e.resource = create('Observation') as obs then { qr -> obs then SurveyObservation(qr, it, obs, e) "base"; qr -> obs.code = create('CodeableConcept') as cv then { qr -> cv.coding = create('Coding') as cd then { qr -> cd.system = 'https://fhir.optimalhealth.org/ig/healthy-route/CodeSystem/hr-measurement' "codeSystem"; qr -> cd.code = 'history-ckd' "codeCode"; qr -> cd.display = 'Chronic kidney disease, reported' "codeDisplay"; } "codeCoding"; } "code"; a.value as v -> obs.value = v; } "obs"; a where (value = true) -> bundle.entry as e, e.resource = create('Condition') as cond then { qr -> cond then ReportedCondition(qr, it, cond, e) "base"; qr -> cond.code = create('CodeableConcept') as cv then { qr -> cv.coding = create('Coding') as cd then { qr -> cd.system = 'http://id.who.int/icd/release/11/mms' "codeSystem"; qr -> cd.code = 'GB61' "codeCode"; qr -> cd.display = 'Chronic kidney disease' "codeDisplay"; } "codeCoding"; } "code"; } "condition"; }; } "ckd"; qr.item as it where (linkId = 'history-alcohol') then { it.answer first as a -> bundle.entry as e, e.resource = create('Observation') as obs then { qr -> obs then SurveyObservation(qr, it, obs, e) "base"; qr -> obs.category = create('CodeableConcept') as cv then { qr -> cv.coding = create('Coding') as cd then { qr -> cd.system = 'http://terminology.hl7.org/CodeSystem/observation-category' "socialHistorySystem"; qr -> cd.code = 'social-history' "socialHistoryCode"; qr -> cd.display = 'Social History' "socialHistoryDisplay"; } "socialHistoryCoding"; } "socialHistory"; qr -> obs.code = create('CodeableConcept') as cv then { qr -> cv.coding = create('Coding') as cd then { qr -> cd.system = 'https://fhir.optimalhealth.org/ig/healthy-route/CodeSystem/hr-measurement' "codeSystem"; qr -> cd.code = 'history-alcohol' "codeCode"; qr -> cd.display = 'Alcohol use' "codeDisplay"; } "codeCoding"; } "code"; a.value as v -> obs.value = create('CodeableConcept') as concept, concept.coding = v; } "obs"; } "alcohol"; qr.item as it where (linkId = '72166-2') then { it.answer first as a -> bundle.entry as e, e.resource = create('Observation') as obs then { qr -> obs then SurveyObservation(qr, it, obs, e) "base"; qr -> obs.category = create('CodeableConcept') as cv then { qr -> cv.coding = create('Coding') as cd then { qr -> cd.system = 'http://terminology.hl7.org/CodeSystem/observation-category' "socialHistorySystem"; qr -> cd.code = 'social-history' "socialHistoryCode"; qr -> cd.display = 'Social History' "socialHistoryDisplay"; } "socialHistoryCoding"; } "socialHistory"; qr -> obs.code = create('CodeableConcept') as cv then { qr -> cv.coding = create('Coding') as cd then { qr -> cd.system = 'http://loinc.org' "codeSystem"; qr -> cd.code = '72166-2' "codeCode"; qr -> cd.display = 'Tobacco smoking status' "codeDisplay"; } "codeCoding"; } "code"; a.value as v -> obs.value = create('CodeableConcept') as concept, concept.coding = v; } "obs"; } "smoking"; } // What every answer-as-Observation shares. The id is the response id followed // by the item's linkId, which is why a linkId is never longer than the id type // allows once the response id is in front of it. group SurveyObservation(source qr : QR, source it, target obs : Observation, target e) { qr -> evaluate(qr, id.replaceMatches('/_history/.*$', '').replaceMatches('^.*/', '')) as qid then { it.linkId as k -> append(qid, '-', k) as idText, obs.id = cast(idText, 'id') "id"; it.linkId as k -> e.fullUrl = append('Observation/', qid, '-', k) "fullUrl"; it.linkId as k -> e.request as rq then { qr -> rq.method = 'PUT' "method"; qr -> rq.url = append('Observation/', qid, '-', k) "url"; } "request"; } "ids"; qr -> obs.meta as m, m.profile = 'https://fhir.optimalhealth.org/ig/healthy-route/StructureDefinition/hr-observation' "profile"; qr.meta as qm then { qm.tag as t -> obs.meta as m, m.tag = t; } "tags"; qr.extension as x where (url = 'https://fhir.optimalhealth.org/ig/healthy-route/StructureDefinition/hr-tenant') -> obs.extension = x "tenant"; qr -> obs.status = 'final' "status"; qr -> obs.category = create('CodeableConcept') as cv then { qr -> cv.coding = create('Coding') as cd then { qr -> cd.system = 'http://terminology.hl7.org/CodeSystem/observation-category' "surveySystem"; qr -> cd.code = 'survey' "surveyCode"; qr -> cd.display = 'Survey' "surveyDisplay"; } "surveyCoding"; } "survey"; qr.subject as s -> obs.subject = s; qr.encounter as en -> obs.encounter = en; qr.authored as t -> obs.effective = t "effective"; qr.author as au -> obs.performer = au "performer"; } // A Yes to a reported diagnosis, asserted as a Condition that points back at // the answer it came from. group ReportedCondition(source qr : QR, source it, target cond : Condition, target e) { qr -> evaluate(qr, id.replaceMatches('/_history/.*$', '').replaceMatches('^.*/', '')) as qid then { it.linkId as k -> append(qid, '-', k, '-condition') as idText, cond.id = cast(idText, 'id') "id"; it.linkId as k -> e.fullUrl = append('Condition/', qid, '-', k, '-condition') "fullUrl"; it.linkId as k -> e.request as rq then { qr -> rq.method = 'PUT' "method"; qr -> rq.url = append('Condition/', qid, '-', k, '-condition') "url"; } "request"; it.linkId as k -> cond.evidence as ev, ev.reference = create('Reference') as ref, ref.reference = append('Observation/', qid, '-', k) "evidence"; } "ids"; qr -> cond.meta as m, m.profile = 'https://fhir.optimalhealth.org/ig/healthy-route/StructureDefinition/hr-condition' "profile"; qr.meta as qm then { qm.tag as t -> cond.meta as m, m.tag = t; } "tags"; qr.extension as x where (url = 'https://fhir.optimalhealth.org/ig/healthy-route/StructureDefinition/hr-tenant') -> cond.extension = x "tenant"; qr -> cond.clinicalStatus = create('CodeableConcept') as cv then { qr -> cv.coding = create('Coding') as cd then { qr -> cd.system = 'http://terminology.hl7.org/CodeSystem/condition-clinical' "clinicalSystem"; qr -> cd.code = 'active' "clinicalCode"; qr -> cd.display = 'Active' "clinicalDisplay"; } "clinicalCoding"; } "clinical"; qr -> cond.verificationStatus = create('CodeableConcept') as cv then { qr -> cv.coding = create('Coding') as cd then { qr -> cd.system = 'http://terminology.hl7.org/CodeSystem/condition-ver-status' "verificationSystem"; qr -> cd.code = 'unconfirmed' "verificationCode"; qr -> cd.display = 'Unconfirmed' "verificationDisplay"; } "verificationCoding"; } "verification"; qr -> cond.category = create('CodeableConcept') as cv then { qr -> cv.coding = create('Coding') as cd then { qr -> cd.system = 'http://terminology.hl7.org/CodeSystem/condition-category' "categorySystem"; qr -> cd.code = 'problem-list-item' "categoryCode"; qr -> cd.display = 'Problem List Item' "categoryDisplay"; } "categoryCoding"; } "category"; qr.subject as s -> cond.subject = s; qr.encounter as en -> cond.encounter = en; qr.authored as t -> cond.recordedDate = t "recorded"; }