PageRenderTime 46ms CodeModel.GetById 18ms RepoModel.GetById 0ms app.codeStats 0ms

/extras/installer-ftp/lib/Curaga/class/DB/Ethna_DB_PEAR.php

http://xoopscube-modules.googlecode.com/
PHP | 540 lines | 272 code | 53 blank | 215 comment | 51 complexity | 141542885df1719b996136818c11e4ec MD5 | raw file
Possible License(s): GPL-2.0, LGPL-2.1, AGPL-1.0
  1. <?php
  2. // vim: foldmethod=marker
  3. /**
  4. * Ethna_DB_PEAR.php
  5. *
  6. * @author Masaki Fujimoto <fujimoto@php.net>
  7. * @license http://www.opensource.org/licenses/bsd-license.php The BSD License
  8. * @package Ethna
  9. * @version $Id: Ethna_DB_PEAR.php 530 2008-05-12 12:50:34Z mumumu-org $
  10. */
  11. require_once 'DB.php';
  12. // {{{ Ethna_DB_PEAR
  13. /**
  14. * Ethna_DB??????(PEAR?)
  15. *
  16. * @author Masaki Fujimoto <fujimoto@php.net>
  17. * @access public
  18. * @package Ethna
  19. */
  20. class Ethna_DB_PEAR extends Ethna_DB
  21. {
  22. // {{{ properties
  23. /**#@+
  24. * @access private
  25. */
  26. /** @var object DB PEAR DB?????? */
  27. var $db;
  28. /** @var array ?????????????? */
  29. var $transaction = array();
  30. /** @var object Ethna_Logger ???????? */
  31. var $logger;
  32. /** @var object Ethna_AppSQL SQL?????? */
  33. var $sql;
  34. /** @var string DB???(mysql, pgsql...) */
  35. var $type;
  36. /** @var string DSN */
  37. var $dsn;
  38. /** @var array DSN (DB::parseDSN()????) */
  39. var $dsninfo;
  40. /** @var bool ??????? */
  41. var $persistent;
  42. /**#@-*/
  43. // }}}
  44. // {{{ Ethna_DB??????
  45. // {{{ Ethna_DB_PEAR
  46. /**
  47. * Ethna_DB_PEAR???????????
  48. *
  49. * @access public
  50. * @param object Ethna_Controller &$controller ????????????
  51. * @param string $dsn DSN
  52. * @param bool $persistent ??????
  53. */
  54. function Ethna_DB_PEAR(&$controller, $dsn, $persistent)
  55. {
  56. parent::Ethna_DB($controller, $dsn, $persistent);
  57. $this->db = null;
  58. $this->logger =& $controller->getLogger();
  59. $this->sql =& $controller->getSQL();
  60. $this->dsninfo = DB::parseDSN($dsn);
  61. $this->dsninfo['new_link'] = true;
  62. $this->type = $this->dsninfo['phptype'];
  63. }
  64. // }}}
  65. // {{{ connect
  66. /**
  67. * DB?????
  68. *
  69. * @access public
  70. * @return mixed 0:???? Ethna_Error:???
  71. */
  72. function connect()
  73. {
  74. $this->db =& DB::connect($this->dsninfo, $this->persistent);
  75. if (DB::isError($this->db)) {
  76. $error = Ethna::raiseError('DB Connection Error: %s',
  77. E_DB_CONNECT,
  78. $this->db->getUserInfo());
  79. $error->addUserInfo($this->db);
  80. $this->db = null;
  81. return $error;
  82. }
  83. return 0;
  84. }
  85. // }}}
  86. // {{{ disconnect
  87. /**
  88. * DB???????
  89. *
  90. * @access public
  91. */
  92. function disconnect()
  93. {
  94. if ($this->isValid() == false) {
  95. return;
  96. }
  97. $this->db->disconnect();
  98. }
  99. // }}}
  100. // {{{ isValid
  101. /**
  102. * DB???????
  103. *
  104. * @access public
  105. * @return bool true:?? false:???
  106. */
  107. function isValid()
  108. {
  109. if (is_null($this->db)
  110. || is_resource($this->db->connection) == false) {
  111. return false;
  112. } else {
  113. return true;
  114. }
  115. }
  116. // }}}
  117. // {{{ begin
  118. /**
  119. * DB?????????????
  120. *
  121. * @access public
  122. * @return mixed 0:???? Ethna_Error:???
  123. */
  124. function begin()
  125. {
  126. if (count($this->transaction) > 0) {
  127. $this->transaction[] = true;
  128. return 0;
  129. }
  130. $r = $this->query('BEGIN;');
  131. if (Ethna::isError($r)) {
  132. return $r;
  133. }
  134. $this->transaction[] = true;
  135. return 0;
  136. }
  137. // }}}
  138. // {{{ rollback
  139. /**
  140. * DB?????????????
  141. *
  142. * @access public
  143. * @return mixed 0:???? Ethna_Error:???
  144. */
  145. function rollback()
  146. {
  147. if (count($this->transaction) == 0) {
  148. return 0;
  149. }
  150. // ????????????????????????????????
  151. $r = $this->query('ROLLBACK;');
  152. if (Ethna::isError($r)) {
  153. return $r;
  154. }
  155. $this->transaction = array();
  156. return 0;
  157. }
  158. // }}}
  159. // {{{ commit
  160. /**
  161. * DB?????????????
  162. *
  163. * @access public
  164. * @return mixed 0:???? Ethna_Error:???
  165. */
  166. function commit()
  167. {
  168. if (count($this->transaction) == 0) {
  169. return 0;
  170. } else if (count($this->transaction) > 1) {
  171. array_pop($this->transaction);
  172. return 0;
  173. }
  174. $r = $this->query('COMMIT;');
  175. if (Ethna::isError($r)) {
  176. return $r;
  177. }
  178. array_pop($this->transaction);
  179. return 0;
  180. }
  181. // }}}
  182. // {{{ getMetaData
  183. /**
  184. * ?????????????
  185. *
  186. * @access public
  187. * @param string $table ?????
  188. * @return mixed array: PEAR::DB????????? Ethna_Error::???
  189. */
  190. function &getMetaData($table)
  191. {
  192. $def =& $this->db->tableInfo($table);
  193. if (is_array($def) === false) {
  194. return $def;
  195. }
  196. foreach (array_keys($def) as $k) {
  197. $def[$k] = array_map('strtolower', $def[$k]);
  198. // type
  199. $type_map = array(
  200. 'int' => array(
  201. 'int', 'integer', '^int\(?[0-9]\+', '^serial', '[a-z]+int$',
  202. ),
  203. 'boolean' => array(
  204. 'bit', 'bool', 'boolean',
  205. ),
  206. 'datetime' => array(
  207. 'timestamp', 'datetime',
  208. ),
  209. );
  210. foreach ($type_map as $convert_to => $regex) {
  211. foreach ($regex as $r) {
  212. if (preg_match('/'.$r.'/', $def[$k]['type'])) {
  213. $def[$k]['type'] = $convert_to;
  214. break 2;
  215. }
  216. }
  217. }
  218. // flags
  219. $def[$k]['flags'] = explode(' ', $def[$k]['flags']);
  220. switch ($this->type) {
  221. case 'mysql':
  222. // auto_increment ???? sequence
  223. if (in_array('auto_increment', $def[$k]['flags'])) {
  224. $def[$k]['flags'][] = 'sequence';
  225. }
  226. break;
  227. case 'pgsql':
  228. // nextval ???? sequence
  229. foreach ($def[$k]['flags'] as $f) {
  230. if (strpos($f, 'nextval') !== false) {
  231. $def[$k]['flags'][] = 'sequence';
  232. break;
  233. }
  234. }
  235. break;
  236. case 'sqlite':
  237. // integer, primary key ??? auto_increment ???
  238. if ($def[$k]['type'] == 'int'
  239. && in_array('primary_key', $def[$k]['flags'])) {
  240. $def[$k]['flags'][] = 'sequence';
  241. }
  242. break;
  243. }
  244. }
  245. return $def;
  246. }
  247. // }}}
  248. // }}}
  249. // {{{ Ethna_AppObject????????
  250. // {{{ getType
  251. /**
  252. * DB??????
  253. *
  254. * @access public
  255. * @return string DB???
  256. */
  257. function getType()
  258. {
  259. return $this->type;
  260. }
  261. // }}}
  262. // {{{ query
  263. /**
  264. * ????????
  265. *
  266. * @access public
  267. * @param string $query SQL?
  268. * @return mixed DB_Result:???????? Ethna_Error:???
  269. */
  270. function &query($query)
  271. {
  272. return $this->_query($query);
  273. }
  274. // }}}
  275. // {{{ getNextId
  276. /**
  277. * ???INSERT???ID?????
  278. * (pgsql????)
  279. *
  280. * @access public
  281. * @return mixed int
  282. */
  283. function getNextId($table_name, $field_name)
  284. {
  285. if ($this->isValid() == false) {
  286. return null;
  287. } else if ($this->type == 'pgsql') {
  288. $seq_name = sprintf('%s_%s', $table_name, $field_name);
  289. $ret = $this->db->nextId($seq_name);
  290. return $ret;
  291. }
  292. return null;
  293. }
  294. // }}}
  295. // {{{ getInsertId
  296. /**
  297. * ???INSERT???ID?????
  298. * (mysql, sqlite????)
  299. *
  300. * @access public
  301. * @return mixed int:???INSERT????????ID null:?????
  302. */
  303. function getInsertId()
  304. {
  305. if ($this->isValid() == false) {
  306. return null;
  307. } else if ($this->type == 'mysql') {
  308. return mysql_insert_id($this->db->connection);
  309. } else if ($this->type == 'sqlite') {
  310. return sqlite_last_insert_rowid($this->db->connection);
  311. }
  312. return null;
  313. }
  314. // }}}
  315. // {{{ fetchRow
  316. /**
  317. * DB_Result::fetchRow()??????????
  318. *
  319. * @access public
  320. * @return int ????
  321. */
  322. function &fetchRow(&$res, $fetchmode = DB_FETCHMODE_DEFAULT, $rownum = null)
  323. {
  324. $row =& $res->fetchRow($fetchmode, $rownum);
  325. if (is_array($row) === false) {
  326. return $row;
  327. }
  328. if ($this->type === 'sqlite') {
  329. // "table"."column" -> column
  330. foreach ($row as $k => $v) {
  331. unset($row[$k]);
  332. if (($f = strstr($k, '.')) !== false) {
  333. $k = substr($f, 1);
  334. }
  335. if ($k{0} === '"' && $k{strlen($k)-1} === '"') {
  336. $k = substr($k, 1, -1);
  337. }
  338. $row[$k] = $v;
  339. }
  340. }
  341. return $row;
  342. }
  343. // }}}
  344. // {{{ affectedRows
  345. /**
  346. * ??????????????????
  347. *
  348. * @access public
  349. * @return int ????
  350. */
  351. function affectedRows()
  352. {
  353. return $this->db->affectedRows();
  354. }
  355. // }}}
  356. // {{{ quoteIdentifier
  357. /**
  358. * db?type????????quote??
  359. * (??????????quote)
  360. *
  361. * @access protected
  362. * @param mixed $identifier array or string
  363. */
  364. function quoteIdentifier($identifier)
  365. {
  366. if (is_array($identifier)) {
  367. foreach (array_keys($identifier) as $key) {
  368. $identifier[$key] = $this->quoteIdentifier($identifier[$key]);
  369. }
  370. return $identifier;
  371. }
  372. switch ($this->type) {
  373. case 'mysql':
  374. $ret = '`' . $identifier . '`';
  375. break;
  376. case 'pgsql':
  377. case 'sqlite':
  378. default:
  379. $ret = '"' . $identifier . '"';
  380. break;
  381. }
  382. return $ret;
  383. }
  384. // }}}
  385. // }}}
  386. // {{{ Ethna_DB_PEAR?????
  387. // {{{ sqlquery
  388. /**
  389. * SQL???????????
  390. *
  391. * @access public
  392. * @param string $sqlid SQL-ID(+??)
  393. * @return mixed DB_Result:???????? Ethna_Error:???
  394. */
  395. function &sqlquery($sqlid)
  396. {
  397. $args = func_get_args();
  398. array_shift($args);
  399. $query = $this->sql->get($sqlid, $args);
  400. return $this->_query($query);
  401. }
  402. // }}}
  403. // {{{ sql
  404. /**
  405. * SQL??????
  406. *
  407. * @access public
  408. * @param string $sqlid SQL-ID
  409. * @return string SQL?
  410. */
  411. function sql($sqlid)
  412. {
  413. $args = func_get_args();
  414. array_shift($args);
  415. $query = $this->sql->get($sqlid, $args);
  416. return $query;
  417. }
  418. // }}}
  419. // {{{ lock
  420. /**
  421. * ??????????
  422. *
  423. * @access public
  424. * @param mixed ??????????
  425. * @return mixed DB_Result:???????? Ethna_Error:???
  426. */
  427. function lock($tables)
  428. {
  429. $this->message = null;
  430. $sql = "";
  431. foreach (to_array($tables) as $table) {
  432. if ($sql != "") {
  433. $sql .= ", ";
  434. }
  435. $sql .= "$table WRITE";
  436. }
  437. return $this->query("LOCK TABLES $sql");
  438. }
  439. // }}}
  440. // {{{ unlock
  441. /**
  442. * ?????????????
  443. *
  444. * @access public
  445. * @return mixed DB_Result:???????? Ethna_Error:???
  446. */
  447. function unlock()
  448. {
  449. $this->message = null;
  450. return $this->query("UNLOCK TABLES");
  451. }
  452. // }}}
  453. // {{{ _query
  454. /**
  455. * ????????
  456. *
  457. * @access private
  458. * @param string $query SQL?
  459. * @return mixed DB_Result:???????? Ethna_Error:???
  460. */
  461. function &_query($query)
  462. {
  463. $this->logger->log(LOG_DEBUG, "$query");
  464. $r =& $this->db->query($query);
  465. if (DB::isError($r)) {
  466. if ($r->getCode() == DB_ERROR_ALREADY_EXISTS) {
  467. $error = Ethna::raiseNotice('Unique Constraint Error SQL[%s]',
  468. E_DB_DUPENT,
  469. $query,
  470. $this->db->errorNative(),
  471. $r->getUserInfo());
  472. } else {
  473. $error = Ethna::raiseError('Query Error SQL[%s] CODE[%d] MESSAGE[%s]',
  474. E_DB_QUERY,
  475. $query,
  476. $this->db->errorNative(),
  477. $r->getUserInfo());
  478. }
  479. return $error;
  480. }
  481. return $r;
  482. }
  483. // }}}
  484. // }}}
  485. }
  486. // }}}
  487. ?>