<?php defined('SYSPATH') or die('No direct access allowed.');

/**
 *
 * @package    PTA
 * @subpackage Nodes
 * @category   Models
 * @author     Deon George
 * @copyright  (c) 2010 phpTSMadmin Development Team
 * @license    http://phptsmadmin.sf.net/license.html
 */
class Model_NODE extends ORMTSM {
	protected $_table_name = 'NODES';
	protected $_primary_key = 'NODE_NAME';
	protected $_sorting = array(
		'NODE_NAME'=>'ASC',
	);

	protected $_has_one = array(
		'DOMAIN'=>array('foreign_key'=>'DOMAIN_NAME','far_key'=>'DOMAIN_NAME'),
	);
	protected $_has_many = array(
		'FILESPACE'=>array('foreign_key'=>'NODE_NAME','far_key'=>'NODE_NAME'),
		'VOLUMEUSAGE'=>array('foreign_key'=>'NODE_NAME','far_key'=>'NODE_NAME'),
		'ASSOCIATION'=>array('foreign_key'=>'NODE_NAME','far_key'=>'NODE_NAME'),
		'MGMTCLASS'=>array('foreign_key'=>'DOMAIN_NAME','far_key'=>'DOMAIN_NAME'),
		'CLIENTOPT'=>array('foreign_key'=>'OPTIONSET_NAME','far_key'=>'OPTION_SET'),
		'SUMMARY'=>array('foreign_key'=>'ENTITY','far_key'=>'NODE_NAME'),
		'EVENT'=>array('foreign_key'=>'NODE_NAME','far_key'=>'NODE_NAME'),
		'OCC'=>array('foreign_key'=>'NODE_NAME','far_key'=>'NODE_NAME'),
	);

	protected $_tsm = array(
		'db2'=>array(
			'_primary_key'=>'NODENAME',
			'_sorting'=>array(
				'NODENAME'=>'ASC',
			),
			'_has_one'=>array(
				'DOMAIN'=>array('foreign_key'=>'DOMAIN_NAME','far_key'=>'DOMAINNAME'),
			),
			'_has_many'=>array(
				'FILESPACE'=>array('foreign_key'=>'NODEID','far_key'=>'NODEID'),
				'VOLUMEUSAGE'=>array('foreign_key'=>'NODE_NAME','far_key'=>'NODENAME'),
				'ASSOCIATION'=>array('foreign_key'=>'NODE_NAME','far_key'=>'NODENAME'),
				'MGMTCLASS'=>array('foreign_key'=>'DOMAIN_NAME','far_key'=>'DOMAIN_NAME'),
				'CLIENTOPT'=>array('foreign_key'=>'OPTIONSET_NAME','far_key'=>'OPTIONSET'),
				'SUMMARY'=>array('foreign_key'=>'ENTITY','far_key'=>'NODENAME'),
				'EVENT'=>array('foreign_key'=>'NODE_NAME','far_key'=>'NODENAME'),
				'OCC'=>array('foreign_key'=>'NODE_NAME','far_key'=>'NODENAME'),
			),
			'translate'=>array(
				'NODE_NAME'=>'NODENAME',
				'CLIENT_VERSION'=>'CLNTVERSION',
				'CLIENT_RELEASE'=>'CLNTRELEASE',
				'CLIENT_LEVEL'=>'CLNTLEVEL',
				'CLIENT_SUBLEVEL'=>'CLNTSUBLEVEL',
				'PLATFORM_NAME'=>'OSNAME',
				'CLIENT_OS_LEVEL'=>'CLNTOSLEVEL',
				'LASTACC_TIME'=>'LACDATE',
				'REG_TIME'=>'REGDATE',
				'PWSET_TIME'=>'PWSETDATE',
				'LASTSESS_SENT'=>'SESSSENT',
				'LASTSESS_RECVD'=>'SESSRECVD',
				'LASTSESS_DURATION'=>'SESSDURATION',
				'LASTSESS_IDLEWAIT'=>'SESSIDLEWAIT',
				'LASTSESS_COMMWAIT'=>'SESSCOMMWAIT',
				'LASTSESS_MEDIAWAIT'=>'SESSMEDIAWAIT',
				'TCP_ADDRESS'=>NULL,
				'EMAIL_ADDRESS'=>NULL,
				'REG_ADMIN'=>'REGISTRAR',
				'PASSEXP'=>NULL,
				'INVALID_PW_COUNT'=>'INVPWCOUNT',
				'LOCKED'=>'LOCKSTATE',
				'DOMAIN_NAME'=>'DOMAINNAME',
				'OPTION_SET'=>'OPTIONSET',
				'COLLOCGROUP_NAME'=>NULL,
				'COMPRESSION'=>'COMPRESS',
				'ARCHDELETE'=>'ARCHDEL',
				'BACKDELETE'=>'BACKDEL',
				'KEEP_MP'=>NULL,
				'MAX_MP_ALLOWED'=>'MAXNUMMP',
			),
		),
	);

	protected $_display_filters = array(
		'REG_TIME'=>array(
			array('ORMTSM::date',array(':value','d-M-Y')),
		),
		'PWSET_TIME'=>array(
			array('ORMTSM::date',array(':value','d-M-Y')),
		),
		'LASTACC_TIME'=>array(
			array('ORMTSM::date',array(':value','d-M-Y')),
		),
		'LASTSESS_SENT'=>array(
			array('number_format',array(':value',0)),
		),
		'LASTSESS_RECVD'=>array(
			array('number_format',array(':value',0)),
		),
		'LASTSESS_DURATION'=>array(
			array('number_format',array(':value',2)),
		),
		'LASTSESS_IDLEWAIT'=>array(
			array('number_format',array(':value',2)),
		),
		'LASTSESS_COMMWAIT'=>array(
			array('number_format',array(':value',2)),
		),
		'LASTSESS_MEDIAWAIT'=>array(
			array('number_format',array(':value',2)),
		),
	);

	// Pools used by a node.
	private $pools = array();

	public function tsmclientversion() {
		if ($this->CLIENT_VERSION)
			return sprintf('%s.%s.%s.%s',$this->CLIENT_VERSION,$this->CLIENT_RELEASE,$this->CLIENT_LEVEL,$this->CLIENT_SUBLEVEL);
		else
			return '';
	}

	public function platform() {
		return sprintf('%s %s',$this->PLATFORM_NAME,$this->CLIENT_OS_LEVEL ? '('.$this->CLIENT_OS_LEVEL.')' : '');
	}

	// @todo This needs to return the global configuration.
	public function passexp() {
		if ($this->PASSEXP)
			return 'TBA';
		else
			return _('No Set');
	}

	public function lasttransferpercent() {
		return 100-($this->LASTSESS_IDLEWAIT+$this->LASTSESS_COMMWAIT+$this->LASTSESS_MEDIAWAIT);
	}

	public function lasttransfertime() {
		if ($this->LASTSESS_DURATION)
			return $this->LASTSESS_DURATION*($this->lasttransferpercent()/100);
		else
			return 0;
	}

	public function lastsendperformance() {
		if ($this->lasttransfertime())
			return $this->LASTSESS_SENT/$this->lasttransfertime()/1024/1024;
		else
			return 0;
	}

	public function lastreceiveperformance() {
		if ($this->lasttransfertime())
			return $this->LASTSESS_RECVD/$this->lasttransfertime()/1024/1024;
		else
			return 0;
	}

	public function lastsendaggperformance() {
		if ((real)$this->LASTSESS_DURATION)
			return $this->LASTSESS_SENT/$this->LASTSESS_DURATION/1024/1024;
		else
			return 0;
	}

	public function lastreceiveaggperformance() {
		if ((real)$this->LASTSESS_DURATION)
			return $this->LASTSESS_RECVD/$this->LASTSESS_DURATION/1024/1024;
		else
			return 0;
	}

	// @todo This should return the system setting (cloptset), if the node setting is not configured.
	public function txngroupmax() {
		return $this->TXNGROUPMAX;
	}

	// Work out all the storage pools used by a node.
	// $dtype is BACKUP (Bkup) or ARCHIVE (Arch)
	public function getStoragePools($dtype) {
		return isset($this->pools[$dtype]) ? $this->pools[$dtype] : $this->_getpools($dtype);
	}

	// $dtype is BACKUP (Bkup) or ARCHIVE (Arch)
	private function _getpools($dtype) {
		$this->pools[$dtype] = array();

		foreach ($this->FILESPACE->find_all() as $fso)
			foreach ($fso->storagepools($dtype) as $po)
				if (! isset($this->pools[$dtype][$po->POOLTYPE][$po->STGPOOL_NAME]))
					$this->pools[$dtype][$po->POOLTYPE][$po->STGPOOL_NAME] = $po;

		return $this->pools[$dtype];
	}

	// Test to see if a node has any data of type
	// $dtype is BACKUP (Bkup) or ARCHIVE (Arch)
	public function hasData($dtype) {
		return $this->getStoragePools($dtype) ? TRUE : FALSE;
	}

	public function getAllStoragePoolsType($ptype) {
		$result = array();

		foreach (Kohana::config('config.tsmdatatypes') as $btype => $ctype)
			$result = array_merge($result,$this->getStoragePoolsType($btype,$ptype));

		return $result;
	}

	// Return the storage pools used for a backup type
	// $dtype is BACKUP (Bkup) or ARCHIVE (Arch)
	// $ptype is pool type (PRIMARY,ACTIVE,COPY)
	public function getStoragePoolsType($dtype,$ptype) {
		if (! isset($this->pools[$dtype]))
			$this->_getpools($dtype);

		return isset($this->pools[$dtype][$ptype]) ? $this->pools[$dtype][$ptype] : array();
	}

	// $dtype is BACKUP or ARCHIVE
	// $ptype is pool type (PRIMARY,ACTIVE,COPY)
	public function getStorageModeVols($dtype,$ptype,$spo='') {
		$result = array();

		foreach ($this->VOLUMEUSAGE->where('COPY_TYPE','=',$dtype)->find_all() as $vo)
			if ((! $spo OR $vo->STGPOOL_NAME == $spo) AND $vo->STGPOOL->POOLTYPE == $ptype)
				if (! isset($result[$vo->VOLUME_NAME]))
					$result[$vo->VOLUME_NAME] = $vo;

		return $result;
	}

	// $ptype is pool type (PRIMARY,ACTIVE,COPY)
	public function getStorageTypeVols($ptype,$spo='') {
		$result = array();

		foreach (Kohana::config('config.tsmdatatypes') as $btype => $ctype)
			$result = array_merge($result,$this->getStorageModeVols($ctype,$ptype,$spo));

		return $result;
	}

	// $dtype is BACKUP (Bkup) or ARCHIVE (Arch)
	// $ptype is pool type (PRIMARY,ACTIVE,COPY)
	public function getStorageModeFiles($dtype,$ptype,$spo='') {
		$count = 0;

		foreach ($this->OCC->where('TYPE','=',$dtype)->find_all() as $oa)
			if ((! $spo OR $oa->STGPOOL_NAME == $spo) AND $oa->STGPOOL->POOLTYPE == $ptype)
				$count += $oa->NUM_FILES;

		return $count;
	}

	// $ptype is pool type (PRIMARY,ACTIVE,COPY)
	public function getStorageTypeFiles($ptype,$spo='') {
		$count = 0;

		foreach (Kohana::config('config.tsmdatatypes') as $btype => $ctype)
			$count += $this->getStorageModeFiles($btype,$ptype,$spo);

		return $count;
	}

	// $dtype is BACKUP (Bkup) or ARCHIVE (Arch)
	// $ptype is pool type (PRIMARY,ACTIVE,COPY)
	public function getStorageModeData($dtype,$ptype,$spo='') {
		$count = 0;

		foreach ($this->OCC->where('TYPE','=',$dtype)->find_all() as $oa)
			if ((! $spo OR $oa->STGPOOL_NAME == $spo) AND $oa->STGPOOL->POOLTYPE == $ptype)
				$count += $oa->LOGICAL_MB;

		return $count;
	}

	// $ptype is pool type (PRIMARY,ACTIVE,COPY)
	public function getStorageTypeData($ptype,$spo='') {
		$count = 0;

		foreach (Kohana::config('config.tsmdatatypes') as $btype => $ctype)
			$count += $this->getStorageModeData($btype,$ptype,$spo);

		return $count;
	}

	// Return the volumes that this node uses
	// $dtype is BACKUP or ARCHIVE
	public function volumes($dtype) {
		$volumes = array();

		$v = array();
		foreach ($this->VOLUMEUSAGE->where('COPY_TYPE','=',$dtype)->order_by('STGPOOL_NAME,FILESPACE_NAME')->find_all() as $vol)
			if (! in_array($vol->VOLUME->VOLUME_NAME,$v)) {
				$volumes[$vol->STGPOOL_NAME][] = $vol->VOLUME;
				array_push($v,$vol->VOLUME->VOLUME_NAME);
			}

		return $volumes;
	}

	/**
	 * Get all the nodes by OS
	 */
	public function byos() {
		$a = $this->select('count(*) AS node_name,platform_name')
			->group_by('platform_name')
			->order_by('platform_name');

		return $a->find_all();
	}
}
?>