Skip to content

Commit

Permalink
8 cdc chronic disease requests
Browse files Browse the repository at this point in the history
telemedicine visit valueset
initial import
#9

added more outpatient valusets from
CMS165v11 AdultOutpatientEncounters

valueset.py split *encounter* inclusion and exclusion into sets

valueset.py split *rx medications* inclusion and exclusion

steward: CMS165v11 AdvancedIllnessandFrailtyExclusionECQM

inpatient now includes both acute and NON acute inpatient encounters.

define_enc_observation are now exclusion criteria

define_enc_edvisit are now exclusion criteria

define_enc_icu are now exclusion criteria

milestone: Encounter inclusion/exclusion criteria
valusets from CMS165v11 and other sources, most commonly referencing NQF#0018

define_pregnancy: do not exclude pregnant patients

define_esrd.sql end stage renal disease (exclude)
define_frailty.sql frailty by device/dx/encounter (exclude)
define_advanced_illness.sql very sick patients (exclude)

organization: updating paths to prepare for valueset subdir

moved VSAC files to "valueset" dir

count low/high blood pressure from core__observation_vital_sign

https://github.com/smart-on-fhir/cumulus-library/blob/f630f01ee2ad74ce90348213a80840a123f9c203/cumulus_library/studies/core/observation_vital_signs.sql#L18

using US CORE Profile tested against Cerner data.

-- http://hl7.org/fhir/us/vitals/StructureDefinition/blood-pressure-panel
--
--85354-9	Blood pressure panel with all children optional
-- 8480-6	Systolic blood pressure
-- 8462-4	Diastolic blood pressure

performance improvements for buildings tables/counts.
Athena is struggling to index this much data, so we build tables in steps.

fixed table_bp.sql to join "observation_ref", much better SQL speed.
count.py updated to ouput counts for htn__count_bp

count.py now count by number of
PATIENT (instead of encounters)

table_bp.sql added race and ethnicity

htn__dx defined (refactored from counts sql file)

added support or htn__count_rx (optional)

updated README.md

* _htn__count_bp_month_ : BP (blood pressure) measures
* _htn__count_dx_month_ : HTN diagnosis codes
* _htn__count_rx_month_ : HTN blood pressure control meds

scaled back what we count.py

updated counts views.
procedure and medication are optional and by default commented out.

removed "order by cnt desc", will address in more detail later.
smart-on-fhir/cumulus-library#71
  • Loading branch information
comorbidity authored and dogversioning committed Jul 7, 2023
1 parent 1fd2c6e commit b854c53
Show file tree
Hide file tree
Showing 96 changed files with 16,007 additions and 1,886 deletions.
43 changes: 43 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,49 @@ This definition attempts to "multi-solve" counting HTN cases for CDC and CMS use
* CMS Quality Measures
* [Controlling High Blood Pressure CMS Quality #236 (NQF 0018)](https://docs.google.com/spreadsheets/d/1UTxg-MvAf0xMBI8dAw6SEF1cQduZqC330R-0MOAWli4/edit#gid=1986332053)

-----
**COUNT TABLES**

Count number of patients per month matching criteria
* _htn__count_bp_month_ : BP (blood pressure) measures
* _htn__count_dx_month_ : HTN diagnosis codes
* _htn__count_rx_month_ : HTN blood pressure control meds



| **htn__count_bp_month** | [Blood Pressure Panel](http://hl7.org/fhir/us/vitals/STU1/StructureDefinition-blood-pressure-panel.html) |
|-------------------------|----------------------------------------------------------------------------------------------------------------------------------|
| cnt | count number of patients |
| obs_month | Month of BP observation |
| hypertension | BP is 140/90 or higher (true or false) | |
| hypotension | BP is 90/60 or lower (true or false) |
| enc_class_code | [Encounter class](https://terminology.hl7.org/5.1.0/ValueSet-encounter-class.html) ambulatory, emergency, impatient, observation |
| gender | [female or male sex](http://hl7.org/fhir/ValueSet/administrative-gender) |
| age_at_visit | patient age at time of visit |
| race_display | [CDC R5 race](http://hl7.org/fhir/us/core/StructureDefinition/us-core-race) |
| ethnicity_display | [Hispanic or Latino](http://hl7.org/fhir/us/core/StructureDefinition/us-core-ethnicity) |

| **htn__count_dx_month** | Hypertension diagnosis (ICD10-CM or SNOMED-CT) |
|-------------------------|----------------------------------------------------------------------------------------------------------------------------------|
| cnt | count number of patients |
| cond_month | Month of HTN diagnosis |
| cond_display | Display the label of HTN diagnosis |
| cond_system_display | SNOMED-CT or ICD-10-CM | |
| enc_class_code | [Encounter class](https://terminology.hl7.org/5.1.0/ValueSet-encounter-class.html) ambulatory, emergency, impatient, observation |
| gender | female or male sex |
| age_at_visit | patient age at time of visit |
| race_display | CDC R5 code |
| ethnicity_display | Hispanic or Latino |


| **htn__count_rx_month** | Blood Pressure Medications |
|-------------------------|------------------------------------------------------------------------------------------------------------|
| cnt | count number of patients |
| authoredon_month | Month of medication request |
| rx_display | Display RXNORM drug label |
| rx_category_code | [inpatient, outpatient, or community](https://hl7.org/fhir/valueset-medicationrequest-admin-location.html) | |


-----

**DIAGNOSIS**
Expand Down
82 changes: 82 additions & 0 deletions cumulus_library_hypertension/htn/count.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
from typing import List
from cumulus_library.schema import counts

STUDY_PREFIX = 'htn'

def table(tablename: str, duration=None) -> str:
if duration:
return f'{STUDY_PREFIX}__{tablename}_{duration}'
else:
return f'{STUDY_PREFIX}__{tablename}'

def count_bp(duration=None):
view_name = table('count_bp', duration)
from_table = table('bp')
cols = ['hypertension', 'hypotension', 'enc_class_code',
'gender', 'age_at_visit', 'race_display', 'ethnicity_display']

if duration:
cols.append(f'obs_{duration}')

return counts.count_patient(view_name, from_table, cols)

def count_dx(duration='month'):
view_name = table('count_dx', duration)
from_table = table('dx')
cols = [f'cond_{duration}',
'enc_class_code',
'gender', 'age_at_visit', 'race_display', 'ethnicity_display',
'cond_display', 'cond_system_display']
return counts.count_patient(view_name, from_table, cols)

def count_rx(duration='month'):
view_name = table('count_rx', duration)
from_table = table('rx')
cols = ['category_code', 'rx_display']

if duration:
cols.append(f'authoredon_{duration}')

return counts.count_patient(view_name, from_table, cols)

def count_procedure(duration=None):
view_name = table('count_procedure', duration)
from_table = table('procedure')
cols = ['enc_class_display', 'proc_display', 'proc_system']

if duration:
cols.append(f'enc_start_{duration}')

return counts.count_encounter(view_name, from_table, cols)

def concat_view_sql(create_view_list: List[str]) -> str:
"""
:param create_view_list: SQL prepared statements
"""
seperator = '-- ###########################################################'
concat = list()

for create_view in create_view_list:
concat.append(seperator + '\n'+create_view + '\n')

return '\n'.join(concat)

def write_view_sql(view_list_sql: List[str], filename='count.sql') -> None:
"""
:param view_list_sql: SQL prepared statements
:param filename: path to output file, default 'count.sql' in PWD
"""
sql_optimizer = concat_view_sql(view_list_sql).replace('ORDER BY cnt desc', '')
with open(filename, 'w') as fout:
fout.write(sql_optimizer)


if __name__ == '__main__':
write_view_sql([
count_bp(),
count_bp('month'),
count_dx('month'),
# count_rx('month'), # TODO requires support for FHIR MedicationRequest
# count_procedure(), # TODO requires support for FHIR Procedure
# count_procedure('month'), # TODO requires support for FHIR Procedure
])
113 changes: 113 additions & 0 deletions cumulus_library_hypertension/htn/count.sql
Original file line number Diff line number Diff line change
@@ -0,0 +1,113 @@
-- ###########################################################
CREATE or replace VIEW htn__count_bp AS
with powerset as
(
select
count(distinct subject_ref) as cnt_subject

, hypertension, hypotension, enc_class_code, gender, age_at_visit, race_display, ethnicity_display
FROM htn__bp
group by CUBE
( hypertension, hypotension, enc_class_code, gender, age_at_visit, race_display, ethnicity_display )
)
select
cnt_subject as cnt
, hypertension, hypotension, enc_class_code, gender, age_at_visit, race_display, ethnicity_display
from powerset
WHERE cnt_subject >= 10
;

-- ###########################################################
CREATE or replace VIEW htn__count_bp_month AS
with powerset as
(
select
count(distinct subject_ref) as cnt_subject

, hypertension, hypotension, enc_class_code, gender, age_at_visit, race_display, ethnicity_display, obs_month
FROM htn__bp
group by CUBE
( hypertension, hypotension, enc_class_code, gender, age_at_visit, race_display, ethnicity_display, obs_month )
)
select
cnt_subject as cnt
, hypertension, hypotension, enc_class_code, gender, age_at_visit, race_display, ethnicity_display, obs_month
from powerset
WHERE cnt_subject >= 10
;

-- ###########################################################
CREATE or replace VIEW htn__count_dx_month AS
with powerset as
(
select
count(distinct subject_ref) as cnt_subject

, cond_month, enc_class_code, gender, age_at_visit, race_display, ethnicity_display, cond_display, cond_system_display
FROM htn__dx
group by CUBE
( cond_month, enc_class_code, gender, age_at_visit, race_display, ethnicity_display, cond_display, cond_system_display )
)
select
cnt_subject as cnt
, cond_month, enc_class_code, gender, age_at_visit, race_display, ethnicity_display, cond_display, cond_system_display
from powerset
WHERE cnt_subject >= 10
;

-- ###########################################################
--CREATE or replace VIEW htn__count_rx_month AS
-- with powerset as
-- (
-- select
-- count(distinct subject_ref) as cnt_subject
--
-- , category_code, rx_display, authoredon_month
-- FROM htn__rx
-- group by CUBE
-- ( category_code, rx_display, authoredon_month )
-- )
-- select
-- cnt_subject as cnt
-- , category_code, rx_display, authoredon_month
-- from powerset
-- WHERE cnt_subject >= 10
-- ;

-- ###########################################################
--CREATE or replace VIEW htn__count_procedure AS
-- with powerset as
-- (
-- select
-- count(distinct subject_ref) as cnt_subject
-- , count(distinct encounter_ref) as cnt_encounter
-- , enc_class_display, proc_display, proc_system
-- FROM htn__procedure
-- group by CUBE
-- ( enc_class_display, proc_display, proc_system )
-- )
-- select
-- cnt_encounter as cnt
-- , enc_class_display, proc_display, proc_system
-- from powerset
-- WHERE cnt_subject >= 10
-- ;

-- ###########################################################
--CREATE or replace VIEW htn__count_procedure_month AS
-- with powerset as
-- (
-- select
-- count(distinct subject_ref) as cnt_subject
-- , count(distinct encounter_ref) as cnt_encounter
-- , enc_class_display, proc_display, proc_system, enc_start_month
-- FROM htn__procedure
-- group by CUBE
-- ( enc_class_display, proc_display, proc_system, enc_start_month )
-- )
-- select
-- cnt_encounter as cnt
-- , enc_class_display, proc_display, proc_system, enc_start_month
-- from powerset
-- WHERE cnt_subject >= 10
-- ;
31 changes: 0 additions & 31 deletions cumulus_library_hypertension/htn/count_bp.sql

This file was deleted.

45 changes: 0 additions & 45 deletions cumulus_library_hypertension/htn/count_dx.sql

This file was deleted.

Loading

0 comments on commit b854c53

Please sign in to comment.