home *** CD-ROM | disk | FTP | other *** search
/ Cricao de Sites - 650 Layouts Prontos / WebMasters.iso / Servidores / xampp-win32-1.6.7-installer.exe / php / tmp / PEAR-1.7.1 / System.php < prev    next >
Encoding:
PHP Script  |  2008-02-15  |  19.5 KB  |  606 lines

  1. <?php
  2. /**
  3.  * File/Directory manipulation
  4.  *
  5.  * PHP versions 4 and 5
  6.  *
  7.  * LICENSE: This source file is subject to version 3.0 of the PHP license
  8.  * that is available through the world-wide-web at the following URI:
  9.  * http://www.php.net/license/3_0.txt.  If you did not receive a copy of
  10.  * the PHP License and are unable to obtain it through the web, please
  11.  * send a note to license@php.net so we can mail you a copy immediately.
  12.  *
  13.  * @category   pear
  14.  * @package    System
  15.  * @author     Tomas V.V.Cox <cox@idecnet.com>
  16.  * @copyright  1997-2008 The PHP Group
  17.  * @license    http://www.php.net/license/3_0.txt  PHP License 3.0
  18.  * @version    CVS: $Id: System.php,v 1.62 2008/01/03 20:26:34 cellog Exp $
  19.  * @link       http://pear.php.net/package/PEAR
  20.  * @since      File available since Release 0.1
  21.  */
  22.  
  23. /**
  24.  * base class
  25.  */
  26. require_once 'PEAR.php';
  27. require_once 'Console/Getopt.php';
  28.  
  29. $GLOBALS['_System_temp_files'] = array();
  30.  
  31. /**
  32. * System offers cross plattform compatible system functions
  33. *
  34. * Static functions for different operations. Should work under
  35. * Unix and Windows. The names and usage has been taken from its respectively
  36. * GNU commands. The functions will return (bool) false on error and will
  37. * trigger the error with the PHP trigger_error() function (you can silence
  38. * the error by prefixing a '@' sign after the function call, but this
  39. * is not recommended practice.  Instead use an error handler with
  40. * {@link set_error_handler()}).
  41. *
  42. * Documentation on this class you can find in:
  43. * http://pear.php.net/manual/
  44. *
  45. * Example usage:
  46. * if (!@System::rm('-r file1 dir1')) {
  47. *    print "could not delete file1 or dir1";
  48. * }
  49. *
  50. * In case you need to to pass file names with spaces,
  51. * pass the params as an array:
  52. *
  53. * System::rm(array('-r', $file1, $dir1));
  54. *
  55. * @category   pear
  56. * @package    System
  57. * @author     Tomas V.V. Cox <cox@idecnet.com>
  58. * @copyright  1997-2006 The PHP Group
  59. * @license    http://www.php.net/license/3_0.txt  PHP License 3.0
  60. * @version    Release: 1.7.1
  61. * @link       http://pear.php.net/package/PEAR
  62. * @since      Class available since Release 0.1
  63. * @static 
  64. */
  65. class System
  66. {
  67.     /**
  68.     * returns the commandline arguments of a function
  69.     *
  70.     * @param    string  $argv           the commandline
  71.     * @param    string  $short_options  the allowed option short-tags
  72.     * @param    string  $long_options   the allowed option long-tags
  73.     * @return   array   the given options and there values
  74.     * @static 
  75.     * @access private
  76.     */
  77.     function _parseArgs($argv, $short_options, $long_options = null)
  78.     {
  79.         if (!is_array($argv) && $argv !== null) {
  80.             $argv = preg_split('/\s+/', $argv, -1, PREG_SPLIT_NO_EMPTY);
  81.         }
  82.         return Console_Getopt::getopt2($argv, $short_options);
  83.     }
  84.  
  85.     /**
  86.     * Output errors with PHP trigger_error(). You can silence the errors
  87.     * with prefixing a "@" sign to the function call: @System::mkdir(..);
  88.     *
  89.     * @param mixed $error a PEAR error or a string with the error message
  90.     * @return bool false
  91.     * @static 
  92.     * @access private
  93.     */
  94.     function raiseError($error)
  95.     {
  96.         if (PEAR::isError($error)) {
  97.             $error = $error->getMessage();
  98.         }
  99.         trigger_error($error, E_USER_WARNING);
  100.         return false;
  101.     }
  102.  
  103.     /**
  104.     * Creates a nested array representing the structure of a directory
  105.     *
  106.     * System::_dirToStruct('dir1', 0) =>
  107.     *   Array
  108.     *    (
  109.     *    [dirs] => Array
  110.     *        (
  111.     *            [0] => dir1
  112.     *        )
  113.     *
  114.     *    [files] => Array
  115.     *        (
  116.     *            [0] => dir1/file2
  117.     *            [1] => dir1/file3
  118.     *        )
  119.     *    )
  120.     * @param    string  $sPath      Name of the directory
  121.     * @param    integer $maxinst    max. deep of the lookup
  122.     * @param    integer $aktinst    starting deep of the lookup
  123.     * @param    bool    $silent     if true, do not emit errors.
  124.     * @return   array   the structure of the dir
  125.     * @static 
  126.     * @access   private
  127.     */
  128.  
  129.     function _dirToStruct($sPath, $maxinst, $aktinst = 0, $silent = false)
  130.     {
  131.         $struct = array('dirs' => array(), 'files' => array());
  132.         if (($dir = @opendir($sPath)) === false) {
  133.             if (!$silent) {
  134.                 System::raiseError("Could not open dir $sPath");
  135.             }
  136.             return $struct; // XXX could not open error
  137.         }
  138.         $struct['dirs'][] = $sPath = realpath($sPath); // XXX don't add if '.' or '..' ?
  139.         $list = array();
  140.         while (false !== ($file = readdir($dir))) {
  141.             if ($file != '.' && $file != '..') {
  142.                 $list[] = $file;
  143.             }
  144.         }
  145.         closedir($dir);
  146.         sort($list);
  147.         if ($aktinst < $maxinst || $maxinst == 0) {
  148.             foreach ($list as $val) {
  149.                 $path = $sPath . DIRECTORY_SEPARATOR . $val;
  150.                 if (is_dir($path) && !is_link($path)) {
  151.                     $tmp = System::_dirToStruct($path, $maxinst, $aktinst+1, $silent);
  152.                     $struct = array_merge_recursive($tmp, $struct);
  153.                 } else {
  154.                     $struct['files'][] = $path;
  155.                 }
  156.             }
  157.         }
  158.         return $struct;
  159.     }
  160.  
  161.     /**
  162.     * Creates a nested array representing the structure of a directory and files
  163.     *
  164.     * @param    array $files Array listing files and dirs
  165.     * @return   array
  166.     * @static 
  167.     * @see System::_dirToStruct()
  168.     */
  169.     function _multipleToStruct($files)
  170.     {
  171.         $struct = array('dirs' => array(), 'files' => array());
  172.         settype($files, 'array');
  173.         foreach ($files as $file) {
  174.             if (is_dir($file) && !is_link($file)) {
  175.                 $tmp = System::_dirToStruct($file, 0);
  176.                 $struct = array_merge_recursive($tmp, $struct);
  177.             } else {
  178.                 $struct['files'][] = $file;
  179.             }
  180.         }
  181.         return $struct;
  182.     }
  183.  
  184.     /**
  185.     * The rm command for removing files.
  186.     * Supports multiple files and dirs and also recursive deletes
  187.     *
  188.     * @param    string  $args   the arguments for rm
  189.     * @return   mixed   PEAR_Error or true for success
  190.     * @static 
  191.     * @access   public
  192.     */
  193.     function rm($args)
  194.     {
  195.         $opts = System::_parseArgs($args, 'rf'); // "f" does nothing but I like it :-)
  196.         if (PEAR::isError($opts)) {
  197.             return System::raiseError($opts);
  198.         }
  199.         foreach ($opts[0] as $opt) {
  200.             if ($opt[0] == 'r') {
  201.                 $do_recursive = true;
  202.             }
  203.         }
  204.         $ret = true;
  205.         if (isset($do_recursive)) {
  206.             $struct = System::_multipleToStruct($opts[1]);
  207.             foreach ($struct['files'] as $file) {
  208.                 if (!@unlink($file)) {
  209.                     $ret = false;
  210.                 }
  211.             }
  212.             foreach ($struct['dirs'] as $dir) {
  213.                 if (!@rmdir($dir)) {
  214.                     $ret = false;
  215.                 }
  216.             }
  217.         } else {
  218.             foreach ($opts[1] as $file) {
  219.                 $delete = (is_dir($file)) ? 'rmdir' : 'unlink';
  220.                 if (!@$delete($file)) {
  221.                     $ret = false;
  222.                 }
  223.             }
  224.         }
  225.         return $ret;
  226.     }
  227.  
  228.     /**
  229.     * Make directories.
  230.     *
  231.     * The -p option will create parent directories
  232.     * @param    string  $args    the name of the director(y|ies) to create
  233.     * @return   bool    True for success
  234.     * @static 
  235.     * @access   public
  236.     */
  237.     function mkDir($args)
  238.     {
  239.         $opts = System::_parseArgs($args, 'pm:');
  240.         if (PEAR::isError($opts)) {
  241.             return System::raiseError($opts);
  242.         }
  243.         $mode = 0777; // default mode
  244.         foreach ($opts[0] as $opt) {
  245.             if ($opt[0] == 'p') {
  246.                 $create_parents = true;
  247.             } elseif ($opt[0] == 'm') {
  248.                 // if the mode is clearly an octal number (starts with 0)
  249.                 // convert it to decimal
  250.                 if (strlen($opt[1]) && $opt[1]{0} == '0') {
  251.                     $opt[1] = octdec($opt[1]);
  252.                 } else {
  253.                     // convert to int
  254.                     $opt[1] += 0;
  255.                 }
  256.                 $mode = $opt[1];
  257.             }
  258.         }
  259.         $ret = true;
  260.         if (isset($create_parents)) {
  261.             foreach ($opts[1] as $dir) {
  262.                 $dirstack = array();
  263.                 while ((!file_exists($dir) || !is_dir($dir)) &&
  264.                         $dir != DIRECTORY_SEPARATOR) {
  265.                     array_unshift($dirstack, $dir);
  266.                     $dir = dirname($dir);
  267.                 }
  268.                 while ($newdir = array_shift($dirstack)) {
  269.                     if (!is_writeable(dirname($newdir))) {
  270.                         $ret = false;
  271.                         break;
  272.                     }
  273.                     if (!mkdir($newdir, $mode)) {
  274.                         $ret = false;
  275.                     }
  276.                 }
  277.             }
  278.         } else {
  279.             foreach($opts[1] as $dir) {
  280.                 if ((@file_exists($dir) || !is_dir($dir)) && !mkdir($dir, $mode)) {
  281.                     $ret = false;
  282.                 }
  283.             }
  284.         }
  285.         return $ret;
  286.     }
  287.  
  288.     /**
  289.     * Concatenate files
  290.     *
  291.     * Usage:
  292.     * 1) $var = System::cat('sample.txt test.txt');
  293.     * 2) System::cat('sample.txt test.txt > final.txt');
  294.     * 3) System::cat('sample.txt test.txt >> final.txt');
  295.     *
  296.     * Note: as the class use fopen, urls should work also (test that)
  297.     *
  298.     * @param    string  $args   the arguments
  299.     * @return   boolean true on success
  300.     * @static 
  301.     * @access   public
  302.     */
  303.     function &cat($args)
  304.     {
  305.         $ret = null;
  306.         $files = array();
  307.         if (!is_array($args)) {
  308.             $args = preg_split('/\s+/', $args, -1, PREG_SPLIT_NO_EMPTY);
  309.         }
  310.  
  311.         $count_args = count($args);
  312.         for ($i = 0; $i < $count_args; $i++) {
  313.             if ($args[$i] == '>') {
  314.                 $mode = 'wb';
  315.                 $outputfile = $args[$i+1];
  316.                 break;
  317.             } elseif ($args[$i] == '>>') {
  318.                 $mode = 'ab+';
  319.                 $outputfile = $args[$i+1];
  320.                 break;
  321.             } else {
  322.                 $files[] = $args[$i];
  323.             }
  324.         }
  325.         $outputfd = false;
  326.         if (isset($mode)) {
  327.             if (!$outputfd = fopen($outputfile, $mode)) {
  328.                 $err = System::raiseError("Could not open $outputfile");
  329.                 return $err;
  330.             }
  331.             $ret = true;
  332.         }
  333.         foreach ($files as $file) {
  334.             if (!$fd = fopen($file, 'r')) {
  335.                 System::raiseError("Could not open $file");
  336.                 continue;
  337.             }
  338.             while ($cont = fread($fd, 2048)) {
  339.                 if (is_resource($outputfd)) {
  340.                     fwrite($outputfd, $cont);
  341.                 } else {
  342.                     $ret .= $cont;
  343.                 }
  344.             }
  345.             fclose($fd);
  346.         }
  347.         if (is_resource($outputfd)) {
  348.             fclose($outputfd);
  349.         }
  350.         return $ret;
  351.     }
  352.  
  353.     /**
  354.     * Creates temporary files or directories. This function will remove
  355.     * the created files when the scripts finish its execution.
  356.     *
  357.     * Usage:
  358.     *   1) $tempfile = System::mktemp("prefix");
  359.     *   2) $tempdir  = System::mktemp("-d prefix");
  360.     *   3) $tempfile = System::mktemp();
  361.     *   4) $tempfile = System::mktemp("-t /var/tmp prefix");
  362.     *
  363.     * prefix -> The string that will be prepended to the temp name
  364.     *           (defaults to "tmp").
  365.     * -d     -> A temporary dir will be created instead of a file.
  366.     * -t     -> The target dir where the temporary (file|dir) will be created. If
  367.     *           this param is missing by default the env vars TMP on Windows or
  368.     *           TMPDIR in Unix will be used. If these vars are also missing
  369.     *           c:\windows\temp or /tmp will be used.
  370.     *
  371.     * @param   string  $args  The arguments
  372.     * @return  mixed   the full path of the created (file|dir) or false
  373.     * @see System::tmpdir()
  374.     * @static 
  375.     * @access  public
  376.     */
  377.     function mktemp($args = null)
  378.     {
  379.         static $first_time = true;
  380.         $opts = System::_parseArgs($args, 't:d');
  381.         if (PEAR::isError($opts)) {
  382.             return System::raiseError($opts);
  383.         }
  384.         foreach ($opts[0] as $opt) {
  385.             if ($opt[0] == 'd') {
  386.                 $tmp_is_dir = true;
  387.             } elseif ($opt[0] == 't') {
  388.                 $tmpdir = $opt[1];
  389.             }
  390.         }
  391.         $prefix = (isset($opts[1][0])) ? $opts[1][0] : 'tmp';
  392.         if (!isset($tmpdir)) {
  393.             $tmpdir = System::tmpdir();
  394.         }
  395.         if (!System::mkDir(array('-p', $tmpdir))) {
  396.             return false;
  397.         }
  398.         $tmp = tempnam($tmpdir, $prefix);
  399.         if (isset($tmp_is_dir)) {
  400.             unlink($tmp); // be careful possible race condition here
  401.             if (!mkdir($tmp, 0700)) {
  402.                 return System::raiseError("Unable to create temporary directory $tmpdir");
  403.             }
  404.         }
  405.         $GLOBALS['_System_temp_files'][] = $tmp;
  406.         if ($first_time) {
  407.             PEAR::registerShutdownFunc(array('System', '_removeTmpFiles'));
  408.             $first_time = false;
  409.         }
  410.         return $tmp;
  411.     }
  412.  
  413.     /**
  414.     * Remove temporary files created my mkTemp. This function is executed
  415.     * at script shutdown time
  416.     *
  417.     * @static 
  418.     * @access private
  419.     */
  420.     function _removeTmpFiles()
  421.     {
  422.         if (count($GLOBALS['_System_temp_files'])) {
  423.             $delete = $GLOBALS['_System_temp_files'];
  424.             array_unshift($delete, '-r');
  425.             System::rm($delete);
  426.             $GLOBALS['_System_temp_files'] = array();
  427.         }
  428.     }
  429.  
  430.     /**
  431.     * Get the path of the temporal directory set in the system
  432.     * by looking in its environments variables.
  433.     * Note: php.ini-recommended removes the "E" from the variables_order setting,
  434.     * making unavaible the $_ENV array, that s why we do tests with _ENV
  435.     *
  436.     * @static 
  437.     * @return string The temporary directory on the system
  438.     */
  439.     function tmpdir()
  440.     {
  441.         if (OS_WINDOWS) {
  442.             if ($var = isset($_ENV['TMP']) ? $_ENV['TMP'] : getenv('TMP')) {
  443.                 return $var;
  444.             }
  445.             if ($var = isset($_ENV['TEMP']) ? $_ENV['TEMP'] : getenv('TEMP')) {
  446.                 return $var;
  447.             }
  448.             if ($var = isset($_ENV['USERPROFILE']) ? $_ENV['USERPROFILE'] : getenv('USERPROFILE')) {
  449.                 return $var;
  450.             }
  451.             if ($var = isset($_ENV['windir']) ? $_ENV['windir'] : getenv('windir')) {
  452.                 return $var;
  453.             }
  454.             return getenv('SystemRoot') . '\temp';
  455.         }
  456.         if ($var = isset($_ENV['TMPDIR']) ? $_ENV['TMPDIR'] : getenv('TMPDIR')) {
  457.             return $var;
  458.         }
  459.         return realpath('/tmp');
  460.     }
  461.  
  462.     /**
  463.     * The "which" command (show the full path of a command)
  464.     *
  465.     * @param string $program The command to search for
  466.     * @param mixed  $fallback Value to return if $program is not found
  467.     *
  468.     * @return mixed A string with the full path or false if not found
  469.     * @static 
  470.     * @author Stig Bakken <ssb@php.net>
  471.     */
  472.     function which($program, $fallback = false)
  473.     {
  474.         // enforce API
  475.         if (!is_string($program) || '' == $program) {
  476.             return $fallback;
  477.         }
  478.  
  479.         // full path given
  480.         if (basename($program) != $program) {
  481.             $path_elements[] = dirname($program);
  482.             $program = basename($program);
  483.         } else {
  484.             // Honor safe mode
  485.             if (!ini_get('safe_mode') || !$path = ini_get('safe_mode_exec_dir')) {
  486.                 $path = getenv('PATH');
  487.                 if (!$path) {
  488.                     $path = getenv('Path'); // some OSes are just stupid enough to do this
  489.                 }
  490.             }
  491.             $path_elements = explode(PATH_SEPARATOR, $path);
  492.         }
  493.  
  494.         if (OS_WINDOWS) {
  495.             $exe_suffixes = getenv('PATHEXT')
  496.                                 ? explode(PATH_SEPARATOR, getenv('PATHEXT'))
  497.                                 : array('.exe','.bat','.cmd','.com');
  498.             // allow passing a command.exe param
  499.             if (strpos($program, '.') !== false) {
  500.                 array_unshift($exe_suffixes, '');
  501.             }
  502.             // is_executable() is not available on windows for PHP4
  503.             $pear_is_executable = (function_exists('is_executable')) ? 'is_executable' : 'is_file';
  504.         } else {
  505.             $exe_suffixes = array('');
  506.             $pear_is_executable = 'is_executable';
  507.         }
  508.  
  509.         foreach ($exe_suffixes as $suff) {
  510.             foreach ($path_elements as $dir) {
  511.                 $file = $dir . DIRECTORY_SEPARATOR . $program . $suff;
  512.                 if (@$pear_is_executable($file)) {
  513.                     return $file;
  514.                 }
  515.             }
  516.         }
  517.         return $fallback;
  518.     }
  519.  
  520.     /**
  521.     * The "find" command
  522.     *
  523.     * Usage:
  524.     *
  525.     * System::find($dir);
  526.     * System::find("$dir -type d");
  527.     * System::find("$dir -type f");
  528.     * System::find("$dir -name *.php");
  529.     * System::find("$dir -name *.php -name *.htm*");
  530.     * System::find("$dir -maxdepth 1");
  531.     *
  532.     * Params implmented:
  533.     * $dir            -> Start the search at this directory
  534.     * -type d         -> return only directories
  535.     * -type f         -> return only files
  536.     * -maxdepth <n>   -> max depth of recursion
  537.     * -name <pattern> -> search pattern (bash style). Multiple -name param allowed
  538.     *
  539.     * @param  mixed Either array or string with the command line
  540.     * @return array Array of found files
  541.     * @static 
  542.     *
  543.     */
  544.     function find($args)
  545.     {
  546.         if (!is_array($args)) {
  547.             $args = preg_split('/\s+/', $args, -1, PREG_SPLIT_NO_EMPTY);
  548.         }
  549.         $dir = realpath(array_shift($args));
  550.         if (!$dir) {
  551.             return array();
  552.         }
  553.         $patterns = array();
  554.         $depth = 0;
  555.         $do_files = $do_dirs = true;
  556.         $args_count = count($args);
  557.         for ($i = 0; $i < $args_count; $i++) {
  558.             switch ($args[$i]) {
  559.                 case '-type':
  560.                     if (in_array($args[$i+1], array('d', 'f'))) {
  561.                         if ($args[$i+1] == 'd') {
  562.                             $do_files = false;
  563.                         } else {
  564.                             $do_dirs = false;
  565.                         }
  566.                     }
  567.                     $i++;
  568.                     break;
  569.                 case '-name':
  570.                     $name = preg_quote($args[$i+1], '#');
  571.                     // our magic characters ? and * have just been escaped,
  572.                     // so now we change the escaped versions to PCRE operators
  573.                     $name = strtr($name, array('\?' => '.', '\*' => '.*'));
  574.                     $patterns[] = '('.$name.')';
  575.                     $i++;
  576.                     break;
  577.                 case '-maxdepth':
  578.                     $depth = $args[$i+1];
  579.                     break;
  580.             }
  581.         }
  582.         $path = System::_dirToStruct($dir, $depth, 0, true);
  583.         if ($do_files && $do_dirs) {
  584.             $files = array_merge($path['files'], $path['dirs']);
  585.         } elseif ($do_dirs) {
  586.             $files = $path['dirs'];
  587.         } else {
  588.             $files = $path['files'];
  589.         }
  590.         if (count($patterns)) {
  591.             $dsq = preg_quote(DIRECTORY_SEPARATOR, '#');
  592.             $pattern = '#(^|'.$dsq.')'.implode('|', $patterns).'($|'.$dsq.')#';
  593.             $ret = array();
  594.             $files_count = count($files);
  595.             for ($i = 0; $i < $files_count; $i++) {
  596.                 // only search in the part of the file below the current directory
  597.                 $filepart = basename($files[$i]);
  598.                 if (preg_match($pattern, $filepart)) {
  599.                     $ret[] = $files[$i];
  600.                 }
  601.             }
  602.             return $ret;
  603.         }
  604.         return $files;
  605.     }
  606. }