Highway to PSR2
[openemr.git] / library / classes / rulesets / Cqm / library / AbstractCqmReport.php
blobfb2382907ed60c0e568ef22927d5952963c4078f
1 <?php
2 // Copyright (C) 2011 Ken Chapple <ken@mi-squared.com>
3 //
4 // This program is free software; you can redistribute it and/or
5 // modify it under the terms of the GNU General Public License
6 // as published by the Free Software Foundation; either version 2
7 // of the License, or (at your option) any later version.
8 //
9 require_once(dirname(__FILE__)."/../../../../clinical_rules.php");
11 abstract class AbstractCqmReport implements RsReportIF
13 protected $_cqmPopulation;
15 protected $_resultsArray = array();
17 protected $_rowRule;
18 protected $_ruleId;
19 protected $_beginMeasurement;
20 protected $_endMeasurement;
22 public function __construct(array $rowRule, array $patientIdArray, $dateTarget)
24 // require all .php files in the report's sub-folder
25 $className = get_class($this);
26 foreach (glob(dirname(__FILE__)."/../reports/".$className."/*.php") as $filename) {
27 require_once($filename);
30 // require common .php files
31 foreach (glob(dirname(__FILE__)."/../reports/common/*.php") as $filename) {
32 require_once($filename);
35 // require clinical types
36 foreach (glob(dirname(__FILE__)."/../../../ClinicalTypes/*.php") as $filename) {
37 require_once($filename);
40 $this->_cqmPopulation = new CqmPopulation($patientIdArray);
41 $this->_rowRule = $rowRule;
42 $this->_ruleId = isset($rowRule['id']) ? $rowRule['id'] : '';
43 // Calculate measurement period
44 $tempDateArray = explode("-", $dateTarget);
45 $tempYear = $tempDateArray[0];
46 $this->_beginMeasurement = $tempDateArray[0] . "-01-01 00:00:00";
47 $this->_endMeasurement = $tempDateArray[0] . "-12-31 23:59:59";
50 abstract public function createPopulationCriteria();
52 public function getBeginMeasurement()
54 return $this->_beginMeasurement;
57 public function getEndMeasurement()
59 return $this->_endMeasurement;
62 public function getResults()
64 return $this->_resultsArray;
67 public function execute()
69 $populationCriterias = $this->createPopulationCriteria();
70 if (!is_array($populationCriterias)) {
71 $tmpPopulationCriterias = array();
72 $tmpPopulationCriterias[]= $populationCriterias;
73 $populationCriterias = $tmpPopulationCriterias;
76 foreach ($populationCriterias as $populationCriteria) {
77 // If itemization is turned on, then iterate the rule id iterator
78 if ($GLOBALS['report_itemizing_temp_flag_and_id']) {
79 $GLOBALS['report_itemized_test_id_iterator']++;
82 if ($populationCriteria instanceof CqmPopulationCrtiteriaFactory) {
83 $initialPatientPopulationFilter = $populationCriteria->createInitialPatientPopulation();
84 if (!$initialPatientPopulationFilter instanceof CqmFilterIF) {
85 throw new Exception("InitialPatientPopulation must be an instance of CqmFilterIF");
88 $denominator = $populationCriteria->createDenominator();
89 if (!$denominator instanceof CqmFilterIF) {
90 throw new Exception("Denominator must be an instance of CqmFilterIF");
93 $numerators = $populationCriteria->createNumerators();
94 if (!is_array($numerators)) {
95 $tmpNumerators = array();
96 $tmpNumerators[]= $numerators;
97 $numerators = $tmpNumerators;
100 $exclusion = $populationCriteria->createExclusion();
101 if (!$exclusion instanceof CqmFilterIF) {
102 throw new Exception("Exclusion must be an instance of CqmFilterIF");
105 //Denominator Exception added
106 $denomExept = false;
107 if (method_exists($populationCriteria, 'createDenominatorException')) {
108 $denomExept = true;
111 $totalPatients = count($this->_cqmPopulation);
112 $initialPatientPopulation = 0;
113 $denominatorPatientPopulation = 0;
114 $exclusionsPatientPopulation = 0;
115 $exceptionsPatientPopulation = 0; // this is a bridge to no where variable (calculated but not used below). Will keep for now, though.
116 $patExclArr = array();
117 $patExceptArr = array();
118 $numeratorPatientPopulations = $this->initNumeratorPopulations($numerators);
119 foreach ($this->_cqmPopulation as $patient) {
120 if (!$initialPatientPopulationFilter->test($patient, $this->_beginMeasurement, $this->_endMeasurement)) {
121 continue;
124 $initialPatientPopulation++;
126 // If itemization is turned on, then record the "Initial Patient population" item
127 if ($GLOBALS['report_itemizing_temp_flag_and_id']) {
128 insertItemReportTracker($GLOBALS['report_itemizing_temp_flag_and_id'], $GLOBALS['report_itemized_test_id_iterator'], 3, $patient->id);
131 if (!$denominator->test($patient, $this->_beginMeasurement, $this->_endMeasurement)) {
132 continue;
135 $denominatorPatientPopulation++;
137 if ($exclusion->test($patient, $this->_beginMeasurement, $this->_endMeasurement)) {
138 $exclusionsPatientPopulation++;
139 $patExclArr[] = $patient->id;
142 //Denominator Exception added
143 if ($denomExept) {
144 $denom_exception = $populationCriteria->createDenominatorException();
145 if ($denom_exception->test($patient, $this->_beginMeasurement, $this->_endMeasurement)) {
146 $exceptionsPatientPopulation++; // this is a bridge to no where variable (not used below). Will keep for now, though.
147 $patExceptArr[] = $patient->id;
151 foreach ($numerators as $numerator) {
152 $this->testNumerator($patient, $numerator, $numeratorPatientPopulations);
156 // tally results, run exclusion on each numerator
157 $pass_filt = $denominatorPatientPopulation;
158 $exclude_filt = $exclusionsPatientPopulation;
159 foreach ($numeratorPatientPopulations as $title => $pass_targ) {
160 if (count($patExclArr) > 0) {
161 foreach ($patExclArr as $patVal) {
162 // If itemization is turned on, then record the "excluded" item
163 if ($GLOBALS['report_itemizing_temp_flag_and_id']) {
164 insertItemReportTracker($GLOBALS['report_itemizing_temp_flag_and_id'], $GLOBALS['report_itemized_test_id_iterator'], 2, $patVal, $title);
169 if (count($patExceptArr) > 0) {
170 foreach ($patExceptArr as $patVal) {
171 // If itemization is turned on, then record the "exception" item
172 if ($GLOBALS['report_itemizing_temp_flag_and_id']) {
173 insertItemReportTracker($GLOBALS['report_itemizing_temp_flag_and_id'], $GLOBALS['report_itemized_test_id_iterator'], 4, $patVal, $title);
178 $percentage = calculate_percentage($pass_filt, $exclude_filt, $pass_targ);
179 $this->_resultsArray[]= new CqmResult(
180 $this->_rowRule,
181 $title,
182 $populationCriteria->getTitle(),
183 $totalPatients,
184 $pass_filt,
185 $exclude_filt,
186 $pass_targ,
187 $percentage,
188 $initialPatientPopulation,
189 $exceptionsPatientPopulation
195 return $this->_resultsArray;
198 private function initNumeratorPopulations(array $numerators)
200 $numeratorPatientPopulations = array();
201 foreach ($numerators as $numerator) {
202 $numeratorPatientPopulations[$numerator->getTitle()] = 0;
205 return $numeratorPatientPopulations;
208 private function testNumerator($patient, $numerator, &$numeratorPatientPopulations)
210 if ($numerator instanceof CqmFilterIF) {
211 if ($numerator->test($patient, $this->_beginMeasurement, $this->_endMeasurement)) {
212 $numeratorPatientPopulations[$numerator->getTitle()]++;
214 // If itemization is turned on, then record the "passed" item
215 if ($GLOBALS['report_itemizing_temp_flag_and_id']) {
216 insertItemReportTracker($GLOBALS['report_itemizing_temp_flag_and_id'], $GLOBALS['report_itemized_test_id_iterator'], 1, $patient->id, $numerator->getTitle());
218 } else {
219 // If itemization is turned on, then record the "failed" item
220 if ($GLOBALS['report_itemizing_temp_flag_and_id']) {
221 insertItemReportTracker($GLOBALS['report_itemizing_temp_flag_and_id'], $GLOBALS['report_itemized_test_id_iterator'], 0, $patient->id, $numerator->getTitle());
224 } else {
225 throw new Exception("Numerator must be an instance of CqmFilterIF");