TimeTrex/classes/modules/soap/TimeTrexSoapClient.class.php

968 lines
34 KiB
PHP
Raw Permalink Normal View History

2022-12-13 07:10:06 +01:00
<?php
/*********************************************************************************
*
* TimeTrex is a Workforce Management program developed by
* TimeTrex Software Inc. Copyright (C) 2003 - 2021 TimeTrex Software Inc.
*
* This program is free software; you can redistribute it and/or modify it under
* the terms of the GNU Affero General Public License version 3 as published by
* the Free Software Foundation with the addition of the following permission
* added to Section 15 as permitted in Section 7(a): FOR ANY PART OF THE COVERED
* WORK IN WHICH THE COPYRIGHT IS OWNED BY TIMETREX, TIMETREX DISCLAIMS THE
* WARRANTY OF NON INFRINGEMENT OF THIRD PARTY RIGHTS.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
* FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more
* details.
*
*
* You should have received a copy of the GNU Affero General Public License along
* with this program; if not, see http://www.gnu.org/licenses or write to the Free
* Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301 USA.
*
*
* You can contact TimeTrex headquarters at Unit 22 - 2475 Dobbin Rd. Suite
* #292 West Kelowna, BC V4T 2E9, Canada or at email address info@timetrex.com.
*
*
* The interactive user interfaces in modified source and object code versions
* of this program must display Appropriate Legal Notices, as required under
* Section 5 of the GNU Affero General Public License version 3.
*
*
* In accordance with Section 7(b) of the GNU Affero General Public License
* version 3, these Appropriate Legal Notices must retain the display of the
* "Powered by TimeTrex" logo. If the display of the logo is not reasonably
* feasible for technical reasons, the Appropriate Legal Notices must display
* the words "Powered by TimeTrex".
*
********************************************************************************/
/**
* Add custom soap client that automatically retries calls on network errors like "Could not connect to host"
* Class TTSoapClient
*/
class TTSoapClient extends SoapClient {
public $_initial_location = null;
public function __construct( $wsdl, $options = [] ) {
//Pull out the location and save it so it can be used later to fall back to non-SSL.
if ( isset( $options['location'] ) ) {
$this->_initial_location = $options['location'];
}
return parent::__construct( $wsdl, $options );
}
/**
* @param string $function_name
* @param array $arguments
* @return mixed|SoapFault
*/
#[\ReturnTypeWillChange]
public function __call( $function_name, $arguments ) {
$max_retries = 4;
$retry_count = 0;
while ( $retry_count < $max_retries ) {
if ( $retry_count == ( $max_retries - 1 ) && isset( $this->_initial_location ) ) {
//On last retry, attempt to fall back to HTTP rather than HTTPS
$this->__setLocation( str_replace( 'https://', 'http://', $this->_initial_location ) );
Debug::Text( 'WARNING: Due to failed connection attempts, falling back to non-SSL SOAP communication: ' . $this->_initial_location, __FILE__, __LINE__, __METHOD__, 10 );
}
if ( Debug::getEnable() == true && Debug::getVerbosity() >= 11 ) {
$result = parent::__call( $function_name, $arguments );
} else {
$result = @parent::__call( $function_name, $arguments );
}
if ( is_soap_fault( $result ) && ( $result->faultstring == 'Could not connect to host' || $result->faultstring == 'Error Fetching http headers' || $result->faultstring == 'Failed Sending HTTP SOAP request' ) ) {
Debug::Text( 'SOAP connection failed: '. $result->faultstring .' retrying...', __FILE__, __LINE__, __METHOD__, 10 );
sleep( 2 );
$retry_count++;
} else {
break;
}
}
if ( $retry_count == $max_retries ) {
return new SoapFault( 'HTTP', 'Could not connect to host after maximum retry attempts.' );
}
return $result;
}
}
/**
* @package Modules\SOAP
*/
class TimeTrexSoapClient {
var $soap_client_obj = null;
/**
* TimeTrexSoapClient constructor.
*/
function __construct() {
$this->getSoapObject();
return true;
}
/**
* @return null|TTSoapClient
*/
function getSoapObject() {
if ( $this->soap_client_obj == null ) {
if ( function_exists( 'openssl_encrypt' ) ) {
$location = 'https://';
} else {
$location = 'http://';
}
$location .= 'www.timetrex.com/ext_soap/server.php?MessageID='. TTUUID::generateUUID(); //Unique message ID for each SoapClientObject session (not every call), so specific requests can be easily differentiated.
// Use this to allow self-signed certificates.
//$context = stream_context_create( [
// 'ssl' => [
// 'verify_peer' => false,
// 'verify_peer_name' => false,
// 'allow_self_signed' => true,
// ],
// ] );
$context = stream_context_create();
$this->soap_client_obj = new TTSoapClient( null, [
'location' => $location,
'uri' => 'urn:test',
'style' => SOAP_RPC,
'use' => SOAP_ENCODED,
'encoding' => 'UTF-8',
'connection_timeout' => 30,
'keep_alive' => false, //This should help prevent "Error fetching HTTP headers" or "errno=10054 An existing connection was forcibly closed by the remote host." SOAP errors.
'trace' => 1,
'exceptions' => 0,
'stream_context' => $context,
]
);
Debug::Text( 'SOAP Client initialized with URL: '. $location, __FILE__, __LINE__, __METHOD__, 10 );
}
return $this->soap_client_obj;
}
/**
* @param $data
* @param string $format
* @return null
*/
function convertDocument( $data, $format = 'pdf' ) {
$company_data = $this->getPrimaryCompanyData();
if ( is_array( $company_data ) ) {
return $this->getSoapObject()->convertDocument( $data, $format, $company_data );
}
return null; //Return NULL when no data available, and FALSE to try again later.
}
/**
* @param $resume_data
* @param $file_name
* @return null
*/
function parseResume( $resume_data, $file_name ) {
$company_data = $this->getPrimaryCompanyData();
if ( is_array( $company_data ) ) {
return $this->getSoapObject()->parseResume( $resume_data, $file_name, $company_data );
}
return null; //Return NULL when no data available, and FALSE to try again later.
}
function printSoapDebug() {
echo "<pre>\n";
echo "Request :\n" . htmlspecialchars( $this->getSoapObject()->__getLastRequest() ) . "\n";
echo "Response :\n" . htmlspecialchars( $this->getSoapObject()->__getLastResponse() ) . "\n";
echo "</pre>\n";
}
/**
* @return mixed
*/
function ping( $ping_key = null ) {
$retval = $this->getSoapObject()->ping( $ping_key );
if ( is_object( $retval ) && get_class( $retval ) == 'SoapFault' ) {
Debug::Arr( $this->getSoapObject()->__getLastResponse(), 'ERROR: Last Response: ', __FILE__, __LINE__, __METHOD__, 10 );
Debug::Arr( $retval, 'ERROR: ping() failed!', __FILE__, __LINE__, __METHOD__, 10 );
return false;
} else {
return $retval;
}
}
/**
* @return bool
*/
function isUpdateNotifyEnabled() {
global $config_vars;
if ( getTTProductEdition() >= TT_PRODUCT_PROFESSIONAL && DEPLOYMENT_ON_DEMAND == true && isset( $config_vars['other']['enable_update_notify'] ) && $config_vars['other']['enable_update_notify'] == false ) {
return false; //Disabled with On-Demand service.
}
if ( getTTProductEdition() == 10 ) {
$value = SystemSettingFactory::getSystemSettingValueByKey( 'update_notify' );
if ( $value == 0 ) {
return false;
}
}
return true;
}
/**
* @return array|bool
*/
function getPrimaryCompanyData() {
global $config_vars, $db;
/* @formatter:off */ $obj_class = "\124\124\114\x69\x63\x65\x6e\x73\x65"; @$obj = new $obj_class; $hardware_id = $obj->getHardwareID(); unset( $obj, $obj_class ); /* @formatter:on*/
//Make sure a database connection has been established at least, otherwise this can cause FATAL error
//which during installation (before any database exists) is bad.
if ( !isset( $db ) || !is_object( $db ) || ( isset( $config_vars['other']['installer_enabled'] ) && $config_vars['other']['installer_enabled'] == true ) ) {
//If installer is enabled, check to make sure "company" table exists, as a PHP error being triggered and sending an email before the database schema is setup could prevent error reports from being sent.
$install_obj = new Install();
$install_obj->setDatabaseConnection( $db ); //Default Connection
if ( $install_obj->checkTableExists('company') == false ) {
Debug::Text( 'WARNING: No database connection or company table not created yet...', __FILE__, __LINE__, __METHOD__, 10 );
$company_data = [
'system_version' => APPLICATION_VERSION,
'application_version_date' => APPLICATION_VERSION_DATE,
'registration_key' => 'N/A',
'hardware_id' => ( ( isset( $hardware_id ) ) ? $hardware_id : 'N/A' ),
'product_edition_id' => getTTProductEdition(),
'product_edition_available' => getTTProductEdition(),
'name' => '<Company Table Not Exists>',
'short_name' => 'N/A',
];
return $company_data;
}
}
$clf = TTnew( 'CompanyListFactory' ); /** @var CompanyListFactory $clf */
if ( !isset( $config_vars['other']['primary_company_id'] ) || ( isset( $config_vars['other']['primary_company_id'] ) && TTUUID::isUUID( $config_vars['other']['primary_company_id'] ) == false ) ) {
//Find the first created company that is still active.
Debug::Text( 'WARNING: Primary company is not defined in .ini file, attempting to guess...', __FILE__, __LINE__, __METHOD__, 10 );
$clf->getAll( 1, null, [ 'status_id' => '= 10' ], [ 'created_date' => 'asc' ] ); //Limit 1
if ( $clf->getRecordCount() == 1 ) {
$config_vars['other']['primary_company_id'] = $clf->getCurrent()->getId();
}
}
try {
$clf->getById( $config_vars['other']['primary_company_id'] );
if ( $clf->getRecordCount() > 0 ) {
foreach ( $clf as $c_obj ) {
$company_data = [
'system_version' => APPLICATION_VERSION,
'application_version_date' => APPLICATION_VERSION_DATE,
'registration_key' => $this->getLocalRegistrationKey(),
'hardware_id' => ( ( isset( $hardware_id ) ) ? $hardware_id : 'N/A' ),
'product_edition_id' => $c_obj->getProductEdition(),
'product_edition_available' => getTTProductEdition(),
'name' => $c_obj->getName(),
'short_name' => $c_obj->getShortName(),
'work_phone' => $c_obj->getWorkPhone(),
'city' => $c_obj->getCity(),
'country' => $c_obj->getCountry(),
'province' => $c_obj->getProvince(),
'postal_code' => $c_obj->getPostalCode(),
];
}
return $company_data;
} else {
Debug::Text( 'ERROR: Primary company does not exist: ' . $config_vars['other']['primary_company_id'], __FILE__, __LINE__, __METHOD__, 10 );
}
} catch ( Exception $e ) {
unset( $e ); //code standards
Debug::Text( 'ERROR: Cant get company data for downloading upgrade file, database is likely down...', __FILE__, __LINE__, __METHOD__, 10 );
}
return false;
}
/**
* @param string $company_id UUID
* @return bool
*/
function isLatestVersion( $company_id ) {
$version = SystemSettingFactory::getSystemSettingValueByKey( 'system_version' );
if ( $version !== false ) {
$retval = $this->getSoapObject()->isLatestVersion( $this->getLocalRegistrationKey(), $company_id, $version, getTTProductEdition() );
if ( is_object( $retval ) && get_class( $retval ) == 'SoapFault' ) {
Debug::Arr( $retval, 'ERROR: Cant check for latest version, SOAP connection failed!', __FILE__, __LINE__, __METHOD__, 10 );
} else {
Debug::Text( ' Current Version: ' . $version . ' Retval: ' . (int)$retval, __FILE__, __LINE__, __METHOD__, 10 );
return $retval;
}
}
return true; //Default to TRUE (already running latest version) in the event that something goes wrong.
}
/**
* @param $key
* @return bool
*/
function isValidRegistrationKey( $key ) {
$key = trim( $key );
if ( strlen( $key ) == 32 || strlen( $key ) == 40 ) {
return true;
}
return false;
}
/**
* @return bool
*/
function getLocalRegistrationKey() {
$key = SystemSettingFactory::getSystemSettingValueByKey( 'registration_key' );
//If key is invalid, attempt to obtain a new one.
if ( $this->isValidRegistrationKey( $key ) == false ) {
$this->saveRegistrationKey();
return false;
}
return $key;
}
/**
* @return mixed
*/
function getRegistrationKey() {
return $this->getSoapObject()->generateRegistrationKey();
}
/**
* @return bool
*/
function saveRegistrationKey() {
$sslf = TTnew( 'SystemSettingListFactory' ); /** @var SystemSettingListFactory $sslf */
$sslf->getByName( 'registration_key' );
$get_new_key = false;
if ( $sslf->getRecordCount() > 1 ) {
Debug::Text( 'Too many registration keys, removing them...', __FILE__, __LINE__, __METHOD__, 10 );
foreach ( $sslf as $ss_obj ) {
$ss_obj->Delete();
}
$get_new_key = true;
} else if ( $sslf->getRecordCount() == 1 ) {
$key = $sslf->getCurrent()->getValue();
if ( $this->isValidRegistrationKey( $key ) == false ) {
foreach ( $sslf as $ss_obj ) {
$ss_obj->Delete();
}
$get_new_key = true;
}
}
if ( $get_new_key == true || $sslf->getRecordCount() == 0 ) {
//Get registration key from TimeTrex server.
$key = trim( $this->getRegistrationKey() );
Debug::Text( 'Registration Key from server: ' . $key, __FILE__, __LINE__, __METHOD__, 10 );
if ( $this->isValidRegistrationKey( $key ) == false ) {
$key = md5( uniqid( null, true ) );
Debug::Text( 'Failed getting registration key from server...', __FILE__, __LINE__, __METHOD__, 10 );
}
$sslf->setName( 'registration_key' );
$sslf->setValue( $key );
if ( $sslf->isValid() == true ) {
$sslf->Save();
}
return true;
} else {
Debug::Text( 'Registration key is valid, skipping...', __FILE__, __LINE__, __METHOD__, 10 );
}
return true;
}
/**
* @param string $company_id UUID
* @return bool
*/
function sendCompanyVersionData( $company_id ) {
Debug::Text( 'Sending Company Version Data...', __FILE__, __LINE__, __METHOD__, 10 );
$cf = TTnew( 'CompanyFactory' ); /** @var CompanyFactory $cf */
$tt_version_data = [];
$tt_version_data['registration_key'] = $this->getLocalRegistrationKey();
$tt_version_data['company_id'] = $company_id;
$tt_version_data['system_version'] = SystemSettingFactory::getSystemSettingValueByKey( 'system_version' );
$tt_version_data['tax_engine_version'] = SystemSettingFactory::getSystemSettingValueByKey( 'tax_engine_version' );
$tt_version_data['tax_data_version'] = SystemSettingFactory::getSystemSettingValueByKey( 'tax_data_version' );
$tt_version_data['schema_version']['A'] = SystemSettingFactory::getSystemSettingValueByKey( 'schema_version_group_A' );
$tt_version_data['schema_version']['B'] = SystemSettingFactory::getSystemSettingValueByKey( 'schema_version_group_B' );
$tt_version_data['schema_version']['C'] = SystemSettingFactory::getSystemSettingValueByKey( 'schema_version_group_C' );
$tt_version_data['schema_version']['D'] = SystemSettingFactory::getSystemSettingValueByKey( 'schema_version_group_D' );
$tt_version_data['schema_version']['T'] = SystemSettingFactory::getSystemSettingValueByKey( 'schema_version_group_T' );
if ( empty( $tt_version_data['system_version'] ) ) { //Just in case the version was not set in the system setting table for some reason.
$tt_version_data['system_version'] = APPLICATION_VERSION;
}
if ( isset( $_SERVER['SERVER_SOFTWARE'] ) ) {
$server_software = $_SERVER['SERVER_SOFTWARE'];
} else {
$server_software = 'N/A';
}
$server_name = Misc::getHostName( true );
$db_server_info = $cf->db->ServerInfo();
$sys_version_data = [
'php_version' => phpversion(),
'zend_version' => zend_version(),
'web_server' => $server_software,
'database_type' => $cf->db->databaseType,
'database_version' => $db_server_info['version'],
'database_description' => $db_server_info['description'],
'server_name' => $server_name,
'base_url' => Environment::getBaseURL(),
'php_os' => PHP_OS,
'system_information' => php_uname(),
];
$version_data = array_merge( $tt_version_data, $sys_version_data );
if ( isset( $version_data ) && is_array( $version_data ) ) {
Debug::Text( 'Sent Company Version Data!', __FILE__, __LINE__, __METHOD__, 10 );
$retval = $this->getSoapObject()->saveCompanyVersionData( $version_data );
if ( $retval == false ) {
Debug::Text( 'Server failed saving data!', __FILE__, __LINE__, __METHOD__, 10 );
}
//$this->printSoapDebug();
return $retval;
}
Debug::Text( 'NOT Sending Company Version Data!', __FILE__, __LINE__, __METHOD__, 10 );
return false;
}
/**
* @param string $company_id UUID
* @return bool
*/
function sendCompanyUserCountData( $company_id ) {
$cuclf = TTnew( 'CompanyUserCountListFactory' ); /** @var CompanyUserCountListFactory $cuclf */
$cuclf->getActiveUsers();
$user_counts = [];
if ( $cuclf->getRecordCount() > 0 ) {
foreach ( $cuclf as $cuc_obj ) {
$user_counts[$cuc_obj->getColumn( 'company_id' )]['active'] = $cuc_obj->getColumn( 'total' );
}
}
$cuclf->getInActiveUsers();
if ( $cuclf->getRecordCount() > 0 ) {
foreach ( $cuclf as $cuc_obj ) {
$user_counts[$cuc_obj->getColumn( 'company_id' )]['inactive'] = $cuc_obj->getColumn( 'total' );
}
}
$cuclf->getDeletedUsers();
if ( $cuclf->getRecordCount() > 0 ) {
foreach ( $cuclf as $cuc_obj ) {
$user_counts[$cuc_obj->getColumn( 'company_id' )]['deleted'] = $cuc_obj->getColumn( 'total' );
}
}
if ( isset( $user_counts[$company_id] ) ) {
$user_counts[$company_id]['registration_key'] = $this->getLocalRegistrationKey();
$user_counts[$company_id]['company_id'] = $company_id;
return $this->getSoapObject()->saveCompanyUserCountData( $user_counts[$company_id] );
}
return false;
}
/**
* @param string $company_id UUID
* @return bool
*/
function sendCompanyUserLocationData( $company_id ) {
if ( $company_id == '' ) {
return false;
}
$clf = TTnew( 'CompanyListFactory' ); /** @var CompanyListFactory $clf */
$clf->getById( $company_id );
if ( $clf->getRecordCount() > 0 ) {
$location_data = [];
$location_data['registration_key'] = $this->getLocalRegistrationKey();
$location_data['company_id'] = $company_id;
$ulf = TTnew( 'UserListFactory' ); /** @var UserListFactory $ulf */
$ulf->getByCompanyId( $company_id );
if ( $ulf->getRecordCount() > 0 ) {
foreach ( $ulf as $u_obj ) {
$key = str_replace( ' ', '', strtolower( $u_obj->getCity() . $u_obj->getCity() . $u_obj->getCountry() ) );
$location_data['location_data'][$key] = [
'city' => $u_obj->getCity(),
'province' => $u_obj->getProvince(),
'country' => $u_obj->getCountry(),
];
}
if ( isset( $location_data['location_data'] ) ) {
return $this->getSoapObject()->saveCompanyUserLocationData( $location_data );
}
}
}
return false;
}
/**
* @param string $company_id UUID
* @param bool $force
* @return bool
*/
function sendCompanyData( $company_id, $force = false ) {
Debug::Text( 'Sending Company Data...', __FILE__, __LINE__, __METHOD__, 10 );
if ( $company_id == '' ) {
return false;
}
//Check for anonymous update notifications
$anonymous_update_notify = 0;
if ( $force == false || getTTProductEdition() == 10 ) {
$anonymous_update_notify = (int)SystemSettingFactory::getSystemSettingValueByKey( 'anonymous_update_notify' );
}
/* @formatter:off */ $obj_class = "\124\124\114\x69\x63\x65\x6e\x73\x65"; @$obj = new $obj_class; $hardware_id = $obj->getHardwareID(); unset($obj, $obj_class); /* @formatter:on */
$clf = TTnew( 'CompanyListFactory' ); /** @var CompanyListFactory $clf */
$clf->getById( $company_id );
$company_data = array();
if ( $clf->getRecordCount() > 0 ) {
foreach ( $clf as $c_obj ) {
$company_data['id'] = $c_obj->getId();
$company_data['production'] = PRODUCTION;
$company_data['registration_key'] = $this->getLocalRegistrationKey();
$company_data['hardware_id'] = $hardware_id;
$company_data['status_id'] = $c_obj->getStatus();
$company_data['application_name'] = APPLICATION_NAME;
$company_data['product_edition_id'] = $c_obj->getProductEdition();
$company_data['is_professional_edition_available'] = getTTProductEdition();
$company_data['product_edition_available'] = getTTProductEdition();
$company_data['industry_id'] = $c_obj->getIndustry();
if ( $anonymous_update_notify == 0 ) {
$company_data['name'] = $c_obj->getName();
$company_data['short_name'] = $c_obj->getShortName();
$company_data['business_number'] = $c_obj->getBusinessNumber();
$company_data['address1'] = $c_obj->getAddress1();
$company_data['address2'] = $c_obj->getAddress2();
$company_data['work_phone'] = $c_obj->getWorkPhone();
$company_data['fax_phone'] = $c_obj->getFaxPhone();
$ulf = TTnew( 'UserListFactory' ); /** @var UserListFactory $ulf */
if ( $c_obj->getBillingContact() != '' ) {
$ulf->getById( $c_obj->getBillingContact() );
if ( $ulf->getRecordCount() == 1 ) {
$u_obj = $ulf->getCurrent();
if ( $u_obj->getWorkEmail() != '' ) {
$email = $u_obj->getWorkEmail();
} else {
$email = $u_obj->getHomeEmail();
}
$company_data['billing_contact'] = '"' . $u_obj->getFullName() . '" <' . $email . '>';
}
}
if ( $c_obj->getAdminContact() != '' ) {
$ulf->getById( $c_obj->getAdminContact() );
if ( $ulf->getRecordCount() == 1 ) {
$u_obj = $ulf->getCurrent();
if ( $u_obj->getWorkEmail() != '' ) {
$email = $u_obj->getWorkEmail();
} else {
$email = $u_obj->getHomeEmail();
}
$company_data['admin_contact'] = '"' . $u_obj->getFullName() . '" <' . $email . '>';
}
}
if ( $c_obj->getSupportContact() != '' ) {
$ulf->getById( $c_obj->getSupportContact() );
if ( $ulf->getRecordCount() == 1 ) {
$u_obj = $ulf->getCurrent();
if ( $u_obj->getWorkEmail() != '' ) {
$email = $u_obj->getWorkEmail();
} else {
$email = $u_obj->getHomeEmail();
}
$company_data['support_contact'] = '"' . $u_obj->getFullName() . '" <' . $email . '>';
}
}
$logo_file = $c_obj->getLogoFileName( $c_obj->getId(), false ); //Ignore default logo
if ( $logo_file != '' && file_exists( $logo_file ) ) {
$company_data['logo'] = array('file_name' => $logo_file, 'data' => base64_encode( file_get_contents( $logo_file ) ));
}
}
$company_data['city'] = $c_obj->getCity();
$company_data['country'] = $c_obj->getCountry();
$company_data['province'] = $c_obj->getProvince();
$company_data['postal_code'] = $c_obj->getPostalCode();
//Get Last user login date.
$ulf = TTnew( 'UserListFactory' ); /** @var UserListFactory $ulf */
$ulf->getByCompanyId( $company_id, 1, null, array('last_login_date' => 'is not null'), array('last_login_date' => 'desc') );
if ( $ulf->getRecordCount() == 1 ) {
$company_data['last_login_date'] = $ulf->getCurrent()->getLastLoginDate();
}
//Get Last Punch Date (before today). Use PunchControl table only as its much faster.
$plf = TTnew( 'PunchControlListFactory' ); /** @var PunchControlListFactory $plf */
$plf->getByCompanyId( $company_id, 1, null, array(array('date_stamp' => ">= '" . $plf->db->BindTimeStamp( TTDate::getBeginDayEpoch( time() - ( 86400 * 30 ) ) ) . "'"), array('date_stamp' => "<= '" . $plf->db->BindTimeStamp( TTDate::getEndDayEpoch( time() ) ) . "'")), array('date_stamp' => 'desc') );
if ( $plf->getRecordCount() == 1 ) {
$company_data['last_punch_date'] = $plf->getCurrent()->getDateStamp();
}
//Get Last Schedule Date (before today)
$slf = TTnew( 'ScheduleListFactory' ); /** @var ScheduleListFactory $slf */
$slf->getByCompanyId( $company_id, 1, null, array(array('date_stamp' => ">= '" . $slf->db->BindTimeStamp( TTDate::getBeginDayEpoch( time() - ( 86400 * 30 ) ) ) . "'"), array('date_stamp' => "<= '" . $slf->db->BindTimeStamp( TTDate::getEndDayEpoch( time() ) ) . "'")), array('date_stamp' => 'desc') );
if ( $slf->getRecordCount() == 1 ) {
$company_data['last_schedule_date'] = $slf->getCurrent()->getStartTime();
}
//Get Last Pay Stub Date (before today)
$pslf = TTnew( 'PayStubListFactory' ); /** @var PayStubListFactory $pslf */
$pslf->getByCompanyId( $company_id, 1, null, array(array('a.start_date' => ">= '" . $pslf->db->BindTimeStamp( TTDate::getBeginDayEpoch( time() - ( 86400 * 30 ) ) ) . "'"), array('a.start_date' => "<= '" . $pslf->db->BindTimeStamp( TTDate::getEndDayEpoch( time() ) ) . "'")), array('a.start_date' => 'desc') );
if ( $pslf->getRecordCount() == 1 ) {
$company_data['last_pay_stub_date'] = $pslf->getCurrent()->getEndDate();
}
//Get Last Review Date (before today)
$rclf = TTnew( 'UserReviewControlListFactory' ); /** @var UserReviewControlListFactory $rclf */
$rclf->getByCompanyId( $company_id, 1, null, array(array('a.created_date' => ">= " . TTDate::getBeginDayEpoch( time() - ( 86400 * 30 ) )), array('a.created_date' => "<= " . TTDate::getEndDayEpoch( time() ))), array('a.created_date' => 'desc') );
if ( $rclf->getRecordCount() == 1 ) {
$company_data['last_user_review_date'] = $rclf->getCurrent()->getCreatedDate();
}
Debug::Text( 'Sent Company Data...', __FILE__, __LINE__, __METHOD__, 10 );
$retval = $this->getSoapObject()->saveCompanyData( $company_data );
//$this->printSoapDebug();
if ( is_array( $retval ) ) {
foreach ( $retval as $command => $command_data ) { //Must be v7.3.x or higher.
Debug::Text( 'Running Command: ' . $command, __FILE__, __LINE__, __METHOD__, 10 );
switch ( strtolower( $command ) ) {
case 'system_settings':
if ( is_array( $command_data ) ) {
foreach ( $command_data as $name => $value ) {
Debug::Text( 'Defining System Setting: ' . $name, __FILE__, __LINE__, __METHOD__, 10 );
SystemSettingFactory::setSystemSetting( $name, $value );
}
unset( $name, $value );
}
break;
case 'config_file':
if ( is_array( $command_data ) ) {
Debug::Arr( $command_data, 'Defining Config File Settings: ', __FILE__, __LINE__, __METHOD__, 10 );
$install_obj = new Install();
$install_obj->writeConfigFile( $command_data );
unset( $install_obj );
}
break;
default:
break;
}
}
return true;
} else {
return $retval;
}
}
}
return false;
}
//
// Currency Data Feed functions
//
/**
* @param string $company_id UUID
* @param $currency_arr
* @param $base_currency
* @return array|bool
*/
function getCurrencyExchangeRates( $company_id, $currency_arr, $base_currency ) {
/*
Contact info@timetrex.com to request adding custom currency data feeds.
*/
if ( $company_id == '' ) {
return false;
}
if ( !is_array( $currency_arr ) ) {
return false;
}
if ( $base_currency == '' ) {
return false;
}
$currency_rates = $this->getSoapObject()->getCurrencyExchangeRates( $this->getLocalRegistrationKey(), $company_id, $currency_arr, $base_currency );
if ( isset( $currency_rates ) && is_array( $currency_rates ) && count( $currency_rates ) > 0 ) {
return $currency_rates;
}
return false;
}
/**
* @param string $company_id UUID
* @param $currency_arr
* @param $base_currency
* @param int $start_date EPOCH
* @param int $end_date EPOCH
* @return bool|array
*/
function getCurrencyExchangeRatesByDate( $company_id, $currency_arr, $base_currency, $start_date = null, $end_date = null ) {
/*
Contact info@timetrex.com to request adding custom currency data feeds.
*/
if ( $company_id == '' ) {
return false;
}
if ( !is_array( $currency_arr ) ) {
return false;
}
if ( $base_currency == '' ) {
return false;
}
if ( $start_date == '' ) {
$start_date = time();
}
if ( $end_date == '' ) {
$end_date = time();
}
$currency_rates = $this->getSoapObject()->getCurrencyExchangeRatesByDate( $this->getLocalRegistrationKey(), $company_id, $currency_arr, $base_currency, $start_date, $end_date );
if ( isset( $currency_rates ) && is_array( $currency_rates ) && count( $currency_rates ) > 0 ) {
return $currency_rates;
}
return false;
}
/**
* @param bool $force
* @return bool
*/
function isNewVersionReadyForUpgrade( $force = false ) {
$company_data = $this->getPrimaryCompanyData();
if ( is_array( $company_data ) ) {
$company_data['force'] = $force;
$retval = $this->getSoapObject()->isNewVersionReadyForUpgrade( $company_data );
Debug::Arr( array($company_data, $retval), 'Checking for new version based on this data: ', __FILE__, __LINE__, __METHOD__, 10 );
return $retval;
}
return false;
}
/**
* @param bool $force
* @return bool
*/
function getUpgradeFileURL( $force = false ) {
$company_data = $this->getPrimaryCompanyData();
if ( is_array( $company_data ) ) {
$company_data['force'] = $force;
$retval = $this->getSoapObject()->getUpgradeFileURL( $company_data );
return $retval;
}
return false;
}
//
// Email relay through SOAP
//
/**
* @param $email
* @return bool
*/
function validateEmail( $email ) {
$company_data = $this->getPrimaryCompanyData();
if ( is_array( $company_data ) && $email != '' ) {
return $this->getSoapObject()->validateEmail( $email, $company_data );
}
return false;
}
/**
* @param $to
* @param $headers
* @param $body
* @return bool
*/
function sendEmail( $to, $headers, $body ) {
$company_data = $this->getPrimaryCompanyData();
if ( is_array( $company_data ) && $to != '' && $body != '' ) {
$retval = $this->getSoapObject()->sendEmail( $to, $headers, $body, $company_data );
//Debug::Arr( $retval, 'TimeTrexSoapClient::sendEmail() response: ', __FILE__, __LINE__, __METHOD__, 10 );
if ( $retval === 'unsubscribe' ) {
UserFactory::UnsubscribeEmail( $to );
$retval = false;
}
return $retval;
}
return false;
}
function syncNotifications( $last_check_epoch, $force = false ) {
if ( PRODUCTION == false && $force !== true ) {
Debug::Text( 'Not in production mode, not syncing notifications...', __FILE__, __LINE__, __METHOD__, 10 );
return true;
}
if ( DEMO_MODE == true ) {
Debug::Text( 'In DEMO mode, not syncing notifications...', __FILE__, __LINE__, __METHOD__, 10 );
return true;
}
$company_data = $this->getPrimaryCompanyData();
if ( is_array( $company_data ) ) { //Must allow no title/body here for sending background push notifications.
$retval = $this->getSoapObject()->syncNotifications( $last_check_epoch, $company_data );
return $retval;
}
return false;
}
/**
* @param $device_tokens
* @param $title
* @param $body
* @param null $payload_data
* @param int $ttl
* @param string $priority
* @param bool $force
* @return bool
*/
function sendNotification( $device_tokens, $title, $body, $payload_data = null, $ttl = 0, $priority = 'normal', $force = false ) {
if ( PRODUCTION == false && $force !== true ) {
Debug::Text( 'Not in production mode, not sending notifications...', __FILE__, __LINE__, __METHOD__, 10 );
Debug::Text( ' Title: '. $title .' Body: '. $body, __FILE__, __LINE__, __METHOD__, 10 );
return true;
}
if ( DEMO_MODE == true ) {
Debug::Text( 'In DEMO mode, not sending notifications...', __FILE__, __LINE__, __METHOD__, 10 );
return true;
}
$company_data = $this->getPrimaryCompanyData();
if ( is_array( $company_data ) && $device_tokens != '' ) { //Must allow no title/body here for sending background push notifications.
$retval = $this->getSoapObject()->sendNotification( $device_tokens, $title, $body, $payload_data, $ttl, $priority, $company_data );
return $retval;
}
return false;
}
//
// GEO Coding
//
/**
* @param $address1
* @param $address2
* @param $city
* @param $province
* @param $country
* @param $postal_code
* @return null
*/
function getGeoCodeByAddress( $address1, $address2, $city, $province, $country, $postal_code ) {
$company_data = $this->getPrimaryCompanyData();
if ( is_array( $company_data ) && $city != '' && $country != '' ) {
return $this->getSoapObject()->getGeoCodeByAddress( $address1, $address2, $city, $province, $country, $postal_code, $company_data );
}
return null; //Return NULL when no data available, and FALSE to try again later.
}
/**
* @param $ip_address
* @return null
*/
function getGeoIPData( $ip_address ) {
$company_data = $this->getPrimaryCompanyData();
if ( is_array( $company_data ) && $ip_address != '' ) {
return $this->getSoapObject()->getGeoIPData( $ip_address, $company_data );
}
return null; //Return NULL when no data available, and FALSE to try again later.
}
/**
* @param $rating
* @param $message
* @param object $u_obj
* @return null
*/
function sendUserFeedback( $rating, $message, $u_obj ) {
$company_data = $this->getPrimaryCompanyData();
if ( is_array( $company_data ) ) {
$user_data = array('company_id' => $u_obj->getCompany(), 'host_name' => Misc::getHostName( false ), 'user_id' => $u_obj->getId(), 'permission_level' => $u_obj->getPermissionLevel(), 'company_name' => $u_obj->getCompanyObject()->getName(), 'full_name' => $u_obj->getFullName(), 'work_phone' => $u_obj->getWorkPhone(), 'work_email' => $u_obj->getWorkEmail(), 'home_email' => $u_obj->getHomeEmail(), 'user_ip_address' => Misc::getRemoteIPAddress(), 'user_agent' => ( isset( $_SERVER['HTTP_USER_AGENT'] ) ? $_SERVER['HTTP_USER_AGENT'] : null ));
return $this->getSoapObject()->sendUserFeedback( $rating, $message, $user_data, $company_data );
}
return null; //Return NULL when no data available, and FALSE to try again later.
}
}
?>