/**
  * If no training associations, delete course. 
  */
 public static function deleteIfNotFound($training_title_option_id, $training_id = 0)
 {
     $tableObj = new Course();
     $select = $tableObj->select()->from('training', array('COUNT(id) AS training_count'))->setIntegrityCheck(false)->where("course_id = {$training_title_option_id} AND id != {$training_id}");
     $row = $tableObj->fetchRow($select);
     if (!$row->training_count) {
         $tableObj = new Course();
         $tableObj->delete("training_title_option_id = {$training_title_option_id}");
         $tableObj = new ITechTable(array('name' => 'training_title_option'));
         $tableObj->delete("id = {$training_title_option_id}");
     }
 }
 public static function saveSponsors($id, $sponsor_array, $sponsor_date_array, $sponsor_end_date_array)
 {
     // save facility_sponsors table data)
     if (empty($sponsor_array)) {
         return false;
     }
     $stable = new ITechTable(array('name' => 'facility_sponsors'));
     $select = $stable->select()->where('facility_id = ' . $id);
     $rows = $stable->fetchAll($select);
     $existing_rows = array();
     foreach ($rows as $i => $row) {
         if ($i > count($sponsor_array)) {
             $row->delete();
         } else {
             $existing_rows[] = $row;
         }
         // re-use row. no ->seek() or getRow()?? i'll use an array
     }
     foreach ($sponsor_array as $i => $sponsid) {
         try {
             // define database row
             if ($existing_rows && count($existing_rows) > $i) {
                 // use existing row if there is one
                 #$existing_rows->getRow($i); // no ->seek() or getRow()??
                 #$row = $existing_rows->current();
                 $row = $existing_rows[$i];
             } else {
                 $row = $stable->createRow();
             }
             if (empty($sponsid)) {
                 // remove unused rows
                 $row->delete();
                 continue;
             }
             // fill row
             $row->facility_id = $id;
             $row->facility_sponsor_phrase_id = $sponsid;
             $row->start_date = isset($sponsor_date_array[$i]) && !empty($sponsor_date_array[$i]) ? date('Y-m-d', strtotime($sponsor_date_array[$i])) : '0000-00-00';
             $row->end_date = isset($sponsor_end_date_array[$i]) && !empty($sponsor_end_date_array[$i]) ? date('Y-m-d', strtotime($sponsor_end_date_array[$i])) : '0000-00-00';
             $row->is_default = 0;
             $row->is_deleted = 0;
             // save
             $row->save();
         } catch (Exception $e) {
             return false;
         }
     }
     return true;
 }
 public function update(array $data, $where)
 {
     if (isset($data['password']) and $data['password']) {
         $data['password'] = md5($data['password']);
     }
     return parent::update($data, $where);
 }
 /**
  * Saves recommended topics for person
  */
 public function saveRecommendedforPerson($person_id, $training_ids)
 {
     if (!is_array($training_ids) || !$training_ids) {
         return;
     }
     $training_ids = array_unique($training_ids);
     $tableObj = new ITechTable(array('name' => 'person_to_training_topic_option'));
     $tableObj->delete("person_id={$person_id}", true);
     foreach ($training_ids as $id) {
         if ($id) {
             $createRow = $tableObj->createRow();
             $createRow->person_id = $person_id;
             $createRow->training_topic_option_id = $id;
             $createRow->save();
         }
     }
 }
 public function update(array $data, $where)
 {
     //save a snapshot now
     require_once 'History.php';
     $historyTable = new History('trainer');
     //cheezy way to get the id
     $parts = explode('=', $where[0]);
     $pid = trim($parts[1]);
     //link to the last history row
     $personHistoryTable = new History('person');
     $hrow = $personHistoryTable->fetchAll("person_id = {$pid}", "vid DESC", 1);
     $historyTable->insert($this, $hrow->current()->vid);
     $rslt = parent::update($data, $where);
     return $rslt;
 }
 function sanityCheck()
 {
     //make sure num location tiers is the same on the right vs. the left
     $_app = new ITechTable(SyncCompare::getDesktopConnectionParams('location', $this->desktopFilePath));
     $tiers = $_app->getAdapter()->query('SELECT COUNT(DISTINCT tier) as "cnt" FROM location');
     $rows = $tiers->fetchAll();
     $settings = System::getAll();
     $city_tier = 2 + $settings['display_region_i'] + $settings['display_region_h'] + $settings['display_region_g'] + $settings['display_region_f'] + $settings['display_region_e'] + $settings['display_region_d'] + $settings['display_region_c'] + $settings['display_region_b'];
     if ($rows[0]['cnt'] != $city_tier) {
         return 'Could not import data: Offline database contains ' . $rows[0]['cnt'] . ' regional levels, while the web database contains ' . $city_tier . '.';
     }
     return false;
 }
 public function trainingApproversAction()
 {
     // ajax handler
     if ($this->getRequest()->isPost() && $this->getSanParam('ajax')) {
         // Update db
         $table = new ITechTable(array('name' => 'user_to_acl'));
         $msg = '';
         $success = false;
         $proceed = true;
         $id = $this->getSanParam('id');
         if (!trim($id) || !is_numeric($id)) {
             $proceed = false;
         }
         if ($this->getSanParam('ajaxAction') == 'elevate' && $proceed) {
             $user_acl = $table->createRow();
             $user_acl->acl_id = 'master_approver';
             $user_acl->user_id = $id;
             $user_acl = $user_acl->save();
             $msg = $user_acl ? t('That user is now a master approver') : t('Unable to make that user a master approver');
             if ($user_acl) {
                 $success = true;
             }
         }
         if ($this->getSanParam('ajaxAction') == 'deelevate' && $proceed) {
             $user_acl = $table->delete("acl_id = 'master_approver' and user_id = {$id}");
             $msg = $user_acl ? t('That user is now a regular approver') : t('Unable to remove that user as a master approver');
             if ($user_acl) {
                 $success = true;
             }
         }
         if ($this->getSanParam('ajaxAction') == 'remove' && $proceed) {
             $user_acl = $table->delete("acl_id = 'approve_trainings' and user_id = {$id}");
             $msg = $user_acl ? t('That user is no longer an approver') : t('Unable to delete that approver');
             if ($user_acl) {
                 $success = true;
             }
         }
         // done
         $_SESSION['status'] = $msg;
         $this->setNoRenderer();
         $output = array('success' => $success, 'msg' => $msg);
         echo json_encode($output);
         exit;
         // no view now
     }
     require_once 'models/table/System.php';
     require_once 'models/table/Translation.php';
     $sysTable = new System();
     $labelNames = array();
     // input name => key_phrase (changes translation table)
     $checkboxFields = array('master_approver' => 'allow_multi_approvers');
     // field => key phrase (changes _system table)
     // edit table & data
     require_once 'views/helpers/EditTableHelper.php';
     $db = Zend_Db_Table_Abstract::getDefaultAdapter();
     $hideMasterLinks = false;
     $noDelete = array();
     $fieldDefs = array('fullname' => t('Name'));
     $fieldDefs['approver'] = t('Approver');
     if ($this->getSanParam('master_approver') || $this->setting('allow_multi_approvers')) {
         $fieldDefs['master_approver'] = t('Master Approver');
         $hideMasterLinks = true;
     }
     $fieldDefs['lnks'] = t('Actions');
     $rows = $db->fetchAll("select *,\r\n\t\t\tCONCAT(first_name, CONCAT(' ', last_name)) as fullname, '" . t('Yes') . "' as approver, m1.id as master_approver, user.id as id\r\n\t\t\tfrom user\r\n\t\t\tinner join user_to_acl acl on (acl.user_id = user.id and acl.acl_id = 'approve_trainings')\r\n\t\t\tleft join  user_to_acl m1 on (m1.user_id = user.id and m1.acl_id = 'master_approver')\r\n\t\t\twhere user.is_blocked = 0 limit 100");
     foreach ($rows as $i => $row) {
         // lets add some data to the resultset to show in the EditTable
         $noDelete[] = $row['id'];
         // add to nodelete array
         $rows[$i]['fullname'] = htmlspecialchars(ucwords($rows[$i]['fullname']), ENT_QUOTES);
         // format name
         if (empty($rows[$i]['master_approver'])) {
             $rows[$i]['master_approver'] = t('No');
             // master approver?
             $rows[$i]['lnks'] = "<a href='#' onclick='ajaxApprover(\"remove\", {$row['id']});return false'>" . t('Remove') . "</a>";
             // links
             if ($hideMasterLinks) {
                 $rows[$i]['lnks'] = " <a href='#' onclick='ajaxApprover(\"elevate\", {$row['id']});return false'>" . t('Make Master') . '</a>';
             }
         } else {
             $rows[$i]['master_approver'] = t('Yes');
             // is approver?
             if ($hideMasterLinks) {
                 $rows[$i]['lnks'] = "<a href='#' onclick='ajaxApprover(\"deelevate\", {$row['id']});return false'>" . t('Make Low Level Approver') . '</a>';
             } else {
                 $rows[$i]['lnks'] = "<a href='#' onclick='ajaxApprover(\"remove\", {$row['id']});return false'>" . t('Remove') . "</a>";
             }
             // same as first 'remove' link above
         }
     }
     // print a edit table
     $html = EditTableHelper::generateHtml('Approvers', $rows, $fieldDefs, array(), $noDelete, true);
     // array(1) and select 1 as id = bugfix: remove delete col
     $this->view->assign('editTable', $html);
     // done
     // process form (copied from other pages)
     if ($this->getRequest()->isPost()) {
         // Update db
         $updateData = array();
         // update translation labels
         $tranTable = new Translation();
         foreach ($labelNames as $input_key => $db_key) {
             if ($this->_getParam($input_key)) {
                 try {
                     $tranTable->update(array('phrase' => $this->_getParam($input_key)), "key_phrase = '{$db_key}'");
                     $this->viewAssignEscaped($input_key, $this->_getParam($input_key));
                 } catch (Zend_Exception $e) {
                     error_log($e);
                 }
             }
         }
         // update _system (checkboxes)
         foreach ($checkboxFields as $input_key => $db_field) {
             $value = $this->_getParam($input_key) == NULL ? 0 : 1;
             $updateData[$db_field] = $value;
             $this->view->assign($input_key, $value);
         }
         $sysTable->update($updateData, '');
     } else {
         // view
         // checkboxes
         $sysRows = $sysTable->fetchRow($sysTable->select()->limit(1));
         foreach ($checkboxFields as $input_key => $field_key) {
             if (isset($sysRows->{$field_key})) {
                 $this->view->assign($input_key, $sysRows->{$field_key});
             }
         }
         // labels
         $t = Translation::getAll();
         foreach ($labelNames as $input_key => $db_key) {
             $this->viewAssignEscaped($input_key, $t[$db_key]);
         }
     }
     // redirect to next page
     if ($this->_getParam('redirect')) {
         header("Location: " . $this->_getParam('redirect'));
         exit;
     } else {
         if ($this->_getParam('saveonly')) {
             $status = ValidationContainer::instance();
             $status->setStatusMessage(t('Your settings have been updated.'));
         }
     }
 }
 public function insert(array $data)
 {
     $data['training_length_interval'] = 'day';
     return parent::insert($data);
 }
 /**
  * Fetch an overview
  * @id int, master row id
  * @return date,  user, changes
  */
 public function fetchAllPerson($id)
 {
     $rtn = array();
     if ($id) {
         //this is all person specific stuff, will need to be modified for other tables
         $select = $this->select()->from($this->_name, array('person_history.*'))->where($this->_parent_table . "_history." . $this->_parent_table . "_id = ?", $id)->order('person_history.vid ASC');
         if (array_search('facility_id', $this->_cols) !== false) {
             $select->setIntegrityCheck(false);
             $select->joinLeft(array('f' => 'facility'), "facility_id = f.id", array('facility_name'));
         }
         if (array_search('primary_qualification_option_id', $this->_cols) !== false) {
             $select->setIntegrityCheck(false);
             $select->joinLeft(array('pq' => 'person_qualification_option'), "primary_qualification_option_id = pq.id", array('qualification' => 'qualification_phrase'));
         }
         if (array_search('primary_responsibility_option_id', $this->_cols) !== false) {
             $select->setIntegrityCheck(false);
             $select->joinLeft(array('pr1' => 'person_primary_responsibility_option'), "primary_responsibility_option_id = pr1.id", array("primary responsibility" => 'responsibility_phrase'));
         }
         if (array_search('secondary_responsibility_option_id', $this->_cols) !== false) {
             $select->setIntegrityCheck(false);
             $select->joinLeft(array('pr2' => 'person_secondary_responsibility_option'), "secondary_responsibility_option_id = pr2.id", array("secondary responsibility" => 'responsibility_phrase'));
         }
         $select->joinLeft(array('tr' => 'trainer_history'), "tr.pvid = person_history.vid", array('ifnull(tr.timestamp_updated,person_history.timestamp_created) as timestamp_updated'));
         $select->setIntegrityCheck(false);
         $select->joinLeft(array('ato' => 'person_active_trainer_option'), "active_trainer_option_id = ato.id", array("active trainer" => 'active_trainer_phrase'));
         $select->joinLeft(array('tao' => 'trainer_affiliation_option'), "affiliation_option_id = tao.id", array("affilition" => 'trainer_affiliation_phrase'));
         $rows = parent::fetchAll($select);
         //get current state
         $select = $this->select()->from($this->_parent_table, array('person.*'))->where("person.id = ?", $id);
         if (array_search('facility_id', $this->_cols) !== false) {
             $select->setIntegrityCheck(false);
             $select->joinLeft(array('f' => 'facility'), "facility_id = f.id", array('facility_name'));
         }
         if (array_search('primary_qualification_option_id', $this->_cols) !== false) {
             $select->setIntegrityCheck(false);
             $select->joinLeft(array('pq' => 'person_qualification_option'), "primary_qualification_option_id = pq.id", array('qualification' => 'qualification_phrase'));
         }
         if (array_search('primary_responsibility_option_id', $this->_cols) !== false) {
             $select->setIntegrityCheck(false);
             $select->joinLeft(array('pr1' => 'person_primary_responsibility_option'), "primary_responsibility_option_id = pr1.id", array("primary responsibility" => 'responsibility_phrase'));
         }
         if (array_search('secondary_responsibility_option_id', $this->_cols) !== false) {
             $select->setIntegrityCheck(false);
             $select->joinLeft(array('pr2' => 'person_secondary_responsibility_option'), "secondary_responsibility_option_id = pr2.id", array("secondary responsibility" => 'responsibility_phrase'));
         }
         $select->joinLeft(array('tr' => 'trainer'), "tr.person_id = person.id");
         $select->setIntegrityCheck(false);
         $select->joinLeft(array('ato' => 'person_active_trainer_option'), "active_trainer_option_id = ato.id", array("active trainer" => 'active_trainer_phrase'));
         $select->joinLeft(array('tao' => 'trainer_affiliation_option'), "affiliation_option_id = tao.id", array("affilition" => 'trainer_affiliation_phrase'));
         $currentRow = parent::fetchAll($select)->current();
         $previous = null;
         while ($rows->next()) {
         }
         $rowArray = $rows->toArray();
         $rowArray[] = $currentRow->toArray();
         foreach ($rowArray as $change) {
             if ($previous != null) {
                 if ($diff = array_diff_assoc($previous, $change)) {
                     if ($diff) {
                         unset($diff['person_id']);
                         unset($diff['training_id']);
                         // we dont need to see these
                         unset($diff['uuid']);
                         $tmp = $diff;
                         // dont alter the data used for compare
                         unset($tmp['vid']);
                         unset($tmp['timestamp_updated']);
                         unset($tmp['timestamp_created']);
                         if (count($tmp)) {
                             // old method was just these 4 lines>>
                             $delta = array();
                             $delta['timestamp_updated'] = $previous['timestamp_created'];
                             $delta['modified_by'] = $previous['modified_by'];
                             $delta['changes'] = $diff;
                             $rtn[] = $delta;
                         }
                     }
                 }
             }
             $previous = $change;
         }
     }
     return $rtn;
 }
    public function scoresImportAction()
    {
        require_once 'models/table/Person.php';
        require_once 'models/table/PersonToTraining.php';
        //labels
        $id = $this->getSanParam('training');
        $db = Zend_Db_Table_Abstract::getDefaultAdapter();
        $status = ValidationContainer::instance();
        $trainingObj = new Training();
        $this->viewAssignEscaped('courseName', $trainingObj->getCourseName($id));
        $this->view->assign('training_id', $id);
        //CSV import -- post
        if (@$_FILES['import']['tmp_name']) {
            $filename = $_FILES['import']['tmp_name'];
            if ($filename) {
                // we need a table to compare names to
                $table = new ITechTable(array('name' => 'score'));
                $persons = new ITechTable(array('name' => 'person'));
                $sql = 'select distinct person_to_training.id as pid,person.first_name,person.last_name from person_to_training
					   left join person on person.id = person_id
					   where person_to_training.training_id = ' . $id;
                $ppl = $db->fetchAll($sql);
                while ($row = $this->_csv_get_row($filename)) {
                    if (is_array($row)) {
                        if (isset($row[0]) && isset($row[4]) && !empty($row[0]) && !empty($row[4])) {
                            // find person
                            $row[0] = trim($row[0]);
                            $row[1] = trim($row[1]);
                            $pid = null;
                            foreach ($ppl as $v) {
                                if ($v['first_name'] == $row[0] && $v['last_name'] == $row[1]) {
                                    $pid = $v['pid'];
                                    break;
                                }
                            }
                            if ($pid) {
                                $new_row = $table->createRow();
                                $new_row->person_to_training_id = $pid;
                                $new_row->training_date = $row[2];
                                $new_row->score_label = $row[3];
                                $new_row->score_value = $row[4];
                                $new_row->save();
                            } else {
                                // err
                                if (!isset($notfound)) {
                                    $notfound = array();
                                }
                                if ($row[0] != t('First Name')) {
                                    $notfound[] = $row[0] . ' ' . $row[1] . '<br>';
                                }
                            }
                        }
                    }
                }
            }
            $_POST['redirect'] = null;
            if ($notfound) {
                $status->setStatusMessage(t('The following users could not be found while importing, perhaps they were not adding to the training:<br>'));
                foreach ($notfound as $v) {
                    $status->setStatusMessage($v);
                }
            }
            // done
        }
        // score view (edit table)
        require_once 'views/helpers/EditTableHelper.php';
        $label = 'Score';
        $fields = array('name' => t('Name'), 'score_label' => t('Label'), 'score_value' => t('Score'));
        $rowRay = $db->fetchAll("select score.*,CONCAT(person.first_name, CONCAT(' ', person.last_name)) as name from person_to_training\r\n\t\t\t\t\t\tinner join score on score.person_to_training_id = person_to_training.id\r\n\t\t\t\t\t\tleft join person on person.id = person_id\r\n\t\t\t\t\t\twhere person_to_training.training_id = {$id}\r\n\t\t\t\t\t\t");
        $this->view->assign('editTable', EditTableHelper::generateHtml($label, $rowRay, $fields, array(), array(), true));
    }
 public function doAddEditView()
 {
     try {
         //validate
         $status = ValidationContainer::instance();
         require_once 'models/table/OptionList.php';
         require_once 'models/table/MultiOptionList.php';
         require_once 'models/table/Location.php';
         $request = $this->getRequest();
         $validateOnly = $request->isXmlHttpRequest();
         $person_id = $this->getSanParam('id');
         $personObj = new Person();
         $personrow = $personObj->findOrCreate($person_id);
         $personArray = $personrow->toArray();
         $helper = new Helper();
         $ssl = $helper->getSkillSmartLookups();
         $this->view->assign('skillsmart', $ssl);
         // nationality dropdown data
         $this->view->assign('lookupnationalities', $helper->getNationalities());
         $train = $helper->getPersonTraining($person_id);
         $this->view->assign('persontraining', $train);
         //locations
         $locations = Location::getAll();
         $this->viewAssignEscaped('locations', $locations);
         if ($validateOnly) {
             $this->setNoRenderer();
         }
         // Figure out reason code "Other" for checking posted data,
         // and for enabling/disabling reason_other field
         $other_reason_option_id = -1;
         $db = Zend_Db_Table_Abstract::getDefaultAdapter();
         $sql = "SELECT * FROM person_attend_reason_option where LCASE(attend_reason_phrase) LIKE '%other%'";
         $rowArray = $db->fetchAll($sql);
         if ($rowArray) {
             $other_reason_option_id = $rowArray[0]['id'];
         }
         $this->viewAssignEscaped('other_reason_option_id', $other_reason_option_id);
         if ($request->isPost()) {
             $errortext = "";
             if ($dupe_id = $this->getSanParam('dupe_id')) {
                 if ($this->getSanParam('maketrainer')) {
                     // require user to add trainer info
                     $status->setRedirect('/person/edit/id/' . $dupe_id . '/trainingredirect/' . $this->getSanParam('trainingredirect') . '/maketrainer/1');
                 } else {
                     if ($this->_getParam('trainingredirect')) {
                         $status->setStatusMessage(t('The person was saved. Refreshing history...'));
                         $_SESSION['status'] = t('The person was saved.');
                         $this->trainingRedirect($dupe_id);
                     } else {
                         $status->setRedirect('/person/edit/id/' . $dupe_id);
                     }
                 }
                 return;
             }
             $status->checkRequired($this, 'first_name', $this->tr('First Name'));
             $status->checkRequired($this, 'last_name', $this->tr('Last Name'));
             $status->checkRequired($this, 'primary_qualification_option_id', t('Professional qualification'));
             if ($this->setting('display_gender') != '0') {
                 $status->checkRequired($this, 'gender', t('Gender'));
             }
             if ($this->setting('display_mod_skillsmart')) {
                 //$status->checkRequired ( $this, 'occupational_category_id', t ( 'Occupational category' ) );
                 if ($this->getSanParam('govemp_option_id')) {
                     //$status->checkRequired ( $this, 'govemp_option_id', t ( 'Government Employee' ) );
                     //$status->checkRequired ( $this, 'occupational_category_id', t ( 'Occupational category' ) );
                     $status->checkRequired($this, 'persal_number', t('Persal Number'));
                 }
             } else {
                 $status->checkRequired($this, 'primary_qualification_option_id', t('Professional qualification'));
             }
             $birthParam = @$this->getSanParam('birth-year') . '-' . @$this->getSanParam('birth-month') . '-' . @$this->getSanParam('birth-day');
             if ($birthParam !== '--' and $birthParam !== '0000-00-00') {
                 $status->isValidDate($this, 'birth-day', t('Birthdate'), $birthParam);
             }
             //trainer only
             if ($this->getSanParam('is_trainer') || $this->getSanParam('active_trainer_option_id') || $this->getSanParam('trainer_type_option_id')) {
                 $status->checkRequired($this, 'trainer_type_option_id', t('Trainer') . ' ' . t('type'));
                 // 10/02/2011 Sean Smith: Removed at client request.
                 //if ($this->setting ( 'display_trainer_affiliations' )) {
                 //	$status->checkRequired ( $this, 'trainer_affiliation_option_id', t ( 'Trainer').' '.t('affiliation' ) );
                 //}
                 //at least one skill
                 $status->checkRequired($this, 'trainer_skill_id', t('Trainer') . ' ' . t('skill'));
             }
             // Check for manual reason for attending entry (if pulldown reason is 'other')
             if ($this->setting('display_attend_reason')) {
                 //if ($status->checkRequired ( $this, 'attend_reason_option_id', t ( 'Reason For Attending' ))) {
                 $reason_id = $this->getSanParam('attend_reason_option_id');
                 $other_reason = $this->getSanParam('attend_reason_other');
                 if (($reason_id || $reason_id == 0) && $other_reason_option_id >= 0) {
                     if ($reason_id == $other_reason_option_id) {
                         if ($other_reason == "") {
                             $status->addError('attend_reason_other', t('Enter a reason, or select a different reason above.'));
                             $errortext .= "Enter a reason, or select a different reason above.<br>";
                             error_log("Enter a reason, or select a different reason above.");
                         }
                     } else {
                         if ($other_reason != "") {
                             $status->addError('attend_reason_other', t('You can not type in a reason with the reason selected above.'));
                             $errortext .= "You can not type in a reason with the reason selected above.<br>";
                             error_log("You can not type in a reason with the reason selected above.");
                         }
                     }
                 }
                 //}
             }
             //check facility
             if ($status->checkRequired($this, 'facilityInput', t('Facility'))) {
                 $facility_id = $this->getSanParam('facilityInput');
                 if (is_array($facility_id)) {
                     $fac_arr = array();
                     foreach ($facility_id as $fac_id) {
                         if ($strrpos = strrpos($fac_id, '_')) {
                             $fac_arr[] = substr($fac_id, $strrpos + 1);
                         }
                     }
                     $personrow->multi_facility_ids = json_encode($fac_arr);
                     $facility_id = current($facility_id);
                 } else {
                     $personrow->multi_facility_ids = '';
                 }
                 if ($strrpos = strrpos($facility_id, '_')) {
                     $facility_id = array_pop(explode('_', $facility_id));
                 }
                 //find by name
                 if ($facility_id) {
                     $facilityByName = new Facility();
                     $row = $facilityByName->fetchRow('id = ' . $facility_id);
                     //$row = $facilityByName->fetchRow($facilityByName->select()->where('facility_name = ?', $this->getSanParam('facilityInput')));
                 }
                 if (@$row->id) {
                     $personrow->facility_id = $row->id;
                 } else {
                     $status->addError('facilityInput', t('That facility name could not be found.'));
                     $errortext .= "That facility name could not be found.<br>";
                     error_log("That facility name could not be found.");
                 }
             }
             //get home city name
             $city_id = false;
             $criteria = $this->_getAllParams();
             require_once 'views/helpers/Location.php';
             $home_city_parent_id = regionFiltersGetLastID('home', $criteria);
             if ($criteria['home_city'] && !$criteria['is_new_home_city']) {
                 $city_id = Location::verifyHierarchy($criteria['home_city'], $home_city_parent_id, $this->setting('num_location_tiers'));
                 if ($city_id === false) {
                     $status->addError('home_city', t("That city does not appear to be located in the chosen region. If you want to create a new city, check the new city box."));
                     $errortext .= "That city does not appear to be located in the chosen region. If you want to create a new city, check the new city box.<br>";
                     error_log("That city does not appear to be located in the chosen region. If you want to create a new city, check the new city box.");
                 }
             }
             if ($status->hasError()) {
                 foreach ($status->messages as $k => $v) {
                     $errortext .= $v . "<br>";
                 }
                 $status->setStatusMessage(t('The person could not be saved. <br>' . $errortext));
             } else {
                 $personrow = self::fillFromArray($personrow, $this->_getAllParams());
                 if ($city_id === false && $this->getSanParam('is_new_home_city')) {
                     $city_id = Location::insertIfNotFound($criteria['home_city'], $home_city_parent_id, $this->setting('num_location_tiers'));
                     if ($city_id === false) {
                         $status->addError('home_city', t('Could not save that city.'));
                     }
                 }
                 if ($city_id) {
                     $personrow->home_location_id = $city_id;
                 } else {
                     $home_location_id = Location::verifyHierarchy($criteria['home_city'], $home_city_parent_id, $this->setting('num_location_tiers'));
                     if ($home_location_id) {
                         $personrow->home_location_id = $home_location_id;
                     }
                 }
                 //these are transitionary database fields, will go away soon
                 //  $personrow->home_district_id = null;
                 //  $personrow->home_province_id = null;
                 if (!$personrow->home_city) {
                     $personrow->home_city = '';
                 }
                 // bugfix, field cannot be null.
                 if ($this->getSanParam('active')) {
                     $personrow->active = 'active';
                 } else {
                     $personrow->active = 'inactive';
                 }
                 $personrow->birthdate = @$this->getSanParam('birth-year') . '-' . @$this->getSanParam('birth-month') . '-' . @$this->getSanParam('birth-day');
                 //lookup custom 1 and 2
                 if ($this->getSanParam('custom1Input')) {
                     $id = OptionList::insertIfNotFound('person_custom_1_option', 'custom1_phrase', $this->getSanParam('custom1Input'));
                     $personrow->person_custom_1_option_id = $id;
                 } else {
                     $personrow->person_custom_1_option_id = null;
                 }
                 if ($this->getSanParam('custom2Input')) {
                     $id = OptionList::insertIfNotFound('person_custom_2_option', 'custom2_phrase', $this->getSanParam('custom2Input'));
                     $personrow->person_custom_2_option_id = $id;
                 } else {
                     $personrow->person_custom_2_option_id = null;
                 }
                 if ($this->setting('display_mod_skillsmart')) {
                     $personrow->govemp_option_id = $this->getSanParam('govemp_option_id');
                     $personrow->occupational_category_id = $this->getSanParam('occupational_category_id');
                     $personrow->persal_number = $this->getSanParam('persal_number');
                     $personrow->bodies_id = $this->getSanParam('professionalbodies_id');
                     $personrow->race_option_id = $this->getSanParam('race_option_id');
                     $personrow->disability_option_id = $this->getSanParam('disability_option_id');
                     $personrow->professional_reg_number = $this->getSanParam('professional_reg_number');
                     $personrow->nationality_id = $this->getSanParam('nationality_id');
                     $personrow->nurse_training_id = $this->getSanParam('nurse_training_id');
                     $personrow->care_start_year = $this->getSanParam('care_start_year');
                     $personrow->timespent_rank_pregnant = $this->getSanParam('timespent_rank_pregnant');
                     $personrow->timespent_rank_adults = $this->getSanParam('timespent_rank_adults');
                     $personrow->timespent_rank_children = $this->getSanParam('timespent_rank_children');
                     $personrow->timespent_rank_pregnant_pct = $this->getSanParam('timespent_rank_pregnant_pct');
                     $personrow->timespent_rank_adults_pct = $this->getSanParam('timespent_rank_adults_pct');
                     $personrow->timespent_rank_children_pct = $this->getSanParam('timespent_rank_children_pct');
                     $personrow->supervised_id = $this->getSanParam('supervised_id');
                     $personrow->supervision_frequency_id = $this->getSanParam('supervision_frequency_id');
                     $personrow->supervisors_profession = $this->getSanParam('supervisors_profession');
                     $personrow->facilitydepartment_id = $this->getSanParam('facilitydepartment_id');
                     $training_recieved_arr = array();
                     $training_recieved_data = '';
                     $training_recieved_results = array();
                     foreach ($ssl['training'] as $trainingnode) {
                         $training_recieved_arr[$trainingnode['id']] = $trainingnode['label'];
                     }
                     // build and insert training recieved vars in json
                     foreach ($_POST as $postvar => $postval) {
                         if (strstr($postvar, 'trainingrecieved_') && (isset($_POST[$postvar]) && $_POST[$postvar] != '')) {
                             $recv_str = '';
                             $recv_num = explode('_', $postvar);
                             if (isset($training_recieved_arr[intval($recv_num[1])])) {
                                 $recv_str = $training_recieved_arr[intval($recv_num[1])];
                                 $training_recieved_results[$recv_str][$recv_num[2]] = $postval;
                             }
                         }
                     }
                     if (!empty($training_recieved_results)) {
                         $training_recieved_data = json_encode($training_recieved_results);
                     }
                     $personrow->training_recieved_data = $training_recieved_data;
                     //$personrow->comments_skillsmart = $this->getSanParam('govemp_option_id');//0
                     /*
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('custom1Input');//1
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('race_option_id');//2
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('disability_option_id');//3
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('disability');//4
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('custom2Input');//5
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('rank1_option_id');//6
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('rank2_option_id');//7
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('rank3_option_id');//8
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('percent1');//9
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('percent2');//10
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('percent3');//11
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('supervised_option_id');//12
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('sfreq_option_id');//13
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('specifyfreqinput');//14
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('svoccu');//15
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainother');//16
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('checktrainother');//17
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('selecttrainother');//18
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainotherother');//19
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('specifyoccupationinput');//20
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('trainer_type_option_id1');//21
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainother0');//22
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('checktrainother0');//23
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('selecttrainother0');//24
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainotherother0');//25
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainother1');//26
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('checktrainother1');//27
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('selecttrainother1');//28
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainotherother1');//29
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainother2');//30
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('checktrainother2');//31
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('selecttrainother2');//32
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainotherother2');//33
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainother3');//34
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('checktrainother3');//35
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('selecttrainother3');//36
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainotherother3');//37
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainother4');//38
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('checktrainother4');//39
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('selecttrainother4');//40
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainotherother4');//41
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainother5');//42
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('checktrainother5');//43
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('selecttrainother5');//44
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainotherother5');//45
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainother6');//46
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('checktrainother6');//47
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('selecttrainother6');//48
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainotherother6');//49
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainother7');//50
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('checktrainother7');//51
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('selecttrainother7');//52
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainotherother7');//53
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainother8');//54
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('checktrainother8');//55
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('selecttrainother8');//56
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('texttrainotherother8');//57
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('bodies_id');//58
                     $personrow->comments_skillsmart = $personrow->comments_skillsmart."§".$this->getSanParam('nationality_id');//59
                     */
                     if ($person_id) {
                         $trainsaved = array();
                         $train = $this->getSanParam('train');
                         foreach ($train as $key => $t) {
                             if (isset($t['check'])) {
                                 if ($t['originalid'] != 0) {
                                     // UPDATING EXISTING // moving this - cant really use $person_id before $personrow->save on adding a new user... probably should happen later or only on edits... im not sure
                                     $trainid = $t['originalid'];
                                     $query = "UPDATE link_person_training SET\n\t\t\t\t\t\t\t\t\tpersonid = '" . $person_id . "',\n\t\t\t\t\t\t\t\t\tyear = '" . addslashes($t['year']) . "',\n\t\t\t\t\t\t\t\t\tinstitution = '" . addslashes($t['text']) . "',\n\t\t\t\t\t\t\t\t\tothername = '' WHERE id = " . $trainid;
                                     error_log($query);
                                     $db->query($query);
                                 } else {
                                     // ADDING NEW
                                     $query = "INSERT INTO link_person_training SET\n\t\t\t\t\t\t\t\t\t\t\tpersonid = '" . $person_id . "',\n\t\t\t\t\t\t\t\t\t\t\ttrainingid = '" . addslashes($key) . "',\n\t\t\t\t\t\t\t\t\t\t\tyear = '" . addslashes($t['year']) . "',\n\t\t\t\t\t\t\t\t\t\t\tinstitution = '" . addslashes($t['text']) . "',\n\t\t\t\t\t\t\t\t\t\t\tothername = ''";
                                     error_log($query);
                                     $db->query($query);
                                     $trainid = $db->lastInsertId();
                                 }
                                 $trainsaved[] = $trainid;
                             }
                         }
                         if (count($trainsaved) > 0) {
                             // REMOVE ALL NON-SAVED TRAINING IDS FOR PERSON
                             $query = "DELETE FROM link_person_training WHERE personid = " . $person_id . " AND id NOT IN (" . implode(",", $trainsaved) . ")";
                             error_log($query);
                             $db->query($query);
                         } else {
                             // REMOVE ALL TRAINING IDS FOR PERSON
                             $query = "DELETE FROM link_person_training WHERE personid = " . $person_id;
                             error_log($query);
                             $db->query($query);
                         }
                     }
                 }
                 if ($personrow->save()) {
                     $status->setStatusMessage(t('The person was saved. Refreshing change history...'));
                     $_SESSION['status'] = t('The person was saved.');
                     $person_id = $personrow->id;
                     if ($this->setting('display_mod_skillsmart')) {
                         if (strlen($this->getSanParam('Facilities')) > 0) {
                             $db->query('UPDATE `facs` SET `Active`=\'N\' WHERE `person`=' . $person_id . ' AND `Active`=\'Y\';');
                             $Facs = split('\\$', $this->getSanParam('Facilities'));
                             foreach ($Facs as $kys => $vls) {
                                 $Locs = split("~", $vls);
                                 $Fac = $Locs[0];
                                 if ($strrpos = strrpos($Fac, '_')) {
                                     $Fac = substr($Fac, $strrpos + 1);
                                 }
                                 $db->query('INSERT INTO `facs` ( `person`, `facility`, `facstring`, `active`) VALUES (' . $person_id . ', ' . $Fac . ', \'' . $vls . '\', \'Y\');');
                             }
                         }
                         $co = 0;
                         for ($co = 1; $co <= 20; $co++) {
                             $db->query('UPDATE `trans` SET `Active`=\'N\' WHERE `person`=' . $person_id . ' AND `id`=' . $co . ' AND `Active`=\'Y\';');
                             if ($this->getSanParam('checktrain' . $co) == 'on') {
                                 $db->query('INSERT INTO `trans` ( `person`, `id`, `chk`, `yr`, `transstring`, `active`) VALUES (' . $person_id . ', ' . $co . ', \'' . $this->getSanParam('checktrain' . $co) . '\', \'' . $this->getSanParam('selecttrain' . $co) . '\', \'' . $this->getSanParam('texttrain' . $co) . '\', \'Y\');');
                             }
                         }
                     }
                     //get trainer information
                     $trainerTable = new Trainer();
                     $trainerRow = $trainerTable->fetchRow('person_id = ' . $person_id);
                     if (!$trainerRow and ($this->getSanParam('active_trainer_option_id') or $this->getSanParam('trainer_type_option_id'))) {
                         // add trainer
                         $trainerRow = $trainerTable->createRow();
                         $trainerRow->person_id = $personrow->id;
                     }
                     if ($trainerRow) {
                         //trainer info
                         $trainerRow->is_active = 1;
                         //deprecated //($this->getSanParam ( 'is_trainer' ) ? 1 : 0);
                         $trainerRow->active_trainer_option_id = $this->getSanParam('active_trainer_option_id');
                         $trainerRow->type_option_id = $this->getSanParam('trainer_type_option_id');
                         $trainerRow->affiliation_option_id = $this->setting('display_trainer_affiliations') ? $this->getSanParam('trainer_affiliation_option_id') ? $this->getSanParam('trainer_affiliation_option_id') : 0 : 0;
                         if (!$trainerRow->save()) {
                             $status->setStatusMessage(t('The') . ' ' . t('trainer') . ' ' . t('information could not be saved.'));
                         } else {
                             MultiOptionList::updateOptions('trainer_to_trainer_skill_option', 'trainer_skill_option', 'trainer_id', $person_id, 'trainer_skill_option_id', $this->getSanParam('trainer_skill_id'));
                             $language_ids = $this->getSanParam('trainer_language_id');
                             $planguage_id = $this->getSanParam('primary_language_id');
                             $primary_settings = array();
                             $found = false;
                             if ($language_ids) {
                                 foreach ($language_ids as $lid) {
                                     if ($lid == $planguage_id) {
                                         $primary_settings[] = 1;
                                         $found = true;
                                     } else {
                                         $primary_settings[] = 0;
                                     }
                                 }
                             }
                             if (!$found) {
                                 $primary_settings[] = 1;
                                 $language_ids[] = $planguage_id;
                             }
                             MultiOptionList::updateOptions('trainer_to_trainer_language_option', 'trainer_language_option', 'trainer_id', $person_id, 'trainer_language_option_id', $language_ids, 'is_primary', $primary_settings);
                         }
                     }
                     TrainingRecommend::saveRecommendedforPerson($person_id, $this->getSanParam('training_recommend'));
                     if ($this->_getParam('redirectUrl')) {
                         $status->redirect = $this->_getParam('redirectUrl');
                     } else {
                         if ($this->_getParam('trainingredirect')) {
                             // redirect back to training session
                             $this->trainingRedirect($person_id);
                         } else {
                             //if it's an add then redirect to the view page
                             if ($this->setting('display_mod_skillsmart')) {
                                 //$status->setRedirect ( '/person/view/id/' . $person_id );
                                 $qs = OptionList::suggestionListHierarchical('person_qualification_option', 'qualification_phrase', false, false, array('0 AS is_default', 'child.is_default'));
                                 $parent_id = $this->getSanParam('primary_qualification_option_id');
                                 foreach ($qs as $k => $v) {
                                     if ($v['id'] == $parent_id) {
                                         $parent_id = $v['parent_id'];
                                         break;
                                     }
                                 }
                                 $comps = $helper->getPersonCompetenciesDetailed($person_id);
                                 // Disabled redirect to competency page as per Robert's request, 11/19/2012, CDL
                                 //							if (count($comps) > 0){
                                 //								$status->setRedirect ( '/person/editcompetency/id/' . $person_id );
                                 //							} else {
                                 $status->setRedirect('/person/edit/id/' . $person_id);
                                 //							}
                                 /*
                                 							if($parent_id=="6")
                                 							{
                                 								$status->setRedirect ( '/person/addcomc/id/' . $person_id );
                                 							}
                                 							if($parent_id=="7")
                                 							{
                                 								$status->setRedirect ( '/person/addcomd/id/' . $person_id );
                                 							}
                                 							if($parent_id=="8")
                                 							{
                                 								$status->setRedirect ( '/person/addcomn/id/' . $person_id );
                                 							}
                                 							if($parent_id=="9")
                                 							{
                                 								$status->setRedirect ( '/person/addcomp/id/' . $person_id );
                                 							}
                                 */
                             } else {
                                 $status->setRedirect('/person/edit/id/' . $person_id);
                             }
                         }
                     }
                 } else {
                     $status->setStatusMessage(t('ERROR: The person could not be saved. ' . __LINE__));
                 }
             }
             if ($validateOnly) {
                 $this->sendData($status);
             } else {
                 $this->view->assign('status', $status);
             }
         }
         if ($this->setting('display_mod_skillsmart')) {
             if ($person_id) {
                 $rows = $db->fetchAll('SELECT `facstring` FROM `facs` INNER JOIN `facility` ON `facs`.`facility` = `facility`.`id` WHERE `facility`.`is_deleted`=0 AND `facs`.`person`=' . $person_id . ' AND `facs`.`Active`=\'Y\' ORDER BY `facs`.`sno` ASC;');
                 $Fcs = "";
                 foreach ($rows as $rw) {
                     $Fcs = $Fcs . $rw['facstring'] . '$';
                 }
                 $Fcs = trim($Fcs, '$');
                 $this->view->assign('Fcs', $Fcs);
                 $rows = $db->fetchAll('SELECT `id`, `chk`, `yr`, `transstring` FROM `trans` WHERE `person`=' . $person_id . ' AND `Active`=\'Y\' ORDER BY sno ASC;');
                 $Trs = array();
                 $c*k = 0;
                 for ($c*k = 1; $c*k <= 20; $c*k++) {
                     $Trs[$c*k] = NULL;
                 }
                 foreach ($rows as $rw) {
                     $Trs[$rw['id']] = $rw;
                 }
                 $this->view->assign('Trs', $Trs);
             }
         }
         //view it
         $facilityObj = new Facility();
         $facilityrow = $facilityObj->findOrCreate($personrow->facility_id);
         $personArray['facility'] = $facilityrow->toArray();
         //facility location
         $region_ids = Location::getCityInfo($facilityrow->location_id, $this->setting('num_location_tiers'));
         $region_ids = Location::regionsToHash($region_ids, 'person_facility');
         $personArray = array_merge($personArray, $region_ids);
         //audit history
         $creatorObj = new User();
         $updaterObj = new User();
         $creatorrow = $creatorObj->findOrCreate($personrow->created_by);
         $personArray['creator'] = addslashes($creatorrow->first_name . ' ' . $creatorrow->last_name);
         $updaterrow = $updaterObj->findOrCreate($personrow->modified_by);
         $personArray['updater'] = addslashes($updaterrow->first_name . ' ' . $updaterrow->last_name);
         $personArray['birthdate-year'] = '';
         $personArray['birthdate-month'] = '';
         $personArray['birthdate-day'] = '';
         //split birthdate fields
         if ($person_id and $personrow->birthdate) {
             $parts = explode(' ', $personrow->birthdate);
             $parts = explode('-', $parts[0]);
             $personArray['birthdate-year'] = $parts[0];
             $personArray['birthdate-month'] = $parts[1];
             $personArray['birthdate-day'] = $parts[2];
         }
         //custom fields
         if ($person_id) {
             $personArray['custom1'] = ITechTable::getCustomValue('person_custom_1_option', 'custom1_phrase', $personArray['person_custom_1_option_id']);
             $personArray['custom2'] = ITechTable::getCustomValue('person_custom_2_option', 'custom2_phrase', $personArray['person_custom_2_option_id']);
         }
         //qualifications
         $qualificationsArray = OptionList::suggestionListHierarchical('person_qualification_option', 'qualification_phrase', false, false, array('0 AS is_default', 'child.is_default'));
         $personQualificationId = $personArray['primary_qualification_option_id'];
         // get parent qualification id, if user has sub qualification selected
         $personArray['primary_qualification_option_id_parent'] = $personQualificationId;
         foreach ($qualificationsArray as $k => $qualArray) {
             if ($qualArray['parent_phrase'] == 'unknown') {
                 unset($qualificationsArray[$k]);
                 //remove unknown as an option
             }
             if ($qualArray['id'] == $personQualificationId) {
                 $personArray['primary_qualification_option_id_parent'] = $qualArray['parent_id'];
             }
         }
         $this->viewAssignEscaped('qualifications', $qualificationsArray);
         // occupational categories
         $occupationalsArray = OptionList::suggestionListHierarchical('occupational_categories', 'category_phrase', false, false, array('0 AS is_default', 'child.is_default'));
         $personQualificationId = $personArray['primary_qualification_option_id'];
         // get parent occupational category id, if user has sub qualification selected
         $personArray['occupational_category_id_parent'] = $personQualificationId;
         foreach ($occupationalsArray as $k => $catArray) {
             if ($catArray['category_phrase'] == 'unknown') {
                 unset($qualificationsArray[$k]);
                 //remove unknown as an option
             }
             if ($catArray['id'] == $personQualificationId) {
                 $personArray['occupational_category_id'] = $catArray['parent_id'];
             }
         }
         $this->viewAssignEscaped('occupationalcats', $occupationalsArray);
         // get recommended trainings class topics
         $training_recommend = TrainingRecommend::getRecommendedTrainingTopics($personArray['primary_qualification_option_id_parent']);
         $this->viewAssignEscaped('training_recommend', $training_recommend);
         // get saved recommended trainings class titles
         $training_recommend_saved = TrainingRecommend::getRecommendedforPerson($person_id);
         $this->viewAssignEscaped('training_recommend_saved', $training_recommend_saved);
         //$classes = TrainingRecommend::getRecommendedClassesforPerson ( $person_id );
         //responsibilities
         if ($this->setting('display_mod_skillsmart')) {
             $responsibilitiesArray = OptionList::suggestionList('person_responsibility_option', 'responsibility_phrase', false, false);
             $this->viewAssignEscaped('responsibilities', $responsibilitiesArray);
         }
         $primaryResponsibilitiesArray = OptionList::suggestionList('person_primary_responsibility_option', 'responsibility_phrase', false, false);
         $this->viewAssignEscaped('primaryResponsibilities', $primaryResponsibilitiesArray);
         $secondaryResponsibilitiesArray = OptionList::suggestionList('person_secondary_responsibility_option', 'responsibility_phrase', false, false);
         $this->viewAssignEscaped('secondaryResponsibilities', $secondaryResponsibilitiesArray);
         $educationlevelsArray = OptionList::suggestionList('person_education_level_option', 'education_level_phrase', false, false);
         $this->viewAssignEscaped('educationlevels', $educationlevelsArray);
         $attendreasonsArray = OptionList::suggestionList('person_attend_reason_option', 'attend_reason_phrase', false, false);
         $this->viewAssignEscaped('attendreasons', $attendreasonsArray);
         $activeTrainerArray = OptionList::suggestionList('person_active_trainer_option', 'active_trainer_phrase', false, false);
         $this->viewAssignEscaped('active_trainer', $activeTrainerArray);
         $titlesArray = OptionList::suggestionList('person_title_option', 'title_phrase', false, false);
         $this->viewAssignEscaped('titles', $titlesArray);
         $suffixesArray = OptionList::suggestionList('person_suffix_option', 'suffix_phrase', false, false);
         $this->viewAssignEscaped('suffixes', $suffixesArray);
         //training types
         //attach Trainer attributes
         $trainerTable = new Trainer();
         $trainerrow = $trainerTable->findOrCreate($person_id);
         $personArray['trainer_is_active'] = $this->getSanParam('maketrainer') ? 1 : $trainerrow->is_active;
         $personArray['active_trainer_option_id'] = $trainerrow->active_trainer_option_id;
         $personArray['trainer_type_option_id'] = $trainerrow->type_option_id;
         $personArray['trainer_affiliation_option_id'] = $trainerrow->affiliation_option_id;
         $titlesArray = OptionList::suggestionList('person_title_option', 'title_phrase', false, false);
         $this->viewAssignEscaped('titles', $titlesArray);
         $trainerTypesArray = OptionList::suggestionList('trainer_type_option', 'trainer_type_phrase', false, false);
         $this->viewAssignEscaped('trainer_types', $trainerTypesArray);
         $trainerAffiliationArray = OptionList::suggestionList('trainer_affiliation_option', 'trainer_affiliation_phrase', false, false);
         $this->viewAssignEscaped('trainer_affiliations', $trainerAffiliationArray);
         $trainerSkillsArray = MultiOptionList::choicesList('trainer_to_trainer_skill_option', 'trainer_id', $person_id, 'trainer_skill_option', 'trainer_skill_phrase');
         $this->viewAssignEscaped('trainer_skills', $trainerSkillsArray);
         $trainerLanguagesArray = MultiOptionList::choicesList('trainer_to_trainer_language_option', 'trainer_id', $person_id, 'trainer_language_option', 'language_phrase', 'is_primary');
         $this->viewAssignEscaped('trainer_languages', $trainerLanguagesArray);
         foreach ($trainerLanguagesArray as $lang) {
             if ($lang['is_primary']) {
                 $personArray['primary_language_id'] = $lang['id'];
             }
         }
         //has training history
         $hasTrainerHistory = false;
         if ($trainerrow->person_id) {
             $hasTrainerHistory = true;
             //we could also look up any history now, but we'll be lazy
         }
         $this->view->assign('hasTrainerHistory', $hasTrainerHistory);
         //facility types
         $typesArray = OptionList::suggestionList('facility_type_option', 'facility_type_phrase', false, false);
         $this->viewAssignEscaped('facility_types', $typesArray);
         //get home city name
         if ($personrow->home_location_id) {
             $region_ids = Location::getCityInfo($personrow->home_location_id, $this->setting('num_location_tiers'));
             $personArray['home_city'] = $region_ids[0];
             $region_ids = Location::regionsToHash($region_ids, 'home');
             $personArray = array_merge($personArray, $region_ids);
         }
         //sponsor types
         $sponsorsArray = OptionList::suggestionList('facility_sponsor_option', 'facility_sponsor_phrase', false, false);
         $this->viewAssignEscaped('facility_sponsors', $sponsorsArray);
         $this->viewAssignEscaped('person', $personArray);
         //facilities list
         //$rowArray = OptionList::suggestionList('facility',array('facility_name','id'),false,9999);
         $rowArray = Facility::selectAllFacilities($this->setting('num_location_tiers'));
         $this->viewAssignEscaped('facilities', $rowArray);
         if ($this->hasACL('edit_facility')) {
             $this->view->assign('insertFacilityLink', '<a href="#" id="show">' . str_replace(' ', '&nbsp;', t('Insert new facility')) . '</a>');
         }
         //see if it is referenced anywhere
         $this->view->assign('okToDelete', !$person_id or !Person::isReferenced($person_id));
         // create reference for GET paramaters
         if ($this->_getParam('trainingredirect')) {
             $this->view->assign('trainingredirect', $this->_getParam('trainingredirect'));
         }
         if ($this->_getParam('maketrainer')) {
             $this->view->assign('maketrainer', $this->_getParam('maketrainer'));
         }
         if ($this->_getParam('days')) {
             $this->view->assign('days', $this->_getParam('days'));
         }
     } catch (Exception $e) {
         print $e->getMessage();
     }
 }
 /**
  * $table - a string for the table name, or an array of rows to be used as the option values
  * $id      - option value to select as default
  * $jsonUrl - do not begin or end with slash or add output type
  */
 public static function generateHtml($table, $column, $id = false, $jsonUrl = false, $disabled = false, $allowIds = false, $multiple = false, $attributes = array(), $set_default = true)
 {
     $mutliple_id = false;
     if (is_int($multiple) or $multiple === 0) {
         $mutliple_id = $multiple;
     }
     $multiple = $multiple !== false ? '[]' : '';
     // allow multiple drop-downs w/same table
     if (is_string($table)) {
         $tableObj = new ITechTable(array('name' => $table));
         $info = $tableObj->info();
         $cols = array($column);
         if ($set_default) {
             if (array_search('is_default', $info['cols'])) {
                 $cols = array($column, 'is_default');
             }
         }
         $rows = $tableObj->fetchAll($tableObj->select($cols));
     } else {
         if (is_array($table) or is_object($table)) {
             $rows = $table;
             $info = $rows->getTable()->info();
             $table = $info['name'];
         }
     }
     $name = $table . '_id' . $multiple;
     if (isset($attributes['name'])) {
         $name = $attributes['name'];
         unset($attributes['name']);
     }
     $html = '<select name="' . $name . '" id="select_' . $table . ($multiple && $mutliple_id !== false ? '_' . $mutliple_id : '') . '"' . ($disabled ? ' disabled="disabled" ' : ' ');
     foreach ($attributes as $k => $v) {
         $html .= " {$k}=\"{$v}\"";
     }
     $html .= ' >';
     $html .= "\t<option value=\"\">&mdash; " . t('select') . " &mdash;</option>\n";
     foreach ($rows as $r) {
         if ($allowIds === false or array_search($r->id, $allowIds) !== false) {
             $isSelected = '';
             //check for default value in table
             if ($set_default && isset($r->is_default) && $r->is_default && ($id === false || $id === null)) {
                 $isSelected = ' selected="selected" ';
             } else {
                 if ($r->id === $id) {
                     //assign default value
                     $isSelected = ' selected="selected" ';
                 }
             }
             $html .= "\t<option value=\"{$r->id}\"{$isSelected}>{$r->{$column}}</option>\n";
         }
     }
     $html .= "</select>\n\n";
     // add edit link
     if ($jsonUrl && !$disabled) {
         $fieldlabel = explode('_', str_replace('_phrase', '', $column));
         $label = $fieldlabel[0];
         if (isset($fieldlabel[1])) {
             $label .= ' ' . $fieldlabel[1];
         }
         //$label = substr($column, strpos($column, '_'));
         //$label = str_replace('phrase', '', $label);
         //$label = trim(str_replace('_', ' ', $label));
         if (trim($label)) {
             switch ($label) {
                 // modify so label translates nicely, if needed
                 case 'training got':
                     $label = "GOT Curriculum";
                     break;
                 default:
                     break;
             }
             require_once 'models/table/Translation.php';
             $translate = @Translation::translate(ucwords($label));
             if ($translate) {
                 $label = $translate;
             }
         }
         $jsonUrl = "{$jsonUrl}/table/{$table}/column/{$column}";
         $jsonUrl = Settings::$COUNTRY_BASE_URL . '/' . $jsonUrl . '/outputType/json';
         $html .= " <a href=\"#\" onclick=\"addToSelect('" . str_replace("'", "\\" . "'", t('Please enter your new')) . " {$label}:', 'select_{$table}', '{$jsonUrl}'); return false;\">" . t('Insert new') . "</a>";
     }
     return $html;
 }
 /**
  * JSON course add/delete/edit function for employee_edit
  *
  * see: employee_course_table.phtml
  */
 public function coursesAction()
 {
     try {
         if (!$this->hasACL('edit_employee')) {
             if ($this->_getParam('outputType') == 'json') {
                 $this->sendData(array('msg' => 'Not Authorized'));
                 exit;
                 return;
             }
             $this->doNoAccessError();
         }
         $ret = array();
         $params = $this->getAllParams();
         if ($params['mode'] == 'addedit') {
             // add or update a record based on $params[id]
             if (empty($params['id'])) {
                 unset($params['id']);
             }
             // unset ID (primary key) for Zend if 0 or '' (insert new record)
             $id = $this->_findOrCreateSaveGeneric('employee_to_course', $params);
             // wrapper for find or create
             $params['id'] = $id;
             if ($id) {
                 // saved
                 // reload the data
                 $db = $this->dbfunc();
                 $ret = $db->fetchRow("select * from employee_to_course where id = {$id}");
                 $ret['msg'] = 'ok';
             } else {
                 $ret['errored'] = true;
                 $ret['msg'] = t('Error creating record.');
             }
         } else {
             if ($params['mode'] == 'delete' && $params['id']) {
                 // delete a record
                 try {
                     $course_link_table = new ITechTable(array('name' => 'employee_to_course'));
                     $num_rows = $course_link_table->delete('id = ' . $params['id']);
                     if (!$num_rows) {
                         $ret['msg'] = t('Error finding that record in the database.');
                     }
                     $ret['num_rows'] = $num_rows;
                 } catch (Exception $e) {
                     $ret['errored'] = true;
                     $ret['msg'] = t('Error finding that record in the database.');
                 }
             }
         }
         if (strtolower($params['outputType']) == 'json') {
             $this->sendData($ret);
             // probably always json no need to check for output
         }
     } catch (Exception $e) {
         if ($this->_getParam('outputType') == 'json') {
             $this->sendData(array('errored' => true, 'msg' => 'Error: ' . $e->getMessage()));
             return;
         } else {
             echo $e->getMessage();
         }
     }
 }
 function __construct($syncFileId)
 {
     $this->_fid = $syncFileId;
     parent::__construct();
 }
 public function viewAction()
 {
     require_once 'models/table/OptionList.php';
     if ($id = $this->getSanParam('id')) {
         if ($this->hasACL('edit_people')) {
             //redirect to edit mode
             $this->_redirect(str_replace('view', 'edit', 'http://' . $_SERVER['SERVER_NAME'] . $_SERVER['REQUEST_URI']));
         }
         $facility = new Facility();
         $facilityRow = $facility->fetchRow('id = ' . $id);
         $facilityArray = $facilityRow->toArray();
     } else {
         $facilityArray = array();
         $facilityArray['id'] = null;
     }
     //facilities list
     $rowArray = OptionList::suggestionList('facility', array('facility_name', 'id'), false, 9999);
     $facilitiesArray = array();
     foreach ($rowArray as $key => $val) {
         if ($val['id'] != 0) {
             $facilitiesArray[] = $val;
         }
     }
     $this->viewAssignEscaped('facilities', $facilitiesArray);
     //locations
     $this->viewAssignEscaped('locations', Location::getAll());
     //facility types
     $typesArray = OptionList::suggestionList('facility_type_option', 'facility_type_phrase', false, false);
     $this->viewAssignEscaped('facility_types', $typesArray);
     //sponsor types
     $sponsorsArray = OptionList::suggestionList('facility_sponsor_option', 'facility_sponsor_phrase', false, false);
     $this->viewAssignEscaped('facility_sponsors', $sponsorsArray);
     //sponsors
     $sponsorsArray = OptionList::suggestionList('facility_sponsors', 'facility_sponsor_phrase_id', false, false, true, 'id = ' . $id);
     $stable = new ITechTable(array('name' => 'facility_sponsors'));
     $select = $stable->select()->where('facility_id = ' . $id);
     $rows = $stable->fetchAll($select);
     if ($rows) {
         $this->viewAssignEscaped('sponsor_data', $rows->toArray());
     }
     list($cname, $prov, $dist, $regc) = Location::getCityInfo($facilityRow->location_id, $this->setting('num_location_tiers'));
     $facilityArray['facility_city'] = $cname;
     $facilityArray['region_c_id'] = $regc;
     $facilityArray['district_id'] = $dist;
     $facilityArray['province_id'] = $prov;
     $this->viewAssignEscaped('facility', $facilityArray);
 }
 public function insert(array $data)
 {
     $auth = Zend_Auth::getInstance();
     $user_id = $auth->getIdentity()->id;
     $user_table = new User();
     $user_row = $user_table->fetchRow('id = ' . $user_id);
     $data['created_by'] = $user_id;
     if (!isset($data['approval_status']) or !$data['approval_status']) {
         $data['approval_status'] = 'new';
     }
     //get recipients
     $training_id = $data['training_id'];
     $select = $this->select()->setIntegrityCheck(false)->from($this->_name)->join(array('u' => 'user'), "training_approval_history.created_by = u.id", array('email', 'first_name', 'last_name'))->where("training_id = {$training_id} AND u.is_blocked = 0");
     $previous_history_rows = $this->fetchAll($select);
     $recipients = array();
     foreach ($previous_history_rows as $rec) {
         $recipients[$rec->created_by] = array('email' => $rec->email, 'name' => $rec->first_name . ' ' . $rec->last_name);
     }
     //send to anyone other than creator
     unset($recipients[$user_id]);
     //insert the row
     $data['recipients'] = implode(',', array_keys($recipients));
     parent::insert($data);
     //send the mail
     #echo print_r($recipients, true) . '//'.$data['approval_status'];
     #$recipients = array('name' => '*****@*****.**', 'email' => '*****@*****.**');
     if ($recipients && $data['approval_status']) {
         require_once 'models/table/Training.php';
         $training = new Training();
         $training_name = $training->getCourseName($training_id);
         $view = new Zend_View();
         $view->setScriptPath(Globals::$BASE_PATH . '/app/views/scripts/email');
         $view->assign('creator', $user_row->first_name . ' ' . $user_row->last_name);
         $view->assign('training_name', $training_name);
         $view->assign('comments', $data['message']);
         $view->assign('link', Settings::$COUNTRY_BASE_URL . '/training/edit/id/' . $training_id);
         $mail = new Zend_Mail();
         switch ($data['approval_status']) {
             case 'approved':
                 $text = $view->render('text/approved.phtml');
                 $html = $view->render('html/approved.phtml');
                 $mail->setSubject(t('Training') . ' ' . t('Approved'));
                 break;
             case 'rejected':
                 $text = $view->render('text/rejected.phtml');
                 $html = $view->render('html/rejected.phtml');
                 $mail->setSubject(t('Training') . ' ' . t('Rejected'));
                 break;
             case 'resubmitted':
                 $text = $view->render('text/resubmitted.phtml');
                 $html = $view->render('html/resubmitted.phtml');
                 $mail->setSubject(t('Training') . ' ' . t('Resubmitted'));
                 break;
         }
         $mail->setBodyText($text);
         $mail->setBodyHtml($html);
         $mail->setFrom(Settings::$EMAIL_ADDRESS, Settings::$EMAIL_NAME);
         foreach ($recipients as $guy) {
             $mail->addTo($guy['email'], $guy['name']);
         }
         //$mail->send();
     }
 }
 public static function getCustomValue($table, $phrase_col, $id)
 {
     if (!$id) {
         return null;
     }
     $customTable = new ITechTable(array('name' => $table));
     $select = $customTable->select()->from($table, $phrase_col)->where("id = ?", $id);
     $row = $customTable->fetchRow($select);
     if ($row) {
         return $row->{$phrase_col};
     }
     return null;
 }
    public function dataAction()
    {
        $request = $this->getRequest();
        $id = $this->getSanParam('id');
        //get training and evaluation ids
        list($evaluation_id, $training_id) = Evaluation::fetchAssignment($id);
        if (!$evaluation_id) {
            $status->setStatusMessage(t('The evaluation could not be loaded.'));
            return;
        }
        //load training
        $trainingTable = new Training();
        $course_name = $trainingTable->getCourseName($training_id);
        $this->view->assign('course_name', $course_name);
        list($title, $qtext, $qtype, $qid) = $this->_fetchQuestions($evaluation_id);
        $answerArray = Evaluation::fetchRelatedCustomAnswers($evaluation_id);
        if ($request->isPost()) {
            //validate
            $status = ValidationContainer::instance();
            if ($status->hasError()) {
                $status->setStatusMessage(t('The evaluation could not be saved.'));
            } else {
                //make sure we have at least one response
                $found = false;
                foreach ($qid as $qidi) {
                    if ($this->getSanParam('value_' . $qidi) !== null && $this->getSanParam('value_' . $qidi) !== '') {
                        $found = true;
                    }
                }
                if ($found) {
                    //save response row
                    $qr_table = new ITechTable(array('name' => 'evaluation_response'));
                    $qr_row = $qr_table->createRow();
                    $qr_row->evaluation_to_training_id = $id;
                    if (isset($qr_row->trainer_person_id)) {
                        $qr_row->trainer_person_id = $this->getSanParam('trainer_id') ? $this->getSanParam('trainer_id') : null;
                    }
                    if (isset($qr_row->person_id)) {
                        $qr_row->person_id = $this->getSanParam('person_id') ? $this->getSanParam('person_id') : null;
                    }
                    $qr_id = $qr_row->save();
                    //save question rows
                    $erq_table = new ITechTable(array('name' => 'evaluation_question_response'));
                    foreach ($qid as $qk => $qidi) {
                        //  $q_table = new ITechTable(array('name'=>'evaluation_question'));
                        $qrow = $erq_table->createRow();
                        $qrow->evaluation_response_id = $qr_id;
                        $qrow->evaluation_question_id = $qidi;
                        $response_value = $this->getSanParam('value_' . $qidi);
                        if ($qtype[$qk] == 'Text' || !empty($answerArray[$qidi])) {
                            // is text or relabeled (will store as text)
                            $qrow->value_text = $response_value;
                        } else {
                            $qrow->value_int = $response_value;
                        }
                        if ($response_value) {
                            $qrow->save();
                        }
                    }
                }
                if ($this->getSanParam('go')) {
                    $this->_redirect('training/edit/id/' . $training_id);
                }
            }
        }
        $this->view->assign('title', $title);
        $this->view->assign('qtext', $qtext);
        $this->view->assign('qtype', $qtype);
        $this->view->assign('qid', $qid);
        $this->view->assign('answers', $answerArray);
        // list of trainers
        require_once 'models/table/TrainingToTrainer.php';
        require_once 'models/table/PersonToTraining.php';
        $this->view->assign('trainers', TrainingToTrainer::getTrainers($training_id)->toArray());
        $this->view->assign('participants', PersonToTraining::getParticipants($training_id)->toArray());
        // all evaluations attached to this training
        if ($training_id) {
            $otherEvalDropDown = '';
            $db = $this->dbfunc();
            $otherEvals = $db->fetchAll('SELECT ett.id, evaluation_id, title
									FROM evaluation_to_training as ett
									LEFT JOIN evaluation e ON e.id = ett.evaluation_id
									WHERE e.is_deleted = 0 AND ett.training_id = ?', $training_id);
            if ($otherEvals && count($otherEvals) > 1) {
                $selectOptions = array();
                foreach ($otherEvals as $v) {
                    if ($v['id'] && $v['title']) {
                        $selectOptions[] = "<option value=\"{$v['id']}\"" . ($id == $v['id'] ? ' selected' : '') . ">{$v['title']}</option>";
                    }
                }
                $otherEvalDropDown = '<select id="other_evals" name="other_evals">' . implode('', $selectOptions) . '</select>';
            }
            $this->view->assign('otherEvalDropDown', $otherEvalDropDown);
        }
    }
 public function update(array $data, $where)
 {
     //save a snapshot now
     require_once 'History.php';
     $historyTable = new History('person');
     //cheezy way to get the id
     $parts = explode('=', $where[0]);
     $historyTable->insert($this, trim($parts[1]));
     $rslt = parent::update($data, $where);
     return $rslt;
 }
 protected function _findOrCreateSaveGeneric($tableName, $valueArray, $whereCol = 'id', $whereVal = false)
 {
     $tableCustom = new ITechTable(array('name' => $tableName));
     $whereVal = $whereVal ? $whereVal : $valueArray['id'];
     // usually looking for id
     $row = $whereVal ? $tableCustom->fetchRow($tableCustom->select()->where("{$whereCol} = ?", $whereVal)) : false;
     // lookup or set to false which will cause row to be created
     if (!$row) {
         // created row or if not found
         $row = $tableCustom->createRow();
     }
     $this->fillFromArray($row, $valueArray);
     // fill data from array
     if (isset($row->is_default) && !isset($valueArray['is_default'])) {
         // breaks otherwise
         $row->is_default = 0;
     }
     $id = $row->save();
     return $id;
 }
 /**
  * Return evaluation_id and training_id from assignment row
  *
  * @param unknown_type $evaluation_to_training_id
  */
 public static function fetchAssignment($evaluation_to_training_id)
 {
     $q_table = new ITechTable(array('name' => 'evaluation_to_training'));
     $select = $q_table->select()->from($q_table->_name)->setIntegrityCheck(false)->where("id = {$evaluation_to_training_id}");
     $rows = $q_table->fetchAll($select);
     //just return an array of training ids
     $r = $rows->current();
     if ($r) {
         return array($r->evaluation_id, $r->training_id);
     }
     return array(null, null);
 }