diff --git a/library/clinical_rules.php b/library/clinical_rules.php index c56ad5f65fa..dd5596e03a9 100644 --- a/library/clinical_rules.php +++ b/library/clinical_rules.php @@ -172,6 +172,12 @@ function test_rules_clinic($provider='',$type='',$dateTarget='',$mode='',$patien $dateCounter = 1; // for reminder mode to keep track of which date checking foreach ( $target_dates as $dateFocus ) { + //Skip if date is set to SKIP + if ($dateFocus == "SKIP") { + $dateCounter++; + continue; + } + //Set date counter and reminder token (applicable for reminders only) if ($dateCounter == 1) { $reminder_due = "soon_due"; @@ -189,6 +195,7 @@ function test_rules_clinic($provider='',$type='',$dateTarget='',$mode='',$patien $pass_filter++; } else { + $dateCounter++; continue; } @@ -245,6 +252,12 @@ function test_rules_clinic($provider='',$type='',$dateTarget='',$mode='',$patien $dateCounter = 1; // for reminder mode to keep track of which date checking foreach ( $target_dates as $dateFocus ) { + //Skip if date is set to SKIP + if ($dateFocus == "SKIP") { + $dateCounter++; + continue; + } + //Set date counter and reminder token (applicable for reminders only) if ($dateCounter == 1) { $reminder_due = "soon_due"; @@ -464,6 +477,11 @@ function test_targets($patient_id,$rule,$group_id='',$dateTarget) { $target = resolve_target_sql($rule,$group_id,'target_proc'); if ((!empty($target)) && !procedure_check($patient_id,$target,$interval,$dateTarget)) return false; + // -------- Appointment Target ---- + // Appointment Target (includes) (Specialized functionality for appointment reminders) + $target = resolve_target_sql($rule,$group_id,'target_appt'); + if ((!empty($target)) && appointment_check($patient_id,$dateTarget)) return false; + // Passed all target tests, so return true. return true; } @@ -716,6 +734,46 @@ function procedure_check($patient_id,$filter,$interval='',$dateTarget='') { return $isMatch; } +// Function to check for appointment +// Parameters: +// $patient_id - pid of selected patient. +// $dateTarget - target date. +// Return: boolean if appt exist, otherwise false +function appointment_check($patient_id,$dateTarget='') { + $isMatch = false; //matching flag + + // Set date to current if not set (although should always be set) + $dateTarget = ($dateTarget) ? $dateTarget : date('Y-m-d H:i:s'); + $dateTargetRound = date('Y-m-d',$dateTarget); + + // Set current date + $currentDate = date('Y-m-d H:i:s'); + $currentDateRound = date('Y-m-d',$dateCurrent); + + // Basically, if the appointment is within the current date to the target date, + // then return true. (will not send reminders on same day as appointment) + $sql = sqlStatement("SELECT openemr_postcalendar_events.pc_eid, " . + "openemr_postcalendar_events.pc_title, " . + "openemr_postcalendar_events.pc_eventDate, " . + "openemr_postcalendar_events.pc_startTime, " . + "openemr_postcalendar_events.pc_endTime " . + "FROM openemr_postcalendar_events " . + "WHERE openemr_postcalendar_events.pc_eventDate > ? " . + "AND openemr_postcalendar_events.pc_eventDate <= ? " . + "AND openemr_postcalendar_events.pc_pid = ?", array($currentDate,$dateTarget,$patient_id) ); + + // return results of check + // + // TODO: Figure out how to have multiple appointment and changing appointment reminders. + // Plan to send back array of appt info (eid, time, date, etc.) + // to do this. + if (sqlNumRows($sql) > 0) { + $isMatch = true; + } + + return $isMatch; +} + // Function to check lists filters and targets // Customizable and currently includes diagnoses, medications, // allergies and surgeries. @@ -1153,6 +1211,15 @@ function calculate_reminder_dates($rule, $dateTarget='',$type) { // Set date to current if not set $dateTarget = ($dateTarget) ? $dateTarget : date('Y-m-d H:i:s'); + // Collect the current date settings (to ensure not skip) + $res = resolve_reminder_sql($rule, $type.'_current'); + if (!empty($res)) { + $row = $res[0]; + if ($row ['method_detail'] == "SKIP") { + $dateTarget = "SKIP"; + } + } + // Collect the past_due date $past_due_date == ""; $res = resolve_reminder_sql($rule, $type.'_post'); @@ -1164,6 +1231,12 @@ function calculate_reminder_dates($rule, $dateTarget='',$type) { if ($row ['method_detail'] == "month") { $past_due_date = date("Y-m-d H:i:s", strtotime($dateTarget . " -" . $row ['value'] . " month")); } + if ($row ['method_detail'] == "hour") { + $past_due_date = date("Y-m-d H:i:s", strtotime($dateTarget . " -" . $row ['value'] . " hour")); + } + if ($row ['method_detail'] == "SKIP") { + $past_due_date = "SKIP"; + } } else { // empty settings, so use default of one month @@ -1181,6 +1254,12 @@ function calculate_reminder_dates($rule, $dateTarget='',$type) { if ($row ['method_detail'] == "month") { $soon_due_date = date("Y-m-d H:i:s", strtotime($dateTarget . " +" . $row ['value'] . " month")); } + if ($row ['method_detail'] == "hour") { + $soon_due_date = date("Y-m-d H:i:s", strtotime($dateTarget . " -" . $row ['value'] . " hour")); + } + if ($row ['method_detail'] == "SKIP") { + $soon_due_date = "SKIP"; + } } else { // empty settings, so use default of one month diff --git a/sql/database.sql b/sql/database.sql index 3726a503e39..7628abea89c 100644 --- a/sql/database.sql +++ b/sql/database.sql @@ -3550,6 +3550,11 @@ INSERT INTO `clinical_rules` ( `id`, `pid`, `active`, `active_alert_flag`, `pass -- INSERT INTO `clinical_rules` ( `id`, `pid`, `active`, `active_alert_flag`, `passive_alert_flag`, `cqm_flag`, `cqm_code`, `patient_reminder_flag` ) VALUES ('rule_inr_monitor', 0, 1, 0, 1, 0, '', 1); +-- +-- Rule for appointment reminder +-- +INSERT INTO `clinical_rules` ( `id`, `pid`, `active`, `active_alert_flag`, `passive_alert_flag`, `cqm_flag`, `cqm_code`, `patient_reminder_flag` ) VALUES ('rule_appt_reminder', 0, 1, 0, 0, 0, '', 1); + -- Clinical rule titles INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default` ) VALUES ('lists' ,'clinical_rules','Clinical Rules', 3, 0); INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default` ) VALUES ('clinical_rules', 'rule_htn_bp_measure_cqm', 'Hypertension: Blood Pressure Measurement (CQM)', 10, 0); @@ -3580,6 +3585,7 @@ INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default` ) VALUES ('clinical_rules', 'rule_cs_colon', 'Cancer Screening: Colon Cancer Screening', 640, 0); INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default` ) VALUES ('clinical_rules', 'rule_cs_prostate', 'Cancer Screening: Prostate Cancer Screening', 650, 0); INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default` ) VALUES ('clinical_rules', 'rule_inr_monitor', 'Coumadin Management - INR Monitoring', 1000, 0); +INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default` ) VALUES ('clinical_rules', 'rule_appt_reminder', 'Appointment Reminder Rule', 2000, 0); -- -------------------------------------------------------- @@ -3721,6 +3727,11 @@ INSERT INTO `rule_filter` ( `id`, `include_flag`, `required_flag`, `method`, `me INSERT INTO `rule_filter` ( `id`, `include_flag`, `required_flag`, `method`, `method_detail`, `value` ) VALUES ('rule_inr_monitor', 1, 0, 'filt_lists', 'medication', 'coumadin'); INSERT INTO `rule_filter` ( `id`, `include_flag`, `required_flag`, `method`, `method_detail`, `value` ) VALUES ('rule_inr_monitor', 1, 0, 'filt_lists', 'medication', 'warfarin'); +-- +-- For appointment reminder +-- +-- no filter + -- -- Associated lists -- @@ -3918,6 +3929,11 @@ INSERT INTO `rule_target` ( `id`, `group_id`, `include_flag`, `required_flag`, ` INSERT INTO `rule_target` ( `id`, `group_id`, `include_flag`, `required_flag`, `method`, `value`, `interval` ) VALUES ('rule_inr_monitor', 1, 1, 1, 'target_interval', 'week', 3); INSERT INTO `rule_target` ( `id`, `group_id`, `include_flag`, `required_flag`, `method`, `value`, `interval` ) VALUES ('rule_inr_monitor', 1, 1, 1, 'target_proc', 'INR::::::::ge::1', 0); +-- +-- For appointment reminder +-- +INSERT INTO `rule_target` ( `id`, `group_id`, `include_flag`, `required_flag`, `method`, `value`, `interval` ) VALUES ('rule_appt_reminder', 1, 1, 1, 'target_appt', '', 0); + -- -- Associated lists -- @@ -3989,6 +4005,7 @@ INSERT INTO `rule_action` ( `id`, `group_id`, `category`, `item` ) VALUES ('rule INSERT INTO `rule_action` ( `id`, `group_id`, `category`, `item` ) VALUES ('rule_cs_colon', 1, 'act_cat_assess', 'act_colon_cancer_screen'); INSERT INTO `rule_action` ( `id`, `group_id`, `category`, `item` ) VALUES ('rule_cs_prostate', 1, 'act_cat_assess', 'act_prostate_cancer_screen'); INSERT INTO `rule_action` ( `id`, `group_id`, `category`, `item` ) VALUES ('rule_inr_monitor', 1, 'act_cat_measure', 'act_lab_inr'); +INSERT INTO `rule_action` ( `id`, `group_id`, `category`, `item` ) VALUES ('rule_appt_reminder', 1, 'act_cat_remind', 'act_appointment'); -- -------------------------------------------------------- @@ -4023,6 +4040,7 @@ INSERT INTO `rule_action_item` ( `category`, `item`, `clin_rem_link`, `reminder_ INSERT INTO `rule_action_item` ( `category`, `item`, `clin_rem_link`, `reminder_message`, `custom_flag` ) VALUES ('act_cat_assess', 'act_colon_cancer_screen', '', '', 1); INSERT INTO `rule_action_item` ( `category`, `item`, `clin_rem_link`, `reminder_message`, `custom_flag` ) VALUES ('act_cat_assess', 'act_prostate_cancer_screen', '', '', 1); INSERT INTO `rule_action_item` ( `category`, `item`, `clin_rem_link`, `reminder_message`, `custom_flag` ) VALUES ('act_cat_measure', 'act_lab_inr', '', '', 0); +INSERT INTO `rule_action_item` ( `category`, `item`, `clin_rem_link`, `reminder_message`, `custom_flag` ) VALUES ('act_cat_remind', 'act_appointment', '', '', 0); -- -- Associated lists @@ -4035,6 +4053,7 @@ INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default` ) VALUES ('rule_action_category' ,'act_cat_inter', 'Intervention', 40, 0); INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default` ) VALUES ('rule_action_category' ,'act_cat_measure', 'Measurement', 50, 0); INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default` ) VALUES ('rule_action_category' ,'act_cat_treat', 'Treatment', 60, 0); +INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default` ) VALUES ('rule_action_category' ,'act_cat_remind', 'Reminder', 70, 0); INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default` ) VALUES ('lists' ,'rule_action', 'Clinical Rule Action Item', 3, 0); INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default` ) VALUES ('rule_action' ,'act_bp', 'Blood Pressure', 10, 0); @@ -4052,6 +4071,7 @@ INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default` ) VALUES ('rule_action' ,'act_colon_cancer_screen', 'Colon Cancer Screening', 130, 0); INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default` ) VALUES ('rule_action' ,'act_prostate_cancer_screen', 'Prostate Cancer Screening', 140, 0); INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default` ) VALUES ('rule_action' ,'act_lab_inr', 'INR', 150, 0); +INSERT INTO `list_options` ( `list_id`, `option_id`, `title`, `seq`, `is_default` ) VALUES ('rule_action' ,'act_appointment', 'Appointment', 160, 0); -- -------------------------------------------------------- @@ -4190,6 +4210,11 @@ INSERT INTO `rule_reminder` ( `id`, `method`, `method_detail`, `value` ) VALUES INSERT INTO `rule_reminder` ( `id`, `method`, `method_detail`, `value` ) VALUES ('rule_inr_monitor', 'patient_reminder_pre', 'week', '2'); INSERT INTO `rule_reminder` ( `id`, `method`, `method_detail`, `value` ) VALUES ('rule_inr_monitor', 'patient_reminder_post', 'month', '1'); +-- Appointment Rrminder +INSERT INTO `rule_reminder` ( `id`, `method`, `method_detail`, `value` ) VALUES ('rule_appt_remind', 'patient_reminder_pre', 'hour', '72'); +INSERT INTO `rule_reminder` ( `id`, `method`, `method_detail`, `value` ) VALUES ('rule_appt_remind', 'patient_reminder_post', 'SKIP', '0'); +INSERT INTO `rule_reminder` ( `id`, `method`, `method_detail`, `value` ) VALUES ('rule_appt_remind', 'patient_reminder_current', 'SKIP', '0'); + -- -- Associated lists --