<?php
/**
Error codes:
 102. Couldn't grab html from website
 103. Website contains badwords
 201. Error while inserting data
 202. Error while updating data
*/
Yii::import('application.library.*');
set_time_limit(0);
class CalculateCommand extends CConsoleCommand {
	protected $domain, $idn, $ip, $html, $errorcode, $price,
		$alexa = array(),
		$antivirus = array(),
		$catalog = array(),
		$location = array(),
		$metatag = array(),
		$searchengine = array(),
		$social = array(),
		$whois;

	private function _init($domain, $idn, $ip) {
		$this->domain = $domain;
		$this->ip = $ip;
		$this->idn=$idn;
	}

	public function actionInsert($domain, $idn, $ip) {
		$this->_init($domain, $idn, $ip);

		if(!$this -> grabHtml()) {
			return $this -> errorcode;
		}

		if($this -> existsBadwords()) {
			return $this -> errorcode;
		}

		$this->collectWebsiteData();
		$this->setWebsiteCost();

		// Begin transaction
		$transaction = Yii::app() -> db -> beginTransaction();
		try {
		$website = new Website;
		$website->attributes=array("price"=>$this->price, "domain"=>$this->domain, "idn"=>$this->idn);
		if(!$website->save(false)) { throw new Exception("An error occuried while inserting webdata_main"); }
		$wid = $website->id;

		$alexa = new WebdataAlexa;
		$alexa->attributes = array_merge(array("wid"=>$wid), $this->alexa);
		if(!$alexa->save(false)) { throw new Exception("An error occuried while inserting webdata_alexa"); }

		$antivirus = new WebdataAntivirus;
		$antivirus->attributes = array_merge(array("wid"=>$wid), $this->antivirus);
		if(!$antivirus->save(false)) { throw new Exception("An error occuried while inserting webdata_antivirus"); }

		$catalog = new WebdataCatalog;
		$catalog->attributes = array_merge(array("wid"=>$wid), $this->catalog);
		if(!$catalog->save(false)) { throw new Exception("An error occuried while inserting webdata_catalog"); }

		$location = new WebdataLocation;
		$location->attributes = array_merge(array("wid"=>$wid), $this->location);
		if(!$location->save(false)) { throw new Exception("An error occuried while inserting webdata_location"); }

		$meta_tags = new WebdataMetaTags;
		$meta_tags->attributes = array_merge(array("wid"=>$wid), $this->metatag);
		if(!$meta_tags->save(false)) { throw new Exception("An error occuried while inserting webdata_metatags"); }

		$search_engine = new WebdataSearchEngine;
		$search_engine->attributes = array_merge(array("wid"=>$wid), $this->searchengine);
		if(!$search_engine->save(false)) { throw new Exception("An error occuried while inserting webdata_search_engine"); }

		$social = new WebdataSocial;
		$social->attributes = array_merge(array("wid"=>$wid), $this->social);
		if(!$social->save(false)) { throw new Exception("An error occuried while inserting webdata_social"); }

		$whois = new WebdataWhois;
		$whois->attributes = array("wid"=>$wid, 'text'=>$this->whois);
		if(!$whois->save(false)) { throw new Exception("An error occuried while inserting webdata_whois"); }

		$transaction->commit();
		} catch(Exception $e) {
			$transaction -> rollback();
			Yii::log($e->getMessage(), 'error', 'application.command.calculate.insert');
			return 201;
		}
		return 0;
	}

	public function actionUpdate($domain, $idn, $ip, $wid) {
		$this->_init($domain, $idn, $ip);
		if(!$this -> grabHtml()) {
			return $this -> errorcode;
		}

		if($this -> existsBadwords()) {
			return $this -> errorcode;
		}

		$this->collectWebsiteData();
		$this->setWebsiteCost();

		// Begin transaction
		$transaction = Yii::app() -> db -> beginTransaction();
		try {

		Website::model()->updateByPk($wid, array('price' => $this->price, 'modified_at'=>date("Y-m-d H:i:s")));
		WebdataAlexa::model()->updateByPk($wid, $this->alexa);
		WebdataAntivirus::model()->updateByPk($wid, $this->antivirus);
		WebdataCatalog::model()->updateByPk($wid, $this->catalog);
		WebdataLocation::model()->updateByPk($wid, $this->location);
		WebdataMetaTags::model()->updateByPk($wid, $this->metatag);
		WebdataSearchEngine::model()->updateByPk($wid, $this->searchengine);
		WebdataSocial::model()->updateByPk($wid, $this->social);
		WebdataWhois::model()->updateByPk($wid, array("text"=>$this->whois));

		$transaction->commit();
		} catch(Exception $e) {
			$transaction -> rollback();
			Yii::log($e->getMessage(), 'error', 'application.command.calculate.update');
			return 202;
		}
		return 0;
	}


	private function setWebsiteCost() {
		$calc = new WebsiteCostCalculator;

		$calc->setFbLike($this->social['facebook_like_count']);
		$calc->setGPlus($this->social['gplus']);
		$calc->setTweet($this->social['twitter']);

		$calc->setGooglePage($this->searchengine['google_index']);
		$calc->setBingPage($this->searchengine['bing_index']);
		$calc->setYahooPage($this->searchengine['yahoo_index']);

		$calc->setPageRank($this->searchengine['page_rank']);
		$calc->setAlexa($this->alexa['rank']);

		$calc->setBackLinks($this->searchengine['google_backlinks']);

		$this->price = $calc->getPrice() * Yii::app()->params['dollarRate'];
	}

	private function collectWebsiteData() {
		$this->alexa = SearchCatalog::alexa($this->domain);

		$this->antivirus['google'] = Diagnostic::google($this->domain);
		$this->antivirus['mcafee'] = Diagnostic::mcafee($this->domain);

		$this->catalog['dmoz'] = SearchCatalog::dmoz($this->domain);
		$this->catalog['yahoo'] = SearchCatalog::yahoo($this->domain);

		$this->location = Location::get($this->ip);

		$metatags = new MetaTags($this -> html);
		$this->metatag["title"] = $metatags -> getTitle();
		$this->metatag["description"] = $metatags -> getDescription();
		$this->metatag["keywords"] = $metatags -> getKeywords();

		$this->searchengine['google_index'] = SearchEngine::google($this->domain);
		$this->searchengine['bing_index'] = SearchEngine::bing($this->domain);
		$this->searchengine['yahoo_index'] = SearchEngine::yahoo($this->domain);


		$pagerank = new PageRank;
		$pr = $pagerank->get_google_pagerank($this->domain);
		$pr = $pr === null ? 'n-a' : trim($pr);
		$this->searchengine['page_rank'] = $pr;
		$this->searchengine['google_backlinks'] = SearchEngine::googleBackLinks($this->domain);

		$fb = Social::facebook($this->domain);
		$this->social['facebook_share_count'] = $fb['share_count'];
		$this->social['facebook_like_count'] = $fb['like_count'];
		$this->social['facebook_comment_count'] = $fb['comment_count'];
		$this->social['facebook_total_count'] = $fb['total_count'];
		$this->social['facebook_click_count'] = $fb['click_count'];
		$this->social['gplus'] = Social::gplus($this->domain);
		$this->social['twitter'] = Social::twitter($this->domain);

		$whois = new PHPWhois(
			$this->domain,
			Yii::app()->basePath.'/config/whois.servers.php',
			Yii::app()->basePath.'/config/whois.servers_charset.php'
		);
		$this->whois = $whois->query();
	}

	public function actionCheck($domain) {
		if(!$website = Website::model()->with(array(
			"alexa", "antivirus", "catalog", "location", "meta_tags", "search_engine", "social", "whois"
		))->findByAttributes(array(
			"md5domain"=>md5($domain),
		))) {
			throw new CHttpException(404, "Website $domain hasn't found in database");
		}
		$calc = new WebsiteCostCalculator;

		$calc->setFbLike($website->social->facebook_like_count);
		$calc->setGPlus($website->social->gplus);
		$calc->setTweet($website->social->twitter);

		$calc->setGooglePage($website->search_engine->google_index);
		$calc->setBingPage($website->search_engine->bing_index);
		$calc->setYahooPage($website->search_engine->yahoo_index);

		$calc->setPageRank($website->search_engine->page_rank);
		$calc->setAlexa($website->alexa->rank);

		$calc->setBackLinks($website->search_engine->google_backlinks);


		$this->price = $calc->getPrice() * Yii::app()->params['dollarRate'];
		var_dump($this->price);
		die();
	}

	public function actionTest($domain) {
		$ip=gethostbyname($domain);
		$res = Diagnostic::mcafee($domain);
		var_dump($res);
	}

	private function existsBadwords() {
		if(!Yii::app() -> params['checkForBadwords']) {
			return false;
		}
		$strip = ParseUtils::striptags($this -> html);
		$badwords = include_once Yii::getPathOfAlias("application.config.badwords") . ".php";
		$existsBadWord = preg_match_all("/\b(" . implode($badwords,"|") . ")\b/i",  $strip, $matches);
		if($existsBadWord) {
			$this -> errorcode = 103;
			return true;
		}
		return false;
	}

	private function grabHtml() {
		$this -> html = Helper::curl('http://'.$this -> domain);
		if(!$this -> html) {
			$this -> errorcode = 102;
			return false;
		}
		$m = new MetaTags($this -> html);
		$charset = $m -> getCharset();
		if(!empty($charset) AND strtolower($charset) != 'utf-8')
			$this -> html = iconv($charset, "utf-8", $this -> html);
		return true;
	}
}