<?php
/*
Copyright (C) 2001-2004 ZZOSS GbR, http://www.zzoss.com
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation; either
version 2.1 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public
License along with this library; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
/**
@version $Id: Utils.php,v 1.9 2004/04/06 16:40:11 czonsius Exp $
@copyright Copyright © 2001-2004 ZZ/OSS GbR, http://www.zzoss.com
@license http://opensource.org/licenses/lgpl-license.php GNU Lesser General Public License
*/
/**
* Helper methods for several occasions.
*/
class ZZOSS_InstallerUtils
{
// serializes $var and dumps it
// to disk
function serializeToFile($file, $var) {
$fp = fopen($file, "w");
fwrite($fp, serialize($var));
fclose($fp);
}
// reads a serialized dump from disk
// and returns it unserialized
function unserializeFromFile($file) {
if(file_exists($file)){
$fp = fopen($file,"r");
$ser = fread ($fp, filesize ($file));
fclose($fp);
return unserialize($ser);
}
}
// RMDIR
// --------
// removes directory recursively, even if non-empty
function rmdir ($dirName) {
if($d = @opendir ($dirName)) {
while($entry = @readdir($d)) {
if ($entry != "." && $entry != ".." && $entry != "") {
if (is_dir($dirName.DIRECTORY_SEPARATOR.$entry)) {
ZZOSS_InstallerUtils::rmdir($dirName.DIRECTORY_SEPARATOR.$entry);
} else {
@unlink($dirName.DIRECTORY_SEPARATOR.$entry);
}
}
}
closedir($d);
}
return @rmdir($dirName);
}
/*
* MY MKDIR
*
* make directories recursively
*/
function mkdir ( $path )
{
// fix incorrect path
$path = ZZOSS_InstallerUtils::fixPath( $path );
// split data path in directories
$dataDirs = explode( DIRECTORY_SEPARATOR, $path );
$currPath = '';
for( $a=0; $a<count($dataDirs); $a++) {
$currPath .= $dataDirs[$a].DIRECTORY_SEPARATOR;
// does directory to store data exist?
if(!is_dir( $currPath )) {
// if not, then make directory
//echo $currPath.'<br>';
mkdir( $currPath, 0777 );
}
}
}
// MY CRYPT
// --------
// generates DES encrypted string using random salt
function crypt($pw)
{
// generate random salt
srand((double)microtime()*1000000);
$saltseeds = array( '.','/','0','1','2','3','4','5','6','7','8','9',
'a','b','c','d','e','f','g','h','i','j','k','l','m',
'n','o','p','q','r','s','t','u','v','w','x','y','z',
'A','B','C','D','E','F','G','H','I','J','K','L','M',
'N','O','P','Q','R','S','T','U','V','W','X','Y','Z');
$salt = $saltseeds[rand(0,63)] . $saltseeds[rand(0,63)];
// encrypt
return crypt(trim($pw),$salt);
}
/*
* Replaces special chars of a string to make the string compatible with
* filename conventions.
*/
function convertStringToFilename($title)
{
$nametitle = strtolower($title);
$nametitle = str_replace('Ä','ae',$nametitle);
$nametitle = str_replace('Ö','oe',$nametitle);
$nametitle = str_replace('Ü','ue',$nametitle);
$nametitle = str_replace('?','_',$nametitle);
$nametitle = str_replace('\'','_',$nametitle);
$nametitle = str_replace("´",'_',$nametitle);
$nametitle = str_replace('&','_',$nametitle);
$nametitle = str_replace('+','_',$nametitle);
$nametitle = str_replace('$','_',$nametitle);
$nametitle = str_replace('-','_',$nametitle);
$nametitle = str_replace('%','_',$nametitle);
$nametitle = str_replace("'",'_',$nametitle);
$nametitle = str_replace('&','_',$nametitle);
$nametitle = str_replace('<','_',$nametitle);
$nametitle = str_replace('>','_',$nametitle);
$nametitle = str_replace(' ','_',$nametitle);
$nametitle = str_replace('§','_',$nametitle);
$nametitle = str_replace('&','_',$nametitle);
$nametitle = str_replace(' ','e',$nametitle);
$nametitle = str_replace('ä','ae',$nametitle);
$nametitle = str_replace('ö','oe',$nametitle);
$nametitle = str_replace('ü','ue',$nametitle);
$nametitle = str_replace('/','_',$nametitle);
$nametitle = str_replace('\\','_',$nametitle);
$nametitle = str_replace('ß','_',$nametitle);
//$nametitle = str_replace('.','_',$nametitle);
$nametitle = str_replace(':','_',$nametitle);
$nametitle = str_replace('#','_',$nametitle);
$nametitle = str_replace('*','_',$nametitle);
$nametitle = str_replace('~','_',$nametitle);
$nametitle = str_replace('"','_',$nametitle);
return($nametitle);
}
/*
* GET UTC TIME WITH TIME ZONE OFFSET
*/
// get date, time, GMT difference
function getUTCDateTime()
{
$offset = ZZOSS_InstallerUtils::getUTCOffset();
$offsetHHMM = mktime(0,0,$offsetSec,date("m"),date("d"),date("Y"));
$formattedString = date('Y-m-d\TH:i:s').$offset;
return $formattedString;
}
/*
* Get UTC/GMT offset
*/
function getUTCOffset()
{
$offsetSec = date('Z');
if($offsetSec[0] == '-') {
$offsetSec = str_replace( '-', '', $offsetSec );
$offsetDiff = '-';
} else {
$offsetDiff = '+';
}
$offsetHHMM = mktime(0,0,$offsetSec,date("m"),date("d"),date("Y"));
return $offsetDiff.date( 'H:i', $offsetHHMM );
}
function copy($src, $dest, $recursive = true, $overwrite = true, $ignore_list = array())
{
// lowercase all entries in ignorelist
foreach($ignore_list as $key => $val) {
$ignore_list[$key] = strtolower($val);
}
if (is_dir($src)){
if (!ZZOSS_InstallerUtils::copy_rec($src, $dest, $recursive, $overwrite, $ignore_list)){
return false;
}
if (is_file($src) && ($overwrite || !file_exists($dest))){ // do regular copy
if (!copy($src, $dest)){
return false;
}
}
}
return true;
}
function copy_rec($src, $dest, $recursive = true, $overwrite = true, $ignore_list = array())
{
//$CMD = 'mv '.$src.' '.$dest;
//exec($CMD);
//echo $src.' -> '.$dest.'<br/>';
ZZOSS_InstallerUtils::mkdir($dest);
$handle = opendir($src);
while ($file = readdir($handle)){
if(!in_array(strtolower($file), $ignore_list)) {
$src_file = $src.$file;
//echo ' -> ';
$dest_file = $dest.$file;
//echo '<br/>';
if ($recursive && is_dir($src_file) && $file !="." && $file != "..")
if (!ZZOSS_InstallerUtils::copy_rec($src_file.DIRECTORY_SEPARATOR, $dest_file.DIRECTORY_SEPARATOR,$recursive, $overwrite, $ignore_list))
return false;
if (is_file($src_file) && ($overwrite || !file_exists($dest_file)))
if (!copy($src_file, $dest_file))
return false;
}
}
closedir($handle);
return true;
}
function downloadFile($src, $dest) {
if(file_exists($dest)) {
@unlink($dest);
}
$dest_dir = $dest;
if(!is_dir($dest)){
$dest_dir = dirname($dest);
}
include_once 'PEAR/Common.php';
//$callback = array('ZZOSS_InstallerUtils');
$result = PEAR_Common::downloadHttp($src, &$ui, $dest_dir);
// WORKAROUND, did not understand how to define
// the full file path in PEAR's method, so we
// copy the saved file to the defined location,
// but only if the differ
//echo "$dest != $result";
if(is_object($result)) {
// TODO: trigger error since we got a pear error object
return PEAR::raiseError("Unable to get file $src");
} elseif(!is_dir($dest) && $dest != $result){
copy($result, $dest);
unlink($result);
}
return $result;
}
// {{{ downloadHttp()
/**
* Download a file through HTTP. Considers suggested file name in
* Content-disposition: header and can run a callback function for
* different events. The callback will be called with two
* parameters: the callback type, and parameters. The implemented
* callback types are:
*
* 'setup' called at the very beginning, parameter is a UI object
* that should be used for all output
* 'message' the parameter is a string with an informational message
* 'saveas' may be used to save with a different file name, the
* parameter is the filename that is about to be used.
* If a 'saveas' callback returns a non-empty string,
* that file name will be used as the filename instead.
* Note that $save_dir will not be affected by this, only
* the basename of the file.
* 'start' download is starting, parameter is number of bytes
* that are expected, or -1 if unknown
* 'bytesread' parameter is the number of bytes read so far
* 'done' download is complete, parameter is the total number
* of bytes read
* 'connfailed' if the TCP connection fails, this callback is called
* with array(host,port,errno,errmsg)
* 'writefailed' if writing to disk fails, this callback is called
* with array(destfile,errmsg)
*
* If an HTTP proxy has been configured (http_proxy PEAR_Config
* setting), the proxy will be used.
*
* @param string $url the URL to download
* @param object $config PEAR_Config instance
* @param string $save_dir (optional) directory to save file in
* @param mixed $callback (optional) function/method to call for status
* updates
*
* @return string Returns the full path of the downloaded file or a PEAR
* error on failure. If the error is caused by
* socket-related errors, the error object will
* have the fsockopen error code available through
* getCode().
*
* @access public
*/
function _downloadHttp($url, $save_dir = '.', $dest_file = null, $callback = null, $proxy = null)
{
if (preg_match('!^http://([^/:?#]*)(:(\d+))?(/.*)!', $url, $matches)) {
list(,$host,,$port,$path) = $matches;
}
$proxy_host = $proxy_port = $proxy_user = $proxy_pass = '';
if (is_array($proxy)) {
$proxy_host = @$proxy['host'];
$proxy_port = @$proxy['port'];
$proxy_user = @$proxy['user'];
$proxy_pass = @$proxy['pass'];
if ($proxy_port == '') {
$proxy_port = 8080;
}
if ($callback) {
call_user_func($callback, 'message', "Using HTTP proxy $host:$port");
}
}
if (empty($port)) {
$port = 80;
}
if ($proxy_host != '') {
$fp = @fsockopen($proxy_host, $proxy_port, $errno, $errstr);
if (!$fp) {
if ($callback) {
call_user_func($callback, 'connfailed', array($proxy_host, $proxy_port,
$errno, $errstr));
}
return PEAR::raiseError("Connection to `$proxy_host:$proxy_port' failed: $errstr", $errno);
}
$request = "GET $url HTTP/1.0\r\n";
} else {
$fp = @fsockopen($host, $port, $errno, $errstr);
if (!$fp) {
if ($callback) {
call_user_func($callback, 'connfailed', array($host, $port,
$errno, $errstr));
}
return PEAR::raiseError("Connection to `$host:$port' failed: $errstr", $errno);
}
$request = "GET $path HTTP/1.0\r\n";
}
$request .= "Host: $host:$port\r\n".
"User-Agent: PHP/".PHP_VERSION."\r\n";
if ($proxy_host != '' && $proxy_user != '') {
$request .= 'Proxy-Authorization: Basic ' .
base64_encode($proxy_user . ':' . $proxy_pass) . "\r\n";
}
$request .= "\r\n";
fwrite($fp, $request);
$headers = array();
while (trim($line = fgets($fp, 1024))) {
if (preg_match('/^([^:]+):\s+(.*)\s*$/', $line, $matches)) {
$headers[strtolower($matches[1])] = trim($matches[2]);
} elseif (preg_match('|^HTTP/1.[01] ([0-9]{3}) |', $line, $matches)) {
if ($matches[1] != 200) {
return PEAR::raiseError("File http://$host:$port$path not valid (received: $line)");
}
}
}
if (isset($headers['content-disposition']) &&
preg_match('/\sfilename=\"([^;]*\S)\"\s*(;|$)/', $headers['content-disposition'], $matches)) {
$save_as = basename($matches[1]);
} else {
$save_as = basename($url);
}
if ($callback) {
$tmp = call_user_func($callback, 'saveas', $save_as);
if ($tmp) {
$save_as = $tmp;
}
}
if($dest_file == null) {
$dest_file = $save_dir . DIRECTORY_SEPARATOR . $save_as;
}
if (!$wp = @fopen($dest_file, 'wb')) {
fclose($fp);
if ($callback) {
call_user_func($callback, 'writefailed', array($dest_file, $php_errormsg));
}
return PEAR::raiseError("could not open $dest_file for writing");
}
if (isset($headers['content-length'])) {
$length = $headers['content-length'];
} else {
$length = -1;
}
$bytes = 0;
if ($callback) {
call_user_func($callback, 'start', $length);
}
while ($data = @fread($fp, 1024)) {
$bytes += strlen($data);
if ($callback) {
call_user_func($callback, 'bytesread', $bytes);
}
if (!@fwrite($wp, $data)) {
fclose($fp);
if ($callback) {
call_user_func($callback, 'writefailed', array($dest_file, $php_errormsg));
}
return PEAR::raiseError("$dest_file: write failed ($php_errormsg)");
}
}
fclose($fp);
fclose($wp);
if ($callback) {
call_user_func($callback, 'done', $bytes);
}
return $dest_file;
}
// }}}
function trimArray($array) {
if(is_array($array)) {
foreach($array as $key => $val) {
if(is_array($val)) {
$array[$key] = ZZOSS_InstallerUtils::trimArray($val);
} else {
$array[$key] = trim($val);
}
}
}
return $array;
}
/**
* Takes care that a slash occurs only once.
*/
function fixPath($path, $slash = NULL)
{
if(is_null($slash)){
$slash = DIRECTORY_SEPARATOR;
}
$path = str_replace('/', $slash, $path);
$path = str_replace('\\', $slash, $path);
$path = str_replace($slash.'.'.$slash, $slash, $path);
$path = preg_replace('/\/{2,}|\\\{1,}/i', $slash, $path);
$path = preg_replace('/\.$/', '', $path);
return $path;
}
/**
* Fixes wrong slashes (e.g. Linux slashes on Windows) and takes care
* that a slash occurs only once.
*/
function fixSlashes($path)
{
if(DIRECTORY_SEPARATOR == '/'){
$wrong_separator = '\\';
} else {
$wrong_separator = '/';
}
$path = preg_replace('/\\'.DIRECTORY_SEPARATOR.'{2,}|\\'.$wrong_separator.'{1,}/i', DIRECTORY_SEPARATOR, $path);
return $path;
}
}
?>