CakePHP
  • Documentation
    • Book
    • API
    • Videos
    • Reporting Security Issues
    • Privacy Policy
    • Logos & Trademarks
  • Business Solutions
  • Swag
  • Road Trip
  • Team
  • Community
    • Community
    • Get Involved
    • Issues (GitHub)
    • Bakery
    • Featured Resources
    • Training
    • Meetups
    • My CakePHP
    • CakeFest
    • Newsletter
    • Linkedin
    • YouTube
    • Facebook
    • Twitter
    • Mastodon
    • Help & Support
    • Forum
    • Stack Overflow
    • Slack
    • Paid Support
CakePHP

C CakePHP 2.0 API

  • Overview
  • Tree
  • Deprecated
  • Version:
    • 2.0
      • 4.2
      • 4.1
      • 4.0
      • 3.9
      • 3.8
      • 3.7
      • 3.6
      • 3.5
      • 3.4
      • 3.3
      • 3.2
      • 3.1
      • 3.0
      • 2.10
      • 2.9
      • 2.8
      • 2.7
      • 2.6
      • 2.5
      • 2.4
      • 2.3
      • 2.2
      • 2.1
      • 2.0
      • 1.3
      • 1.2

Packages

  • Cake
    • Cache
      • Engine
    • Configure
    • Console
      • Command
        • Task
    • Controller
      • Component
        • Auth
    • Core
    • Error
    • I18n
    • Log
      • Engine
    • Model
      • Behavior
      • Datasource
        • Database
        • Session
    • Network
      • Email
      • Http
    • Routing
      • Route
    • TestSuite
      • Coverage
      • Fixture
      • Reporter
    • Utility
    • View
      • Helper

Classes

  • ClassRegistry
  • Debugger
  • File
  • Folder
  • Inflector
  • ObjectCollection
  • Sanitize
  • Security
  • Set
  • String
  • Validation
  • Xml
  1: <?php
  2: /**
  3:  * Convenience class for handling directories.
  4:  *
  5:  * PHP 5
  6:  *
  7:  * CakePHP(tm) : Rapid Development Framework (http://cakephp.org)
  8:  * Copyright 2005-2011, Cake Software Foundation, Inc. (http://cakefoundation.org)
  9:  *
 10:  * Licensed under The MIT License
 11:  * Redistributions of files must retain the above copyright notice.
 12:  *
 13:  * @copyright     Copyright 2005-2011, Cake Software Foundation, Inc. (http://cakefoundation.org)
 14:  * @link          http://cakephp.org CakePHP(tm) Project
 15:  * @package       Cake.Utility
 16:  * @since         CakePHP(tm) v 0.2.9
 17:  * @license       MIT License (http://www.opensource.org/licenses/mit-license.php)
 18:  */
 19: 
 20: /**
 21:  * Folder structure browser, lists folders and files.
 22:  * Provides an Object interface for Common directory related tasks.
 23:  *
 24:  * @package       Cake.Utility
 25:  */
 26: class Folder {
 27: 
 28: /**
 29:  * Path to Folder.
 30:  *
 31:  * @var string
 32:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::$path
 33:  */
 34:     public $path = null;
 35: 
 36: /**
 37:  * Sortedness. Whether or not list results
 38:  * should be sorted by name.
 39:  *
 40:  * @var boolean
 41:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::$sort
 42:  */
 43:     public $sort = false;
 44: 
 45: /**
 46:  * Mode to be used on create. Does nothing on windows platforms.
 47:  *
 48:  * @var integer
 49:  * http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::$mode
 50:  */
 51:     public $mode = 0755;
 52: 
 53: /**
 54:  * Holds messages from last method.
 55:  *
 56:  * @var array
 57:  */
 58:     protected $_messages = array();
 59: 
 60: /**
 61:  * Holds errors from last method.
 62:  *
 63:  * @var array
 64:  */
 65:     protected $_errors = array();
 66: 
 67: /**
 68:  * Holds array of complete directory paths.
 69:  *
 70:  * @var array
 71:  */
 72:     protected $_directories;
 73: 
 74: /**
 75:  * Holds array of complete file paths.
 76:  *
 77:  * @var array
 78:  */
 79:     protected $_files;
 80: 
 81: /**
 82:  * Constructor.
 83:  *
 84:  * @param string $path Path to folder
 85:  * @param boolean $create Create folder if not found
 86:  * @param mixed $mode Mode (CHMOD) to apply to created folder, false to ignore
 87:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder
 88:  */
 89:     public function __construct($path = false, $create = false, $mode = false) {
 90:         if (empty($path)) {
 91:             $path = TMP;
 92:         }
 93:         if ($mode) {
 94:             $this->mode = $mode;
 95:         }
 96: 
 97:         if (!file_exists($path) && $create === true) {
 98:             $this->create($path, $this->mode);
 99:         }
100:         if (!Folder::isAbsolute($path)) {
101:             $path = realpath($path);
102:         }
103:         if (!empty($path)) {
104:             $this->cd($path);
105:         }
106:     }
107: 
108: /**
109:  * Return current path.
110:  *
111:  * @return string Current path
112:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::pwd
113:  */
114:     public function pwd() {
115:         return $this->path;
116:     }
117: 
118: /**
119:  * Change directory to $path.
120:  *
121:  * @param string $path Path to the directory to change to
122:  * @return string The new path. Returns false on failure
123:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::cd
124:  */
125:     public function cd($path) {
126:         $path = $this->realpath($path);
127:         if (is_dir($path)) {
128:             return $this->path = $path;
129:         }
130:         return false;
131:     }
132: 
133: /**
134:  * Returns an array of the contents of the current directory.
135:  * The returned array holds two arrays: One of directories and one of files.
136:  *
137:  * @param boolean $sort Whether you want the results sorted, set this and the sort property
138:  *   to false to get unsorted results.
139:  * @param mixed $exceptions Either an array or boolean true will not grab dot files
140:  * @param boolean $fullPath True returns the full path
141:  * @return mixed Contents of current directory as an array, an empty array on failure
142:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::read
143:  */
144:     public function read($sort = true, $exceptions = false, $fullPath = false) {
145:         $dirs = $files = array();
146: 
147:         if (!$this->pwd()) {
148:             return array($dirs, $files);
149:         }
150:         if (is_array($exceptions)) {
151:             $exceptions = array_flip($exceptions);
152:         }
153:         $skipHidden = isset($exceptions['.']) || $exceptions === true;
154: 
155:         try {
156:             $iterator = new DirectoryIterator($this->path);
157:         } catch (Exception $e) {
158:             return array($dirs, $files);
159:         }
160: 
161:         foreach ($iterator as $item) {
162:             if ($item->isDot()) {
163:                 continue;
164:             }
165:             $name = $item->getFileName();
166:             if ($skipHidden && $name[0] === '.' || isset($exceptions[$name])) {
167:                 continue;
168:             }
169:             if ($fullPath) {
170:                 $name = $item->getPathName();
171:             }
172:             if ($item->isDir()) {
173:                 $dirs[] = $name;
174:             } else {
175:                 $files[] = $name;
176:             }
177:         }
178:         if ($sort || $this->sort) {
179:             sort($dirs);
180:             sort($files);
181:         }
182:         return array($dirs, $files);
183:     }
184: 
185: /**
186:  * Returns an array of all matching files in current directory.
187:  *
188:  * @param string $regexpPattern Preg_match pattern (Defaults to: .*)
189:  * @param boolean $sort Whether results should be sorted.
190:  * @return array Files that match given pattern
191:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::find
192:  */
193:     public function find($regexpPattern = '.*', $sort = false) {
194:         list($dirs, $files) = $this->read($sort);
195:         return array_values(preg_grep('/^' . $regexpPattern . '$/i', $files)); ;
196:     }
197: 
198: /**
199:  * Returns an array of all matching files in and below current directory.
200:  *
201:  * @param string $pattern Preg_match pattern (Defaults to: .*)
202:  * @param boolean $sort Whether results should be sorted.
203:  * @return array Files matching $pattern
204:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::findRecursive
205:  */
206:     public function findRecursive($pattern = '.*', $sort = false) {
207:         if (!$this->pwd()) {
208:             return array();
209:         }
210:         $startsOn = $this->path;
211:         $out = $this->_findRecursive($pattern, $sort);
212:         $this->cd($startsOn);
213:         return $out;
214:     }
215: 
216: /**
217:  * Private helper function for findRecursive.
218:  *
219:  * @param string $pattern Pattern to match against
220:  * @param boolean $sort Whether results should be sorted.
221:  * @return array Files matching pattern
222:  */
223:     protected function _findRecursive($pattern, $sort = false) {
224:         list($dirs, $files) = $this->read($sort);
225:         $found = array();
226: 
227:         foreach ($files as $file) {
228:             if (preg_match('/^' . $pattern . '$/i', $file)) {
229:                 $found[] = Folder::addPathElement($this->path, $file);
230:             }
231:         }
232:         $start = $this->path;
233: 
234:         foreach ($dirs as $dir) {
235:             $this->cd(Folder::addPathElement($start, $dir));
236:             $found = array_merge($found, $this->findRecursive($pattern, $sort));
237:         }
238:         return $found;
239:     }
240: 
241: /**
242:  * Returns true if given $path is a Windows path.
243:  *
244:  * @param string $path Path to check
245:  * @return boolean true if windows path, false otherwise
246:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::isWindowsPath
247:  */
248:     public static function isWindowsPath($path) {
249:         return (preg_match('/^[A-Z]:\\\\/i', $path) || substr($path, 0, 2) == '\\\\');
250:     }
251: 
252: /**
253:  * Returns true if given $path is an absolute path.
254:  *
255:  * @param string $path Path to check
256:  * @return boolean true if path is absolute.
257:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::isAbsolute
258:  */
259:     public static function isAbsolute($path) {
260:         return !empty($path) && ($path[0] === '/' || preg_match('/^[A-Z]:\\\\/i', $path) || substr($path, 0, 2) == '\\\\');
261:     }
262: 
263: /**
264:  * Returns a correct set of slashes for given $path. (\\ for Windows paths and / for other paths.)
265:  *
266:  * @param string $path Path to check
267:  * @return string Set of slashes ("\\" or "/")
268:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::normalizePath
269:  */
270:     public static function normalizePath($path) {
271:         return Folder::correctSlashFor($path);
272:     }
273: 
274: /**
275:  * Returns a correct set of slashes for given $path. (\\ for Windows paths and / for other paths.)
276:  *
277:  * @param string $path Path to check
278:  * @return string Set of slashes ("\\" or "/")
279:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::correctSlashFor
280:  */
281:     public static function correctSlashFor($path) {
282:         return (Folder::isWindowsPath($path)) ? '\\' : '/';
283:     }
284: 
285: /**
286:  * Returns $path with added terminating slash (corrected for Windows or other OS).
287:  *
288:  * @param string $path Path to check
289:  * @return string Path with ending slash
290:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::slashTerm
291:  */
292:     public static function slashTerm($path) {
293:         if (Folder::isSlashTerm($path)) {
294:             return $path;
295:         }
296:         return $path . Folder::correctSlashFor($path);
297:     }
298: 
299: /**
300:  * Returns $path with $element added, with correct slash in-between.
301:  *
302:  * @param string $path Path
303:  * @param string $element Element to and at end of path
304:  * @return string Combined path
305:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::addPathElement
306:  */
307:     public static function addPathElement($path, $element) {
308:         return rtrim($path, DS) . DS . $element;
309:     }
310: 
311: /**
312:  * Returns true if the File is in a given CakePath.
313:  *
314:  * @param string $path The path to check.
315:  * @return boolean
316:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::inCakePath
317:  */
318:     public function inCakePath($path = '') {
319:         $dir = substr(Folder::slashTerm(ROOT), 0, -1);
320:         $newdir = $dir . $path;
321: 
322:         return $this->inPath($newdir);
323:     }
324: 
325: /**
326:  * Returns true if the File is in given path.
327:  *
328:  * @param string $path The path to check that the current pwd() resides with in.
329:  * @param boolean $reverse
330:  * @return boolean
331:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::inPath
332:  */
333:     public function inPath($path = '', $reverse = false) {
334:         $dir = Folder::slashTerm($path);
335:         $current = Folder::slashTerm($this->pwd());
336: 
337:         if (!$reverse) {
338:             $return = preg_match('/^(.*)' . preg_quote($dir, '/') . '(.*)/', $current);
339:         } else {
340:             $return = preg_match('/^(.*)' . preg_quote($current, '/') . '(.*)/', $dir);
341:         }
342:         return (bool)$return;
343:     }
344: 
345: /**
346:  * Change the mode on a directory structure recursively. This includes changing the mode on files as well.
347:  *
348:  * @param string $path The path to chmod
349:  * @param integer $mode octal value 0755
350:  * @param boolean $recursive chmod recursively, set to false to only change the current directory.
351:  * @param array $exceptions array of files, directories to skip
352:  * @return boolean Returns TRUE on success, FALSE on failure
353:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::chmod
354:  */
355:     public function chmod($path, $mode = false, $recursive = true, $exceptions = array()) {
356:         if (!$mode) {
357:             $mode = $this->mode;
358:         }
359: 
360:         if ($recursive === false && is_dir($path)) {
361:             if (@chmod($path, intval($mode, 8))) {
362:                 $this->_messages[] = __d('cake_dev', '%s changed to %s', $path, $mode);
363:                 return true;
364:             }
365: 
366:             $this->_errors[] = __d('cake_dev', '%s NOT changed to %s', $path, $mode);
367:             return false;
368:         }
369: 
370:         if (is_dir($path)) {
371:             $paths = $this->tree($path);
372: 
373:             foreach ($paths as $type) {
374:                 foreach ($type as $key => $fullpath) {
375:                     $check = explode(DS, $fullpath);
376:                     $count = count($check);
377: 
378:                     if (in_array($check[$count - 1], $exceptions)) {
379:                         continue;
380:                     }
381: 
382:                     if (@chmod($fullpath, intval($mode, 8))) {
383:                         $this->_messages[] = __d('cake_dev', '%s changed to %s', $fullpath, $mode);
384:                     } else {
385:                         $this->_errors[] = __d('cake_dev', '%s NOT changed to %s', $fullpath, $mode);
386:                     }
387:                 }
388:             }
389: 
390:             if (empty($this->_errors)) {
391:                 return true;
392:             }
393:         }
394:         return false;
395:     }
396: 
397: /**
398:  * Returns an array of nested directories and files in each directory
399:  *
400:  * @param string $path the directory path to build the tree from
401:  * @param mixed $exceptions Array of files to exclude, false to exclude dot files.
402:  * @param string $type either file or dir. null returns both files and directories
403:  * @return mixed array of nested directories and files in each directory
404:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::tree
405:  */
406:     public function tree($path = null, $exceptions = true, $type = null) {
407:         if ($path == null) {
408:             $path = $this->path;
409:         }
410:         $files = array();
411:         $directories = array($path);
412:         $skipHidden = false;
413: 
414:         if ($exceptions === false) {
415:             $skipHidden = true;
416:         }
417:         if (is_array($exceptions)) {
418:             $exceptions = array_flip($exceptions);
419:             if (isset($exceptions['.'])) {
420:                 $skipHidden = true;
421:                 unset($exceptions['.']);
422:             }
423:         }
424: 
425:         try {
426:             $directory = new RecursiveDirectoryIterator($path, RecursiveDirectoryIterator::KEY_AS_PATHNAME | RecursiveDirectoryIterator::CURRENT_AS_SELF);
427:             $iterator = new RecursiveIteratorIterator($directory, RecursiveIteratorIterator::SELF_FIRST);
428:         } catch (Exception $e) {
429:             if ($type === null) {
430:                 return array(array(), array());
431:             }
432:             return array();
433:         }
434:         $pathLength = strlen($path);
435:         foreach ($iterator as $itemPath => $fsIterator) {
436:             if ($skipHidden) {
437:                 $subPathName = $fsIterator->getSubPathname();
438:                 if ($subPathName{0} == '.' || strpos($subPathName, DS . '.') !== false) {
439:                     continue;
440:                 }
441:             }
442:             $item = $fsIterator->current();
443:             if (!empty($exceptions) && isset($exceptions[$item->getFilename()])) {
444:                 continue;
445:             }
446: 
447:             if ($item->isFile()) {
448:                 $files[] = $itemPath;
449:             } elseif ($item->isDir() && !$item->isDot()) {
450:                 $directories[] = $itemPath;
451:             }
452:         }
453:         if ($type === null) {
454:             return array($directories, $files);
455:         }
456:         if ($type === 'dir') {
457:             return $directories;
458:         }
459:         return $files;
460:     }
461: 
462: /**
463:  * Private method to list directories and files in each directory
464:  *
465:  * @param string $path The Path to read.
466:  * @param mixed $exceptions Array of files to exclude from the read that will be performed.
467:  * @return void
468:  */
469:     protected function _tree($path, $exceptions) {
470:         $this->path = $path;
471:         list($dirs, $files) = $this->read(false, $exceptions, true);
472:         $this->_directories = array_merge($this->_directories, $dirs);
473:         $this->_files = array_merge($this->_files, $files);
474:     }
475: 
476: /**
477:  * Create a directory structure recursively. Can be used to create
478:  * deep path structures like `/foo/bar/baz/shoe/horn`
479:  *
480:  * @param string $pathname The directory structure to create
481:  * @param integer $mode octal value 0755
482:  * @return boolean Returns TRUE on success, FALSE on failure
483:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::create
484:  */
485:     public function create($pathname, $mode = false) {
486:         if (is_dir($pathname) || empty($pathname)) {
487:             return true;
488:         }
489: 
490:         if (!$mode) {
491:             $mode = $this->mode;
492:         }
493: 
494:         if (is_file($pathname)) {
495:             $this->_errors[] = __d('cake_dev', '%s is a file', $pathname);
496:             return false;
497:         }
498:         $pathname = rtrim($pathname, DS);
499:         $nextPathname = substr($pathname, 0, strrpos($pathname, DS));
500: 
501:         if ($this->create($nextPathname, $mode)) {
502:             if (!file_exists($pathname)) {
503:                 $old = umask(0);
504:                 if (mkdir($pathname, $mode)) {
505:                     umask($old);
506:                     $this->_messages[] = __d('cake_dev', '%s created', $pathname);
507:                     return true;
508:                 } else {
509:                     umask($old);
510:                     $this->_errors[] = __d('cake_dev', '%s NOT created', $pathname);
511:                     return false;
512:                 }
513:             }
514:         }
515:         return false;
516:     }
517: 
518: /**
519:  * Returns the size in bytes of this Folder and its contents.
520:  *
521:  * @return integer size in bytes of current folder
522:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::dirsize
523:  */
524:     public function dirsize() {
525:         $size = 0;
526:         $directory = Folder::slashTerm($this->path);
527:         $stack = array($directory);
528:         $count = count($stack);
529:         for ($i = 0, $j = $count; $i < $j; ++$i) {
530:             if (is_file($stack[$i])) {
531:                 $size += filesize($stack[$i]);
532:             } elseif (is_dir($stack[$i])) {
533:                 $dir = dir($stack[$i]);
534:                 if ($dir) {
535:                     while (false !== ($entry = $dir->read())) {
536:                         if ($entry === '.' || $entry === '..') {
537:                             continue;
538:                         }
539:                         $add = $stack[$i] . $entry;
540: 
541:                         if (is_dir($stack[$i] . $entry)) {
542:                             $add = Folder::slashTerm($add);
543:                         }
544:                         $stack[] = $add;
545:                     }
546:                     $dir->close();
547:                 }
548:             }
549:             $j = count($stack);
550:         }
551:         return $size;
552:     }
553: 
554: /**
555:  * Recursively Remove directories if the system allows.
556:  *
557:  * @param string $path Path of directory to delete
558:  * @return boolean Success
559:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::delete
560:  */
561:     public function delete($path = null) {
562:         if (!$path) {
563:             $path = $this->pwd();
564:         }
565:         if (!$path) {
566:             return null;
567:         }
568:         $path = Folder::slashTerm($path);
569:         if (is_dir($path) === true) {
570:             $normalFiles = glob($path . '*');
571:             $hiddenFiles = glob($path . '\.?*');
572: 
573:             $normalFiles = $normalFiles ? $normalFiles : array();
574:             $hiddenFiles = $hiddenFiles ? $hiddenFiles : array();
575: 
576:             $files = array_merge($normalFiles, $hiddenFiles);
577:             if (is_array($files)) {
578:                 foreach ($files as $file) {
579:                     if (preg_match('/(\.|\.\.)$/', $file)) {
580:                         continue;
581:                     }
582:                     if (is_file($file) === true) {
583:                         if (@unlink($file)) {
584:                             $this->_messages[] = __d('cake_dev', '%s removed', $file);
585:                         } else {
586:                             $this->_errors[] = __d('cake_dev', '%s NOT removed', $file);
587:                         }
588:                     } elseif (is_dir($file) === true && $this->delete($file) === false) {
589:                         return false;
590:                     }
591:                 }
592:             }
593:             $path = substr($path, 0, strlen($path) - 1);
594:             if (rmdir($path) === false) {
595:                 $this->_errors[] = __d('cake_dev', '%s NOT removed', $path);
596:                 return false;
597:             } else {
598:                 $this->_messages[] = __d('cake_dev', '%s removed', $path);
599:             }
600:         }
601:         return true;
602:     }
603: 
604: /**
605:  * Recursive directory copy.
606:  *
607:  * ### Options
608:  *
609:  * - `to` The directory to copy to.
610:  * - `from` The directory to copy from, this will cause a cd() to occur, changing the results of pwd().
611:  * - `mode` The mode to copy the files/directories with.
612:  * - `skip` Files/directories to skip.
613:  *
614:  * @param mixed $options Either an array of options (see above) or a string of the destination directory.
615:  * @return boolean Success
616:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::copy
617:  */
618:     public function copy($options = array()) {
619:         if (!$this->pwd()) {
620:             return false;
621:         }
622:         $to = null;
623:         if (is_string($options)) {
624:             $to = $options;
625:             $options = array();
626:         }
627:         $options = array_merge(array('to' => $to, 'from' => $this->path, 'mode' => $this->mode, 'skip' => array()), $options);
628: 
629:         $fromDir = $options['from'];
630:         $toDir = $options['to'];
631:         $mode = $options['mode'];
632: 
633:         if (!$this->cd($fromDir)) {
634:             $this->_errors[] = __d('cake_dev', '%s not found', $fromDir);
635:             return false;
636:         }
637: 
638:         if (!is_dir($toDir)) {
639:             $this->create($toDir, $mode);
640:         }
641: 
642:         if (!is_writable($toDir)) {
643:             $this->_errors[] = __d('cake_dev', '%s not writable', $toDir);
644:             return false;
645:         }
646: 
647:         $exceptions = array_merge(array('.', '..', '.svn'), $options['skip']);
648:         if ($handle = @opendir($fromDir)) {
649:             while (false !== ($item = readdir($handle))) {
650:                 if (!in_array($item, $exceptions)) {
651:                     $from = Folder::addPathElement($fromDir, $item);
652:                     $to = Folder::addPathElement($toDir, $item);
653:                     if (is_file($from)) {
654:                         if (copy($from, $to)) {
655:                             chmod($to, intval($mode, 8));
656:                             touch($to, filemtime($from));
657:                             $this->_messages[] = __d('cake_dev', '%s copied to %s', $from, $to);
658:                         } else {
659:                             $this->_errors[] = __d('cake_dev', '%s NOT copied to %s', $from, $to);
660:                         }
661:                     }
662: 
663:                     if (is_dir($from) && !file_exists($to)) {
664:                         $old = umask(0);
665:                         if (mkdir($to, $mode)) {
666:                             umask($old);
667:                             $old = umask(0);
668:                             chmod($to, $mode);
669:                             umask($old);
670:                             $this->_messages[] = __d('cake_dev', '%s created', $to);
671:                             $options = array_merge($options, array('to' => $to, 'from' => $from));
672:                             $this->copy($options);
673:                         } else {
674:                             $this->_errors[] = __d('cake_dev', '%s not created', $to);
675:                         }
676:                     }
677:                 }
678:             }
679:             closedir($handle);
680:         } else {
681:             return false;
682:         }
683: 
684:         if (!empty($this->_errors)) {
685:             return false;
686:         }
687:         return true;
688:     }
689: 
690: /**
691:  * Recursive directory move.
692:  *
693:  * ### Options
694:  *
695:  * - `to` The directory to copy to.
696:  * - `from` The directory to copy from, this will cause a cd() to occur, changing the results of pwd().
697:  * - `chmod` The mode to copy the files/directories with.
698:  * - `skip` Files/directories to skip.
699:  *
700:  * @param array $options (to, from, chmod, skip)
701:  * @return boolean Success
702:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::move
703:  */
704:     public function move($options) {
705:         $to = null;
706:         if (is_string($options)) {
707:             $to = $options;
708:             $options = (array)$options;
709:         }
710:         $options = array_merge(
711:             array('to' => $to, 'from' => $this->path, 'mode' => $this->mode, 'skip' => array()),
712:             $options
713:         );
714: 
715:         if ($this->copy($options)) {
716:             if ($this->delete($options['from'])) {
717:                 return (bool)$this->cd($options['to']);
718:             }
719:         }
720:         return false;
721:     }
722: 
723: /**
724:  * get messages from latest method
725:  *
726:  * @return array
727:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::messages
728:  */
729:     public function messages() {
730:         return $this->_messages;
731:     }
732: 
733: /**
734:  * get error from latest method
735:  *
736:  * @return array
737:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::errors
738:  */
739:     public function errors() {
740:         return $this->_errors;
741:     }
742: 
743: /**
744:  * Get the real path (taking ".." and such into account)
745:  *
746:  * @param string $path Path to resolve
747:  * @return string The resolved path
748:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::realpath
749:  */
750:     public function realpath($path) {
751:         $path = str_replace('/', DS, trim($path));
752:         if (strpos($path, '..') === false) {
753:             if (!Folder::isAbsolute($path)) {
754:                 $path = Folder::addPathElement($this->path, $path);
755:             }
756:             return $path;
757:         }
758:         $parts = explode(DS, $path);
759:         $newparts = array();
760:         $newpath = '';
761:         if ($path[0] === DS) {
762:             $newpath = DS;
763:         }
764: 
765:         while (($part = array_shift($parts)) !== NULL) {
766:             if ($part === '.' || $part === '') {
767:                 continue;
768:             }
769:             if ($part === '..') {
770:                 if (!empty($newparts)) {
771:                     array_pop($newparts);
772:                     continue;
773:                 } else {
774:                     return false;
775:                 }
776:             }
777:             $newparts[] = $part;
778:         }
779:         $newpath .= implode(DS, $newparts);
780: 
781:         return Folder::slashTerm($newpath);
782:     }
783: 
784: /**
785:  * Returns true if given $path ends in a slash (i.e. is slash-terminated).
786:  *
787:  * @param string $path Path to check
788:  * @return boolean true if path ends with slash, false otherwise
789:  * @link http://book.cakephp.org/2.0/en/core-utility-libraries/file-folder.html#Folder::isSlashTerm
790:  */
791:     public static function isSlashTerm($path) {
792:         $lastChar = $path[strlen($path) - 1];
793:         return $lastChar === '/' || $lastChar === '\\';
794:     }
795: }
796: 
OpenHub
Rackspace
Rackspace
  • Business Solutions
  • Showcase
  • Documentation
  • Book
  • API
  • Videos
  • Reporting Security Issues
  • Privacy Policy
  • Logos & Trademarks
  • Community
  • Get Involved
  • Issues (GitHub)
  • Bakery
  • Featured Resources
  • Training
  • Meetups
  • My CakePHP
  • CakeFest
  • Newsletter
  • Linkedin
  • YouTube
  • Facebook
  • Twitter
  • Mastodon
  • Help & Support
  • Forum
  • Stack Overflow
  • Slack
  • Paid Support

Generated using CakePHP API Docs