<?php

/**
 *      【橙创家校通v4.0】 (C)2010-2012 Tuntron Inc.
 *      
 *    	 http://www.tuntron.com   QQ：1121251729
 *
 *      &数据库mysql类文件&
 */

if (!defined('IS_RUN')) die('Forbidden');

G_class('mysql_result');

class tj_mysql {

    var $dbinfo = '';
	var $query_num = 0;
	var $link = '';

    var $sqls = '';

	function tj_mysql(& $dbinfo) {
		$this->__construct($dbinfo);
	}
	
	function __construct(& $dbinfo) {
        $this->dbinfo = $dbinfo;
        if(DEBUG) $this->sqls = array();
    }

	function connect() {
        $func = $this->dbinfo['pconnect'] ? "mysql_pconnect" : "mysql_connect";
        if(!$this->link = @$func($this->dbinfo['dbhost'], $this->dbinfo['dbuser'], $this->dbinfo['dbpw'], 1)) {
        	$this->_halt("无法链接Mysql数据库，可能由于数据库关闭或用户密码错误");
        }
        if($this->version() > '4.1' && $this->dbinfo['dbcharset']) {
			mysql_query("SET NAMES '" . $this->dbinfo['dbcharset'] . "'", $this->link);
		}
        if($this->version() > '5.0.1') {
			mysql_query("SET sql_mode=''", $this->link);
        }
		if($this->dbinfo['dbname']) {
			if (!@mysql_select_db($this->dbinfo['dbname'], $this->link)) $this->_halt('无法链接数据库 "'.$this->dbinfo['dbname'].'",可能该数据库被删除');
        }
	}

	/**
	 * 选择一个数据库
	 *
	 * @param string $dbname 数据库名
	 */
	function select_db($dbname) {
		$this->dbinfo['dbname'] = $dbname;
		if (!@mysql_select_db($dbname, $this->link)) 
			$this->_halt('无法链接数据库 '.$dbname.'<br>可能该数据库被删除！');
	}

	/**
	 * 查询数据库版本信息
	 *
	 * @return string
	 */
	function version() {
		return mysql_get_server_info();
	}

	/**
	 * Ping数据库，如果无法ping通，就重连数据库
	 *
	 * @return string
	 */
    function ping() {
        if(!mysql_ping($this->link)) {
            $this->close(); //注意：一定要先执行数据库关闭，这是关键
            $this->connect();
        }
    }

	/**
	 * 发送一条 MySQL 查询
	 *
	 * @param string $SQL SQL语法 
     * @param string $method 查询方式 [空=自动获取并缓存结果集] [unbuffer=并不获取和缓存结果的行]
	 * @return tj_mysql_result 资源标识符
	 */
	function & query($SQL, $method = '') {
        if(DEBUG) {
			$mtime = explode(' ', microtime());
			$starttime = $mtime[1] + $mtime[0];
            $this->sqls[] = 'Query' . ($this->query_num+1) . ':' . $SQL;
        }
        if($this->dbinfo['ping']) $this->ping();
        if($method == 'unbuffer' && function_exists('mysql_unbuffered_query')) {
			$query = mysql_unbuffered_query($SQL, $this->link);
		} else {
			
			$query = mysql_query($SQL, $this->link);
			
        }
		if (!$query && $method != 'SILENT') {
            $this->_halt('MySQL Query Error: ' . $SQL);
        }
        $this->query_num++;
        if(DEBUG) {
            $mtime = explode(' ', microtime());
            $querytime = number_format(($mtime[1] + $mtime[0] - $starttime), 6) ;
            $this->sqls[] = 'Time:'.$querytime;
			if(strtolower(substr($SQL,0,7)) == 'select ' && $this->link) {
                if($result = mysql_query('EXPLAIN '.$SQL, $this->link)) {
                    $explain = mysql_fetch_assoc($result);
                    $table = '';
                    if($explain) {
                        $table = '<table border="1" cellspacing="1" cellpadding="1"><tr>';
                        foreach(array_keys($explain) as $key) {
                            $table .= "<td>$key</td>";
                        }
                        $table  .= '</tr><tr>';
                        foreach($explain as $key=>$val) {
                            $table .= "<td>$val</td>";
                        }
                        $table  .= '</tr></table>';
                    }
                }
			}
            $this->sqls[] = $table;
        }
        if(!is_resource($query)) return;
        if(mysql_num_rows($query)) {
			
            $result = new tj_mysql_result($query);
        } else {
			
            $result = FALSE;
        }
		
		
        return $result;
	}
	
	/*
	 *发送c查询语句
	 */
	 
	function cquery($sql){
		$result = mysql_query($sql,$this->link);
		$queryCount++;
		if (!$result){
			$this->_halt("SQL语句执行错误：$sql <br />");
		}else{
			return $result;
		}
	}
	
	/**
	 * 执行一条 MySQL 查询
	 *
	 * @param string $SQL SQL语法 
	 * @param string $method 查询方式 [空=自动获取并缓存结果集] [unbuffer=并不获取和缓存结果的行]
	 * @return resource 资源标识符
	 */
    function exec($SQL, $method = '') {
        if(DEBUG) {
            $mtime = explode(' ', microtime());
			$starttime = $mtime[1] + $mtime[0];
            $this->sqls[] = 'Exec ' . ($this->query_num+1) . ':' . $SQL;
        }
        if($this->dbinfo['ping']) $this->ping();
        if($method == 'unbuffer' && function_exists('mysql_unbuffered_query')) {
			$query = mysql_unbuffered_query($SQL, $this->link);
		} else {
			$query = mysql_query($SQL, $this->link);
        }
		if (!$query && $method != 'SILENT') {
            $this->_halt('MySQL Query Error: ' . $SQL);
        }
        $this->query_num++;
        if(DEBUG) {
            $mtime = explode(' ', microtime());
            $querytime = number_format(($mtime[1] + $mtime[0] - $starttime), 6) ;
            $this->sqls[] = 'Time:'.$querytime;
        }
        return $query;
    }

    /**
     * 返回上一次执行SQL后，被影响修改的条(行)数
     *
     * @return int
     */
	function affected_rows() {
		return mysql_affected_rows($this->link);
	}

	/**
	 * 取得上一步 INSERT 操作产生的 ID 
	 *
	 * @return int
	 */
	function insert_id() {
		return ($id = mysql_insert_id($this->link)) >= 0 ? $id : $this->result($this->query("SELECT last_insert_id()"), 0);
	}

	/**
	 * 关闭 MySQL 连
	 *
	 * @return bool
	 */
	function close() {
		return mysql_close($this->link);
	}

	/**
	 * 返回上一个 MySQL 操作产生的文本错误信息
	 *
	 * @return string
	 */
    function error() {
        return (($this->link) ? mysql_error($this->link) : mysql_error());
    }

    /**
     * 返回上一个 MySQL 操作中的错误信息的数字编码 
     *
     * @return integer
     */
    function errno() {
        return intval(($this->link) ? mysql_errno($this->link) : mysql_errno());
    }

    /**
     * 对字符串处理加入引号 
     *
     * @param string $str
     * @return string
     */
	function _escape_str($str) {
		if (function_exists('mysql_escape_string')) {
			return mysql_escape_string($str);
		} else {
			return addslashes($str);
		}
	}

    /**
     * 过滤字段名 
     *
     * @param string $field
     * @return string
     */
	 
    function _ck_field($field) {
		
        if(preg_match("/[\'\\\"\<\>]+/", $field)) {
            show_error(lang('global_sql_invalid_field', $field));
        }
		
        return $field;
    }

    /**
     * 显示错误信息 
     *
     * @param string $msg
     */
		function _halt($msg,$button='>>点击返回<<',$url='javascript:history.back(-1);', $debug=true){

		if($debug){
	echo 
<<<EOT
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>TuntronJxt 提示</title>
<style type="text/css">
<!--
body {
font-family: Arial;
font-size: 12px;
line-height:150%;
text-align:center;
}
a{color:#555555;}
.main {
width:500px;
background-color:#FFFFFF;
font-size: 12px;
color: #666666;
margin:100px auto 0;
list-style:none;
padding:20px;
background-color: #DDF4FB;
	border-color: #C6EDF9;
	color: #404040;
	text-shadow: 0 1px 0 rgba(255, 255, 255, 0.5);
	border: solid 1px #C6EDF9;
	text-shadow: 0 1px 0 white;
border-radius: 2px;
-webkit-border-radius: 2px;
-moz-border-radius: 2px;
}
.main p {
line-height: 18px;
margin: 5px 20px;
font-size:14px;
}
.main .info {
}
.main .but {
color: #646464;
font: 12px Helvetica, Arial, sans-serif;
text-decoration: none;
padding: 7px 17px;
position: relative;
display: inline-block;
text-shadow: 0 1px 0 white;
background: #F3F3F3;
background: -webkit-gradient(linear,0% 40%,0% 70%,from(whiteSmoke),to(#F1F1F1));
background: -moz-linear-gradient(linear,0% 40%,0% 70%,from(whiteSmoke),to(#F1F1F1));
border: solid 1px gainsboro;
border-radius: 2px;
-webkit-border-radius: 2px;
-moz-border-radius: 2px;
}
-->
</style>
</head>
<body>
<div class="main">
<p class="info">$msg</p>
<p><a href="$url" class="but">$button</a></p>
</div>
</body>
</html>
EOT;
	exit;
		}
	}

    /**
     * 显示SQL查询记录 
     *
     */
	function debug_print() {
		global $_G;
        if(!$this->sqls) return;
		$style = 'margin:5px auto;width:98%;line-height:18px;font-family:Courier New;text-align:left;background:#eee;border-width:1px; border-style:solid;border-color:#CCC;';
		$content ='<div style="'.$style.'">';
        $content .='<h3 style="font-size:16px;border-bottom:1px solid #FF9900;margin:5px;padding:0 0 5px;"><a href="javascript:;" onclick="$(\'#debug_sql_history\').toggle();">SQL History</a> ('.count($this->sqls).')</h3>';
		$content .= '<ul style="margin:0;padding:0 0 5px;list-style:none;" id="debug_sql_history">';
		foreach($this->sqls as $val) {
			$content .= '<li style="padding:1px 8px;font-size:12px;">' . $val . '</li>';
		}
		$content .= '</ul></div>';

		return $content;
	}
}

