PageRenderTime 48ms CodeModel.GetById 16ms RepoModel.GetById 0ms app.codeStats 0ms

/protected/extensions/elfinder/php/elFinderVolumeMySQL.class.php

https://bitbucket.org/rohitrox/hotc
PHP | 896 lines | 556 code | 93 blank | 247 comment | 65 complexity | 1a0ff9589f1df929abb2396eed418040 MD5 | raw file
Possible License(s): MIT
  1. <?php
  2. /**
  3. * Simple elFinder driver for MySQL.
  4. *
  5. * @author Dmitry (dio) Levashov
  6. **/
  7. class elFinderVolumeMySQL extends elFinderVolumeDriver {
  8. /**
  9. * Driver id
  10. * Must be started from letter and contains [a-z0-9]
  11. * Used as part of volume id
  12. *
  13. * @var string
  14. **/
  15. protected $driverId = 'm';
  16. /**
  17. * Database object
  18. *
  19. * @var mysqli
  20. **/
  21. protected $db = null;
  22. /**
  23. * Tables to store files
  24. *
  25. * @var string
  26. **/
  27. protected $tbf = '';
  28. /**
  29. * Directory for tmp files
  30. * If not set driver will try to use tmbDir as tmpDir
  31. *
  32. * @var string
  33. **/
  34. protected $tmpPath = '';
  35. /**
  36. * Numbers of sql requests (for debug)
  37. *
  38. * @var int
  39. **/
  40. protected $sqlCnt = 0;
  41. /**
  42. * Last db error message
  43. *
  44. * @var string
  45. **/
  46. protected $dbError = '';
  47. /**
  48. * Constructor
  49. * Extend options with required fields
  50. *
  51. * @return void
  52. * @author Dmitry (dio) Levashov
  53. **/
  54. public function __construct() {
  55. $opts = array(
  56. 'host' => 'localhost',
  57. 'user' => '',
  58. 'pass' => '',
  59. 'db' => '',
  60. 'port' => null,
  61. 'socket' => null,
  62. 'files_table' => 'elfinder_file',
  63. 'tmbPath' => '',
  64. 'tmpPath' => ''
  65. );
  66. $this->options = array_merge($this->options, $opts);
  67. $this->options['mimeDetect'] = 'internal';
  68. }
  69. /*********************************************************************/
  70. /* INIT AND CONFIGURE */
  71. /*********************************************************************/
  72. /**
  73. * Prepare driver before mount volume.
  74. * Connect to db, check required tables and fetch root path
  75. *
  76. * @return bool
  77. * @author Dmitry (dio) Levashov
  78. **/
  79. protected function init() {
  80. if (!($this->options['host'] || $this->options['socket'])
  81. || !$this->options['user']
  82. || !$this->options['pass']
  83. || !$this->options['db']
  84. || !$this->options['path']
  85. || !$this->options['files_table']) {
  86. return false;
  87. }
  88. $this->db = new mysqli($this->options['host'], $this->options['user'], $this->options['pass'], $this->options['db'], $this->options['port'], $this->options['socket']);
  89. if ($this->db->connect_error || @mysqli_connect_error()) {
  90. return false;
  91. }
  92. $this->db->set_charset('utf8');
  93. if ($res = $this->db->query('SHOW TABLES')) {
  94. while ($row = $res->fetch_array()) {
  95. if ($row[0] == $this->options['files_table']) {
  96. $this->tbf = $this->options['files_table'];
  97. break;
  98. }
  99. }
  100. }
  101. if (!$this->tbf) {
  102. return false;
  103. }
  104. $this->updateCache($this->options['path'], $this->_stat($this->options['path']));
  105. return true;
  106. }
  107. /**
  108. * Set tmp path
  109. *
  110. * @return void
  111. * @author Dmitry (dio) Levashov
  112. **/
  113. protected function configure() {
  114. parent::configure();
  115. if (($tmp = $this->options['tmpPath'])) {
  116. if (!file_exists($tmp)) {
  117. if (@mkdir($tmp)) {
  118. @chmod($tmp, $this->options['tmbPathMode']);
  119. }
  120. }
  121. $this->tmpPath = is_dir($tmp) && is_writable($tmp) ? $tmp : false;
  122. }
  123. if (!$this->tmpPath && $this->tmbPath && $this->tmbPathWritable) {
  124. $this->tmpPath = $this->tmbPath;
  125. }
  126. $this->mimeDetect = 'internal';
  127. }
  128. /**
  129. * Close connection
  130. *
  131. * @return void
  132. * @author Dmitry (dio) Levashov
  133. **/
  134. public function umount() {
  135. $this->db->close();
  136. }
  137. /**
  138. * Return debug info for client
  139. *
  140. * @return array
  141. * @author Dmitry (dio) Levashov
  142. **/
  143. public function debug() {
  144. $debug = parent::debug();
  145. $debug['sqlCount'] = $this->sqlCnt;
  146. if ($this->dbError) {
  147. $debug['dbError'] = $this->dbError;
  148. }
  149. return $debug;
  150. }
  151. /**
  152. * Perform sql query and return result.
  153. * Increase sqlCnt and save error if occured
  154. *
  155. * @param string $sql query
  156. * @return misc
  157. * @author Dmitry (dio) Levashov
  158. **/
  159. protected function query($sql) {
  160. $this->sqlCnt++;
  161. $res = $this->db->query($sql);
  162. if (!$res) {
  163. $this->dbError = $this->db->error;
  164. }
  165. return $res;
  166. }
  167. /**
  168. * Create empty object with required mimetype
  169. *
  170. * @param string $path parent dir path
  171. * @param string $name object name
  172. * @param string $mime mime type
  173. * @return bool
  174. * @author Dmitry (dio) Levashov
  175. **/
  176. protected function make($path, $name, $mime) {
  177. $sql = 'INSERT INTO %s (`parent_id`, `name`, `size`, `mtime`, `mime`, `content`, `read`, `write`) VALUES ("%s", "%s", 0, %d, "%s", "", "%d", "%d")';
  178. $sql = sprintf($sql, $this->tbf, $path, $this->db->real_escape_string($name), time(), $mime, $this->defaults['read'], $this->defaults['write']);
  179. // echo $sql;
  180. return $this->query($sql) && $this->db->affected_rows > 0;
  181. }
  182. /**
  183. * Return temporary file path for required file
  184. *
  185. * @param string $path file path
  186. * @return string
  187. * @author Dmitry (dio) Levashov
  188. **/
  189. protected function tmpname($path) {
  190. return $this->tmpPath.DIRECTORY_SEPARATOR.md5($path);
  191. }
  192. /**
  193. * Resize image
  194. *
  195. * @param string $hash image file
  196. * @param int $width new width
  197. * @param int $height new height
  198. * @param bool $crop crop image
  199. * @return array|false
  200. * @author Dmitry (dio) Levashov
  201. * @author Alexey Sukhotin
  202. **/
  203. public function resize($hash, $width, $height, $x, $y, $mode = 'resize', $bg = '', $degree = 0) {
  204. if ($this->commandDisabled('resize')) {
  205. return $this->setError(elFinder::ERROR_PERM_DENIED);
  206. }
  207. if (($file = $this->file($hash)) == false) {
  208. return $this->setError(elFinder::ERROR_FILE_NOT_FOUND);
  209. }
  210. if (!$file['write'] || !$file['read']) {
  211. return $this->setError(elFinder::ERROR_PERM_DENIED);
  212. }
  213. $path = $this->decode($hash);
  214. if (!$this->canResize($path, $file)) {
  215. return $this->setError(elFinder::ERROR_UNSUPPORT_TYPE);
  216. }
  217. $img = $this->tmpname($path);
  218. if (!($fp = @fopen($img, 'w+'))) {
  219. return false;
  220. }
  221. if (($res = $this->query('SELECT content FROM '.$this->tbf.' WHERE id="'.$path.'"'))
  222. && ($r = $res->fetch_assoc())) {
  223. fwrite($fp, $r['content']);
  224. rewind($fp);
  225. fclose($fp);
  226. } else {
  227. return false;
  228. }
  229. switch($mode) {
  230. case 'propresize':
  231. $result = $this->imgResize($img, $width, $height, true, true);
  232. break;
  233. case 'crop':
  234. $result = $this->imgCrop($img, $width, $height, $x, $y);
  235. break;
  236. case 'fitsquare':
  237. $result = $this->imgSquareFit($img, $width, $height, 'center', 'middle', $bg ? $bg : $this->options['tmbBgColor']);
  238. break;
  239. default:
  240. $result = $this->imgResize($img, $width, $height, false, true);
  241. break;
  242. }
  243. if ($result) {
  244. $sql = sprintf('UPDATE %s SET content=LOAD_FILE("%s"), mtime=UNIX_TIMESTAMP() WHERE id=%d', $this->tbf, $this->loadFilePath($img), $path);
  245. if (!$this->query($sql)) {
  246. $content = file_get_contents($img);
  247. $sql = sprintf('UPDATE %s SET content="%s", mtime=UNIX_TIMESTAMP() WHERE id=%d', $this->tbf, $this->db->real_escape_string($content), $path);
  248. if (!$this->query($sql)) {
  249. @unlink($img);
  250. return false;
  251. }
  252. }
  253. @unlink($img);
  254. if (!empty($file['tmb']) && $file['tmb'] != "1") {
  255. $this->rmTmb($file['tmb']);
  256. }
  257. $this->clearcache();
  258. return $this->stat($path);
  259. }
  260. return false;
  261. }
  262. /*********************************************************************/
  263. /* FS API */
  264. /*********************************************************************/
  265. /**
  266. * Cache dir contents
  267. *
  268. * @param string $path dir path
  269. * @return void
  270. * @author Dmitry Levashov
  271. **/
  272. protected function cacheDir($path) {
  273. $this->dirsCache[$path] = array();
  274. $sql = 'SELECT f.id, f.parent_id, f.name, f.size, f.mtime AS ts, f.mime, f.read, f.write, f.locked, f.hidden, f.width, f.height, IF(ch.id, 1, 0) AS dirs
  275. FROM '.$this->tbf.' AS f
  276. LEFT JOIN '.$this->tbf.' AS ch ON ch.parent_id=f.id AND ch.mime="directory"
  277. WHERE f.parent_id="'.$path.'"
  278. GROUP BY f.id';
  279. $res = $this->query($sql);
  280. if ($res) {
  281. while ($row = $res->fetch_assoc()) {
  282. // debug($row);
  283. $id = $row['id'];
  284. if ($row['parent_id']) {
  285. $row['phash'] = $this->encode($row['parent_id']);
  286. }
  287. if ($row['mime'] == 'directory') {
  288. unset($row['width']);
  289. unset($row['height']);
  290. } else {
  291. unset($row['dirs']);
  292. }
  293. unset($row['id']);
  294. unset($row['parent_id']);
  295. if (($stat = $this->updateCache($id, $row)) && empty($stat['hidden'])) {
  296. $this->dirsCache[$path][] = $id;
  297. }
  298. }
  299. }
  300. return $this->dirsCache[$path];
  301. }
  302. /**
  303. * Return array of parents paths (ids)
  304. *
  305. * @param int $path file path (id)
  306. * @return array
  307. * @author Dmitry (dio) Levashov
  308. **/
  309. protected function getParents($path) {
  310. $parents = array();
  311. while ($path) {
  312. if ($file = $this->stat($path)) {
  313. array_unshift($parents, $path);
  314. $path = isset($file['phash']) ? $this->decode($file['phash']) : false;
  315. }
  316. }
  317. if (count($parents)) {
  318. array_pop($parents);
  319. }
  320. return $parents;
  321. }
  322. /**
  323. * Return correct file path for LOAD_FILE method
  324. *
  325. * @param string $path file path (id)
  326. * @return string
  327. * @author Troex Nevelin
  328. **/
  329. protected function loadFilePath($path) {
  330. $realPath = realpath($path);
  331. if (DIRECTORY_SEPARATOR == '\\') { // windows
  332. $realPath = str_replace('\\', '\\\\', $realPath);
  333. }
  334. return $this->db->real_escape_string($realPath);
  335. }
  336. /*********************** paths/urls *************************/
  337. /**
  338. * Return parent directory path
  339. *
  340. * @param string $path file path
  341. * @return string
  342. * @author Dmitry (dio) Levashov
  343. **/
  344. protected function _dirname($path) {
  345. return ($stat = $this->stat($path)) ? ($stat['phash'] ? $this->decode($stat['phash']) : $this->root) : false;
  346. }
  347. /**
  348. * Return file name
  349. *
  350. * @param string $path file path
  351. * @return string
  352. * @author Dmitry (dio) Levashov
  353. **/
  354. protected function _basename($path) {
  355. return ($stat = $this->stat($path)) ? $stat['name'] : false;
  356. }
  357. /**
  358. * Join dir name and file name and return full path
  359. *
  360. * @param string $dir
  361. * @param string $name
  362. * @return string
  363. * @author Dmitry (dio) Levashov
  364. **/
  365. protected function _joinPath($dir, $name) {
  366. $sql = 'SELECT id FROM '.$this->tbf.' WHERE parent_id="'.$dir.'" AND name="'.$this->db->real_escape_string($name).'"';
  367. if (($res = $this->query($sql)) && ($r = $res->fetch_assoc())) {
  368. $this->updateCache($r['id'], $this->_stat($r['id']));
  369. return $r['id'];
  370. }
  371. return -1;
  372. }
  373. /**
  374. * Return normalized path, this works the same as os.path.normpath() in Python
  375. *
  376. * @param string $path path
  377. * @return string
  378. * @author Troex Nevelin
  379. **/
  380. protected function _normpath($path) {
  381. return $path;
  382. }
  383. /**
  384. * Return file path related to root dir
  385. *
  386. * @param string $path file path
  387. * @return string
  388. * @author Dmitry (dio) Levashov
  389. **/
  390. protected function _relpath($path) {
  391. return $path;
  392. }
  393. /**
  394. * Convert path related to root dir into real path
  395. *
  396. * @param string $path file path
  397. * @return string
  398. * @author Dmitry (dio) Levashov
  399. **/
  400. protected function _abspath($path) {
  401. return $path;
  402. }
  403. /**
  404. * Return fake path started from root dir
  405. *
  406. * @param string $path file path
  407. * @return string
  408. * @author Dmitry (dio) Levashov
  409. **/
  410. protected function _path($path) {
  411. if (($file = $this->stat($path)) == false) {
  412. return '';
  413. }
  414. $parentsIds = $this->getParents($path);
  415. $path = '';
  416. foreach ($parentsIds as $id) {
  417. $dir = $this->stat($id);
  418. $path .= $dir['name'].$this->separator;
  419. }
  420. return $path.$file['name'];
  421. }
  422. /**
  423. * Return true if $path is children of $parent
  424. *
  425. * @param string $path path to check
  426. * @param string $parent parent path
  427. * @return bool
  428. * @author Dmitry (dio) Levashov
  429. **/
  430. protected function _inpath($path, $parent) {
  431. return $path == $parent
  432. ? true
  433. : in_array($parent, $this->getParents($path));
  434. }
  435. /***************** file stat ********************/
  436. /**
  437. * Return stat for given path.
  438. * Stat contains following fields:
  439. * - (int) size file size in b. required
  440. * - (int) ts file modification time in unix time. required
  441. * - (string) mime mimetype. required for folders, others - optionally
  442. * - (bool) read read permissions. required
  443. * - (bool) write write permissions. required
  444. * - (bool) locked is object locked. optionally
  445. * - (bool) hidden is object hidden. optionally
  446. * - (string) alias for symlinks - link target path relative to root path. optionally
  447. * - (string) target for symlinks - link target path. optionally
  448. *
  449. * If file does not exists - returns empty array or false.
  450. *
  451. * @param string $path file path
  452. * @return array|false
  453. * @author Dmitry (dio) Levashov
  454. **/
  455. protected function _stat($path) {
  456. $sql = 'SELECT f.id, f.parent_id, f.name, f.size, f.mtime AS ts, f.mime, f.read, f.write, f.locked, f.hidden, f.width, f.height, IF(ch.id, 1, 0) AS dirs
  457. FROM '.$this->tbf.' AS f
  458. LEFT JOIN '.$this->tbf.' AS p ON p.id=f.parent_id
  459. LEFT JOIN '.$this->tbf.' AS ch ON ch.parent_id=f.id AND ch.mime="directory"
  460. WHERE f.id="'.$path.'"
  461. GROUP BY f.id';
  462. $res = $this->query($sql);
  463. if ($res) {
  464. $stat = $res->fetch_assoc();
  465. if ($stat['parent_id']) {
  466. $stat['phash'] = $this->encode($stat['parent_id']);
  467. }
  468. if ($stat['mime'] == 'directory') {
  469. unset($stat['width']);
  470. unset($stat['height']);
  471. } else {
  472. unset($stat['dirs']);
  473. }
  474. unset($stat['id']);
  475. unset($stat['parent_id']);
  476. return $stat;
  477. }
  478. return array();
  479. }
  480. /**
  481. * Return true if path is dir and has at least one childs directory
  482. *
  483. * @param string $path dir path
  484. * @return bool
  485. * @author Dmitry (dio) Levashov
  486. **/
  487. protected function _subdirs($path) {
  488. return ($stat = $this->stat($path)) && isset($stat['dirs']) ? $stat['dirs'] : false;
  489. }
  490. /**
  491. * Return object width and height
  492. * Usualy used for images, but can be realize for video etc...
  493. *
  494. * @param string $path file path
  495. * @param string $mime file mime type
  496. * @return string
  497. * @author Dmitry (dio) Levashov
  498. **/
  499. protected function _dimensions($path, $mime) {
  500. return ($stat = $this->stat($path)) && isset($stat['width']) && isset($stat['height']) ? $stat['width'].'x'.$stat['height'] : '';
  501. }
  502. /******************** file/dir content *********************/
  503. /**
  504. * Return files list in directory.
  505. *
  506. * @param string $path dir path
  507. * @return array
  508. * @author Dmitry (dio) Levashov
  509. **/
  510. protected function _scandir($path) {
  511. return isset($this->dirsCache[$path])
  512. ? $this->dirsCache[$path]
  513. : $this->cacheDir($path);
  514. }
  515. /**
  516. * Open file and return file pointer
  517. *
  518. * @param string $path file path
  519. * @param string $mode open file mode (ignored in this driver)
  520. * @return resource|false
  521. * @author Dmitry (dio) Levashov
  522. **/
  523. protected function _fopen($path, $mode='rb') {
  524. $fp = $this->tmbPath
  525. ? @fopen($this->tmpname($path), 'w+')
  526. : @tmpfile();
  527. if ($fp) {
  528. if (($res = $this->query('SELECT content FROM '.$this->tbf.' WHERE id="'.$path.'"'))
  529. && ($r = $res->fetch_assoc())) {
  530. fwrite($fp, $r['content']);
  531. rewind($fp);
  532. return $fp;
  533. } else {
  534. $this->_fclose($fp, $path);
  535. }
  536. }
  537. return false;
  538. }
  539. /**
  540. * Close opened file
  541. *
  542. * @param resource $fp file pointer
  543. * @return bool
  544. * @author Dmitry (dio) Levashov
  545. **/
  546. protected function _fclose($fp, $path='') {
  547. @fclose($fp);
  548. if ($path) {
  549. @unlink($this->tmpname($path));
  550. }
  551. }
  552. /******************** file/dir manipulations *************************/
  553. /**
  554. * Create dir and return created dir path or false on failed
  555. *
  556. * @param string $path parent dir path
  557. * @param string $name new directory name
  558. * @return string|bool
  559. * @author Dmitry (dio) Levashov
  560. **/
  561. protected function _mkdir($path, $name) {
  562. return $this->make($path, $name, 'directory') ? $this->_joinPath($path, $name) : false;
  563. }
  564. /**
  565. * Create file and return it's path or false on failed
  566. *
  567. * @param string $path parent dir path
  568. * @param string $name new file name
  569. * @return string|bool
  570. * @author Dmitry (dio) Levashov
  571. **/
  572. protected function _mkfile($path, $name) {
  573. return $this->make($path, $name, 'text/plain') ? $this->_joinPath($path, $name) : false;
  574. }
  575. /**
  576. * Create symlink. FTP driver does not support symlinks.
  577. *
  578. * @param string $target link target
  579. * @param string $path symlink path
  580. * @return bool
  581. * @author Dmitry (dio) Levashov
  582. **/
  583. protected function _symlink($target, $path, $name) {
  584. return false;
  585. }
  586. /**
  587. * Copy file into another file
  588. *
  589. * @param string $source source file path
  590. * @param string $targetDir target directory path
  591. * @param string $name new file name
  592. * @return bool
  593. * @author Dmitry (dio) Levashov
  594. **/
  595. protected function _copy($source, $targetDir, $name) {
  596. $this->clearcache();
  597. $id = $this->_joinPath($targetDir, $name);
  598. $sql = $id > 0
  599. ? sprintf('REPLACE INTO %s (id, parent_id, name, content, size, mtime, mime, width, height, `read`, `write`, `locked`, `hidden`) (SELECT %d, %d, name, content, size, mtime, mime, width, height, `read`, `write`, `locked`, `hidden` FROM %s WHERE id=%d)', $this->tbf, $id, $this->_dirname($id), $this->tbf, $source)
  600. : sprintf('INSERT INTO %s (parent_id, name, content, size, mtime, mime, width, height, `read`, `write`, `locked`, `hidden`) SELECT %d, "%s", content, size, %d, mime, width, height, `read`, `write`, `locked`, `hidden` FROM %s WHERE id=%d', $this->tbf, $targetDir, $this->db->real_escape_string($name), time(), $this->tbf, $source);
  601. return $this->query($sql);
  602. }
  603. /**
  604. * Move file into another parent dir.
  605. * Return new file path or false.
  606. *
  607. * @param string $source source file path
  608. * @param string $target target dir path
  609. * @param string $name file name
  610. * @return string|bool
  611. * @author Dmitry (dio) Levashov
  612. **/
  613. protected function _move($source, $targetDir, $name) {
  614. $sql = 'UPDATE %s SET parent_id=%d, name="%s" WHERE id=%d LIMIT 1';
  615. $sql = sprintf($sql, $this->tbf, $targetDir, $this->db->real_escape_string($name), $source);
  616. return $this->query($sql) && $this->db->affected_rows > 0;
  617. }
  618. /**
  619. * Remove file
  620. *
  621. * @param string $path file path
  622. * @return bool
  623. * @author Dmitry (dio) Levashov
  624. **/
  625. protected function _unlink($path) {
  626. return $this->query(sprintf('DELETE FROM %s WHERE id=%d AND mime!="directory" LIMIT 1', $this->tbf, $path)) && $this->db->affected_rows;
  627. }
  628. /**
  629. * Remove dir
  630. *
  631. * @param string $path dir path
  632. * @return bool
  633. * @author Dmitry (dio) Levashov
  634. **/
  635. protected function _rmdir($path) {
  636. return $this->query(sprintf('DELETE FROM %s WHERE id=%d AND mime="directory" LIMIT 1', $this->tbf, $path)) && $this->db->affected_rows;
  637. }
  638. /**
  639. * undocumented function
  640. *
  641. * @return void
  642. * @author Dmitry Levashov
  643. **/
  644. protected function _setContent($path, $fp) {
  645. rewind($fp);
  646. $fstat = fstat($fp);
  647. $size = $fstat['size'];
  648. }
  649. /**
  650. * Create new file and write into it from file pointer.
  651. * Return new file path or false on error.
  652. *
  653. * @param resource $fp file pointer
  654. * @param string $dir target dir path
  655. * @param string $name file name
  656. * @return bool|string
  657. * @author Dmitry (dio) Levashov
  658. **/
  659. protected function _save($fp, $dir, $name, $mime, $w, $h) {
  660. $this->clearcache();
  661. $id = $this->_joinPath($dir, $name);
  662. rewind($fp);
  663. $stat = fstat($fp);
  664. $size = $stat['size'];
  665. if (($tmpfile = tempnam($this->tmpPath, $this->id))) {
  666. if (($trgfp = fopen($tmpfile, 'wb')) == false) {
  667. unlink($tmpfile);
  668. } else {
  669. while (!feof($fp)) {
  670. fwrite($trgfp, fread($fp, 8192));
  671. }
  672. fclose($trgfp);
  673. $sql = $id > 0
  674. ? 'REPLACE INTO %s (id, parent_id, name, content, size, mtime, mime, width, height) VALUES ('.$id.', %d, "%s", LOAD_FILE("%s"), %d, %d, "%s", %d, %d)'
  675. : 'INSERT INTO %s (parent_id, name, content, size, mtime, mime, width, height) VALUES (%d, "%s", LOAD_FILE("%s"), %d, %d, "%s", %d, %d)';
  676. $sql = sprintf($sql, $this->tbf, $dir, $this->db->real_escape_string($name), $this->loadFilePath($tmpfile), $size, time(), $mime, $w, $h);
  677. $res = $this->query($sql);
  678. unlink($tmpfile);
  679. if ($res) {
  680. return $id > 0 ? $id : $this->db->insert_id;
  681. }
  682. }
  683. }
  684. $content = '';
  685. rewind($fp);
  686. while (!feof($fp)) {
  687. $content .= fread($fp, 8192);
  688. }
  689. $sql = $id > 0
  690. ? 'REPLACE INTO %s (id, parent_id, name, content, size, mtime, mime, width, height) VALUES ('.$id.', %d, "%s", "%s", %d, %d, "%s", %d, %d)'
  691. : 'INSERT INTO %s (parent_id, name, content, size, mtime, mime, width, height) VALUES (%d, "%s", "%s", %d, %d, "%s", %d, %d)';
  692. $sql = sprintf($sql, $this->tbf, $dir, $this->db->real_escape_string($name), $this->db->real_escape_string($content), $size, time(), $mime, $w, $h);
  693. unset($content);
  694. if ($this->query($sql)) {
  695. return $id > 0 ? $id : $this->db->insert_id;
  696. }
  697. return false;
  698. }
  699. /**
  700. * Get file contents
  701. *
  702. * @param string $path file path
  703. * @return string|false
  704. * @author Dmitry (dio) Levashov
  705. **/
  706. protected function _getContents($path) {
  707. return ($res = $this->query(sprintf('SELECT content FROM %s WHERE id=%d', $this->tbf, $path))) && ($r = $res->fetch_assoc()) ? $r['content'] : false;
  708. }
  709. /**
  710. * Write a string to a file
  711. *
  712. * @param string $path file path
  713. * @param string $content new file content
  714. * @return bool
  715. * @author Dmitry (dio) Levashov
  716. **/
  717. protected function _filePutContents($path, $content) {
  718. return $this->query(sprintf('UPDATE %s SET content="%s", size=%d, mtime=%d WHERE id=%d LIMIT 1', $this->tbf, $this->db->real_escape_string($content), strlen($content), time(), $path));
  719. }
  720. /**
  721. * Detect available archivers
  722. *
  723. * @return void
  724. **/
  725. protected function _checkArchivers() {
  726. return;
  727. }
  728. /**
  729. * Unpack archive
  730. *
  731. * @param string $path archive path
  732. * @param array $arc archiver command and arguments (same as in $this->archivers)
  733. * @return void
  734. * @author Dmitry (dio) Levashov
  735. * @author Alexey Sukhotin
  736. **/
  737. protected function _unpack($path, $arc) {
  738. return;
  739. }
  740. /**
  741. * Recursive symlinks search
  742. *
  743. * @param string $path file/dir path
  744. * @return bool
  745. * @author Dmitry (dio) Levashov
  746. **/
  747. protected function _findSymlinks($path) {
  748. return false;
  749. }
  750. /**
  751. * Extract files from archive
  752. *
  753. * @param string $path archive path
  754. * @param array $arc archiver command and arguments (same as in $this->archivers)
  755. * @return true
  756. * @author Dmitry (dio) Levashov,
  757. * @author Alexey Sukhotin
  758. **/
  759. protected function _extract($path, $arc) {
  760. return false;
  761. }
  762. /**
  763. * Create archive and return its path
  764. *
  765. * @param string $dir target dir
  766. * @param array $files files names list
  767. * @param string $name archive name
  768. * @param array $arc archiver options
  769. * @return string|bool
  770. * @author Dmitry (dio) Levashov,
  771. * @author Alexey Sukhotin
  772. **/
  773. protected function _archive($dir, $files, $name, $arc) {
  774. return false;
  775. }
  776. } // END class