PageRenderTime 69ms CodeModel.GetById 22ms RepoModel.GetById 0ms app.codeStats 1ms

/interface/modules/zend_modules/module/Carecoordination/src/Carecoordination/Model/EncounterccdadispatchTable.php

https://bitbucket.org/openemr/openemr
PHP | 2574 lines | 2004 code | 262 blank | 308 comment | 132 complexity | dc025a64b99cd19d539b4f84e70f047b MD5 | raw file
Possible License(s): Apache-2.0, AGPL-1.0, GPL-2.0, LGPL-3.0, BSD-3-Clause, Unlicense, MPL-2.0, GPL-3.0, LGPL-2.1
  1. <?php
  2. /**
  3. * interface/modules/zend_modules/module/Carecoordination/src/Carecoordination/Model/EncounterccdadispatchTable.php
  4. *
  5. * @package OpenEMR
  6. * @link https://www.open-emr.org
  7. * @author Vinish K <vinish@zhservices.com>
  8. * @author Riju K P <rijukp@zhservices.com>
  9. * @copyright Copyright (c) 2014 Z&H Consultancy Services Private Limited <sam@zhservices.com>
  10. * @license https://github.com/openemr/openemr/blob/master/LICENSE GNU General Public License 3
  11. */
  12. namespace Carecoordination\Model;
  13. use Application\Listener\Listener;
  14. use Application\Model\ApplicationTable;
  15. use Carecoordination\Model\CarecoordinationTable;
  16. use CouchDB;
  17. use Laminas\Db\Adapter\Driver\Pdo\Result;
  18. use Laminas\Db\TableGateway\AbstractTableGateway;
  19. use Matrix\Exception;
  20. use OpenEMR\Common\Crypto\CryptoGen;
  21. use OpenEMR\Common\Uuid\UuidRegistry;
  22. require_once(__DIR__ . "/../../../../../../../../custom/code_types.inc.php");
  23. require_once(__DIR__ . "/../../../../../../../forms/vitals/report.php");
  24. class EncounterccdadispatchTable extends AbstractTableGateway
  25. {
  26. public function __construct()
  27. {
  28. }
  29. /*Fetch Patient data from EMR
  30. * @param $pid
  31. * @param $encounter
  32. * @return $patient_data Patient Data in XML format
  33. */
  34. public function getPatientdata($pid, $encounter)
  35. {
  36. $query = "select patient_data.*, l1.notes AS race_code, l1.title as race_title, l2.notes AS ethnicity_code, l2.title as ethnicity_title, l3.title as religion, l3.notes as religion_code, l4.notes as language_code, l4.title as language_title
  37. from patient_data
  38. left join list_options as l1 on l1.list_id=? AND l1.option_id=race
  39. left join list_options as l2 on l2.list_id=? AND l2.option_id=ethnicity
  40. left join list_options AS l3 ON l3.list_id=? AND l3.option_id=religion
  41. left join list_options AS l4 ON l4.list_id=? AND l4.option_id=language
  42. where pid=?";
  43. $appTable = new ApplicationTable();
  44. $row = $appTable->zQuery($query, array('race', 'ethnicity', 'religious_affiliation', 'language', $pid));
  45. foreach ($row as $result) {
  46. $patient_data = "<patient>
  47. <id>" . xmlEscape($result['pid']) . "</id>
  48. <encounter>" . xmlEscape($encounter) . "</encounter>
  49. <prefix>" . xmlEscape($result['title']) . "</prefix>
  50. <fname>" . xmlEscape($result['fname']) . "</fname>
  51. <mname>" . xmlEscape($result['mname']) . "</mname>
  52. <lname>" . xmlEscape($result['lname']) . "</lname>
  53. <suffix>" . xmlEscape($result['suffix']) . "</suffix>
  54. <birth_fname>" . xmlEscape($result['birth_fname']) . "</birth_fname>
  55. <birth_mname>" . xmlEscape($result['birth_mname']) . "</birth_mname>
  56. <birth_lname>" . xmlEscape($result['birth_lname']) . "</birth_lname>
  57. <street>" . xmlEscape($result['street']) . "</street>
  58. <city>" . xmlEscape($result['city']) . "</city>
  59. <state>" . xmlEscape($result['state']) . "</state>
  60. <postalCode>" . xmlEscape($result['postal_code']) . "</postalCode>
  61. <country>" . xmlEscape($result['country_code']) . "</country>
  62. <ssn>" . xmlEscape($result['ss'] ?: '') . "</ssn>
  63. <dob>" . xmlEscape(str_replace('-', '', $result['DOB'])) . "</dob>
  64. <gender>" . xmlEscape($result['sex']) . "</gender>
  65. <gender_code>" . xmlEscape(strtoupper(substr($result['sex'], 0, 1))) . "</gender_code>
  66. <status>" . xmlEscape($result['status'] ?: "") . "</status>
  67. <status_code>" . xmlEscape($result['status'] ? strtoupper(substr($result['status'], 0, 1)) : 0) . "</status_code>
  68. <phone_home>" . xmlEscape(($result['phone_home'] ?: '')) . "</phone_home>
  69. <phone_mobile>" . xmlEscape(($result['phone_home'] ? $result['phone_cell'] : '')) . "</phone_mobile>
  70. <email>" . xmlEscape(($result['email'] ?: '')) . "</email>
  71. <religion>" . xmlEscape(Listener::z_xlt($result['religion'] ?: "")) . "</religion>
  72. <religion_code>" . xmlEscape($result['religion_code'] ?: '') . "</religion_code>
  73. <race>" . xmlEscape(Listener::z_xlt($result['race_title'])) . "</race>
  74. <race_code>" . xmlEscape($result['race_code']) . "</race_code>
  75. <ethnicity>" . xmlEscape(Listener::z_xlt($result['ethnicity_title'])) . "</ethnicity>
  76. <ethnicity_code>" . xmlEscape($result['ethnicity_code']) . "</ethnicity_code>
  77. <language>" . xmlEscape(Listener::z_xlt($result['language_title'])) . "</language>
  78. <language_code>" . xmlEscape($result['language_code']) . "</language_code>
  79. </patient>
  80. <guardian>
  81. <fname>" . xmlEscape($result['']) . "</fname>
  82. <lname>" . xmlEscape($result['']) . "</lname>
  83. <code>" . xmlEscape($result['']) . "</code>
  84. <relation>" . xmlEscape($result['guardianrelationship']) . "</relation>
  85. <display_name>" . xmlEscape($result['guardiansname']) . "</display_name>
  86. <street>" . xmlEscape($result['guardianaddress']) . "</street>
  87. <city>" . xmlEscape($result['guardiancity']) . "</city>
  88. <state>" . xmlEscape($result['guardianstate']) . "</state>
  89. <postalCode>" . xmlEscape($result['guardianpostalcode']) . "</postalCode>
  90. <country>" . xmlEscape($result['guardiancountry']) . "</country>
  91. <telecom>" . xmlEscape($result['guardianphone']) . "</telecom>
  92. </guardian>";
  93. }
  94. return $patient_data;
  95. }
  96. public function getProviderDetails($pid, $encounter)
  97. {
  98. $provider_details = '';
  99. if (!$encounter) {
  100. $query_enc = "SELECT encounter FROM form_encounter WHERE pid=? ORDER BY date DESC LIMIT 1";
  101. $appTable = new ApplicationTable();
  102. $res_enc = $appTable->zQuery($query_enc, array($pid));
  103. foreach ($res_enc as $row_enc) {
  104. $encounter = $row_enc['encounter'];
  105. }
  106. }
  107. $query = "SELECT * FROM form_encounter as fe
  108. JOIN users AS u ON u.id = fe.provider_id
  109. JOIN facility AS f ON f.id = u.facility_id
  110. WHERE fe.pid = ? AND fe.encounter = ?";
  111. $appTable = new ApplicationTable();
  112. $row = $appTable->zQuery($query, array($pid, $encounter));
  113. foreach ($row as $result) {
  114. $provider_details = "<encounter_provider>
  115. <facility_id>" . xmlEscape($result['id']) . "</facility_id>
  116. <facility_npi>" . xmlEscape($result['facility_npi']) . "</facility_npi>
  117. <facility_oid>" . xmlEscape($result['oid']) . "</facility_oid>
  118. <facility_name>" . xmlEscape($result['name']) . "</facility_name>
  119. <facility_phone>" . xmlEscape(($result['phone'] ? $result['phone'] : 0)) . "</facility_phone>
  120. <facility_fax>" . xmlEscape($result['fax']) . "</facility_fax>
  121. <facility_street>" . xmlEscape($result['street']) . "</facility_street>
  122. <facility_city>" . xmlEscape($result['city']) . "</facility_city>
  123. <facility_state>" . xmlEscape($result['state']) . "</facility_state>
  124. <facility_postal_code>" . xmlEscape($result['postal_code']) . "</facility_postal_code>
  125. <facility_country_code>" . xmlEscape($result['country_code']) . "</facility_country_code>
  126. </encounter_provider>
  127. ";
  128. }
  129. return $provider_details;
  130. }
  131. public function getAuthor($pid, $encounter)
  132. {
  133. $author = '';
  134. $details = $this->getDetails('hie_author_id');
  135. $author = "
  136. <author>
  137. <streetAddressLine>" . xmlEscape($details['street']) . "</streetAddressLine>
  138. <city>" . xmlEscape($details['city']) . "</city>
  139. <state>" . xmlEscape($details['state']) . "</state>
  140. <postalCode>" . xmlEscape($details['zip']) . "</postalCode>
  141. <country>" . xmlEscape($details['']) . "</country>
  142. <telecom>" . xmlEscape(($details['phonew1'] ? $details['phonew1'] : 0)) . "</telecom>
  143. <fname>" . xmlEscape($details['fname']) . "</fname>
  144. <lname>" . xmlEscape($details['lname']) . "</lname>
  145. <npi>" . xmlEscape($details['npi']) . "</npi>
  146. </author>";
  147. return $author;
  148. }
  149. public function getDataEnterer($pid, $encounter)
  150. {
  151. $data_enterer = '';
  152. $details = $this->getDetails('hie_data_enterer_id');
  153. $data_enterer = "
  154. <data_enterer>
  155. <streetAddressLine>" . xmlEscape($details['street']) . "</streetAddressLine>
  156. <city>" . xmlEscape($details['city']) . "</city>
  157. <state>" . xmlEscape($details['state']) . "</state>
  158. <postalCode>" . xmlEscape($details['zip']) . "</postalCode>
  159. <country>" . xmlEscape($details['']) . "</country>
  160. <telecom>" . xmlEscape(($details['phonew1'] ? $details['phonew1'] : 0)) . "</telecom>
  161. <fname>" . xmlEscape($details['fname']) . "</fname>
  162. <lname>" . xmlEscape($details['lname']) . "</lname>
  163. </data_enterer>";
  164. return $data_enterer;
  165. }
  166. public function getInformant($pid, $encounter)
  167. {
  168. $informant = '';
  169. $details = $this->getDetails('hie_informant_id');
  170. $personal_informant = $this->getDetails('hie_personal_informant_id');
  171. $informant = "<informer>
  172. <streetAddressLine>" . xmlEscape($details['street']) . "</streetAddressLine>
  173. <city>" . xmlEscape($details['city']) . "</city>
  174. <state>" . xmlEscape($details['state']) . "</state>
  175. <postalCode>" . xmlEscape($details['zip']) . "</postalCode>
  176. <country>" . xmlEscape($details['']) . "</country>
  177. <telecom>" . xmlEscape(($details['phonew1'] ? $details['phonew1'] : 0)) . "</telecom>
  178. <fname>" . xmlEscape($details['fname']) . "</fname>
  179. <lname>" . xmlEscape($details['lname']) . "</lname>
  180. <personal_informant>" . xmlEscape($this->getSettings('Carecoordination', 'hie_personal_informant_id')) . "</personal_informant>
  181. </informer>";
  182. return $informant;
  183. }
  184. public function getCustodian($pid, $encounter)
  185. {
  186. $custodian = '';
  187. $details = $this->getDetails('hie_custodian_id');
  188. $custodian = "<custodian>
  189. <streetAddressLine>" . xmlEscape($details['street']) . "</streetAddressLine>
  190. <city>" . xmlEscape($details['city']) . "</city>
  191. <state>" . xmlEscape($details['state']) . "</state>
  192. <postalCode>" . xmlEscape($details['zip']) . "</postalCode>
  193. <country>" . xmlEscape($details['']) . "</country>
  194. <telecom>" . xmlEscape(($details['phonew1'] ? $details['phonew1'] : 0)) . "</telecom>
  195. <name>" . xmlEscape($details['organization']) . "</name>
  196. <organization>" . xmlEscape($details['organization']) . "</organization>
  197. </custodian>";
  198. return $custodian;
  199. }
  200. public function getInformationRecipient($pid, $encounter, $recipients, $params)
  201. {
  202. $information_recipient = '';
  203. $field_name = array();
  204. $details = $this->getDetails('hie_recipient_id');
  205. $appTable = new ApplicationTable();
  206. if ($recipients == 'hie') {
  207. $details['fname'] = 'MyHealth';
  208. $details['lname'] = '';
  209. $details['organization'] = '';
  210. } elseif ($recipients == 'emr_direct') {
  211. $query = "select fname, lname, organization, street, city, state, zip, phonew1 from users where email = ?";
  212. $field_name[] = $params;
  213. } elseif ($recipients == 'patient') {
  214. $query = "select fname, lname from patient_data WHERE pid = ?";
  215. $field_name[] = $params;
  216. } else {
  217. if (!$params) {
  218. $params = $_SESSION['authUserID'];
  219. }
  220. $query = "select fname, lname, organization, street, city, state, zip, phonew1 from users where id = ?";
  221. $field_name[] = $params;
  222. }
  223. if ($recipients != 'hie') {
  224. $res = $appTable->zQuery($query, $field_name);
  225. $result = $res->current();
  226. $details['fname'] = $result['fname'];
  227. $details['lname'] = $result['lname'];
  228. $details['organization'] = $result['organization'];
  229. $details['street'] = $result['street'];
  230. $details['city'] = $result['city'];
  231. $details['state'] = $result['state'];
  232. $details['zip'] = $result['zip'];
  233. $details['phonew1'] = $result['phonew1'];
  234. }
  235. $information_recipient = "<information_recipient>
  236. <fname>" . xmlEscape($details['fname']) . "</fname>
  237. <lname>" . xmlEscape($details['lname']) . "</lname>
  238. <organization>" . xmlEscape($details['organization']) . "</organization>
  239. <street>" . xmlEscape($details['street']) . "</street>
  240. <city>" . xmlEscape($details['city']) . "</city>
  241. <state>" . xmlEscape($details['state']) . "</state>
  242. <zip>" . xmlEscape($details['zip']) . "</zip>
  243. <phonew1>" . xmlEscape($details['phonew1']) . "</phonew1>
  244. </information_recipient>";
  245. return $information_recipient;
  246. }
  247. public function getLegalAuthenticator($pid, $encounter)
  248. {
  249. $legal_authenticator = '';
  250. $details = $this->getDetails('hie_legal_authenticator_id');
  251. $legal_authenticator = "<legal_authenticator>
  252. <streetAddressLine>" . xmlEscape($details['street']) . "</streetAddressLine>
  253. <city>" . xmlEscape($details['city']) . "</city>
  254. <state>" . xmlEscape($details['state']) . "</state>
  255. <postalCode>" . xmlEscape($details['zip']) . "</postalCode>
  256. <country>" . xmlEscape($details['']) . "</country>
  257. <telecom>" . xmlEscape(($details['phonew1'] ? $details['phonew1'] : 0)) . "</telecom>
  258. <fname>" . xmlEscape($details['fname']) . "</fname>
  259. <lname>" . xmlEscape($details['lname']) . "</lname>
  260. </legal_authenticator>";
  261. return $legal_authenticator;
  262. }
  263. public function getAuthenticator($pid, $encounter)
  264. {
  265. $authenticator = '';
  266. $details = $this->getDetails('hie_authenticator_id');
  267. $authenticator = "<authenticator>
  268. <streetAddressLine>" . xmlEscape($details['street']) . "</streetAddressLine>
  269. <city>" . xmlEscape($details['city']) . "</city>
  270. <state>" . xmlEscape($details['state']) . "</state>
  271. <postalCode>" . xmlEscape($details['zip']) . "</postalCode>
  272. <country>" . xmlEscape($details['']) . "</country>
  273. <telecom>" . xmlEscape(($details['phonew1'] ? $details['phonew1'] : 0)) . "</telecom>
  274. <fname>" . xmlEscape($details['fname']) . "</fname>
  275. <lname>" . xmlEscape($details['lname']) . "</lname>
  276. </authenticator>";
  277. return $authenticator;
  278. }
  279. public function getPrimaryCareProvider($pid, $encounter)
  280. {
  281. // primary from demo
  282. $getprovider = $this->getProviderId($pid);
  283. if (!empty($getprovider)) { // from patient_data
  284. $details = $this->getUserDetails($getprovider);
  285. } else { // get from CCM setup
  286. $details = $this->getDetails('hie_primary_care_provider_id');
  287. }
  288. // Note for NPI: Many times a care team member may not have an NPI so instead of
  289. // an NPI OID use facility/document unique OID with user table reference for extension.
  290. $get_care_team_provider = explode("|", $this->getCareTeamProviderId($pid));
  291. $primary_care_provider = "
  292. <primary_care_provider>
  293. <provider>
  294. <prefix>" . xmlEscape($details['title']) . "</prefix>
  295. <fname>" . xmlEscape($details['fname']) . "</fname>
  296. <lname>" . xmlEscape($details['lname']) . "</lname>
  297. <speciality>" . xmlEscape($details['specialty']) . "</speciality>
  298. <organization>" . xmlEscape($details['organization']) . "</organization>
  299. <telecom>" . xmlEscape(($details['phonew1'] ? $details['phonew1'] : 0)) . "</telecom>
  300. <addr>" . xmlEscape($details['']) . "</addr>
  301. <table_id>" . xmlEscape("provider-" . $getprovider) . "</table_id>
  302. <npi>" . xmlEscape($details['npi'] ?: '') . "</npi>
  303. <physician_type>" . xmlEscape($details['physician_type']) . "</physician_type>
  304. <physician_type_code>" . xmlEscape($details['physician_type_code']) . "</physician_type_code>
  305. <taxonomy>" . xmlEscape($details['taxonomy']) . "</taxonomy>
  306. <taxonomy_description>" . xmlEscape($details['taxonomy_desc']) . "</taxonomy_description>
  307. </provider>
  308. </primary_care_provider>";
  309. $care_team_provider = "<care_team>";
  310. foreach ($get_care_team_provider as $team_member) {
  311. if ((int)$getprovider === (int)$team_member) {
  312. // primary should be a part of care team but just in case
  313. // I've kept primary separate. So either way, primary gets included.
  314. // in this case, we don't want to duplicate the provider.
  315. continue;
  316. }
  317. $details2 = $this->getUserDetails($team_member);
  318. if (empty($details2)) {
  319. continue;
  320. }
  321. $care_team_provider .= "<provider>
  322. <prefix>" . xmlEscape($details2['title']) . "</prefix>
  323. <fname>" . xmlEscape($details2['fname']) . "</fname>
  324. <lname>" . xmlEscape($details2['lname']) . "</lname>
  325. <speciality>" . xmlEscape($details2['specialty']) . "</speciality>
  326. <organization>" . xmlEscape($details2['organization']) . "</organization>
  327. <telecom>" . xmlEscape(($details2['phonew1'] ?: '')) . "</telecom>
  328. <addr>" . xmlEscape($details2['']) . "</addr>
  329. <table_id>" . xmlEscape("provider-" . $team_member) . "</table_id>
  330. <npi>" . xmlEscape($details2['npi']) . "</npi>
  331. <physician_type>" . xmlEscape($details2['physician_type']) . "</physician_type>
  332. <physician_type_code>" . xmlEscape($details2['physician_type_code']) . "</physician_type_code>
  333. <taxonomy>" . xmlEscape($details2['taxonomy']) . "</taxonomy>
  334. <taxonomy_description>" . xmlEscape($details2['taxonomy_desc']) . "</taxonomy_description>
  335. </provider>
  336. ";
  337. }
  338. $care_team_provider .= "</care_team>
  339. ";
  340. return $primary_care_provider . $care_team_provider;
  341. }
  342. /*
  343. #******************************************************#
  344. # CONTINUITY OF CARE #
  345. #******************************************************#
  346. */
  347. public function getAllergies($pid, $encounter)
  348. {
  349. $allergies = '';
  350. $query = "SELECT l.id, l.title, l.begdate, l.enddate, lo.title AS observation,
  351. SUBSTRING(lo.codes, LOCATE(':',lo.codes)+1, LENGTH(lo.codes)) AS observation_code,
  352. SUBSTRING(l.`diagnosis`,1,LOCATE(':',l.diagnosis)-1) AS code_type_real,
  353. l.reaction, l.diagnosis, l.diagnosis AS code
  354. FROM lists AS l
  355. LEFT JOIN list_options AS lo ON lo.list_id = ? AND lo.option_id = l.severity_al
  356. WHERE l.type = ? AND l.pid = ?";
  357. $appTable = new ApplicationTable();
  358. $res = $appTable->zQuery($query, array('severity_ccda', 'allergy', $pid));
  359. $allergies = "<allergies>";
  360. foreach ($res as $row) {
  361. $split_codes = explode(';', $row['code']);
  362. foreach ($split_codes as $key => $single_code) {
  363. $code = $code_text = $code_rx = $code_text_rx = $code_snomed = $code_text_snomed = $reaction_text = $reaction_code = '';
  364. $get_code_details = explode(':', $single_code);
  365. if ($get_code_details[0] == 'RXNORM' || $get_code_details[0] == 'RXCUI') {
  366. $code_rx = $get_code_details[1];
  367. $code_text_rx = lookup_code_descriptions($single_code);
  368. } elseif ($get_code_details[0] == 'SNOMED' || $get_code_details[0] == 'SNOMED-CT') {
  369. $code_snomed = $get_code_details[1];
  370. $code_text_snomed = lookup_code_descriptions($row['code']);
  371. } else {
  372. $code = $get_code_details[1];
  373. $code_text = lookup_code_descriptions($single_code);
  374. }
  375. $active = $status_table = '';
  376. if ($row['enddate']) {
  377. $active = 'completed';
  378. $allergy_status = 'completed';
  379. $status_table = 'Resolved';
  380. $status_code = '73425007';
  381. } else {
  382. $active = 'completed';
  383. $allergy_status = 'active';
  384. $status_table = 'Active';
  385. $status_code = '55561003';
  386. }
  387. if ($row['reaction']) {
  388. $reaction_text = (new CarecoordinationTable())->getListTitle($row['reaction'], 'reaction', '');
  389. $reaction_code = (new CarecoordinationTable())->getCodes($row['reaction'], 'reaction');
  390. $reaction_code = explode(':', $reaction_code);
  391. }
  392. $allergies .= "<allergy>
  393. <id>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'] . $single_code)) . "</id>
  394. <sha_id>" . xmlEscape("36e3e930-7b14-11db-9fe1-0800200c9a66") . "</sha_id>
  395. <title>" . xmlEscape($row['title']) . ($single_code ? " [" . xmlEscape($single_code) . "]" : '') . "</title>
  396. <diagnosis_code>" . xmlEscape(($code ? $code : 0)) . "</diagnosis_code>
  397. <diagnosis>" . xmlEscape(($code_text ? Listener::z_xlt($code_text) : "")) . "</diagnosis>
  398. <rxnorm_code>" . xmlEscape(($code_rx ? $code_rx : 0)) . "</rxnorm_code>
  399. <rxnorm_code_text>" . xmlEscape(($code_text_rx ? Listener::z_xlt($code_text_rx) : "")) . "</rxnorm_code_text>
  400. <snomed_code>" . xmlEscape(($code_snomed ? $code_snomed : 0)) . "</snomed_code>
  401. <snomed_code_text>" . xmlEscape(($code_text_snomed ? Listener::z_xlt($code_text_snomed) : "")) . "</snomed_code_text>
  402. <status_table>" . ($status_table ? xmlEscape($status_table) : "") . "</status_table>
  403. <status>" . ($active ? xmlEscape($active) : "") . "</status>
  404. <allergy_status>" . ($allergy_status ? xmlEscape($allergy_status) : "") . "</allergy_status>
  405. <status_code>" . ($status_code ? xmlEscape($status_code) : 0) . "</status_code>
  406. <outcome>" . xmlEscape(($row['observation'] ? Listener::z_xlt($row['observation']) : "")) . "</outcome>
  407. <outcome_code>" . xmlEscape(($row['observation_code'] ? $row['observation_code'] : 0)) . "</outcome_code>
  408. <startdate>" . xmlEscape($row['begdate'] ? preg_replace('/-/', '', $row['begdate']) : "00000000") . "</startdate>
  409. <enddate>" . xmlEscape($row['enddate'] ? preg_replace('/-/', '', $row['enddate']) : "00000000") . "</enddate>
  410. <reaction_text>" . xmlEscape($reaction_text ? Listener::z_xlt($reaction_text) : "") . "</reaction_text>
  411. <reaction_code>" . xmlEscape($reaction_code[1] ?: '') . "</reaction_code>
  412. <reaction_code_type>" . xmlEscape(str_replace('-', ' ', $reaction_code[0]) ?: '') . "</reaction_code_type>
  413. <RxNormCode>" . xmlEscape($code_rx) . "</RxNormCode>
  414. <RxNormCode_text>" . xmlEscape(!empty($code_text_rx) ? $code_text_rx : $row['title']) . "</RxNormCode_text>
  415. </allergy>";
  416. }
  417. }
  418. $allergies .= "</allergies>";
  419. return $allergies;
  420. }
  421. public function getMedications($pid, $encounter)
  422. {
  423. $medications = '';
  424. $query = "select l.id, l.date_added, l.start_date, l.drug, l.dosage, l.quantity, l.size, l.substitute, l.drug_info_erx, l.active, SUBSTRING(l3.codes, LOCATE(':',l3.codes)+1, LENGTH(l3.codes)) AS route_code,
  425. l.rxnorm_drugcode, l1.title as unit, l1.codes as unit_code,l2.title as form,SUBSTRING(l2.codes, LOCATE(':',l2.codes)+1, LENGTH(l2.codes)) AS form_code, l3.title as route, l4.title as `interval`,
  426. u.title, u.fname, u.lname, u.mname, u.npi, u.street, u.streetb, u.city, u.state, u.zip, u.phonew1, l.note
  427. from prescriptions as l
  428. left join list_options as l1 on l1.option_id=unit AND l1.list_id = ?
  429. left join list_options as l2 on l2.option_id=form AND l2.list_id = ?
  430. left join list_options as l3 on l3.option_id=route AND l3.list_id = ?
  431. left join list_options as l4 on l4.option_id=`interval` AND l4.list_id = ?
  432. left join users as u on u.id = l.provider_id
  433. where l.patient_id = ? and l.active = 1";
  434. $appTable = new ApplicationTable();
  435. $res = $appTable->zQuery($query, array('drug_units', 'drug_form', 'drug_route', 'drug_interval', $pid));
  436. $medications = "<medications>";
  437. foreach ($res as $row) {
  438. if (!$row['rxnorm_drugcode']) {
  439. $row['rxnorm_drugcode'] = $this->generate_code($row['drug']);
  440. }
  441. $unit = $str = $active = '';
  442. if ($row['size'] > 0) {
  443. $unit = $row['size'] . " " . Listener::z_xlt($row['unit']) . " ";
  444. }
  445. $str = $unit . " " . Listener::z_xlt($row['route']) . " " . $row['dosage'] . " " . Listener::z_xlt($row['form'] . " " . $row['interval']);
  446. if ($row['active'] > 0) {
  447. $active = 'active';
  448. } else {
  449. $active = 'completed';
  450. }
  451. if ($row['start_date']) {
  452. $start_date = str_replace('-', '', $row['start_date']);
  453. $start_date_formatted = \Application\Model\ApplicationTable::fixDate($row['start_date'], $GLOBALS['date_display_format'], 'yyyy-mm-dd');
  454. ;
  455. }
  456. $medications .= "<medication>
  457. <id>" . xmlEscape($row['id']) . "</id>
  458. <extension>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'])) . "</extension>
  459. <sha_extension>" . xmlEscape("cdbd33f0-6cde-11db-9fe1-0800200c9a66") . "</sha_extension>
  460. <performer_name>" . xmlEscape($row['fname'] . " " . $row['mname'] . " " . $row['lname']) . "</performer_name>
  461. <fname>" . xmlEscape($row['fname']) . "</fname>
  462. <mname>" . xmlEscape($row['mname']) . "</mname>
  463. <lname>" . xmlEscape($row['lname']) . "</lname>
  464. <title>" . xmlEscape($row['title']) . "</title>
  465. <npi>" . xmlEscape($row['npi']) . "</npi>
  466. <address>" . xmlEscape($row['street']) . "</address>
  467. <city>" . xmlEscape($row['city']) . "</city>
  468. <state>" . xmlEscape($row['state']) . "</state>
  469. <zip>" . xmlEscape($row['zip']) . "</zip>
  470. <work_phone>" . xmlEscape($row['phonew1']) . "</work_phone>
  471. <drug>" . xmlEscape($row['drug']) . "</drug>
  472. <direction>" . xmlEscape($str) . "</direction>
  473. <dosage>" . xmlEscape($row['dosage']) . "</dosage>
  474. <size>" . xmlEscape(($row['size'] ? $row['size'] : 0)) . "</size>
  475. <unit>" . xmlEscape(($row['unit'] ? preg_replace('/\s*/', '', Listener::z_xlt($row['unit'])) : '')) . "</unit>
  476. <unit_code>" . xmlEscape(($row['unit_code'] ? $row['unit_code'] : 0)) . "</unit_code>
  477. <form>" . xmlEscape(Listener::z_xlt($row['form'])) . "</form>
  478. <form_code>" . xmlEscape(Listener::z_xlt($row['form_code'])) . "</form_code>
  479. <route_code>" . xmlEscape($row['route_code'] ?: $row['route']) . "</route_code>
  480. <route>" . xmlEscape($row['route']) . "</route>
  481. <interval>" . xmlEscape(Listener::z_xlt($row['interval'])) . "</interval>
  482. <start_date>" . xmlEscape($start_date) . "</start_date>
  483. <start_date_formatted>" . xmlEscape($row['start_date']) . "</start_date_formatted>
  484. <end_date>" . xmlEscape('') . "</end_date>
  485. <status>" . xmlEscape($active) . "</status>
  486. <indications>" . xmlEscape(($row['pres_erx_diagnosis_name'] ? $row['pres_erx_diagnosis_name'] : "")) . "</indications>
  487. <indications_code>" . xmlEscape(($row['pres_erx_diagnosis'] ? $row['pres_erx_diagnosis'] : 0)) . "</indications_code>
  488. <instructions>" . xmlEscape($row['note']) . "</instructions>
  489. <rxnorm>" . xmlEscape($row['rxnorm_drugcode']) . "</rxnorm>
  490. <provider_id></provider_id>
  491. <provider_name></provider_name>
  492. </medication>";
  493. }
  494. $medications .= "</medications>";
  495. return $medications;
  496. }
  497. public function getProblemList($pid, $encounter)
  498. {
  499. UuidRegistry::createMissingUuidsForTables(['lists']);
  500. $problem_lists = '';
  501. $query = "select l.*, lo.title as observation, lo.codes as observation_code, l.diagnosis AS code
  502. from lists AS l
  503. left join list_options as lo on lo.option_id = l.outcome AND lo.list_id = ?
  504. where l.type = ? and l.pid = ? AND l.outcome != ?"; // patched out /* AND l.id NOT IN(SELECT list_id FROM issue_encounter WHERE pid = ?)*/
  505. $appTable = new ApplicationTable();
  506. $res = $appTable->zQuery($query, array('outcome', 'medical_problem', $pid, 1));
  507. $problem_lists .= '<problem_lists>';
  508. foreach ($res as $row) {
  509. $row['uuid'] = UuidRegistry::uuidToString($row['uuid']);
  510. $split_codes = explode(';', $row['code']);
  511. foreach ($split_codes as $key => $single_code) {
  512. $get_code_details = explode(':', $single_code);
  513. $code_type = $get_code_details[0];
  514. $code_type = ($code_type == 'SNOMED' || $code_type == 'SNOMED-CT') ? "SNOMED CT" : "ICD-10-CM";
  515. $code = $get_code_details[1];
  516. $code_text = lookup_code_descriptions($single_code);
  517. $age = $this->getAge($pid, $row['begdate']);
  518. $start_date = str_replace('-', '', $row['begdate']);
  519. $end_date = str_replace('-', '', $row['enddate']);
  520. $status = $status_table = '';
  521. $start_date = $start_date ?: '0';
  522. $end_date = $end_date ?: '0';
  523. //Active - 55561003 Completed - 73425007
  524. if ($end_date) {
  525. $status = 'completed';
  526. $status_table = 'Resolved';
  527. $status_code = '73425007';
  528. } else {
  529. $status = 'active';
  530. $status_table = 'Active';
  531. $status_code = '55561003';
  532. }
  533. $observation = $row['observation'];
  534. $observation_code = explode(':', $row['observation_code']);
  535. $observation_code = $observation_code[1];
  536. $problem_lists .= "<problem>
  537. <problem_id>" . ($code ? xmlEscape($row['$id']) : '') . "</problem_id>
  538. <extension>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'])) . "</extension>
  539. <sha_extension>" . xmlEscape($row['uuid']) . "</sha_extension>
  540. <title>" . xmlEscape($row['title']) . ($single_code ? " [" . xmlEscape($single_code) . "]" : '') . "</title>
  541. <code>" . ($code ? xmlEscape($code) : '') . "</code>
  542. <code_type>" . ($code ? xmlEscape($code_type) : '') . "</code_type>
  543. <code_text>" . xmlEscape(($code_text ?: '')) . "</code_text>
  544. <age>" . xmlEscape($age) . "</age>
  545. <start_date_table>" . xmlEscape($row['begdate']) . "</start_date_table>
  546. <start_date>" . xmlEscape($start_date) . "</start_date>
  547. <end_date>" . xmlEscape($end_date) . "</end_date>
  548. <status>" . xmlEscape($status) . "</status>
  549. <status_table>" . xmlEscape($status_table) . "</status_table>
  550. <status_code>" . xmlEscape($status_code) . "</status_code>
  551. <observation>" . xmlEscape(($observation ? Listener::z_xlt($observation) : "")) . "</observation>
  552. <observation_code>" . xmlEscape(($observation_code ?: '')) . "</observation_code>
  553. <diagnosis>" . xmlEscape($code ?: '') . "</diagnosis>
  554. </problem>";
  555. }
  556. }
  557. $problem_lists .= '</problem_lists>';
  558. return $problem_lists;
  559. }
  560. public function getMedicalDeviceList($pid, $encounter)
  561. {
  562. $medical_devices = '';
  563. $query = "select l.*, lo.title as observation, lo.codes as observation_code, l.diagnosis AS code
  564. from lists AS l
  565. left join list_options as lo on lo.option_id = l.outcome AND lo.list_id = ?
  566. where l.type = ? and l.pid = ? AND l.outcome != ? AND l.id NOT IN(SELECT list_id FROM issue_encounter WHERE pid = ?)";
  567. $appTable = new ApplicationTable();
  568. $res = $appTable->zQuery($query, array('outcome', 'medical_device', $pid, 1, $pid));
  569. $medical_devices .= '<medical_devices>';
  570. foreach ($res as $row) {
  571. $split_codes = explode(';', $row['code']);
  572. foreach ($split_codes as $key => $single_code) {
  573. $get_code_details = explode(':', $single_code);
  574. $code_type = $get_code_details[0];
  575. $code_type = ($code_type == 'SNOMED' || $code_type == 'SNOMED-CT') ? "SNOMED CT" : "ICD-10-CM";
  576. $code = $get_code_details[1];
  577. $code_text = lookup_code_descriptions($single_code);
  578. $start_date = str_replace('-', '', $row['begdate']);
  579. $end_date = str_replace('-', '', $row['enddate']);
  580. $status = $status_table = '';
  581. $start_date = $start_date ?: '';
  582. $end_date = $end_date ?: '';
  583. //Active - 55561003 Completed - 73425007
  584. if ($end_date) {
  585. $status = 'completed';
  586. $status_table = 'Resolved';
  587. $status_code = '73425007';
  588. } else {
  589. $status = 'active';
  590. $status_table = 'Active';
  591. $status_code = '55561003';
  592. }
  593. $observation = $row['observation'];
  594. $observation_code = explode(':', $row['observation_code']);
  595. $observation_code = $observation_code[1];
  596. $medical_devices .= "<device>
  597. <extension>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'])) . "</extension>
  598. <sha_extension>" . xmlEscape($this->formatUid($_SESSION['site_id'] . $row['udi'])) . "</sha_extension>
  599. <title>" . xmlEscape($row['title']) . ($single_code ? " [" . xmlEscape($single_code) . "]" : '') . "</title>
  600. <code>" . ($code ? xmlEscape($code) : '') . "</code>
  601. <code_type>" . ($code ? xmlEscape($code_type) : '') . "</code_type>
  602. <code_text>" . xmlEscape(($code_text ?: '')) . "</code_text>
  603. <udi>" . xmlEscape($row['udi']) . "</udi>
  604. <start_date_table>" . xmlEscape($row['begdate']) . "</start_date_table>
  605. <start_date>" . xmlEscape($start_date) . "</start_date>
  606. <end_date>" . xmlEscape($end_date) . "</end_date>
  607. <status>" . xmlEscape($status) . "</status>
  608. <status_table>" . xmlEscape($status_table) . "</status_table>
  609. <status_code>" . xmlEscape($status_code) . "</status_code>
  610. <observation>" . xmlEscape(($observation ? Listener::z_xlt($observation) : "")) . "</observation>
  611. <observation_code>" . xmlEscape(($observation_code ?: '')) . "</observation_code>
  612. <diagnosis>" . xmlEscape($code ?: '') . "</diagnosis>
  613. </device>";
  614. }
  615. }
  616. $medical_devices .= '</medical_devices>';
  617. return $medical_devices;
  618. }
  619. public function getImmunization($pid, $encounter)
  620. {
  621. $immunizations = '';
  622. $query = "SELECT im.*, cd.code_text, DATE(administered_date) AS administered_date,
  623. DATE_FORMAT(administered_date,'%Y%m%d') AS administered_formatted, lo.title as route_of_administration,
  624. u.title, u.fname, u.mname, u.lname, u.npi, u.street, u.streetb, u.city, u.state, u.zip, u.phonew1,
  625. f.name, f.phone, SUBSTRING(lo.codes, LOCATE(':',lo.codes)+1, LENGTH(lo.codes)) AS route_code
  626. FROM immunizations AS im
  627. LEFT JOIN codes AS cd ON cd.code = im.cvx_code
  628. JOIN code_types AS ctype ON ctype.ct_key = 'CVX' AND ctype.ct_id=cd.code_type
  629. LEFT JOIN list_options AS lo ON lo.list_id = 'drug_route' AND lo.option_id = im.route
  630. LEFT JOIN users AS u ON u.id = im.administered_by_id
  631. LEFT JOIN facility AS f ON f.id = u.facility_id
  632. WHERE im.patient_id=? AND added_erroneously = 0";
  633. $appTable = new ApplicationTable();
  634. $res = $appTable->zQuery($query, array($pid));
  635. $immunizations .= '<immunizations>';
  636. foreach ($res as $row) {
  637. $immunizations .= "
  638. <immunization>
  639. <extension>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'])) . "</extension>
  640. <sha_extension>" . xmlEscape("e6f1ba43-c0ed-4b9b-9f12-f435d8ad8f92") . "</sha_extension>
  641. <id>" . xmlEscape($row['id']) . "</id>
  642. <cvx_code>" . xmlEscape($row['cvx_code']) . "</cvx_code>
  643. <code_text>" . xmlEscape($row['code_text']) . "</code_text>
  644. <reaction>" . xmlEscape($row['reaction']) . "</reaction>
  645. <npi>" . xmlEscape($row['npi']) . "</npi>
  646. <administered_by>" . xmlEscape($row['administered_by']) . "</administered_by>
  647. <fname>" . xmlEscape($row['fname']) . "</fname>
  648. <mname>" . xmlEscape($row['mname']) . "</mname>
  649. <lname>" . xmlEscape($row['lname']) . "</lname>
  650. <title>" . xmlEscape($row['title']) . "</title>
  651. <address>" . xmlEscape($row['street']) . "</address>
  652. <city>" . xmlEscape($row['city']) . "</city>
  653. <state>" . xmlEscape($row['state']) . "</state>
  654. <zip>" . xmlEscape($row['zip']) . "</zip>
  655. <work_phone>" . xmlEscape($row['phonew1']) . "</work_phone>
  656. <administered_on>" . xmlEscape($row['administered_date']) . "</administered_on>
  657. <administered_formatted>" . xmlEscape($row['administered_formatted']) . "</administered_formatted>
  658. <note>" . xmlEscape($row['note']) . "</note>
  659. <route_of_administration>" . xmlEscape(Listener::z_xlt($row['route_of_administration'])) . "</route_of_administration>
  660. <route_code>" . xmlEscape($row['route_code']) . "</route_code>
  661. <status>completed</status>
  662. <facility_name>" . xmlEscape($row['name']) . "</facility_name>
  663. <facility_phone>" . xmlEscape($row['phone']) . "</facility_phone>
  664. </immunization>";
  665. }
  666. $immunizations .= '</immunizations>';
  667. return $immunizations;
  668. }
  669. public function getProcedures($pid, $encounter)
  670. {
  671. $wherCon = '';
  672. $sqlBindArray = [];
  673. if ($encounter) {
  674. $wherCon = " b.encounter = ? AND ";
  675. $sqlBindArray[] = $encounter;
  676. }
  677. $procedure = '';
  678. $query = "select b.id, b.date as proc_date, b.code_text, b.code, fe.date,
  679. u.fname, u.lname, u.mname, u.npi, u.street, u.city, u.state, u.zip,
  680. f.id as fid, f.name, f.phone, f.street as fstreet, f.city as fcity, f.state as fstate, f.postal_code as fzip, f.country_code, f.phone as fphone
  681. from billing as b
  682. LEFT join code_types as ct on ct.ct_key
  683. LEFT join codes as c on c.code = b.code AND c.code_type = ct.ct_id
  684. LEFT join form_encounter as fe on fe.pid = b.pid AND fe.encounter = b.encounter
  685. LEFT JOIN users AS u ON u.id = b.provider_id
  686. LEFT JOIN facility AS f ON f.id = fe.facility_id
  687. where $wherCon b.pid = ? and b.activity = ?";
  688. array_push($sqlBindArray, $pid, 1);
  689. $appTable = new ApplicationTable();
  690. $res = $appTable->zQuery($query, $sqlBindArray);
  691. $procedure = '<procedures>';
  692. foreach ($res as $row) {
  693. $procedure .= "<procedure>
  694. <extension>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'])) . "</extension>
  695. <sha_extension>" . xmlEscape("d68b7e32-7810-4f5b-9cc2-acd54b0fd85d") . "</sha_extension>
  696. <description>" . xmlEscape($row['code_text']) . "</description>
  697. <code>" . xmlEscape($row['code']) . "</code>
  698. <date>" . xmlEscape(substr($row['date'], 0, 10)) . "</date>
  699. <npi>" . xmlEscape($row['npi']) . "</npi>
  700. <fname>" . xmlEscape($row['fname']) . "</fname>
  701. <mname>" . xmlEscape($row['mname']) . "</mname>
  702. <lname>" . xmlEscape($row['lname']) . "</lname>
  703. <address>" . xmlEscape($row['street']) . "</address>
  704. <city>" . xmlEscape($row['city']) . "</city>
  705. <state>" . xmlEscape($row['state']) . "</state>
  706. <zip>" . xmlEscape($row['zip']) . "</zip>
  707. <work_phone>" . xmlEscape($row['phonew1']) . "</work_phone>
  708. <facility_extension>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['fid'])) . "</facility_extension>
  709. <facility_sha_extension>" . xmlEscape("c2ee9ee9-ae31-4628-a919-fec1cbb58686") . "</facility_sha_extension>
  710. <facility_name>" . xmlEscape($row['name']) . "</facility_name>
  711. <facility_address>" . xmlEscape($row['fstreet']) . "</facility_address>
  712. <facility_city>" . xmlEscape($row['fcity']) . "</facility_city>
  713. <facility_state>" . xmlEscape($row['fstate']) . "</facility_state>
  714. <facility_country>" . xmlEscape($row['country_code']) . "</facility_country>
  715. <facility_zip>" . xmlEscape($row['fzip']) . "</facility_zip>
  716. <facility_phone>" . xmlEscape($row['fphone']) . "</facility_phone>
  717. <procedure_date>" . xmlEscape(preg_replace('/-/', '', substr($row['proc_date'], 0, 10))) . "</procedure_date>
  718. </procedure>";
  719. }
  720. $procedure .= '</procedures>';
  721. return $procedure;
  722. }
  723. public function getResults($pid, $encounter)
  724. {
  725. $wherCon = '';
  726. $sqlBindArray = [];
  727. if ($encounter) {
  728. $wherCon = " po.encounter_id = ? AND ";
  729. $sqlBindArray[] = $encounter;
  730. }
  731. $results = '';
  732. $query = "SELECT prs.result AS result_value, prs.units, prs.range, prs.result_text as order_title, prs.result_code, prs.procedure_result_id,
  733. prs.result_text as result_desc, prs.procedure_result_id AS test_code, poc.procedure_code, poc.procedure_name, poc.diagnoses, po.date_ordered, prs.date AS result_time, prs.abnormal AS abnormal_flag,po.order_status AS order_status
  734. FROM procedure_order AS po
  735. JOIN procedure_order_code as poc on poc.procedure_order_id = po.procedure_order_id
  736. JOIN procedure_report AS pr ON pr.procedure_order_id = po.procedure_order_id
  737. JOIN procedure_result AS prs ON prs.procedure_report_id = pr.procedure_report_id
  738. WHERE $wherCon po.patient_id = ? AND prs.result NOT IN ('DNR','TNP')";
  739. array_push($sqlBindArray, $pid);
  740. $appTable = new ApplicationTable();
  741. $res = $appTable->zQuery($query, $sqlBindArray);
  742. $results_list = array();
  743. foreach ($res as $row) {
  744. if (empty($row['result_code']) && empty($row['abnormal_flag'])) {
  745. continue;
  746. }
  747. $results_list[$row['test_code']]['test_code'] = $row['test_code'];
  748. $results_list[$row['test_code']]['order_title'] = $row['order_title'];
  749. $results_list[$row['test_code']]['order_status'] = $row['order_status'];
  750. $results_list[$row['test_code']]['date_ordered'] = substr(str_replace("-", '', $row['date_ordered']), 0, 8);
  751. $results_list[$row['test_code']]['date_ordered_table'] = $row['date_ordered'];
  752. $results_list[$row['test_code']]['procedure_code'] = $row['procedure_code'];
  753. $results_list[$row['test_code']]['procedure_name'] = $row['procedure_name'];
  754. $results_list[$row['test_code']]['subtest'][$row['procedure_result_id']]['result_code'] = ($row['result_code'] ? $row['result_code'] : 0);
  755. $results_list[$row['test_code']]['subtest'][$row['procedure_result_id']]['result_desc'] = $row['result_desc'];
  756. $results_list[$row['test_code']]['subtest'][$row['procedure_result_id']]['units'] = $row['units'];
  757. $results_list[$row['test_code']]['subtest'][$row['procedure_result_id']]['range'] = $row['range'];
  758. $results_list[$row['test_code']]['subtest'][$row['procedure_result_id']]['result_value'] = $row['result_value'];
  759. $results_list[$row['test_code']]['subtest'][$row['procedure_result_id']]['result_time'] = substr(preg_replace('/-/', '', $row['result_time']), 0, 8);
  760. $results_list[$row['test_code']]['subtest'][$row['procedure_result_id']]['abnormal_flag'] = $row['abnormal_flag'];
  761. }
  762. $results = '<results>';
  763. foreach ($results_list as $row) {
  764. $order_status = $order_status_table = '';
  765. if ($row['order_status'] == 'complete') {
  766. $order_status = 'completed';
  767. $order_status_table = 'completed';
  768. } elseif ($row['order_status'] == 'pending') {
  769. $order_status = 'active';
  770. $order_status_table = 'pending';
  771. } else {
  772. $order_status = 'completed';
  773. $order_status_table = '';
  774. }
  775. $results .= '<result>
  776. <extension>' . xmlEscape(base64_encode($_SESSION['site_id'] . $row['test_code'])) . '</extension>
  777. <root>' . xmlEscape("7d5a02b0-67a4-11db-bd13-0800200c9a66") . '</root>
  778. <date_ordered>' . xmlEscape($row['date_ordered']) . '</date_ordered>
  779. <date_ordered_table>' . xmlEscape($row['date_ordered_table']) . '</date_ordered_table>
  780. <title>' . xmlEscape($row['order_title']) . '</title>
  781. <test_code>' . xmlEscape($row['procedure_code']) . '</test_code>
  782. <test_name>' . xmlEscape($row['procedure_name']) . '</test_name>
  783. <order_status_table>' . xmlEscape($order_status_table) . '</order_status_table>
  784. <order_status>' . xmlEscape($order_status) . '</order_status>';
  785. foreach ($row['subtest'] as $row_1) {
  786. $units = $row_1['units'] ?: '';
  787. $highlow = preg_split("/[\s,-\--]+/", $row_1['range']);
  788. $results .= '
  789. <subtest>
  790. <extension>' . xmlEscape(base64_encode($_SESSION['site_id'] . $row['result_code'])) . '</extension>
  791. <root>' . xmlEscape("7d5a02b0-67a4-11db-bd13-0800200c9a66") . '</root>
  792. <range>' . xmlEscape($row_1['range']) . '</range>
  793. <low>' . xmlEscape(trim($highlow[0])) . '</low>
  794. <high>' . xmlEscape(trim($highlow[1])) . '</high>
  795. <unit>' . xmlEscape($units) . '</unit>
  796. <result_code>' . xmlEscape($row_1['result_code']) . '</result_code>
  797. <result_desc>' . xmlEscape($row_1['result_desc']) . '</result_desc>
  798. <result_value>' . xmlEscape(($row_1['result_value'] ? $row_1['result_value'] : 0)) . '</result_value>
  799. <result_time>' . xmlEscape($row_1['result_time']) . '</result_time>
  800. <abnormal_flag>' . xmlEscape($row_1['abnormal_flag']) . '</abnormal_flag>
  801. </subtest>';
  802. }
  803. $results .= '
  804. </result>';
  805. }
  806. $results .= '</results>';
  807. return $results;
  808. }
  809. /*
  810. #**************************************************#
  811. # ENCOUNTER HISTORY #
  812. #**************************************************#
  813. */
  814. public function getEncounterHistory($pid, $encounter)
  815. {
  816. $wherCon = '';
  817. $sqlBindArray = [];
  818. if ($encounter) {
  819. $wherCon = " fe.encounter = ? AND ";
  820. $sqlBindArray[] = $encounter;
  821. }
  822. $results = "";
  823. $query = "SELECT fe.date, fe.encounter,fe.reason,
  824. f.id as fid, f.name, f.phone, f.street as fstreet, f.city as fcity, f.state as fstate, f.postal_code as fzip, f.country_code, f.phone as fphone, f.facility_npi as fnpi,
  825. f.facility_code as foid, u.fname, u.mname, u.lname, u.npi, u.street, u.city, u.state, u.zip, u.phonew1, cat.pc_catname, lo.title AS physician_type, lo.codes AS physician_type_code,
  826. SUBSTRING(ll.diagnosis, LENGTH('SNOMED-CT:')+1, LENGTH(ll.diagnosis)) AS encounter_diagnosis, ll.diagnosis as raw_diagnosis, ll.title, ll.begdate, ll.enddate
  827. FROM form_encounter AS fe
  828. LEFT JOIN facility AS f ON f.id=fe.facility_id
  829. LEFT JOIN users AS u ON u.id=fe.provider_id
  830. LEFT JOIN openemr_postcalendar_categories AS cat ON cat.pc_catid=fe.pc_catid
  831. LEFT JOIN list_options AS lo ON lo.list_id = 'physician_type' AND lo.option_id = u.physician_type
  832. LEFT JOIN issue_encounter AS ie ON ie.encounter=fe.encounter AND ie.pid=fe.pid
  833. LEFT JOIN lists AS ll ON ll.id=ie.list_id AND ll.pid=fe.pid
  834. WHERE $wherCon fe.pid = ? ORDER BY fe.date";
  835. array_push($sqlBindArray, $pid);
  836. $appTable = new ApplicationTable();
  837. $res = $appTable->zQuery($query, $sqlBindArray);
  838. $results = "<encounter_list>";
  839. foreach ($res as $row) {
  840. $tmp = explode(":", $row['physician_type_code']);
  841. $physician_code_type = str_replace('-', ' ', $tmp[0]);
  842. $row['physician_type_code'] = $tmp[1];
  843. $encounter_reason = '';
  844. if ($row['reason'] !== '') {
  845. $encounter_reason = "<encounter_reason>" . xmlEscape($this->date_format(substr($row['date'], 0, 10)) . " - " . $row['reason']) . "</encounter_reason>";
  846. }
  847. $codes = "";
  848. $query_procedures = "SELECT c.code, c.code_text FROM billing AS b
  849. JOIN code_types AS ct ON ct.ct_key = ?
  850. JOIN codes AS c ON c.code = b.code AND c.code_type = ct.ct_id
  851. WHERE b.pid = ? AND b.code_type = ? AND activity = 1 AND b.encounter = ?";
  852. $appTable_procedures = new ApplicationTable();
  853. $res_procedures = $appTable_procedures->zQuery($query_procedures, array('CPT4', $pid, 'CPT4', $row['encounter']));
  854. foreach ($res_procedures as $row_procedures) {
  855. $codes .= "
  856. <procedures>
  857. <code>" . xmlEscape($row_procedures['code']) . "</code>
  858. <code_type>" . xmlEscape("CPT4") . "</code_type>
  859. <text>" . xmlEscape($row_procedures['code_text']) . "</text>
  860. </procedures>";
  861. }
  862. $encounter_diagnosis = "";
  863. if ($row['encounter_diagnosis']) {
  864. $tmp = explode(":", $row['raw_diagnosis']);
  865. $code_type = str_replace('-', ' ', $tmp[0]);
  866. $encounter_activity = '';
  867. if ($row['enddate'] !== '') {
  868. $encounter_activity = 'Completed';
  869. } else {
  870. $encounter_activity = 'Active';
  871. }
  872. // this just duplicates in all procedures.
  873. // from problem attached to encounter
  874. $encounter_diagnosis = "
  875. <encounter_diagnosis>
  876. <code>" . xmlEscape($tmp[1]) . "</code>
  877. <code_type>" . xmlEscape($code_type) . "</code_type>
  878. <text>" . xmlEscape(Listener::z_xlt($row['title'])) . "</text>
  879. <status>" . xmlEscape($encounter_activity) . "</status>
  880. </encounter_diagnosis>";
  881. $codes .= $encounter_diagnosis;
  882. }
  883. $location_details = ($row['name'] !== '') ? (',' . $row['fstreet'] . ',' . $row['fcity'] . ',' . $row['fstate'] . ' ' . $row['fzip']) : '';
  884. $results .= "
  885. <encounter>
  886. <extension>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['encounter'])) . "</extension>
  887. <sha_extension>" . xmlEscape($this->formatUid($_SESSION['site_id'] . $row['encounter'])) . "</sha_extension>
  888. <encounter_id>" . xmlEscape($row['encounter']) . "</encounter_id>
  889. <visit_category>" . xmlEscape($row['pc_catname']) . "</visit_category>
  890. <performer>" . xmlEscape($row['fname'] . " " . $row['mname'] . " " . $row['lname']) . "</performer>
  891. <physician_type_code>" . xmlEscape($row['physician_type_code']) . "</physician_type_code>
  892. <physician_type>" . xmlEscape($row['physician_type']) . "</physician_type>
  893. <physician_code_type>" . xmlEscape($physician_code_type) . "</physician_code_type>
  894. <npi>" . xmlEscape($row['npi']) . "</npi>
  895. <fname>" . xmlEscape($row['fname']) . "</fname>
  896. <mname>" . xmlEscape($row['mname']) . "</mname>
  897. <lname>" . xmlEscape($row['lname']) . "</lname>
  898. <street>" . xmlEscape($row['street']) . "</street>
  899. <city>" . xmlEscape($row['city']) . "</city>
  900. <state>" . xmlEscape($row['state']) . "</state>
  901. <zip>" . xmlEscape($row['zip']) . "</zip>
  902. <work_phone>" . xmlEscape($row['phonew1']) . "</work_phone>
  903. <location>" . xmlEscape($row['name']) . "</location>
  904. <location_details>" . xmlEscape($location_details) . "</location_details>
  905. <date>" . xmlEscape($this->date_format(substr($row['date'], 0, 10))) . "</date>
  906. <date_formatted>" . xmlEscape(str_replace("-", '', substr($row['date'], 0, 10))) . "</date_formatted>
  907. <facility_extension>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['fid'])) . "</facility_extension>
  908. <facility_sha_extension>" . xmlEscape($this->formatUid($_SESSION['site_id'] . $row['fid'])) . "</facility_sha_extension>
  909. <facility_npi>" . xmlEscape($row['fnpi']) . "</facility_npi>
  910. <facility_oid>" . xmlEscape($row['foid']) . "</facility_oid>
  911. <facility_name>" . xmlEscape($row['name']) . "</facility_name>
  912. <facility_address>" . xmlEscape($row['fstreet']) . "</facility_address>
  913. <facility_city>" . xmlEscape($row['fcity']) . "</facility_city>
  914. <facility_state>" . xmlEscape($row['fstate']) . "</facility_state>
  915. <facility_country>" . xmlEscape($row['country_code']) . "</facility_country>
  916. <facility_zip>" . xmlEscape($row['fzip']) . "</facility_zip>
  917. <facility_phone>" . xmlEscape($row['fphone']) . "</facility_phone>
  918. <encounter_procedures>$codes</encounter_procedures>
  919. $encounter_diagnosis
  920. $encounter_reason
  921. </encounter>";
  922. }
  923. $results .= "</encounter_list>";
  924. return $results;
  925. }
  926. /*
  927. #**************************************************#
  928. # PROGRESS NOTES #
  929. #**************************************************#
  930. */
  931. public function getProgressNotes($pid, $encounter)
  932. {
  933. $progress_notes = '';
  934. $formTables_details = $this->fetchFields('progress_note', 'assessment_plan', 1);
  935. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  936. $progress_notes .= "<progressNotes>";
  937. foreach ($result as $row) {
  938. foreach ($row as $key => $value) {
  939. $progress_notes .= "<item>" . xmlEscape($value) . "</item>";
  940. }
  941. }
  942. $progress_notes .= "</progressNotes>";
  943. return $progress_notes;
  944. }
  945. /*
  946. #**************************************************#
  947. # DISCHARGE SUMMARY #
  948. #**************************************************#
  949. */
  950. public function getHospitalCourse($pid, $encounter)
  951. {
  952. $hospital_course = '';
  953. $formTables_details = $this->fetchFields('discharge_summary', 'hospital_course', 1);
  954. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  955. $hospital_course .= "<hospitalCourse><item>";
  956. foreach ($result as $row) {
  957. $hospital_course .= xmlEscape(implode(' ', $row));
  958. }
  959. $hospital_course .= "</item></hospitalCourse>";
  960. return $hospital_course;
  961. }
  962. public function getDischargeDiagnosis($pid, $encounter)
  963. {
  964. $discharge_diagnosis = '';
  965. $formTables_details = $this->fetchFields('discharge_summary', 'hospital_discharge_diagnosis', 1);
  966. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  967. $discharge_diagnosis .= "<dischargediagnosis><item>";
  968. foreach ($result as $row) {
  969. $discharge_diagnosis .= xmlEscape(implode(' ', $row));
  970. }
  971. $discharge_diagnosis .= "</item></dischargediagnosis>";
  972. return $discharge_diagnosis;
  973. }
  974. public function getDischargeMedications($pid, $encounter)
  975. {
  976. $discharge_medications = '';
  977. $formTables_details = $this->fetchFields('discharge_summary', 'hospital_discharge_medications', 1);
  978. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  979. $discharge_medications .= "<dischargemedication><item>";
  980. foreach ($result as $row) {
  981. $discharge_medications .= xmlEscape(implode(' ', $row));
  982. }
  983. $discharge_medications .= "</item></dischargemedication>";
  984. return $discharge_medications;
  985. }
  986. /*
  987. #***********************************************#
  988. # PROCEDURE NOTES #
  989. #***********************************************#
  990. Sub section of PROCEDURE NOTES in CCDA.
  991. * @param int $pid Patient Internal Identifier.
  992. * @param int $encounter Current selected encounter.
  993. * return string $complications XML which contains the details collected from the patient.
  994. */
  995. public function getComplications($pid, $encounter)
  996. {
  997. $complications = '';
  998. $formTables_details = $this->fetchFields('procedure_note', 'complications', 1);
  999. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1000. $complications .= "<complications>";
  1001. $complications .= "<age>" . xmlEscape($this->getAge($pid)) . "</age><item>";
  1002. foreach ($result as $row) {
  1003. $complications .= xmlEscape(implode(' ', $row));
  1004. }
  1005. $complications .= "</item></complications>";
  1006. return $complications;
  1007. }
  1008. /*
  1009. Sub section of PROCEDURE NOTES in CCDA.
  1010. * @param int $pid Patient Internal Identifier.
  1011. * @param int $encounter Current selected encounter.
  1012. * return string $procedure_diag XML which contains the details collected from the patient.
  1013. */
  1014. public function getPostProcedureDiag($pid, $encounter)
  1015. {
  1016. $procedure_diag = '';
  1017. $formTables_details = $this->fetchFields('procedure_note', 'postprocedure_diagnosis', 1);
  1018. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1019. $procedure_diag .= '<procedure_diagnosis>';
  1020. $procedure_diag .= "<age>" . xmlEscape($this->getAge($pid)) . "</age><item>";
  1021. foreach ($result as $row) {
  1022. $procedure_diag .= xmlEscape(implode(' ', $row));
  1023. }
  1024. $procedure_diag .= '</item></procedure_diagnosis>';
  1025. return $procedure_diag;
  1026. }
  1027. /*
  1028. Sub section of PROCEDURE NOTES in CCDA.
  1029. * @param int $pid Patient Internal Identifier.
  1030. * @param int $encounter Current selected encounter.
  1031. * return string $procedure_description XML which contains the details collected from the patient.
  1032. */
  1033. public function getProcedureDescription($pid, $encounter)
  1034. {
  1035. $procedure_description = '';
  1036. $formTables_details = $this->fetchFields('procedure_note', 'procedure_description', 1);
  1037. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1038. $procedure_description .= "<procedure_description><item>";
  1039. foreach ($result as $row) {
  1040. $procedure_description .= xmlEscape(implode(' ', $row));
  1041. }
  1042. $procedure_description .= "</item></procedure_description>";
  1043. return $procedure_description;
  1044. }
  1045. /*
  1046. Sub section of PROCEDURE NOTES in CCDA.
  1047. * @param int $pid Patient Internal Identifier.
  1048. * @param int $encounter Current selected encounter.
  1049. * return string $procedure_indications XML which contains the details collected from the patient.
  1050. */
  1051. public function getProcedureIndications($pid, $encounter)
  1052. {
  1053. $procedure_indications = '';
  1054. $formTables_details = $this->fetchFields('procedure_note', 'procedure_indications', 1);
  1055. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1056. $procedure_indications .= "<procedure_indications><item>";
  1057. foreach ($result as $row) {
  1058. $procedure_indications .= xmlEscape(implode(' ', $row));
  1059. }
  1060. $procedure_indications .= "</item></procedure_indications>";
  1061. return $procedure_indications;
  1062. }
  1063. /*
  1064. #***********************************************#
  1065. # OPERATIVE NOTES #
  1066. #***********************************************#
  1067. Sub section of OPERATIVE NOTES in CCDA.
  1068. * @param int $pid Patient Internal Identifier.
  1069. * @param int $encounter Current selected encounter.
  1070. * return string $anesthesia XML which contains the details collected from the patient.
  1071. */
  1072. public function getAnesthesia($pid, $encounter)
  1073. {
  1074. $anesthesia = '';
  1075. $formTables_details = $this->fetchFields('operative_note', 'anesthesia', 1);
  1076. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1077. $anesthesia .= "<anesthesia><item>";
  1078. foreach ($result as $row) {
  1079. $anesthesia .= xmlEscape(implode(' ', $row));
  1080. }
  1081. $anesthesia .= "</item></anesthesia>";
  1082. return $anesthesia;
  1083. }
  1084. /*
  1085. Sub section of OPERATIVE NOTES in CCDA.
  1086. * @param int $pid Patient Internal Identifier.
  1087. * @param int $encounter Current selected encounter.
  1088. * return string $post_operative_diag XML which contains the details collected from the patient.
  1089. */
  1090. public function getPostoperativeDiag($pid, $encounter)
  1091. {
  1092. $post_operative_diag = '';
  1093. $formTables_details = $this->fetchFields('operative_note', 'post_operative_diagnosis', 1);
  1094. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1095. $post_operative_diag .= "<post_operative_diag><item>";
  1096. foreach ($result as $row) {
  1097. $post_operative_diag .= xmlEscape(implode(' ', $row));
  1098. }
  1099. $post_operative_diag .= "</item></post_operative_diag>";
  1100. return $post_operative_diag;
  1101. }
  1102. /*
  1103. Sub section of OPERATIVE NOTES in CCDA.
  1104. * @param int $pid Patient Internal Identifier.
  1105. * @param int $encounter Current selected encounter.
  1106. * return string $pre_operative_diag XML which contains the details collected from the patient.
  1107. */
  1108. public function getPreOperativeDiag($pid, $encounter)
  1109. {
  1110. $pre_operative_diag = '';
  1111. $formTables_details = $this->fetchFields('operative_note', 'pre_operative_diagnosis', 1);
  1112. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1113. $pre_operative_diag .= "<pre_operative_diag><item>";
  1114. foreach ($result as $row) {
  1115. $pre_operative_diag .= xmlEscape(implode(' ', $row));
  1116. }
  1117. $pre_operative_diag .= "</item></pre_operative_diag>";
  1118. return $pre_operative_diag;
  1119. }
  1120. /*
  1121. Sub section of OPERATIVE NOTES in CCDA.
  1122. * @param int $pid Patient Internal Identifier.
  1123. * @param int $encounter Current selected encounter.
  1124. * return string $pre_operative_diag XML which contains the details collected from the patient.
  1125. */
  1126. public function getEstimatedBloodLoss($pid, $encounter)
  1127. {
  1128. $estimated_blood_loss = '';
  1129. $formTables_details = $this->fetchFields('operative_note', 'procedure_estimated_blood_loss', 1);
  1130. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1131. $estimated_blood_loss .= "<blood_loss><item>";
  1132. foreach ($result as $row) {
  1133. $estimated_blood_loss .= xmlEscape(implode(' ', $row));
  1134. }
  1135. $estimated_blood_loss .= "</item></blood_loss>";
  1136. return $estimated_blood_loss;
  1137. }
  1138. /*
  1139. Sub section of OPERATIVE NOTES in CCDA.
  1140. * @param int $pid Patient Internal Identifier.
  1141. * @param int $encounter Current selected encounter.
  1142. * return string $pre_operative_diag XML which contains the details collected from the patient.
  1143. */
  1144. public function getProcedureFindings($pid, $encounter)
  1145. {
  1146. $procedure_findings = '';
  1147. $formTables_details = $this->fetchFields('operative_note', 'procedure_findings', 1);
  1148. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1149. $procedure_findings .= "<procedure_findings><item>";
  1150. foreach ($result as $row) {
  1151. $procedure_findings .= xmlEscape(implode(' ', $row));
  1152. }
  1153. $procedure_findings .= "</item><age>" . xmlEscape($this->getAge($pid)) . "</age></procedure_findings>";
  1154. return $procedure_findings;
  1155. }
  1156. /*
  1157. Sub section of OPERATIVE NOTES in CCDA.
  1158. * @param int $pid Patient Internal Identifier.
  1159. * @param int $encounter Current selected encounter.
  1160. * return string $pre_operative_diag XML which contains the details collected from the patient.
  1161. */
  1162. public function getProcedureSpecimensTaken($pid, $encounter)
  1163. {
  1164. $procedure_specimens = '';
  1165. $formTables_details = $this->fetchFields('operative_note', 'procedure_specimens_taken', 1);
  1166. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1167. $procedure_specimens .= "<procedure_specimens><item>";
  1168. foreach ($result as $row) {
  1169. $procedure_specimens .= xmlEscape(implode(' ', $row));
  1170. }
  1171. $procedure_specimens .= "</item></procedure_specimens>";
  1172. return $procedure_specimens;
  1173. }
  1174. /*
  1175. #***********************************************#
  1176. # CONSULTATION NOTES #
  1177. #***********************************************#
  1178. Sub section of CONSULTATION NOTES in CCDA.
  1179. * @param int $pid Patient Internal Identifier.
  1180. * @param int $encounter Current selected encounter.
  1181. * return string $hp XML which contains the details collected from the patient.
  1182. */
  1183. public function getHP($pid, $encounter)
  1184. {
  1185. $hp = '';
  1186. $formTables_details = $this->fetchFields('consultation_note', 'history_of_present_illness', 1);
  1187. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1188. $hp .= "<hp><item>";
  1189. foreach ($result as $row) {
  1190. $hp .= xmlEscape(implode(' ', $row));
  1191. }
  1192. $hp .= "</item></hp>";
  1193. return $hp;
  1194. }
  1195. /*
  1196. Sub section of CONSULTATION NOTES in CCDA.
  1197. * @param int $pid Patient Internal Identifier.
  1198. * @param int $encounter Current selected encounter.
  1199. * return string $physical_exam XML which contains the details collected from the patient.
  1200. */
  1201. public function getPhysicalExam($pid, $encounter)
  1202. {
  1203. $physical_exam = '';
  1204. $formTables_details = $this->fetchFields('consultation_note', 'physical_exam', 1);
  1205. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1206. $physical_exam .= "<physical_exam><item>";
  1207. foreach ($result as $row) {
  1208. $physical_exam .= xmlEscape(implode(' ', $row));
  1209. }
  1210. $physical_exam .= "</item></physical_exam>";
  1211. return $physical_exam;
  1212. }
  1213. /*
  1214. #********************************************************#
  1215. # HISTORY AND PHYSICAL NOTES #
  1216. #********************************************************#
  1217. Sub section of HISTORY AND PHYSICAL NOTES in CCDA.
  1218. * @param int $pid Patient Internal Identifier.
  1219. * @param int $encounter Current selected encounter.
  1220. * return string $chief_complaint XML which contains the details collected from the patient.
  1221. */
  1222. public function getChiefComplaint($pid, $encounter)
  1223. {
  1224. $chief_complaint = '';
  1225. $formTables_details = $this->fetchFields('history_physical_note', 'chief_complaint', 1);
  1226. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1227. $chief_complaint .= "<chief_complaint><item>";
  1228. foreach ($result as $row) {
  1229. $chief_complaint .= xmlEscape(implode(' ', $row));
  1230. }
  1231. $chief_complaint .= "</item></chief_complaint>";
  1232. return $chief_complaint;
  1233. }
  1234. /*
  1235. Sub section of HISTORY AND PHYSICAL NOTES in CCDA.
  1236. * @param int $pid Patient Internal Identifier.
  1237. * @param int $encounter Current selected encounter.
  1238. * return string $general_status XML which contains the details collected from the patient.
  1239. */
  1240. public function getGeneralStatus($pid, $encounter)
  1241. {
  1242. $general_status = '';
  1243. $formTables_details = $this->fetchFields('history_physical_note', 'general_status', 1);
  1244. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1245. $general_status .= "<general_status><item>";
  1246. foreach ($result as $row) {
  1247. $general_status .= xmlEscape(implode(' ', $row));
  1248. }
  1249. $general_status .= "</item></general_status>";
  1250. return $general_status;
  1251. }
  1252. /*
  1253. Sub section of HISTORY AND PHYSICAL NOTES in CCDA.
  1254. * @param int $pid Patient Internal Identifier.
  1255. * @param int $encounter Current selected encounter.
  1256. * return string $history_past_illness XML which contains the details collected from the patient.
  1257. */
  1258. public function getHistoryOfPastIllness($pid, $encounter)
  1259. {
  1260. $history_past_illness = '';
  1261. $formTables_details = $this->fetchFields('history_physical_note', 'hpi_past_med', 1);
  1262. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1263. $history_past_illness .= "<history_past_illness><item>";
  1264. foreach ($result as $row) {
  1265. $history_past_illness .= xmlEscape(implode(' ', $row));
  1266. }
  1267. $history_past_illness .= "</item></history_past_illness>";
  1268. return $history_past_illness;
  1269. }
  1270. /*
  1271. Sub section of HISTORY AND PHYSICAL NOTES in CCDA.
  1272. * @param int $pid Patient Internal Identifier.
  1273. * @param int $encounter Current selected encounter.
  1274. * return string $review_of_systems XML which contains the details collected from the patient.
  1275. */
  1276. public function getReviewOfSystems($pid, $encounter)
  1277. {
  1278. $review_of_systems = '';
  1279. $formTables_details = $this->fetchFields('history_physical_note', 'review_of_systems', 1);
  1280. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1281. $review_of_systems .= "<review_of_systems><item>";
  1282. foreach ($result as $row) {
  1283. $review_of_systems .= xmlEscape(implode(' ', $row));
  1284. }
  1285. $review_of_systems .= "</item></review_of_systems>";
  1286. return $review_of_systems;
  1287. }
  1288. /*
  1289. Sub section of HISTORY AND PHYSICAL NOTES in CCDA.
  1290. * @param int $pid Patient Internal Identifier.
  1291. * @param int $encounter Current selected encounter.
  1292. * return string $vitals XML which contains the details collected from the patient.
  1293. */
  1294. public function getVitals($pid, $encounter)
  1295. {
  1296. $wherCon = '';
  1297. if ($encounter) {
  1298. $wherCon = "AND fe.encounter = $encounter";
  1299. }
  1300. $vitals = '';
  1301. $query = "SELECT DATE(fe.date) AS date, fv.id, fv.* FROM forms AS f
  1302. JOIN form_encounter AS fe ON fe.encounter = f.encounter AND fe.pid = f.pid
  1303. JOIN form_vitals AS fv ON fv.id = f.form_id
  1304. WHERE f.pid = ? AND f.formdir = 'vitals' AND f.deleted=0 $wherCon
  1305. ORDER BY fe.date DESC LIMIT 1";
  1306. $appTable = new ApplicationTable();
  1307. $res = $appTable->zQuery($query, array($pid));
  1308. $vitals .= "<vitals_list>";
  1309. foreach ($res as $row) {
  1310. $convWeightValue = number_format($row['weight'] * 0.45359237, 2);
  1311. $convHeightValue = round(number_format($row['height'] * 2.54, 2), 1);
  1312. $convTempValue = round(number_format(($row['temperature'] - 32) * (5 / 9), 1));
  1313. if ($GLOBALS['units_of_measurement'] == 2 || $GLOBALS['units_of_measurement'] == 4) {
  1314. $weight_value = $convWeightValue;
  1315. $weight_unit = 'kg';
  1316. $height_value = $convHeightValue;
  1317. $height_unit = 'cm';
  1318. $temp_value = $convTempValue;
  1319. $temp_unit = 'Cel';
  1320. } else {
  1321. $temp = US_weight($row['weight'], 1);
  1322. $tempArr = explode(" ", $temp);
  1323. $weight_value = (float)$tempArr[0];
  1324. $weight_unit = 'lb';
  1325. $height_value = (float)$row['height'];
  1326. $height_unit = 'in';
  1327. $temp_value = (float)$row['temperature'];
  1328. $temp_unit = 'degF';
  1329. }
  1330. $vitals .= "<vitals>
  1331. <extension>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'])) . "</extension>
  1332. <sha_extension>" . xmlEscape("c6f88321-67ad-11db-bd13-0800200c9a66") . "</sha_extension>
  1333. <date>" . xmlEscape(date('Y-m-d', strtotime($row['date'])) ?: '') . "</date>
  1334. <effectivetime>" . xmlEscape(date('Y-m-d H:i:s', strtotime($row['date']))) . "</effectivetime>
  1335. <temperature>" . xmlEscape($temp_value ?: '') . "</temperature>
  1336. <unit_temperature>" . xmlEscape($temp_unit ?: '') . "</unit_temperature>
  1337. <extension_temperature>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'] . 'temperature')) . "</extension_temperature>
  1338. <bpd>" . xmlEscape(($row['bpd'] ?: '')) . "</bpd>
  1339. <extension_bpd>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'] . 'bpd')) . "</extension_bpd>
  1340. <bps>" . xmlEscape(($row['bps'] ?: '')) . "</bps>
  1341. <extension_bps>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'] . 'bps')) . "</extension_bps>
  1342. <head_circ>" . xmlEscape(((float)$row['head_circ'] ?: '')) . "</head_circ>
  1343. <extension_head_circ>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'] . 'head_circ')) . "</extension_head_circ>
  1344. <pulse>" . xmlEscape(((float)$row['pulse'] ?: '')) . "</pulse>
  1345. <extension_pulse>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'] . 'pulse')) . "</extension_pulse>
  1346. <height>" . xmlEscape($height_value ?: '') . "</height>
  1347. <extension_height>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'] . 'height')) . "</extension_height>
  1348. <unit_height>" . xmlEscape($height_unit ?: '') . "</unit_height>
  1349. <oxygen_saturation>" . xmlEscape(((float)$row['oxygen_saturation'] ?: '')) . "</oxygen_saturation>
  1350. <extension_oxygen_saturation>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'] . 'oxygen_saturation')) . "</extension_oxygen_saturation>
  1351. <breath>" . xmlEscape(((float)$row['respiration'] ?: '')) . "</breath>
  1352. <extension_breath>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'] . 'breath')) . "</extension_breath>
  1353. <weight>" . xmlEscape($weight_value ?: '') . "</weight>
  1354. <extension_weight>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'] . 'weight')) . "</extension_weight>
  1355. <unit_weight>" . xmlEscape($weight_unit ?: '') . "</unit_weight>
  1356. <BMI>" . xmlEscape(((float)$row['BMI'] ?: '')) . "</BMI>
  1357. <extension_BMI>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'] . 'BMI')) . "</extension_BMI>
  1358. <BMI_status>" . xmlEscape(($row['BMI_status'] ?: '')) . "</BMI_status>
  1359. <extension_oxygen_flow_rate>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'] . 'oxygen_flow_rate')) . "</extension_oxygen_flow_rate>
  1360. <oxygen_flow_rate>" . xmlEscape(((float)$row['oxygen_flow_rate'] ?: '')) . "</oxygen_flow_rate>
  1361. <extension_ped_weight_height>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'] . 'ped_weight_height')) . "</extension_ped_weight_height>
  1362. <ped_weight_height>" . xmlEscape(((float)$row['ped_weight_height'] ?: '')) . "</ped_weight_height>
  1363. <extension_ped_bmi>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'] . 'ped_bmi')) . "</extension_ped_bmi>
  1364. <ped_bmi>" . xmlEscape(((float)$row['ped_bmi'] ?: '')) . "</ped_bmi>
  1365. <extension_ped_head_circ>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'] . 'ped_head_circ')) . "</extension_ped_head_circ>
  1366. <ped_head_circ>" . xmlEscape(((float)$row['ped_head_circ'] ?: '')) . "</ped_head_circ>
  1367. <extension_inhaled_oxygen_concentration>" . xmlEscape(base64_encode($_SESSION['site_id'] . $row['id'] . 'inhaled_oxygen_concentration')) . "</extension_inhaled_oxygen_concentration>
  1368. <inhaled_oxygen_concentration>" . xmlEscape(((float)$row['inhaled_oxygen_concentration'] ?: '')) . "</inhaled_oxygen_concentration>
  1369. </vitals>";
  1370. }
  1371. $vitals .= "</vitals_list>";
  1372. return $vitals;
  1373. }
  1374. /*
  1375. Sub section of HISTORY AND PHYSICAL NOTES in CCDA.
  1376. * @param int $pid Patient Internal Identifier.
  1377. * @param int $encounter Current selected encounter.
  1378. * return string $social_history XML which contains the details collected from the patient.
  1379. */
  1380. public function getSocialHistory($pid, $encounter)
  1381. {
  1382. $social_history = '';
  1383. $arr = array(
  1384. 'alcohol' => '160573003',
  1385. 'drug' => '363908000',
  1386. 'employment' => '364703007',
  1387. 'exercise' => '256235009',
  1388. 'other_social_history' => '228272008',
  1389. 'diet' => '364393001',
  1390. 'smoking' => '229819007',
  1391. 'toxic_exposure' => '425400000'
  1392. );
  1393. $arr_status = array(
  1394. 'currenttobacco' => 'Current',
  1395. 'quittobacco' => 'Quit',
  1396. 'nevertobacco' => 'Never',
  1397. 'currentalcohol' => 'Current',
  1398. 'quitalcohol' => 'Quit',
  1399. 'neveralcohol' => 'Never'
  1400. );
  1401. $snomeds_status = array(
  1402. 'currenttobacco' => 'completed',
  1403. 'quittobacco' => 'completed',
  1404. 'nevertobacco' => 'completed',
  1405. 'not_applicabletobacco' => 'completed'
  1406. );
  1407. $snomeds = array(
  1408. '1' => '449868002',
  1409. '2' => '428041000124106',
  1410. '3' => '8517006',
  1411. '4' => '266919005',
  1412. '5' => '77176002'
  1413. );
  1414. $alcohol_status = array(
  1415. 'currentalcohol' => 'completed',
  1416. 'quitalcohol' => 'completed',
  1417. 'neveralcohol' => 'completed'
  1418. );
  1419. $alcohol_status_codes = array(
  1420. 'currentalcohol' => '11',
  1421. 'quitalcohol' => '22',
  1422. 'neveralcohol' => '33'
  1423. );
  1424. $query = "SELECT id, tobacco, alcohol, exercise_patterns, recreational_drugs FROM history_data WHERE pid=? ORDER BY id DESC LIMIT 1";
  1425. $appTable = new ApplicationTable();
  1426. $res = $appTable->zQuery($query, array($pid));
  1427. $social_history .= "<social_history>";
  1428. foreach ($res as $row) {
  1429. $tobacco = explode('|', $row['tobacco']);
  1430. $status_code = (new CarecoordinationTable())->getListCodes($tobacco[3], 'smoking_status');
  1431. $status_code = str_replace("SNOMED-CT:", "", $status_code);
  1432. $social_history .= "<history_element>
  1433. <extension>" . xmlEscape(base64_encode('smoking' . $_SESSION['site_id'] . $row['id'])) . "</extension>
  1434. <sha_extension>" . xmlEscape("9b56c25d-9104-45ee-9fa4-e0f3afaa01c1") . "</sha_extension>
  1435. <element>" . xmlEscape('Smoking') . "</element>
  1436. <description>" . xmlEscape((new CarecoordinationTable())->getListTitle($tobacco[3], 'smoking_status')) . "</description>
  1437. <status_code>" . xmlEscape(($status_code ? $status_code : '')) . "</status_code>
  1438. <status>" . xmlEscape(($snomeds_status[$tobacco[1]] ? $snomeds_status[$tobacco[1]] : "")) . "</status>
  1439. <date>" . ($tobacco[2] ? xmlEscape($this->date_format($tobacco[2])) : '') . "</date>
  1440. <date_formatted>" . ($tobacco[2] ? xmlEscape(preg_replace('/-/', '', $tobacco[2])) : '') . "</date_formatted>
  1441. <code>" . xmlEscape(($arr['smoking'] ? $arr['smoking'] : '')) . "</code>
  1442. </history_element>";
  1443. $alcohol = explode('|', $row['alcohol']);
  1444. $social_history .= "<history_element>
  1445. <extension>" . xmlEscape(base64_encode('alcohol' . $_SESSION['site_id'] . $row['id'])) . "</extension>
  1446. <sha_extension>" . xmlEscape("37f76c51-6411-4e1d-8a37-957fd49d2cef") . "</sha_extension>
  1447. <element>" . xmlEscape('Alcohol') . "</element>
  1448. <description>" . xmlEscape($alcohol[0]) . "</description>
  1449. <status_code>" . xmlEscape(($alcohol_status_codes[$alcohol[1]] ? $alcohol_status_codes[$alcohol[1]] : '')) . "</status_code>
  1450. <status>" . xmlEscape(($alcohol_status[$alcohol[1]] ? $alcohol_status[$alcohol[1]] : 'completed')) . "</status>
  1451. <date>" . ($alcohol[2] ? xmlEscape($this->date_format($alcohol[2])) : '') . "</date>
  1452. <date_formatted>" . ($alcohol[2] ? xmlEscape(preg_replace('/-/', '', $alcohol[2])) : '') . "</date_formatted>
  1453. <code>" . xmlEscape($arr['alcohol']) . "</code>
  1454. </history_element>";
  1455. }
  1456. $social_history .= "</social_history>";
  1457. return $social_history;
  1458. }
  1459. /*
  1460. #********************************************************#
  1461. # UNSTRUCTURED DOCUMENTS #
  1462. #********************************************************#
  1463. */
  1464. public function getUnstructuredDocuments($pid, $encounter)
  1465. {
  1466. $image = '';
  1467. $formTables_details = $this->fetchFields('unstructured_document', 'unstructured_doc', 1);
  1468. $result = $this->fetchFormValues($pid, $encounter, $formTables_details);
  1469. $image .= "<document>";
  1470. foreach ($result as $row) {
  1471. foreach ($row as $key => $value) {
  1472. $image .= "<item>";
  1473. $image .= "<type>" . xmlEscape($row[$key][1]) . "</type>";
  1474. $image .= "<content>" . xmlEscape($row[$key][0]) . "</content>";
  1475. $image .= "</item>";
  1476. }
  1477. }
  1478. $image .= "</document>";
  1479. return $image;
  1480. }
  1481. public function getDetails($field_name)
  1482. {
  1483. if ($field_name == 'hie_custodian_id') {
  1484. $query = "SELECT f.name AS organization, f.street, f.city, f.state, f.postal_code AS zip, f.phone AS phonew1
  1485. FROM facility AS f
  1486. JOIN modules AS mo ON mo.mod_directory='Carecoordination'
  1487. JOIN module_configuration AS conf ON conf.field_value=f.id AND mo.mod_id=conf.module_id
  1488. WHERE conf.field_name=?";
  1489. } else {
  1490. $query = "SELECT u.title, u.fname, u.mname, u.lname, u.npi, u.street, u.city, u.state, u.zip, CONCAT_WS(' ','',u.phonew1) AS phonew1, u.organization, u.specialty, conf.field_name, mo.mod_name, lo.title as physician_type, SUBSTRING(lo.codes, LENGTH('SNOMED-CT:')+1, LENGTH(lo.codes)) as physician_type_code
  1491. FROM users AS u
  1492. LEFT JOIN list_options AS lo ON lo.list_id = 'physician_type' AND lo.option_id = u.physician_type
  1493. JOIN modules AS mo ON mo.mod_directory='Carecoordination'
  1494. JOIN module_configuration AS conf ON conf.field_value=u.id AND mo.mod_id=conf.module_id
  1495. WHERE conf.field_name=?";
  1496. }
  1497. $appTable = new ApplicationTable();
  1498. $res = $appTable->zQuery($query, array($field_name));
  1499. foreach ($res as $result) {
  1500. return $result;
  1501. }
  1502. }
  1503. /*
  1504. Get the Age of a patient
  1505. * @param int $pid Patient Internal Identifier.
  1506. * return int $age Age of a patient will be returned
  1507. */
  1508. public function getAge($pid, $date = null)
  1509. {
  1510. if ($date != '') {
  1511. $date = $date;
  1512. } else {
  1513. $date = date('Y-m-d H:i:s');
  1514. }
  1515. $age = 0;
  1516. $query = "select ROUND(DATEDIFF('$date',DOB)/365.25) AS age from patient_data where pid= ? ";
  1517. $appTable = new ApplicationTable();
  1518. $res = $appTable->zQuery($query, array($pid));
  1519. foreach ($res as $row) {
  1520. $age = $row['age'];
  1521. }
  1522. return $age;
  1523. }
  1524. public function getRepresentedOrganization()
  1525. {
  1526. $query = "select * from facility where primary_business_entity = ?";
  1527. $appTable = new ApplicationTable();
  1528. $res = $appTable->zQuery($query, array(1));
  1529. $records = array();
  1530. foreach ($res as $row) {
  1531. $records = $row;
  1532. }
  1533. return $records;
  1534. }
  1535. /*Get the list of items mapped to a particular CCDA section
  1536. * @param $ccda_component CCDA component
  1537. * @param $ccda_section CCDA section of the above component
  1538. * @param $user_id 1
  1539. * @return $ret Array containing the list of items mapped in a particular CCDA section.
  1540. */
  1541. public function fetchFields($ccda_component, $ccda_section, $user_id)
  1542. {
  1543. $form_type = $table_name = $field_names = '';
  1544. $query = "select * from ccda_table_mapping
  1545. left join ccda_field_mapping as ccf on ccf.table_id = ccda_table_mapping.id
  1546. where ccda_component = ? and ccda_component_section = ? and user_id = ? and deleted = 0";
  1547. $appTable = new ApplicationTable();
  1548. $res = $appTable->zQuery($query, array($ccda_component, $ccda_section, $user_id));
  1549. $field_names_type3 = '';
  1550. $ret = array();
  1551. $field_names_type1 = '';
  1552. $field_names_type2 = '';
  1553. foreach ($res as $row) {
  1554. $form_type = $row['form_type'];
  1555. $table_name = $row['form_table'];
  1556. $form_dir = $row['form_dir'];
  1557. if ($form_type == 1) {
  1558. if ($field_names_type1) {
  1559. $field_names_type1 .= ',';
  1560. }
  1561. $field_names_type1 .= $row['ccda_field'];
  1562. $ret[$row['ccda_component_section'] . "_" . $form_dir] = array($form_type, $table_name, $form_dir, $field_names_type1);
  1563. } elseif ($form_type == 2) {
  1564. if ($field_names_type2) {
  1565. $field_names_type2 .= ',';
  1566. }
  1567. $field_names_type2 .= $row['ccda_field'];
  1568. $ret[$row['ccda_component_section'] . "_" . $form_dir] = array($form_type, $table_name, $form_dir, $field_names_type2);
  1569. } elseif ($form_type == 3) {
  1570. if ($field_names_type3) {
  1571. $field_names_type3 .= ',';
  1572. }
  1573. $field_names_type3 .= $row['ccda_field'];
  1574. $ret[$row['ccda_component_section'] . "_" . $form_dir] = array($form_type, $table_name, $form_dir, $field_names_type3);
  1575. }
  1576. }
  1577. return $ret;
  1578. }
  1579. /*Fetch the form values
  1580. * @param $pid
  1581. * @param $encounter
  1582. * @param $formTables
  1583. * @return $res Array of forms values of a single section
  1584. */
  1585. public function fetchFormValues($pid, $encounter, $formTables)
  1586. {
  1587. if (empty($encounter)) {
  1588. return "";
  1589. }
  1590. $res = array();
  1591. $count_folder = 0;
  1592. foreach ($formTables as $formTables_details) {
  1593. /***************Fetching the form id for the patient***************/
  1594. $query = "select form_id,encounter from forms where pid = ? and formdir = ? AND deleted=0";
  1595. $appTable = new ApplicationTable();
  1596. $form_ids = $appTable->zQuery($query, array($pid, $formTables_details[2]));
  1597. /***************Fetching the form id for the patient***************/
  1598. if ($formTables_details[0] == 1) {//Fetching the values from an HTML form
  1599. if (!$formTables_details[1]) {//Fetching the complete form
  1600. foreach ($form_ids as $row) {//Fetching the values of each forms
  1601. foreach ($row as $key => $value) {
  1602. ob_start();
  1603. if (file_exists($GLOBALS['fileroot'] . '/interface/forms/' . $formTables_details[2] . '/report.php')) {
  1604. include_once($GLOBALS['fileroot'] . '/interface/forms/' . $formTables_details[2] . '/report.php');
  1605. call_user_func($formTables_details[2] . "_report", $pid, $encounter, 2, $value);
  1606. }
  1607. $res[0][$value] = ob_get_clean();
  1608. }
  1609. }
  1610. } else {//Fetching a single field from the table
  1611. $primary_key = '';
  1612. $query = "SHOW INDEX FROM ? WHERE Key_name='PRIMARY'";
  1613. $appTable = new ApplicationTable();
  1614. $res_primary = $appTable->zQuery($query, array($formTables_details[1]));
  1615. foreach ($res_primary as $row_primary) {
  1616. $primary_key = $row_primary['Column_name'];
  1617. }
  1618. unset($res_primary);
  1619. $query = "select " . $formTables_details[3] . " from " . $formTables_details[1] . "
  1620. join forms as f on f.pid=? AND f.encounter=? AND f.form_id=" . $formTables_details[1] . "." . $primary_key . " AND f.formdir=?
  1621. where 1 = 1 ";
  1622. $appTable = new ApplicationTable();
  1623. $result = $appTable->zQuery($query, array($pid, $encounter, $formTables_details[2]));
  1624. foreach ($result as $row) {
  1625. foreach ($row as $key => $value) {
  1626. $res[0][$key] .= trim($value);
  1627. }
  1628. }
  1629. }
  1630. } elseif ($formTables_details[0] == 2) {//Fetching the values from an LBF form
  1631. if (!$formTables_details[1]) {//Fetching the complete LBF
  1632. foreach ($form_ids as $row) {
  1633. foreach ($row as $key => $value) {
  1634. //This section will be used to fetch complete LBF. This has to be completed. We are working on this.
  1635. }
  1636. }
  1637. } elseif (!$formTables_details[3]) {//Fetching the complete group from an LBF
  1638. foreach ($form_ids as $row) {//Fetching the values of each encounters
  1639. foreach ($row as $key => $value) {
  1640. ob_start();
  1641. ?>
  1642. <table>
  1643. <?php
  1644. display_layout_rows_group_new($formTables_details[2], '', '', $pid, $value, array($formTables_details[1]), '');
  1645. ?>
  1646. </table>
  1647. <?php
  1648. $res[0][$value] = ob_get_clean();
  1649. }
  1650. }
  1651. } else {
  1652. $formid_list = "";
  1653. foreach ($form_ids as $row) {//Fetching the values of each forms
  1654. foreach ($row as $key => $value) {
  1655. if ($formid_list) {
  1656. $formid_list .= ',';
  1657. }
  1658. $formid_list .= $value;
  1659. }
  1660. }
  1661. $formid_list = $formid_list ? $formid_list : "''";
  1662. $lbf = "lbf_data";
  1663. $filename = "{$GLOBALS['srcdir']}/" . $formTables_details[2] . "/" . $formTables_details[2] . "_db.php";
  1664. if (file_exists($filename)) {
  1665. include_once($filename);
  1666. }
  1667. $field_ids = explode(',', $formTables_details[3]);
  1668. $fields_str = '';
  1669. foreach ($field_ids as $key => $value) {
  1670. if ($fields_str != '') {
  1671. $fields_str .= ",";
  1672. }
  1673. $fields_str .= "'$value'";
  1674. }
  1675. $query = "select * from " . $lbf . "
  1676. join forms as f on f.pid = ? AND f.form_id = " . $lbf . ".form_id AND f.formdir = ? AND " . $lbf . ".field_id IN (" . $fields_str . ")
  1677. where deleted = 0";
  1678. $appTable = new ApplicationTable();
  1679. $result = $appTable->zQuery($query, array($pid, $formTables_details[2]));
  1680. foreach ($result as $row) {
  1681. preg_match('/\.$/', trim($row['field_value']), $matches);
  1682. if (count($matches) == 0) {
  1683. $row['field_value'] .= ". ";
  1684. }
  1685. $res[0][$row['field_id']] .= $row['field_value'];
  1686. }
  1687. }
  1688. } elseif ($formTables_details[0] == 3) {//Fetching documents from mapped folders
  1689. $query = "SELECT c.id, c.name, d.id AS document_id, d.type, d.mimetype, d.url, d.docdate
  1690. FROM categories AS c, documents AS d, categories_to_documents AS c2d
  1691. WHERE c.id = ? AND c.id = c2d.category_id AND c2d.document_id = d.id AND d.foreign_id = ?";
  1692. $appTable = new ApplicationTable();
  1693. $result = $appTable->zQuery($query, array($formTables_details[2], $pid));
  1694. foreach ($result as $row_folders) {
  1695. $r = \Documents\Plugin\Documents::getDocument($row_folders['document_id']);
  1696. $res[0][$count_folder][0] = base64_encode($r);
  1697. $res[0][$count_folder][1] = $row_folders['mimetype'];
  1698. $res[0][$count_folder][2] = $row_folders['url'];
  1699. $count_folder++;
  1700. }
  1701. }
  1702. }
  1703. return $res;
  1704. }
  1705. /*
  1706. * Retrive the saved settings of the module from database
  1707. *
  1708. * @param string $module_directory module directory name
  1709. * @param string $field_name field name as in the module_settings table
  1710. */
  1711. public function getSettings($module_directory, $field_name)
  1712. {
  1713. $query = "SELECT mo_conf.field_value FROM modules AS mo
  1714. LEFT JOIN module_configuration AS mo_conf ON mo_conf.module_id = mo.mod_id
  1715. WHERE mo.mod_directory = ? AND mo_conf.field_name = ?";
  1716. $appTable = new ApplicationTable();
  1717. $result = $appTable->zQuery($query, array($module_directory, $field_name));
  1718. foreach ($result as $row) {
  1719. return $row['field_value'];
  1720. }
  1721. }
  1722. /*
  1723. * Get the encounters in a particular date
  1724. *
  1725. * @param Date $date Date format yyyy-mm-dd
  1726. * $return Array $date_list List of encounter in the given date.
  1727. */
  1728. public function getEncounterDate($date)
  1729. {
  1730. $date_list = array();
  1731. $query = "select pid, encounter from form_encounter where date between ? and ?";
  1732. $appTable = new ApplicationTable();
  1733. $result = $appTable->zQuery($query, array($date, $date));
  1734. $count = 0;
  1735. foreach ($result as $row) {
  1736. $date_list[$count]['pid'] = $row['pid'];
  1737. $date_list[$count]['encounter'] = $row['encounter'];
  1738. $count++;
  1739. }
  1740. return $date_list;
  1741. }
  1742. /*
  1743. * Sign Off an encounter
  1744. *
  1745. * @param integer $pid
  1746. * @param integer $encounter
  1747. * @return array $forms List of locked forms
  1748. */
  1749. public function signOff($pid, $encounter)
  1750. {
  1751. /*Saving Demographics to locked data*/
  1752. $query_patient_data = "SELECT * FROM patient_data WHERE pid = ?";
  1753. $appTable = new ApplicationTable();
  1754. $result_patient_data = $appTable->zQuery($query_patient_data, array($pid));
  1755. foreach ($result_patient_data as $row_patient_data) {
  1756. }
  1757. $query_dem = "SELECT field_id FROM layout_options WHERE form_id = ?";
  1758. $appTable = new ApplicationTable();
  1759. $result_dem = $appTable->zQuery($query_dem, array('DEM'));
  1760. foreach ($result_dem as $row_dem) {
  1761. $query_insert_patient_data = "INSERT INTO combination_form_locked_data SET pid = ?, encounter = ?, form_dir = ?, field_name = ?, field_value = ?";
  1762. $appTable = new ApplicationTable();
  1763. $result_dem = $appTable->zQuery($query_insert_patient_data, array($pid, $encounter, 'DEM', $row_dem['field_id'], $row_patient_data[$row_dem['field_id']]));
  1764. }
  1765. /*************************************/
  1766. $query_saved_forms = "SELECT formid FROM combined_encountersaved_forms WHERE pid = ? AND encounter = ?";
  1767. $appTable = new ApplicationTable();
  1768. $result_saved_forms = $appTable->zQuery($query_saved_forms, array($pid, $encounter));
  1769. $count = 0;
  1770. foreach ($result_saved_forms as $row_saved_forms) {
  1771. $form_dir = '';
  1772. $form_type = 0;
  1773. $form_id = 0;
  1774. $temp = explode('***', $row_saved_forms['formid']);
  1775. if ($temp[1] == 1) { //Fetch HTML form id from the Combination form template
  1776. $form_type = 0;
  1777. $form_dir = $temp[0];
  1778. } else { //Fetch LBF form from the Combination form template
  1779. $temp_1 = explode('*', $temp[1]);
  1780. if ($temp_1[1] == 1) { //Complete LBF in Combination form
  1781. $form_type = 1;
  1782. $form_dir = $temp[0];
  1783. } elseif ($temp_1[1] == 2) { //Particular section from LBF in Combination form
  1784. $temp_2 = explode('|', $temp[0]);
  1785. $form_type = 1;
  1786. $form_dir = $temp_2[0];
  1787. }
  1788. }
  1789. /*Fetch form id from the concerned tables*/
  1790. if ($form_dir == 'HIS') { //Fetching History form id
  1791. $query_form_id = "SELECT MAX(id) AS form_id FROM history_data WHERE pid = ?";
  1792. $appTable = new ApplicationTable();
  1793. $result_form_id = $appTable->zQuery($query_form_id, array($pid));
  1794. } else { //Fetching normal form id
  1795. $query_form_id = "select form_id from forms where pid = ? and encounter = ? and formdir = ?";
  1796. $appTable = new ApplicationTable();
  1797. $result_form_id = $appTable->zQuery($query_form_id, array($pid, $encounter, $form_dir));
  1798. }
  1799. foreach ($result_form_id as $row_form_id) {
  1800. $form_id = $row_form_id['form_id'];
  1801. }
  1802. /****************************************/
  1803. $forms[$count]['formdir'] = $form_dir;
  1804. $forms[$count]['formtype'] = $form_type;
  1805. $forms[$count]['formid'] = $form_id;
  1806. $this->lockedthisform($pid, $encounter, $form_dir, $form_type, $form_id);
  1807. $count++;
  1808. }
  1809. return $forms;
  1810. }
  1811. /*
  1812. * Lock a component in combination form
  1813. *
  1814. * @param integer $pid
  1815. * @param integer $encounter
  1816. * @param integer $formdir Form directory
  1817. * @param integer $formtype Form type, 0 => HTML, 1 => LBF
  1818. * @param integer $formid Saved form id from forms table
  1819. *
  1820. * @return None
  1821. */
  1822. public function lockedthisform($pid, $encounter, $formdir, $formtype, $formid)
  1823. {
  1824. $query = "select count(*) as count from combination_form where pid = ? and encounter = ? and form_dir = ? and form_type = ? and form_id = ?";
  1825. $appTable = new ApplicationTable();
  1826. $result = $appTable->zQuery($query, array($pid, $encounter, $formdir, $formtype, $formid));
  1827. foreach ($result as $count) {
  1828. }
  1829. if ($count['count'] == 0) {
  1830. $query_insert = "INSERT INTO combination_form SET pid = ?, encounter = ?, form_dir = ?, form_type = ?, form_id = ?";
  1831. $appTable = new ApplicationTable();
  1832. $result = $appTable->zQuery($query_insert, array($pid, $encounter, $formdir, $formtype, $formid));
  1833. }
  1834. }
  1835. /*
  1836. * Return the list of CCDA components
  1837. *
  1838. * @param $type
  1839. * @return Array $components
  1840. */
  1841. public function getCCDAComponents($type)
  1842. {
  1843. $components = array();
  1844. $query = "select * from ccda_components where ccda_type = ?";
  1845. $appTable = new ApplicationTable();
  1846. $result = $appTable->zQuery($query, array($type));
  1847. foreach ($result as $row) {
  1848. $components[$row['ccda_components_field']] = $row['ccda_components_name'];
  1849. }
  1850. return $components;
  1851. }
  1852. /*
  1853. * Store the status of the CCDA sent to HIE
  1854. *
  1855. * @param integer $pid
  1856. * @param integer $encounter
  1857. * @param integer $content
  1858. * @param integer $time
  1859. * @param integer $status
  1860. * @return None
  1861. */
  1862. public function logCCDA($pid, $encounter, $content, $time, $status, $user_id, $view = 0, $transfer = 0, $emr_transfer = 0)
  1863. {
  1864. $content = base64_decode($content);
  1865. $file_path = '';
  1866. $docid = '';
  1867. $revid = '';
  1868. if ($GLOBALS['document_storage_method'] == 1) {
  1869. $couch = new CouchDB();
  1870. $docid = $couch->createDocId('ccda');
  1871. $binaryUuid = UuidRegistry::uuidToBytes($docid);
  1872. if ($GLOBALS['couchdb_encryption']) {
  1873. $encrypted = 1;
  1874. $cryptoGen = new CryptoGen();
  1875. $resp = $couch->save_doc(['_id' => $docid, 'data' => $cryptoGen->encryptStandard($content, null, 'database')]);
  1876. } else {
  1877. $encrypted = 0;
  1878. $resp = $couch->save_doc(['_id' => $docid, 'data' => base64_encode($content)]);
  1879. }
  1880. $docid = $resp->id;
  1881. $revid = $resp->rev;
  1882. } else {
  1883. $binaryUuid = (new UuidRegistry(['table_name' => 'ccda']))->createUuid();
  1884. $file_name = UuidRegistry::uuidToString($binaryUuid);
  1885. $file_path = $GLOBALS['OE_SITE_DIR'] . '/documents/' . $pid . '/CCDA';
  1886. if (!is_dir($file_path)) {
  1887. if (!mkdir($file_path, 0777, true) && !is_dir($file_path)) {
  1888. // php Exception extends RunTimeException
  1889. throw new Exception(sprintf('Directory "%s" was not created', $file_path));
  1890. }
  1891. }
  1892. $fccda = fopen($file_path . "/" . $file_name, "w");
  1893. if ($GLOBALS['drive_encryption']) {
  1894. $encrypted = 1;
  1895. $cryptoGen = new CryptoGen();
  1896. fwrite($fccda, $cryptoGen->encryptStandard($content, null, 'database'));
  1897. } else {
  1898. $encrypted = 0;
  1899. fwrite($fccda, $content);
  1900. }
  1901. fclose($fccda);
  1902. $file_path = $file_path . "/" . $file_name;
  1903. }
  1904. $query = "insert into ccda (`uuid`, `pid`, `encounter`, `ccda_data`, `time`, `status`, `user_id`, `couch_docid`, `couch_revid`, `hash`, `view`, `transfer`, `emr_transfer`, `encrypted`) values (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)";
  1905. $hash = hash('sha3-512', $content);
  1906. $appTable = new ApplicationTable();
  1907. $result = $appTable->zQuery($query, array($binaryUuid, $pid, $encounter, $file_path, $time, $status, $user_id, $docid, $revid, $hash, $view, $transfer, $emr_transfer, $encrypted));
  1908. return $moduleInsertId = $result->getGeneratedValue();
  1909. }
  1910. public function getCcdaLogDetails($logID = 0)
  1911. {
  1912. $query_ccda_log = "SELECT pid, encounter, ccda_data, time, status, user_id, couch_docid, couch_revid, view, transfer,emr_transfer FROM ccda WHERE id = ?";
  1913. $appTable = new ApplicationTable();
  1914. $res_ccda_log = $appTable->zQuery($query_ccda_log, array($logID));
  1915. return $res_ccda_log->current();
  1916. }
  1917. /*
  1918. * Convert date from database format to required format
  1919. *
  1920. * @param String $date Date from database (format: YYYY-MM-DD)
  1921. * @param String $format Required date format
  1922. *
  1923. * @return String $formatted_date New formatted date
  1924. */
  1925. public function date_format($date, $format = null)
  1926. {
  1927. if (!$date) {
  1928. return;
  1929. }
  1930. $format = $format ?: 'm/d/y';
  1931. $temp = explode(' ', $date); //split using space and consider the first portion, incase of date with time
  1932. $date = $temp[0];
  1933. $date = str_replace('/', '-', $date);
  1934. $arr = explode('-', $date);
  1935. if ($format == 'm/d/y') {
  1936. $formatted_date = $arr[1] . "/" . $arr[2] . "/" . $arr[0];
  1937. }
  1938. $formatted_date = $temp[1] ? $formatted_date . " " . $temp[1] : $formatted_date; //append the time, if exists, with the new formatted date
  1939. return $formatted_date;
  1940. }
  1941. /*
  1942. * Generate CODE for medication, allergies etc.. if the code is not present by default.
  1943. * The code is generated from the text that we give for medications or allergies.
  1944. *
  1945. * The text is encrypted using SHA1() and the string is parsed. Alternate letters from the SHA1 string is fetched
  1946. * and the result is again parsed. We again take the alternate letters from the string. This is done twice to reduce
  1947. * duplicate codes beign generated from this function.
  1948. *
  1949. * @param String Code text
  1950. *
  1951. * @return String Code
  1952. */
  1953. public function generate_code($code_text)
  1954. {
  1955. $rx = sqlQuery("Select drug_code From drugs Where name = ?", array("$code_text"));
  1956. if (!empty($rx)) {
  1957. return $rx['drug_code'];
  1958. }
  1959. $encrypted = sha1($code_text);
  1960. $code = '';
  1961. for ($i = 0, $iMax = strlen($encrypted); $i <= $iMax;) {
  1962. $code .= $encrypted[$i];
  1963. $i = $i + 2;
  1964. }
  1965. $encrypted = $code;
  1966. $code = '';
  1967. for ($i = 0, $iMax = strlen($encrypted); $i <= $iMax;) {
  1968. $code .= $encrypted[$i];
  1969. $i = $i + 2;
  1970. }
  1971. $code = strtoupper(substr($code, 0, 6));
  1972. return $code;
  1973. }
  1974. public function getProviderId($pid)
  1975. {
  1976. $appTable = new ApplicationTable();
  1977. $query = "SELECT providerID FROM patient_data WHERE `pid` = ?";
  1978. $result = $appTable->zQuery($query, array($pid));
  1979. $row = $result->current();
  1980. return $row['providerID'];
  1981. }
  1982. public function getUserDetails($uid)
  1983. {
  1984. $query = "SELECT u.title,npi,fname,mname,lname,street,city,state,zip,CONCAT_WS(' ','',phonew1) AS phonew1, lo.title as physician_type, facility As organization, taxonomy, lous.title as taxonomy_desc, specialty, SUBSTRING(lo.codes, LENGTH('SNOMED-CT:')+1, LENGTH(lo.codes)) as physician_type_code FROM users as u
  1985. LEFT JOIN list_options AS lo ON lo.list_id = 'physician_type' AND lo.option_id = u.physician_type
  1986. LEFT JOIN list_options AS lous ON lous.list_id = 'us-core-provider-specialty' AND lous.option_id = u.taxonomy
  1987. WHERE `id` = ?";
  1988. $appTable = new ApplicationTable();
  1989. $res = $appTable->zQuery($query, array($uid));
  1990. foreach ($res as $result) {
  1991. return $result;
  1992. }
  1993. }
  1994. /**
  1995. * Checks to see if the snomed codes are installed and we can then query against them.
  1996. */
  1997. private function is_snomed_codes_installed(ApplicationTable $appTable)
  1998. {
  1999. $codes_installed = false;
  2000. // this throws an exception... which is sad
  2001. // TODO: is there a better way to know if the snomed codes are installed instead of using this method?
  2002. // we set $error=false or else it will display on the screen, which seems counterintuitive... it also supresses the exception
  2003. $result = $appTable->zQuery("Describe `sct_descriptions`", $params = '', $log = true, $error = false);
  2004. if ($result !== false) { // will return false if there is an error
  2005. $codes_installed = true;
  2006. }
  2007. return $codes_installed;
  2008. }
  2009. /*
  2010. * get details from care plan form
  2011. * @param int $pid Patient Internal Identifier.
  2012. * @param int $encounter Current selected encounter.
  2013. * return string $planofcare XML which contains the details collected from the patient.
  2014. */
  2015. public function getPlanOfCare($pid, $encounter)
  2016. {
  2017. $wherCon = '';
  2018. $appTable = new ApplicationTable();
  2019. if ($encounter) {
  2020. $query = "SELECT form_id, encounter FROM forms WHERE pid = ? AND formdir = ? AND deleted = 0 ORDER BY date DESC LIMIT 1";
  2021. $result = $appTable->zQuery($query, array($pid, 'care_plan'));
  2022. foreach ($result as $row) {
  2023. $form_id = $row['form_id'];
  2024. }
  2025. if ($form_id) {
  2026. $wherCon = "AND f.form_id = '" . add_escape_custom($form_id) . "'";
  2027. }
  2028. }
  2029. UuidRegistry::createMissingUuidsForTables(['lists']);
  2030. $query = "SELECT 'care_plan' AS source,fcp.encounter,fcp.code,fcp.codetext,fcp.description,fcp.date,l.`notes` AS moodCode,fcp.care_plan_type AS care_plan_type,fcp.note_related_to as note_issues
  2031. FROM forms AS f
  2032. LEFT JOIN form_care_plan AS fcp ON fcp.id = f.form_id
  2033. LEFT JOIN codes AS c ON c.code = fcp.code
  2034. LEFT JOIN code_types AS ct ON c.`code_type` = ct.ct_id
  2035. LEFT JOIN `list_options` l ON l.`option_id` = fcp.`care_plan_type` AND l.`list_id`=?
  2036. WHERE f.pid = ? AND f.formdir = ? AND f.deleted = ? $wherCon
  2037. UNION
  2038. SELECT 'referral' AS source,'' encounter,'' AS CODE,'' AS codetext,CONCAT_WS(', ',l1.field_value,CONCAT_WS(' ',u.fname,u.lname),CONCAT('Tel:',u.phonew1),u.street,u.city,CONCAT_WS(' ',u.state,u.zip),CONCAT('Schedule Date: ',l2.field_value)) AS description,l2.field_value AS DATE,'' moodCode,'' care_plan_type, '' note_issues
  2039. FROM transactions AS t
  2040. LEFT JOIN lbt_data AS l1 ON l1.form_id=t.id AND l1.field_id = 'body'
  2041. LEFT JOIN lbt_data AS l2 ON l2.form_id=t.id AND l2.field_id = 'refer_date'
  2042. LEFT JOIN lbt_data AS l3 ON l3.form_id=t.id AND l3.field_id = 'refer_to'
  2043. LEFT JOIN users AS u ON u.id = l3.field_value
  2044. WHERE t.pid = ?";
  2045. $res = $appTable->zQuery($query, ['Plan_of_Care_Type', $pid, 'care_plan', 0, $pid]);
  2046. $status = 'Pending';
  2047. $status_entry = 'active';
  2048. $planofcare = '<planofcare>';
  2049. $goals = '<goals>';
  2050. $concerns = '<health_concerns>';
  2051. foreach ($res as $row) {
  2052. $row['description'] = preg_replace("/\{\|([^\]]*)\|}/", '', $row['description']);
  2053. $tmp = explode(":", $row['code']);
  2054. $code_type = $tmp[0];
  2055. $code = $tmp[1];
  2056. if ($row['source'] === 'referral') {
  2057. if (empty($row['code'])) {
  2058. continue;
  2059. }
  2060. $row['care_plan_type'] = 'referral';
  2061. }
  2062. if ($row['care_plan_type'] === 'health_concern') {
  2063. $issue_uuid = "<issues>\n";
  2064. if (!empty($row['note_issues'])) {
  2065. $issues = json_decode($row['note_issues'], true);
  2066. foreach ($issues as $issue) {
  2067. $q = "Select uuid from lists Where id = ?";
  2068. $uuid = sqlQuery($q, array($issue))['uuid'];
  2069. if (empty($uuid)) {
  2070. continue;
  2071. }
  2072. $uuid_problem = UuidRegistry::uuidToString($uuid);
  2073. $issue_uuid .= "<issue_uuid>" . xmlEscape($uuid_problem) . "</issue_uuid>\n";
  2074. }
  2075. }
  2076. $concerns .= "<concern>" .
  2077. $issue_uuid . "</issues>" .
  2078. "<encounter>" . xmlEscape($row['encounter']) . "</encounter>
  2079. <extension>" . xmlEscape(base64_encode($row['form_id'] . $row['code'])) . "</extension>
  2080. <sha_extension>" . xmlEscape($this->formatUid($row['form_id'] . $row['description'])) . "</sha_extension>
  2081. <text>" . xmlEscape($row['date'] . " " . $row['description']) . '</text>
  2082. <code>' . xmlEscape($code) . '</code>
  2083. <code_type>' . xmlEscape($code_type) . '</code_type>
  2084. <code_text>' . xmlEscape($row['codetext']) . '</code_text>
  2085. <date>' . xmlEscape($row['date']) . '</date>
  2086. <date_formatted>' . xmlEscape(str_replace("-", '', $row['date'])) . '</date_formatted>
  2087. </concern>';
  2088. }
  2089. if ($row['care_plan_type'] === 'goal') {
  2090. $goals .= '<item>
  2091. <extension>' . xmlEscape(base64_encode($row['form_id'] . $row['code'])) . '</extension>
  2092. <sha_extension>' . xmlEscape($this->formatUid($row['form_id'] . $row['description'])) . '</sha_extension>
  2093. <care_plan_type>' . xmlEscape($row['care_plan_type']) . '</care_plan_type>
  2094. <encounter>' . xmlEscape($row['encounter']) . '</encounter>
  2095. <code>' . xmlEscape($code) . '</code>
  2096. <code_text>' . xmlEscape($row['codetext']) . '</code_text>
  2097. <description>' . xmlEscape($row['description']) . '</description>
  2098. <date>' . xmlEscape($row['date']) . '</date>
  2099. <date_formatted>' . xmlEscape(str_replace("-", '', $row['date'])) . '</date_formatted>
  2100. <status>' . xmlEscape($status) . '</status>
  2101. <status_entry>' . xmlEscape($status_entry) . '</status_entry>
  2102. <code_type>' . xmlEscape($code_type) . '</code_type>
  2103. <moodCode>' . xmlEscape($row['moodCode']) . '</moodCode>
  2104. </item>';
  2105. } elseif ($row['care_plan_type'] !== 'health_concern') {
  2106. $planofcare .= '<item>
  2107. <extension>' . xmlEscape(base64_encode($row['form_id'] . $row['code'])) . '</extension>
  2108. <sha_extension>' . xmlEscape($this->formatUid($row['form_id'] . $row['description'])) . '</sha_extension>
  2109. <care_plan_type>' . xmlEscape($row['care_plan_type']) . '</care_plan_type>
  2110. <encounter>' . xmlEscape($row['encounter']) . '</encounter>
  2111. <code>' . xmlEscape($code) . '</code>
  2112. <code_text>' . xmlEscape($row['codetext']) . '</code_text>
  2113. <description>' . xmlEscape($row['description']) . '</description>
  2114. <date>' . xmlEscape($row['date']) . '</date>
  2115. <date_formatted>' . xmlEscape(str_replace("-", '', $row['date'])) . '</date_formatted>
  2116. <status>' . xmlEscape($status) . '</status>
  2117. <status_entry>' . xmlEscape($status_entry) . '</status_entry>
  2118. <code_type>' . xmlEscape($code_type) . '</code_type>
  2119. <moodCode>' . xmlEscape($row['moodCode']) . '</moodCode>
  2120. </item>';
  2121. }
  2122. }
  2123. $planofcare .= '</planofcare>';
  2124. $goals .= '</goals>';
  2125. $concerns .= '</health_concerns>';
  2126. return $planofcare . $goals . $concerns;
  2127. }
  2128. /*
  2129. * get details from functional and cognitive status form
  2130. * @param int $pid Patient Internal Identifier.
  2131. * @param int $encounter Current selected encounter.
  2132. * return string $functional_cognitive XML which contains the details collected from the patient.
  2133. */
  2134. public function getFunctionalCognitiveStatus($pid, $encounter)
  2135. {
  2136. $wherCon = '';
  2137. $sqlBindArray = [];
  2138. if ($encounter) {
  2139. $wherCon = " f.encounter = ? AND ";
  2140. $sqlBindArray[] = $encounter;
  2141. }
  2142. $functional_status = '<functional_status>';
  2143. $cognitive_status = '<mental_status>';
  2144. $query = "SELECT ffcs.* FROM forms AS f
  2145. LEFT JOIN form_functional_cognitive_status AS ffcs ON ffcs.id = f.form_id
  2146. WHERE $wherCon f.pid = ? AND f.formdir = ? AND f.deleted = ?";
  2147. array_push($sqlBindArray, $pid, 'functional_cognitive_status', 0);
  2148. $appTable = new ApplicationTable();
  2149. $res = $appTable->zQuery($query, $sqlBindArray);
  2150. foreach ($res as $row) {
  2151. if ($row['activity'] == 1) {
  2152. $cognitive_status .= '<item>
  2153. <code>' . xmlEscape(($row['code'] ?: '')) . '</code>
  2154. <code_text>' . xmlEscape(($row['codetext'] ?: '')) . '</code_text>
  2155. <description>' . xmlEscape($row['date'] . ' ' . $row['description']) . '</description>
  2156. <date>' . xmlEscape($row['date']) . '</date>
  2157. <date_formatted>' . xmlEscape(str_replace("-", '', $row['date'])) . '</date_formatted>
  2158. <status>' . xmlEscape('completed') . '</status>
  2159. <age>' . xmlEscape($this->getAge($pid)) . '</age>
  2160. </item>';
  2161. } else {
  2162. $functional_status .= '<item>
  2163. <code>' . xmlEscape(($row['code'] ?: '')) . '</code>
  2164. <code_text>' . xmlEscape(($row['codetext'] ?: '')) . '</code_text>
  2165. <description>' . xmlEscape($row['date'] . ' ' . $row['description']) . '</description>
  2166. <date>' . xmlEscape($row['date']) . '</date>
  2167. <date_formatted>' . xmlEscape(str_replace("-", '', $row['date'])) . '</date_formatted>
  2168. <status>' . xmlEscape('completed') . '</status>
  2169. <age>' . xmlEscape($this->getAge($pid)) . '</age>
  2170. </item>';
  2171. }
  2172. }
  2173. $functional_status .= '</functional_status>';
  2174. $cognitive_status .= '</mental_status>';
  2175. return $functional_status . $cognitive_status;
  2176. }
  2177. public function getClinicalNotes($pid, $encounter)
  2178. {
  2179. $wherCon = '';
  2180. $sqlBindArray = [];
  2181. if ($encounter) {
  2182. $wherCon = " f.encounter = ? AND ";
  2183. $sqlBindArray[] = $encounter;
  2184. }
  2185. $clinical_notes = '';
  2186. $query = "SELECT fnote.*, u.*, fac.* FROM forms AS f
  2187. LEFT JOIN `form_clinical_notes` AS fnote ON fnote.`form_id` = f.`form_id`
  2188. LEFT JOIN users as u on u.username = fnote.user
  2189. LEFT JOIN facility as fac on fac.id = u.facility_id
  2190. WHERE $wherCon f.`pid` = ? AND f.`formdir` = ? AND f.`deleted` = ? Order By fnote.`encounter`, fnote.`date`, fnote.`clinical_notes_type` DESC";
  2191. array_push($sqlBindArray, $pid, 'clinical_notes', 0);
  2192. $appTable = new ApplicationTable();
  2193. $res = $appTable->zQuery($query, $sqlBindArray);
  2194. $clinical_notes .= '<clinical_notes>';
  2195. foreach ($res as $row) {
  2196. if (empty($row['clinical_notes_type'])) {
  2197. continue;
  2198. }
  2199. $tmp = explode(":", $row['code']);
  2200. $code_type = $tmp[0];
  2201. $code = $tmp[1];
  2202. $clt = xmlEscape($row['clinical_notes_type']);
  2203. $clinical_notes .= "<$clt>" .
  2204. '<clinical_notes_type>' . $clt . '</clinical_notes_type>
  2205. <encounter>' . xmlEscape($row['encounter']) . '</encounter>
  2206. <author_title>' . xmlEscape($row['title']) . '</author_title>
  2207. <author_first>' . xmlEscape($row['fname']) . '</author_first>
  2208. <author_last>' . xmlEscape($row['lname']) . '</author_last>
  2209. <author_npi>' . xmlEscape($row['npi']) . '</author_npi>
  2210. <facility_name>' . xmlEscape($row['name']) . '</facility_name>
  2211. <facility_npi>' . xmlEscape($row['facility_npi']) . '</facility_npi>
  2212. <facility_oid>' . xmlEscape($row['facility_oid']) . '</facility_oid>
  2213. <code>' . xmlEscape($code) . '</code>
  2214. <code_text>' . xmlEscape($row['codetext']) . '</code_text>
  2215. <description>' . xmlEscape($row['description']) . '</description>
  2216. <date>' . xmlEscape($row['date']) . '</date>
  2217. <date_formatted>' . xmlEscape(str_replace("-", '', $row['date'])) . '</date_formatted>
  2218. <code_type>' . xmlEscape($code_type) . "</code_type>
  2219. </$clt>";
  2220. }
  2221. $clinical_notes .= '</clinical_notes>';
  2222. return $clinical_notes;
  2223. }
  2224. public function getCareTeamProviderId($pid)
  2225. {
  2226. $appTable = new ApplicationTable();
  2227. $query = "SELECT care_team_provider FROM patient_data WHERE `pid` = ?";
  2228. $result = $appTable->zQuery($query, array($pid));
  2229. $row = $result->current();
  2230. return $row['care_team_provider'];
  2231. }
  2232. public function getClinicalInstructions($pid, $encounter)
  2233. {
  2234. $wherCon = '';
  2235. $sqlBindArray = [];
  2236. if ($encounter) {
  2237. $wherCon = " f.encounter = ? AND ";
  2238. $sqlBindArray[] = $encounter;
  2239. }
  2240. $query = "SELECT fci.* FROM forms AS f
  2241. LEFT JOIN form_clinical_instructions AS fci ON fci.id = f.form_id
  2242. WHERE $wherCon f.pid = ? AND f.formdir = ? AND f.deleted = ?";
  2243. array_push($sqlBindArray, $pid, 'clinical_instructions', 0);
  2244. $appTable = new ApplicationTable();
  2245. $res = $appTable->zQuery($query, $sqlBindArray);
  2246. $clinical_instructions = '<clinical_instruction>';
  2247. foreach ($res as $row) {
  2248. $clinical_instructions .= '<item>' . xmlEscape($row['instruction']) . '</item>';
  2249. }
  2250. $clinical_instructions .= '</clinical_instruction>';
  2251. return $clinical_instructions;
  2252. }
  2253. public function getReferrals($pid, $encounter)
  2254. {
  2255. // patched out because I can't think of a reason to send a list of referrals
  2256. /*$wherCon = '';
  2257. if ($encounter) {
  2258. $wherCon = "ORDER BY date DESC LIMIT 1";
  2259. }*/
  2260. $wherCon = "ORDER BY date DESC LIMIT 1";
  2261. $appTable = new ApplicationTable();
  2262. $query = "SELECT field_value FROM transactions JOIN lbt_data ON form_id=id AND field_id = 'body' WHERE pid = ? $wherCon";
  2263. $result = $appTable->zQuery($query, array($pid));
  2264. $referrals = '<referral_reason>';
  2265. foreach ($result as $row) {
  2266. $referrals .= '<text>' . xmlEscape($row['field_value']) . '</text>';
  2267. }
  2268. $referrals .= '</referral_reason>';
  2269. return $referrals;
  2270. }
  2271. public function getLatestEncounter($pid)
  2272. {
  2273. $encounter = '';
  2274. $appTable = new ApplicationTable();
  2275. $query = "SELECT encounter FROM form_encounter WHERE pid = ? ORDER BY id DESC LIMIT 1";
  2276. $result = $appTable->zQuery($query, array($pid));
  2277. foreach ($result as $row) {
  2278. $encounter = $row['encounter'];
  2279. }
  2280. return $encounter;
  2281. }
  2282. public function formatUid($str)
  2283. {
  2284. $sha = sha1($str);
  2285. return substr(preg_replace('/^.{8}|.{4}/', '\0-', $sha, 4), 0, 36);
  2286. }
  2287. }
  2288. ?>