PageRenderTime 38ms CodeModel.GetById 11ms RepoModel.GetById 1ms app.codeStats 0ms

/ThinkPHP/Lib/Driver/Db/DbMysql.class.php

http://thinkphp.googlecode.com/
PHP | 432 lines | 208 code | 18 blank | 206 comment | 44 complexity | 2999f08b80d8e5f60ca3df114c6d26af MD5 | raw file
Possible License(s): MPL-2.0-no-copyleft-exception
  1. <?php
  2. // +----------------------------------------------------------------------
  3. // | ThinkPHP [ WE CAN DO IT JUST THINK IT ]
  4. // +----------------------------------------------------------------------
  5. // | Copyright (c) 2006-2012 http://thinkphp.cn All rights reserved.
  6. // +----------------------------------------------------------------------
  7. // | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
  8. // +----------------------------------------------------------------------
  9. // | Author: liu21st <liu21st@gmail.com>
  10. // +----------------------------------------------------------------------
  11. // $Id: DbMysql.class.php 2929 2012-05-02 06:45:47Z liu21st@gmail.com $
  12. !defined('THINK_PATH') && exit();
  13. define('CLIENT_MULTI_RESULTS', 131072);
  14. /**
  15. +------------------------------------------------------------------------------
  16. * Mysql??????
  17. +------------------------------------------------------------------------------
  18. * @category Think
  19. * @package Think
  20. * @subpackage Db
  21. * @author liu21st <liu21st@gmail.com>
  22. * @version $Id: DbMysql.class.php 2929 2012-05-02 06:45:47Z liu21st@gmail.com $
  23. +------------------------------------------------------------------------------
  24. */
  25. class DbMysql extends Db{
  26. /**
  27. +----------------------------------------------------------
  28. * ???? ?????????
  29. +----------------------------------------------------------
  30. * @access public
  31. +----------------------------------------------------------
  32. * @param array $config ???????
  33. +----------------------------------------------------------
  34. */
  35. public function __construct($config=''){
  36. if ( !extension_loaded('mysql') ) {
  37. throw_exception(L('_NOT_SUPPERT_').':mysql');
  38. }
  39. if(!empty($config)) {
  40. $this->config = $config;
  41. if(empty($this->config['params'])) {
  42. $this->config['params'] = array();
  43. }
  44. }
  45. }
  46. /**
  47. +----------------------------------------------------------
  48. * ???????
  49. +----------------------------------------------------------
  50. * @access public
  51. +----------------------------------------------------------
  52. * @throws ThinkExecption
  53. +----------------------------------------------------------
  54. */
  55. public function connect($config='',$linkNum=0,$force=false) {
  56. if ( !isset($this->linkID[$linkNum]) ) {
  57. if(empty($config)) $config = $this->config;
  58. // ????????socket????
  59. $host = $config['hostname'].($config['hostport']?":{$config['hostport']}":'');
  60. // ?????
  61. $pconnect = !empty($config['params']['persist'])? $config['params']['persist']:$this->pconnect;
  62. if($pconnect) {
  63. $this->linkID[$linkNum] = mysql_pconnect( $host, $config['username'], $config['password'],CLIENT_MULTI_RESULTS);
  64. }else{
  65. $this->linkID[$linkNum] = mysql_connect( $host, $config['username'], $config['password'],true,CLIENT_MULTI_RESULTS);
  66. }
  67. if ( !$this->linkID[$linkNum] || (!empty($config['database']) && !mysql_select_db($config['database'], $this->linkID[$linkNum])) ) {
  68. throw_exception(mysql_error());
  69. }
  70. $dbVersion = mysql_get_server_info($this->linkID[$linkNum]);
  71. if ($dbVersion >= '4.1') {
  72. //??UTF8????? ??mysql 4.1.0????
  73. mysql_query("SET NAMES '".C('DB_CHARSET')."'", $this->linkID[$linkNum]);
  74. }
  75. //?? sql_model
  76. if($dbVersion >'5.0.1'){
  77. mysql_query("SET sql_mode=''",$this->linkID[$linkNum]);
  78. }
  79. // ??????
  80. $this->connected = true;
  81. // ???????????
  82. if(1 != C('DB_DEPLOY_TYPE')) unset($this->config);
  83. }
  84. return $this->linkID[$linkNum];
  85. }
  86. /**
  87. +----------------------------------------------------------
  88. * ??????
  89. +----------------------------------------------------------
  90. * @access public
  91. +----------------------------------------------------------
  92. */
  93. public function free() {
  94. mysql_free_result($this->queryID);
  95. $this->queryID = null;
  96. }
  97. /**
  98. +----------------------------------------------------------
  99. * ???? ?????
  100. +----------------------------------------------------------
  101. * @access public
  102. +----------------------------------------------------------
  103. * @param string $str sql??
  104. +----------------------------------------------------------
  105. * @return mixed
  106. +----------------------------------------------------------
  107. * @throws ThinkExecption
  108. +----------------------------------------------------------
  109. */
  110. public function query($str) {
  111. if(0===stripos($str, 'call')){ // ????????
  112. $this->close();
  113. }
  114. $this->initConnect(false);
  115. if ( !$this->_linkID ) return false;
  116. $this->queryStr = $str;
  117. //?????????
  118. if ( $this->queryID ) { $this->free(); }
  119. N('db_query',1);
  120. // ????????
  121. G('queryStartTime');
  122. $this->queryID = mysql_query($str, $this->_linkID);
  123. $this->debug();
  124. if ( false === $this->queryID ) {
  125. $this->error();
  126. return false;
  127. } else {
  128. $this->numRows = mysql_num_rows($this->queryID);
  129. return $this->getAll();
  130. }
  131. }
  132. /**
  133. +----------------------------------------------------------
  134. * ????
  135. +----------------------------------------------------------
  136. * @access public
  137. +----------------------------------------------------------
  138. * @param string $str sql??
  139. +----------------------------------------------------------
  140. * @return integer
  141. +----------------------------------------------------------
  142. * @throws ThinkExecption
  143. +----------------------------------------------------------
  144. */
  145. public function execute($str) {
  146. $this->initConnect(true);
  147. if ( !$this->_linkID ) return false;
  148. $this->queryStr = $str;
  149. //?????????
  150. if ( $this->queryID ) { $this->free(); }
  151. N('db_write',1);
  152. // ????????
  153. G('queryStartTime');
  154. $result = mysql_query($str, $this->_linkID) ;
  155. $this->debug();
  156. if ( false === $result) {
  157. $this->error();
  158. return false;
  159. } else {
  160. $this->numRows = mysql_affected_rows($this->_linkID);
  161. $this->lastInsID = mysql_insert_id($this->_linkID);
  162. return $this->numRows;
  163. }
  164. }
  165. /**
  166. +----------------------------------------------------------
  167. * ????
  168. +----------------------------------------------------------
  169. * @access public
  170. +----------------------------------------------------------
  171. * @return void
  172. +----------------------------------------------------------
  173. * @throws ThinkExecption
  174. +----------------------------------------------------------
  175. */
  176. public function startTrans() {
  177. $this->initConnect(true);
  178. if ( !$this->_linkID ) return false;
  179. //??rollback ??
  180. if ($this->transTimes == 0) {
  181. mysql_query('START TRANSACTION', $this->_linkID);
  182. }
  183. $this->transTimes++;
  184. return ;
  185. }
  186. /**
  187. +----------------------------------------------------------
  188. * ????????????????
  189. +----------------------------------------------------------
  190. * @access public
  191. +----------------------------------------------------------
  192. * @return boolen
  193. +----------------------------------------------------------
  194. * @throws ThinkExecption
  195. +----------------------------------------------------------
  196. */
  197. public function commit() {
  198. if ($this->transTimes > 0) {
  199. $result = mysql_query('COMMIT', $this->_linkID);
  200. $this->transTimes = 0;
  201. if(!$result){
  202. throw_exception($this->error());
  203. }
  204. }
  205. return true;
  206. }
  207. /**
  208. +----------------------------------------------------------
  209. * ????
  210. +----------------------------------------------------------
  211. * @access public
  212. +----------------------------------------------------------
  213. * @return boolen
  214. +----------------------------------------------------------
  215. * @throws ThinkExecption
  216. +----------------------------------------------------------
  217. */
  218. public function rollback() {
  219. if ($this->transTimes > 0) {
  220. $result = mysql_query('ROLLBACK', $this->_linkID);
  221. $this->transTimes = 0;
  222. if(!$result){
  223. throw_exception($this->error());
  224. }
  225. }
  226. return true;
  227. }
  228. /**
  229. +----------------------------------------------------------
  230. * ?????????
  231. +----------------------------------------------------------
  232. * @access private
  233. +----------------------------------------------------------
  234. * @return array
  235. +----------------------------------------------------------
  236. * @throws ThinkExecption
  237. +----------------------------------------------------------
  238. */
  239. private function getAll() {
  240. //?????
  241. $result = array();
  242. if($this->numRows >0) {
  243. while($row = mysql_fetch_assoc($this->queryID)){
  244. $result[] = $row;
  245. }
  246. mysql_data_seek($this->queryID,0);
  247. }
  248. return $result;
  249. }
  250. /**
  251. +----------------------------------------------------------
  252. * ??????????
  253. +----------------------------------------------------------
  254. * @access public
  255. +----------------------------------------------------------
  256. */
  257. public function getFields($tableName) {
  258. $result = $this->query('SHOW COLUMNS FROM '.$this->parseKey($tableName));
  259. $info = array();
  260. if($result) {
  261. foreach ($result as $key => $val) {
  262. $info[$val['Field']] = array(
  263. 'name' => $val['Field'],
  264. 'type' => $val['Type'],
  265. 'notnull' => (bool) ($val['Null'] === ''), // not null is empty, null is yes
  266. 'default' => $val['Default'],
  267. 'primary' => (strtolower($val['Key']) == 'pri'),
  268. 'autoinc' => (strtolower($val['Extra']) == 'auto_increment'),
  269. );
  270. }
  271. }
  272. return $info;
  273. }
  274. /**
  275. +----------------------------------------------------------
  276. * ?????????
  277. +----------------------------------------------------------
  278. * @access public
  279. +----------------------------------------------------------
  280. */
  281. public function getTables($dbName='') {
  282. if(!empty($dbName)) {
  283. $sql = 'SHOW TABLES FROM '.$dbName;
  284. }else{
  285. $sql = 'SHOW TABLES ';
  286. }
  287. $result = $this->query($sql);
  288. $info = array();
  289. foreach ($result as $key => $val) {
  290. $info[$key] = current($val);
  291. }
  292. return $info;
  293. }
  294. /**
  295. +----------------------------------------------------------
  296. * ????
  297. +----------------------------------------------------------
  298. * @access public
  299. +----------------------------------------------------------
  300. * @param mixed $data ??
  301. * @param array $options ?????
  302. +----------------------------------------------------------
  303. * @return false | integer
  304. +----------------------------------------------------------
  305. */
  306. public function replace($data,$options=array()) {
  307. foreach ($data as $key=>$val){
  308. $value = $this->parseValue($val);
  309. if(is_scalar($value)) { // ???????
  310. $values[] = $value;
  311. $fields[] = $this->parseKey($key);
  312. }
  313. }
  314. $sql = 'REPLACE INTO '.$this->parseTable($options['table']).' ('.implode(',', $fields).') VALUES ('.implode(',', $values).')';
  315. return $this->execute($sql);
  316. }
  317. /**
  318. +----------------------------------------------------------
  319. * ????
  320. +----------------------------------------------------------
  321. * @access public
  322. +----------------------------------------------------------
  323. * @param mixed $datas ??
  324. * @param array $options ?????
  325. * @param boolean $replace ??replace
  326. +----------------------------------------------------------
  327. * @return false | integer
  328. +----------------------------------------------------------
  329. */
  330. public function insertAll($datas,$options=array(),$replace=false) {
  331. if(!is_array($datas[0])) return false;
  332. $fields = array_keys($datas[0]);
  333. array_walk($fields, array($this, 'parseKey'));
  334. $values = array();
  335. foreach ($datas as $data){
  336. $value = array();
  337. foreach ($data as $key=>$val){
  338. $val = $this->parseValue($val);
  339. if(is_scalar($val)) { // ???????
  340. $value[] = $val;
  341. }
  342. }
  343. $values[] = '('.implode(',', $value).')';
  344. }
  345. $sql = ($replace?'REPLACE':'INSERT').' INTO '.$this->parseTable($options['table']).' ('.implode(',', $fields).') VALUES '.implode(',',$values);
  346. return $this->execute($sql);
  347. }
  348. /**
  349. +----------------------------------------------------------
  350. * ?????
  351. +----------------------------------------------------------
  352. * @access public
  353. +----------------------------------------------------------
  354. */
  355. public function close() {
  356. if ($this->_linkID){
  357. mysql_close($this->_linkID);
  358. }
  359. $this->_linkID = null;
  360. }
  361. /**
  362. +----------------------------------------------------------
  363. * ???????
  364. * ??????SQL??
  365. +----------------------------------------------------------
  366. * @access public
  367. +----------------------------------------------------------
  368. * @return string
  369. +----------------------------------------------------------
  370. */
  371. public function error() {
  372. $this->error = mysql_error($this->_linkID);
  373. if($this->debug && '' != $this->queryStr){
  374. $this->error .= "\n [ SQL?? ] : ".$this->queryStr;
  375. }
  376. return $this->error;
  377. }
  378. /**
  379. +----------------------------------------------------------
  380. * SQL??????
  381. +----------------------------------------------------------
  382. * @access public
  383. +----------------------------------------------------------
  384. * @param string $str SQL???
  385. +----------------------------------------------------------
  386. * @return string
  387. +----------------------------------------------------------
  388. */
  389. public function escapeString($str) {
  390. if($this->_linkID) {
  391. return mysql_real_escape_string($str,$this->_linkID);
  392. }else{
  393. return mysql_escape_string($str);
  394. }
  395. }
  396. /**
  397. +----------------------------------------------------------
  398. * ?????????`
  399. +----------------------------------------------------------
  400. * @access protected
  401. +----------------------------------------------------------
  402. * @param string $key
  403. +----------------------------------------------------------
  404. * @return string
  405. +----------------------------------------------------------
  406. */
  407. protected function parseKey(&$key) {
  408. $key = trim($key);
  409. if(!preg_match('/[,\'\"\*\(\)`.\s]/',$key)) {
  410. $key = '`'.$key.'`';
  411. }
  412. return $key;
  413. }
  414. }