-
-
[旧帖] [求助] 外国人写的PHP 注册系统。源程序版 0.00雪花
-
发表于: 2008-8-5 23:26 4648
-
程序如下
ConfigurationFile.class.php
==========================================================
Engine.class.php
==========================================================
File.class.php
ConfigurationFile.class.php
<?php /////////////////////////////////////////////////////////////////////////////// // // Copyright 2006 Point Clark Networks. // /////////////////////////////////////////////////////////////////////////////// // // This program is free software; you can redistribute it and/or // modify it under the terms of the GNU General Public License // as published by the Free Software Foundation; either version 2 // of the License, or (at your option) any later version. // // This program 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 General Public License for more details. // // You should have received a copy of the GNU General Public License // along with this program; if not, write to the Free Software // Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. // /////////////////////////////////////////////////////////////////////////////// /** * Configuration file handling class. * * @package Api * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ /////////////////////////////////////////////////////////////////////////////// // D E P E N D E N C E S /////////////////////////////////////////////////////////////////////////////// require_once("File.class.php"); /////////////////////////////////////////////////////////////////////////////// // E X C E P T I O N C L A S S E S /////////////////////////////////////////////////////////////////////////////// /** * Configuration file exception. * * @package Api * @subpackage Exception * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ class ConfigurationFileException extends EngineException { /** * ConfigurationFileException constructor. * * @param string $filename name of the file * @param int $linenumber linenumber where the error occurred * @param int $code error code */ public function __construct($filename, $linenumber, $code) { parent::__construct(LOCALE_LANG_ERRMSG_PARSE_ERROR.": ".basename($filename)."($linenumber)", $code); } } /////////////////////////////////////////////////////////////////////////////// // C L A S S /////////////////////////////////////////////////////////////////////////////// /** * Configuration file handling class. * * A generic configuration file parser. * * @package Api * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ class ConfigurationFile extends File { /////////////////////////////////////////////////////////////////////////////// // F I E L D S /////////////////////////////////////////////////////////////////////////////// protected $method = 'explode'; protected $token = '='; protected $limit = 2; protected $flags = null; protected $loaded = false; protected $cfg = array(); /////////////////////////////////////////////////////////////////////////////// // M E T H O D S /////////////////////////////////////////////////////////////////////////////// /** * Configuration file constructor. * * Valid method enumerators are: * - ini: parses a samba style ini file * - match: use preg_match, requires a valid regex expression as the "token" parameter * - split: use preg_split, requires a valid regex expression as the "token" parameter * - explode: (default) requires a delimiter as the "token" parameter * * @param string $filename target file * @param string $method configuration file type (default = explode) * @param string $token a valid regex or delimiter * @param int $limit (optional) max number of parts, the first part is always used as the "key" * @param int $flags (optional) preg_match/preg_split accept various flags (cf. @link http://www.php.net ) */ public function __construct($filename, $method = 'explode', $token = '=', $limit = 2, $flags = null) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); parent::__construct($filename, true); switch ($method) { case 'ini': $token = array('/^\s*\[(.*?)\]\s*$/', '='); break; case 'split': if (strlen($token) == 1) { $method = 'explode'; break; } case 'match': if (substr($token,0,1) != '/') { $token = "/".$token; } if (substr($token,-1,1) != '/') { $token .= "/"; } } $this->method = $method; $this->token = $token; $this->limit = $limit; $this->flags = $flags; $this->loaded = false; } /** * Loads a configuration file and returns its values as an array * * @param boolean $reload (optional) if true, a "fresh" copy will be retrieved rather than a cached version * @return array parsed array of elements from configuration file * @throws FileNotFoundException Exception (inherited from GetContentsAsArray) * @throws FileIoException */ public function Load($reload=false) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); if ($reload) $this->loaded = false; if (! $this->loaded) { try { $lines = $this->GetContentsAsArray(); } catch (Exception $e) { throw $e; } $configfile = array(); $n = 0; $match = ""; switch ($this->method) { case 'ini': $key = null; foreach($lines as $line) { $n++; if (preg_match('/^\/\//', $line)) continue; if (preg_match('/^#.*$/', $line)) { continue; } elseif (preg_match('/^\s*$/', $line)) { // a blank line continue; } elseif (preg_match($this->token[0], $line, $match)) { $key = $match[1]; } elseif ((strpos($line,$this->token[1]) !== false) && (!(is_null($key)))) { $match = array_map('trim',explode($this->token[1],$line)); $configfile[$key][$match[0]] = $match[1]; } else { throw new ConfigurationFileException($this->filename, $n, COMMON_NOTICE); } } break; case 'match': foreach ($lines as $line) { $n++; if (preg_match('/^\/\/.*$/', $line)) continue; if (preg_match('/^\#.*$/', $line)) { continue; } elseif (preg_match('/^\s*$/', $line)) { // a blank line continue; } elseif (preg_match($this->token, $line, $match, $this->flags)) { $configfile[$match[1]] = $match[2]; } else { throw new ConfigurationFileException($this->filename, $n, COMMON_ERROR); } } break; case 'split': foreach ($lines as $line) { $n++; if (preg_match('/^\/\/.*$/', $line)) continue; if (preg_match('/^\#.*$/', $line)) { continue; } elseif (preg_match('/^\s*$/', $line)) { // a blank line continue; } else { $match = array_map('trim',preg_split($this->token,$line,$this->limit,$this->flags)); if (($match[0] == $line)||(empty($match[0]))) { throw new ConfigurationFileException($this->filename, $n, COMMON_ERROR); } else { if ($this->limit == 2) { $configfile[$match[0]] = $match[1]; } else { $configfile[$match[0]] = array_slice($match,1); } } } } break; default: foreach ($lines as $line) { $n++; if (preg_match('/^\/\/.*$/', $line)) continue; if (preg_match('/^\#.*$/', $line)) { continue; } elseif (preg_match('/^\s*$/', $line)) { // a blank line continue; } else { $match = array_map('trim',explode($this->token,$line,$this->limit)); if ($match[0] == $line) { throw new ConfigurationFileException($this->filename, $n, COMMON_ERROR); } else { if ($this->limit == 2) { $configfile[$match[0]] = $match[1]; } else { $configfile[$match[0]] = array_slice($match,1); } } } } } $this->cfg = $configfile; $this->loaded = true; } return $this->cfg; } /** * @access private */ public function __destruct() { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); parent::__destruct(); } } // vim: syntax=php ts=4 ?>
==========================================================
Engine.class.php
<?php /////////////////////////////////////////////////////////////////////////////// // // Copyright 2006 Point Clark Networks. // /////////////////////////////////////////////////////////////////////////////// // // This program is free software; you can redistribute it and/or // modify it under the terms of the GNU General Public License // as published by the Free Software Foundation; either version 2 // of the License, or (at your option) any later version. // // This program 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 General Public License for more details. // // You should have received a copy of the GNU General Public License // along with this program; if not, write to the Free Software // Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. // /////////////////////////////////////////////////////////////////////////////// /** * Base class for the API. * * @package Api * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ /////////////////////////////////////////////////////////////////////////////// // D E P E N D E N C I E S /////////////////////////////////////////////////////////////////////////////// require_once(dirname(__FILE__) . '/../common/Globals.inc.php'); require_once(dirname(__FILE__) . '/../common/Logger.class.php'); require_once(dirname(__FILE__) . '/../common/Error.class.php'); /////////////////////////////////////////////////////////////////////////////// // E X C E P T I O N C L A S S E S /////////////////////////////////////////////////////////////////////////////// /** * Base exception for all exceptions in the API. * * @package Api * @subpackage Exception * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ class EngineException extends Exception { /** * EngineException constructor. * * Unlike a core PHP exception, the message and code parameters are required. * * - COMMON_DEBUG - debug message * - COMMON_VALIDATION - validation error message * - COMMON_INFO - informational message (e.g. dynamic DNS updated with IP w.x.y.z) * - COMMON_NOTICE - pedantic warnings (e.g. dynamic DNS updated with IP w.x.y.z) * - COMMON_WARNING - normal but significant errors (e.g. dynamic DNS could not detect WAN IP) * - COMMON_ERROR - errors that should not happen under normal circumstances * - COMMON_FATAL - really nasty errors * * @param string $message error message * @param integer $code error code * @return void */ public function __construct($message, $code) { parent::__construct($message, $code); if ($code >= COMMON_WARNING) Logger::LogException($this, true); } } /** * Validation exception for API. * * @package Api * @subpackage Exception * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ class ValidationException extends EngineException { /** * ValidationException constructor. * * @param string $message error message * @return void */ public function __construct($message) { parent::__construct($message, COMMON_VALIDATION); } } /** * Custom configuration discovered exception. * * In some instances, it may be impossible to manage a configuration file if * it has been customized. For instance, the Amavis configuration file uses * regular expressions in the banned_filename_re parameter. These regular * expressions are flexible, but are impossible to decipher without showing * the end user some not-so-user-friendly details. * * @package Api * @subpackage Exception * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ class CustomConfigurationException extends EngineException { /** * Custom configuration constructor. * * @param string $file file name * @return void */ public function __construct($file) { parent::__construct("Custom configuration discovered" . " - " . $file, COMMON_NOTICE); } } /** * Duplicate entry exception for API. * * @package Api * @subpackage Exception * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ class DuplicateException extends EngineException { /** * DuplicateException constructor. * * @param string $message error message * @return void */ public function __construct($message) { parent::__construct($message, COMMON_WARNING); } } /** * Security violation exception. * * @package Api * @subpackage Exception * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2007, Point Clark Networks */ class SecurityViolationException extends EngineException { /** * SecurityViolationException constructor. * * @return void */ public function __construct() { parent::__construct("Security violation", COMMON_ERROR); } } /** * SQL exception for API. * * @package Api * @subpackage Exception * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ class SqlException extends EngineException { /** * SqlException constructor. * * @param string $message error message * @return void */ public function __construct($message) { parent::__construct($message, COMMON_WARNING); } } /////////////////////////////////////////////////////////////////////////////// // C L A S S /////////////////////////////////////////////////////////////////////////////// /** * Base class for the API. * * @package Api * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ class Engine { /////////////////////////////////////////////////////////////////////////////// // F I E L D S /////////////////////////////////////////////////////////////////////////////// /** * @var array validation error queue */ protected $errors = array(); /////////////////////////////////////////////////////////////////////////////// // M E T H O D S /////////////////////////////////////////////////////////////////////////////// /** * Engine constructor. * * @return void */ function __construct() { if (! file_exists("/etc/system/nosecurity")) { $user = get_current_user(); if (!(($user == "root") || ($user == "webconfig"))) throw new SecurityViolationException(); } require_once(GlobalGetLanguageTemplate(preg_replace("/Engine/", "Locale",__FILE__))); } /** * Prints a message to the log. * * The following log levels are used: * * - COMMON_DEBUG - debug messages * - COMMON_VALIDATION - validation error message * - COMMON_INFO - informational messages (e.g. dynamic DNS updated with IP w.x.y.z) * - COMMON_NOTICE - pedantic warnings (e.g. dynamic DNS updated with IP w.x.y.z) * - COMMON_WARNING - normal but significant errors (e.g. dynamic DNS could not detect WAN IP) * - COMMON_ERROR - errors that should not happen under normal circumstances * - COMMON_FATAL - really nasty errors * * @param int $code error code * @param string $message short and informative message * @param string $tag identifier (usually the method) * @param int $line line number * @return void * @static */ static function Log($code, $message, $tag, $line) { $error = new Error($code, $message, $tag, $line, null, true); Logger::Log($error); } /////////////////////////////////////////////////////////////////////////////// // E R R O R H A N D L I N G /////////////////////////////////////////////////////////////////////////////// /** * Add a validation error to the queue. * * @param string $message error message * @param string $tag tag (usually the method call) * @param integer $line line number * @return void */ protected function AddValidationError($message, $tag, $line) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); $error = new Error(COMMON_VALIDATION, $message, $tag, $line, null, Error::TYPE_ERROR, true); $this->errors[] = $error; if (COMMON_DEBUG_MODE) Logger::Log($error); } /** * Returns an array of validation error messages. * * @param boolean $purge (optional) if true, the error queue will be purged. * @return array validation errors */ public function GetValidationErrors($purge = false) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); $error_messages = array(); foreach ($this->errors as $error) $error_messages[] = $error->GetMessage(); if ($purge) $this->errors = array(); return $error_messages; } /** * Returns an array of validation error objects. * * @param boolean $purge (optional) if true, the error queue will be purged. * @return array validation errors */ public function CopyValidationErrors($purge = false) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); $errors_copy = $this->errors; if ($purge) $this->errors = array(); return $errors_copy; } /** * Returns true if validation errors exist. * * @return boolean true if validation errors exist */ public function CheckValidationErrors() { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); if (empty($this->errors)) return false; else return true; } /** * @access private */ public function __destruct() { // A bit noisy // if (COMMON_DEBUG_MODE) // $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); } } // vim: syntax=php ts=4 ?>
==========================================================
File.class.php
<?php /////////////////////////////////////////////////////////////////////////////// // // Copyright 2006 Point Clark Networks. // /////////////////////////////////////////////////////////////////////////////// // // This program is free software; you can redistribute it and/or // modify it under the terms of the GNU General Public License // as published by the Free Software Foundation; either version 2 // of the License, or (at your option) any later version. // // This program 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 General Public License for more details. // // You should have received a copy of the GNU General Public License // along with this program; if not, write to the Free Software // Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. // /////////////////////////////////////////////////////////////////////////////// /** * File manipulation class. * * @package Api * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ /////////////////////////////////////////////////////////////////////////////// // D E P E N D E N C E S /////////////////////////////////////////////////////////////////////////////// require_once("Engine.class.php"); require_once("ShellExec.class.php"); /////////////////////////////////////////////////////////////////////////////// // E X C E P T I O N C L A S S E S /////////////////////////////////////////////////////////////////////////////// /** * File exception. * * @package Api * @subpackage Exception * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ class FileException extends EngineException { /** * FileException constructor. * * @param string $errmsg error message * @param int $code error code */ public function __construct($errmsg, $code) { parent::__construct($errmsg, $code); } } /** * File permissions exception. * * @package Api * @subpackage Exception * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ class FilePermissionsException extends EngineException { /** * FilePermissionsException constructor. * * @param string $errmsg error message * @param int $code error code */ public function __construct($errmsg, $code) { parent::__construct($errmsg, $code); } } /** * File already exists exception. * * @package Api * @subpackage Exception * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ class FileAlreadyExistsException extends EngineException { /** * FileAlreadyExistsException constructor. * * @param string $filename filename * @param int $code error code */ public function __construct($filename, $code) { parent::__construct(FILE_LANG_ERRMSG_EXISTS . " - " . $filename, $code); } } /** * File not found exception. * * @package Api * @subpackage Exception * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ class FileNotFoundException extends EngineException { /** * FileNotFoundException constructor. * * @param string $filename filename * @param int $code error code */ public function __construct($filename, $code) { parent::__construct(FILE_LANG_ERRMSG_NOTEXIST . " - " . $filename, $code); } } /** * File I/O exception. * * @package Api * @subpackage Exception * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ class FileIoException extends EngineException { /** * FileIoException constructor. * * @param string $filename filename * @param int $code error code */ public function __construct($filename, $code) { parent::__construct(FILE_LANG_ERRMSG_READ . " - " . $filename, $code); } } /** * Value not found in file exception. * * @package Api * @subpackage Exception * @author {@link http://www.pointclark.net/ Point Clark Networks} * @license http://www.gnu.org/copyleft/gpl.html GNU Public License * @copyright Copyright 2006, Point Clark Networks */ class FileNoMatchException extends EngineException { /** * FileNoMatchException constructor. * * @param string $filename filename * @param int $code error code * @param string $key key used to match a string */ public function __construct($filename, $code, $key) { parent::__construct(FILE_LANG_ERRMSG_NO_MATCH . " - $filename for key $key", $code); } } /////////////////////////////////////////////////////////////////////////////// // C L A S S /////////////////////////////////////////////////////////////////////////////// /** * File handling class. * * The File class can be use for creating, reading and manipulating the * contents of a file. If you need to change a configuration file, this may * be the class for you. However, configuration files come in many different * forms, so this might not have what you need. Feel free to do your own file * parsing. * * @package Api * @author Point Clark Networks * @license GNU Public License * @copyright Copyright 2006, Point Clark Networks */ class File extends Engine { /////////////////////////////////////////////////////////////////////////////// // F I E L D S /////////////////////////////////////////////////////////////////////////////// /** * @var string filename */ protected $filename = null; /** * @var superuser superuser */ protected $superuser = false; /** * @var boolean temporary Temporary file */ protected $temporary = false; /** * @var boolean contents loaded flag */ protected $contents = null; const CMD_RM = '/bin/rm'; const CMD_CAT = '/bin/cat'; const CMD_MOVE = '/bin/mv'; const CMD_COPY = '/bin/cp'; const CMD_TOUCH = '/bin/touch'; const CMD_CHOWN = '/bin/chown'; const CMD_CHMOD = '/bin/chmod'; const CMD_LS = '/bin/ls'; const CMD_MD5 = '/usr/bin/md5sum'; const CMD_FILE = '/usr/bin/file'; const CMD_HEAD = '/usr/bin/head'; const CMD_REPLACE = '/usr/sbin/cc-rename'; /////////////////////////////////////////////////////////////////////////////// // M E T H O D S /////////////////////////////////////////////////////////////////////////////// /** * File constructor. * * @param string filename target file * @param boolean $superuser superuser access required to read the file * @param boolean $temporary create a temporary file */ public function __construct($filename, $superuser = false, $temporary = false) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); if ($temporary) { $this->temporary = $temporary; $this->filename = tempnam(COMMON_TEMP_DIR, basename($filename)); } else $this->filename = $filename; $this->superuser = $superuser; parent::__construct(); require_once(GlobalGetLanguageTemplate(__FILE__)); } /** * Returns the filename. * * @return string name of file */ function GetFilename() { return $this->filename; } /** * Returns the contents of a file. * * Set maxbytes to -1 to disable file size limit. * * @param int $maxbytes maximum number of bytes * @return string contents of file * @throws FileNotFoundException, FileException */ function GetContents($maxbytes = -1) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); if (!is_int($maxbytes) || $maxbytes < -1) throw new ValidationException(LOCALE_LANG_ERRMSG_INVALID_TYPE, __METHOD__, __LINE__); $contents = $this->GetContentsAsArray($maxbytes); return implode("\n", $contents); } /** * Returns the contents of a file in an array. * * Set maxbytes to -1 to disable file size limit. * * @param int $maxbytes maximum number of bytes * @return array contents of file * @throws FileNotFoundException, FileException */ function GetContentsAsArray($maxbytes = -1) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); if (!is_int($maxbytes) || $maxbytes < -1) throw new ValidationException(LOCALE_LANG_ERRMSG_INVALID_TYPE, __METHOD__, __LINE__); if (! $this->Exists() ) throw new FileNotFoundException($this->filename, COMMON_INFO); // TODO: use some other semaphore -- this breaks with maxbytes set //if (is_null($this->contents)) { // If readable by webconfig, then use file_get_contents // If file_get_contents fails, try shellexec if (is_readable("$this->filename")) { $maxlen = ($maxbytes >= 0) ? $maxbytes : null; $contents = file_get_contents("$this->filename", false, NULL, 0, $maxlen); if ($contents) { $this->contents = explode("\n", rtrim($contents)); return $this->contents; } } try { $shell = new ShellExec(); if ($maxbytes >= 0) $exitcode = $shell->Execute(File::CMD_HEAD, "-c $maxbytes $this->filename", true); else $exitcode = $shell->Execute(File::CMD_CAT, escapeshellarg($this->filename), true); } catch (Exception $e) { throw new FileException($e->getMessage(), COMMON_WARNING); } if ($exitcode != 0) throw new FileException($shell->GetFirstOutputLine(), COMMON_WARNING); $this->contents = $shell->GetOutput(); return $this->contents; } /** * Returns the contents of a file that match the given regular expression. * * Set maxbytes to -1 to disable file size limit. * * @param string $regex search string * @param int $maxbytes maximum number of bytes * @return array contents of file * @throws FileNotFoundException, FileException */ function GetSearchResults($regex, $maxbytes = -1) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); if (!is_int($maxbytes) || $maxbytes < -1) throw new ValidationException(LOCALE_LANG_ERRMSG_INVALID_TYPE, __METHOD__, __LINE__); $contents = $this->GetContentsAsArray(); $result = array(); $count = 0; foreach ($contents as $line) { if (preg_match("/$regex/", $line)) { $result[] = $line; if ($maxbytes != -1) { $count += strlen($line); if ($count > $maxbytes) break; } } } return $result; } /** * Returns a value for a given unique regular expression. * * This method is handy for simple configuration files with key/value pairs. The * method will return a FileNoMatchException error if no match was made. * * @param string $key search string * @return string value for the give key * @throws ValidationException, FileNoMatchException, FileNotFoundException, FileException */ function LookupValue($key) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); // TODO: input validation (if any?) $contents = $this->GetContentsAsArray(); foreach ($contents as $line) { if (preg_match($key, $line)) { $result = preg_replace($key, "", $line); return trim($result); } } throw new FileNoMatchException($this->filename, COMMON_INFO, $key); } /** * Checks the existence of the file. * * @return boolean true if file exists * @throws FileException */ function Exists() { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); if ($this->superuser) { try { $shell = new ShellExec(); $exitcode = $shell->Execute(File::CMD_LS, escapeshellarg($this->filename), true); } catch (Exception $e) { throw new FileException($e->GetMessage(), COMMON_WARNING); } if ($exitcode == 0) return true; else return false; } else { clearstatcache(); if (file_exists("$this->filename")) return true; else return false; } } /** * Returns the file size. * * @return int the file size * @throws FileException */ function GetSize() { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); if (! $this->Exists()) throw new FileNotFoundException($this->filename, COMMON_INFO); try { $shell = new ShellExec(); $args = "-loL " . escapeshellarg($this->filename); $exitcode = $shell->Execute(self::CMD_LS, $args, true); } catch (Exception $e) { throw new FileException($e->GetMessage(), COMMON_WARNING); } if ($exitcode == 0) { $shell->GetLastOutputLine(); $parts = explode(" ", $shell->GetLastOutputLine()); return (int)$parts[4]; } else { throw new EngineException(LOCALE_LANG_ERRMSG_WEIRD, COMMON_WARNING); } } /** * Returns the MD5 hash of the file. * * @return string the MD5 hash * @throws FileException */ function GetMd5() { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); if (! $this->Exists()) throw new FileNotFoundException($this->filename, COMMON_INFO); if ($this->superuser) { $md5 = md5_file("$this->filename"); if ($md5) return $md5; try { $shell = new ShellExec(); $exitcode = $shell->Execute(self::CMD_MD5, escapeshellarg($this->filename), true); } catch (Exception $e) { throw new FileException($e->GetMessage(), COMMON_WARNING); } if ($exitcode == 0) { $md5 = trim(ereg_replace("$this->filename", "", $shell->GetLastOutputLine())); return $md5; } else { throw new EngineException(LOCALE_LANG_ERRMSG_WEIRD, COMMON_WARNING); } } else { return md5_file($this->GetFilename()); } } /** * Changes file mode. * * @param string $mode mode of the file * @return void * @throws ValidationException, FileNotFoundException, FilePermissionsException, FileException */ function Chmod($mode) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); // TODO: validate $mode if (! $this->Exists()) throw new FileNotFoundException($this->filename, COMMON_NOTICE); try { $shell = new ShellExec(); $exitcode = $shell->Execute(File::CMD_CHMOD, " $mode " . escapeshellarg($this->filename), true); } catch (Exception $e) { throw new FileException($e->GetMessage(), COMMON_WARNING); } if ($exitcode != 0) throw new FilePermissionsException(FILE_LANG_ERRMSG_CHMOD . " - " . $this->filename, COMMON_WARNING); } /** * Changes file owner and/or group. * * Leave the owner or group blank if you do not want change one or the other. * * @param string $owner file owner * @param string $group file group * @return void * @throws ValidationException, FileNotFoundException, FilePermissionsException, FileException */ function Chown($owner, $group) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); if (empty($owner) && empty($group)) throw new ValidationException(LOCALE_LANG_ERRMSG_NO_ENTRIES, __METHOD__, __LINE__); // TODO: more input validation if (! $this->Exists()) throw new FileNotFoundException($this->filename, COMMON_NOTICE); $shell = new ShellExec(); if (! empty($owner)) { try { $exitcode = $shell->Execute(File::CMD_CHOWN, "$owner " . escapeshellarg($this->filename), true); } catch (Exception $e) { throw new FileException($e->getMessage(), COMMON_WARNING); } if ($exitcode != 0) throw new FilePermissionsException(FILE_LANG_ERRMSG_CHOWN . " - " . $this->filename, COMMON_WARNING); } if (! empty($group)) { try { $exitcode = $shell->Execute(File::CMD_CHOWN, " :$group " . escapeshellarg($this->filename), true); } catch (Exception $e) { throw new FileException($e->getMessage(), COMMON_WARNING); } if ($exitcode != 0) throw new FilePermissionsException(FILE_LANG_ERRMSG_CHOWN . " - " . $this->filename, COMMON_WARNING); } } /** * Returns the octal permissions of the current file. * * @return string file permissions * @throws FileNotFoundException, FileException */ function GetPermissions() { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); clearstatcache(); if (! $this->Exists()) throw new FileNotFoundException($this->filename, COMMON_INFO); // TODO: this will fail on files that user webconfig cannot read (protected directories). // Added FileException to docs to futureproof API. return substr(sprintf('%o', fileperms("$this->filename")), -4); } /** * Returns the last modified date of the file. * * @return long representing time file was last modified * @throws FileNotFoundException, FileException */ function LastModified() { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); if (! $this->Exists()) throw new FileNotFoundException($this->filename, COMMON_INFO); if ($this->superuser) { try { $shell = new ShellExec(); $args = "-l --time-style=full-iso " . escapeshellarg($this->filename); $exitcode = $shell->Execute(self::CMD_LS, $args, true); } catch (Exception $e) { throw new FileException($e->GetMessage(), COMMON_WARNING); } if ($exitcode == 0) { $shell->GetLastOutputLine(); $parts = explode(" ", $shell->GetLastOutputLine()); return strtotime($parts[6] . " " . substr($parts[7], 0, 8) . " " . $parts[8]); } else { throw new EngineException(LOCALE_LANG_ERRMSG_WEIRD, COMMON_WARNING); } } else { clearstatcache(); return filemtime("$this->filename"); } } /** * Creates a file on the system. * * @param string $owner file owner * @param string $group file group * @param string $mode mode of the file * @return void * @throws FileAlreadyExistsException, FilePermissionsException, FileException */ function Create($owner, $group, $mode) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); clearstatcache(); if ($this->Exists()) throw new FileAlreadyExistsException($this->filename, COMMON_NOTICE); try { $shell = new ShellExec(); $shell->Execute(File::CMD_TOUCH, escapeshellarg($this->filename), true); if ($owner || $group) $this->Chown($owner, $group); if ($mode) $this->Chmod($mode); } catch (FilePermissionsException $e) { // Delete file if permissions barf, rethrow $this->Delete(); throw new FilePermissionsException($e->GetMessage(), COMMON_WARNING); } catch (Exception $e) { throw new FileException($e->getMessage(), COMMON_WARNING); } $this->contents = null; } /** * Deletes the file. * * @return void * @throws FileNotFoundException, FileException */ function Delete() { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); clearstatcache(); if (! $this->Exists()) throw new FileNotFoundException($this->filename, COMMON_NOTICE); try { $shell = new ShellExec(); $shell->Execute(File::CMD_RM, escapeshellarg($this->filename), true); } catch (Exception $e) { throw new FileException($e->getMessage(), COMMON_WARNING); } $this->contents = null; } /** * Checks to see if specified file is a directory. * * @return boolean true if file is a directory * @throws FileException */ function IsDirectory() { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); $isdir = false; if ($this->superuser) { try { $shell = new ShellExec(); $shell->Execute(File::CMD_FILE, escapeshellarg($this->filename), true); // TODO -- a hack if (preg_match("/directory/", $shell->GetOutput(0))) { $isdir = true; } } catch (Exception $e) { throw new FileException($e->getMessage(),COMMON_WARNING); } } else { $isdir = is_dir("$this->filename"); } return $isdir; } /** * Checks to see if specified file is a symbolic link. * * @return integer 0 if not, 1 if active sym link, -1 if broken sym link * @throws FileException */ function IsSymLink() { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); $issym = 0; if ($this->superuser) { try { $shell = new ShellExec(); $shell->Execute(File::CMD_FILE, escapeshellarg($this->filename), true); // TODO -- a hack if (preg_match("/symbolic link/", $shell->GetFirstOutputLine())) { if (preg_match("/broken/", $shell->GetFirstOutputLine())) $issym = -1; else $issym = 1; } else { $issym = 0; } } catch (Exception $e) { throw new FileException($e->getMessage(),COMMON_WARNING); } } else { if (is_link("$this->filename")) { if (! file_exists(readlink("$this->filename"))) $issym = -1; else $issym = 1; } else { $issym = 0; } } return $issym; } /** * Replaces the contents of the given tempfile to this file. * * This is basically a "mv" with the following behavior: * - This file (the one passed to the constructor) must exist. * - The tempfile is deleted if successful. * - The tempfile will take on the same file permissions and ownership as the target file. * * @param string $tempfile temp file * @return void * @throws FileNotFoundException FileException */ function Replace($tempfile) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); if (! file_exists($tempfile)) throw FileNotFoundException($tempfile, COMMON_NOTICE); if (! $this->Exists()) throw FileNotFoundException($this->filename, COMMON_NOTICE); $tempfile = escapeshellarg($tempfile); $thisfile = escapeshellarg($this->filename); try { $shell = new ShellExec(); $exitcode = $shell->Execute(self::CMD_REPLACE, "$tempfile $thisfile", true); } catch (Exception $e) { throw new FileException($e->getMessage(), COMMON_WARNING); } if ($exitcode != 0) { $errmsg = $shell->GetFirstOutputLine(); throw new FileException($errmsg, COMMON_WARNING); } $this->contents = null; } /** * Writes array data to a file. * * The method does not automatically add a newline - that is up to you! * This method will return an error if the file does not exist. * * @param array $contents an array containing output lines * @return void */ function DumpContentsFromArray($contents) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); $tempfile = tempnam(COMMON_TEMP_DIR, basename("$this->filename")); if (!($fh_t = @fopen($tempfile, "w"))) { $this->AddValidationError(FILE_LANG_ERRMSG_OPEN . $tempfile,__METHOD__,__LINE__); } else { if ($contents) fputs($fh_t, implode("\n", $contents) . "\n"); fclose($fh_t); $this->Replace($tempfile); } } /** * Appends data to a file. * * The method does not automatically add a newline - that is up to you! * * @param string $data line (or lines) to append to the file * @return void * @throws FileNotFoundException FileException */ function AddLines($data) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); $tempfile = tempnam(COMMON_TEMP_DIR, basename("$this->filename")); try { $contents = $this->GetContents(); } catch (Exception $e) { throw $e; } if (!($fh_t = @fopen($tempfile, "w"))) throw new FileException(FILE_LANG_ERRMSG_OPEN . " - " . $tempfile, COMMON_NOTICE); // Remove and then re-insert newline on files... // this catches invalid files with no newline at the end trim($contents); if ($contents) fputs($fh_t, $contents . "\n"); fputs($fh_t, $data); fclose($fh_t); $this->Replace($tempfile); $this->contents = null; } /** * Appends a line (or lines) to a file at a particular location in the file. * * @param string $data line(s) to insert into file * @param string $after regular expression defining the file location * @return void * @throws FileNoMatchException, FileNotFoundException, FileException */ function AddLinesAfter($data, $after) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); $tempfile = tempnam(COMMON_TEMP_DIR, basename("$this->filename")); $lines = $this->GetContentsAsArray(); if (!($fh_t = @fopen($tempfile, "w"))) throw new FileException(FILE_LANG_ERRMSG_OPEN . " - " . $tempfile, COMMON_NOTICE); $match = false; foreach ($lines as $line) { fputs($fh_t, $line . "\n"); if (preg_match($after, $line) && (!$match)) { $match = true; fputs($fh_t, $data); } } fclose($fh_t); if (! $match) { throw new FileNoMatchException($tempfile, COMMON_NOTICE, $after); unlink($tempfile); } $this->Replace($tempfile); $this->contents = null; } /** * Prepends a line (or lines) to a file at a particular location in the file. * * @param string $data line(s) to insert into file * @param string $before regular expression defining the file location * @return void * @throws FileNoMatchException, FileNotFoundException, FileException */ function AddLinesBefore($data, $before) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); $tempfile = tempnam(COMMON_TEMP_DIR, basename("$this->filename")); $lines = $this->GetContentsAsArray(); if (!($fh_t = @fopen($tempfile, "w"))) throw new FileException(FILE_LANG_ERRMSG_OPEN . " - " . $tempfile, COMMON_NOTICE); $match = false; foreach ($lines as $line) { if (preg_match($before, $line) && (!$match)) { $match = true; fputs($fh_t, $data); } fputs($fh_t, $line . "\n"); } fclose($fh_t); if (! $match) { throw new FileNoMatchException($tempfile, COMMON_NOTICE, $before); unlink($tempfile); } $this->Replace($tempfile); $this->contents = null; } /** * Removes lines from a file that match the regular expression. * * @param string $search regular expression used to match removed lines * @return integer number of lines deleted * @throws FileNotFoundException Exception (inherited from GetContents) */ function DeleteLines($search) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); $deleted = $this->ReplaceLines($search, ''); $this->contents = null; return $deleted; } /** * Prepends lines with a string (usually a comment character). * * Any line matching the search string will be changed. * * @param string $prepend prepend string * @param string $search regular expression used to match removed lines * @return boolean true if any matches were made * @throws FileNotFoundException Exception (inherited from GetContentsAsArray) */ function PrependLines($search, $prepend) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); $prependlines = false; $tempfile = tempnam(COMMON_TEMP_DIR, basename("$this->filename")); $lines = $this->GetContentsAsArray(); if (!($fh_t = @fopen($tempfile, "w"))) { $this->AddValidationError(FILE_LANG_ERRMSG_OPEN . $tempfile,__METHOD__,__LINE__); } else { $match = false; foreach ($lines as $line) { if (preg_match($search, $line)) { fputs($fh_t, $prepend . $line . "\n"); $match = true; } else { fputs($fh_t, $line . "\n"); } } fclose($fh_t); if (! $match) { $this->AddValidationError(LOCALE_LANG_ERRMSG_NO_MATCH,__METHOD__,__LINE__); unlink($tempfile); } else { $prependlines = $this->Replace($tempfile); } } return $prependlines; } /** * Searches the file with the given regular expression and returns the first match. * * @param string $search regular expression * @return string matching line * @throws ValidationException, FileNoMatchException, FileNotFoundException, FileException */ function LookupLine($search) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); // TODO: validation (e.g. search must have two slashes) $lines = $this->GetContentsAsArray(); foreach ($lines as $line) { if (preg_match($search, $line)) { return $line; } } throw new FileNoMatchException($this->filename, COMMON_INFO, $search); } /** * Similar to LookupValue, except you can specify a subsection of the target file. * * The start and end are regular expressions. This can be handy in Apache-style configuration * files (e.g. configuring a particular Virtual Host). This method will * return a PLATFORM_EXCEPTION_LOOKUP_NO_MATCH error if no match was made. * * @param string $key search string * @param string $start regular expression specifying the start line * @param string $end regular expression specifying the end line * @return string value for the give key * @throws FileNotFoundException Exception (inherited from GetContentsAsArray) * @throws FileNoMatchException */ function LookupValueBetween($key, $start, $end) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); try { $lines = $this->GetContentsAsArray(); } catch (Exception $e) { throw $e; } // Find start tag foreach ($lines as $line) { if (preg_match($start, $line)) break; array_shift($lines); } foreach ($lines as $line) { // Bail if see the end tag if (preg_match($end, $line)) break; if (preg_match($key, $line)) { $result = trim(preg_replace($key, "", $line)); if (!strlen($result)) return true; return $result; } } throw new FileNoMatchException($this->filename, COMMON_INFO, $key); } /** * Copies the file to new location. * * @param string $destination destination location * @return void * @throws FileException, ValidationException */ function CopyTo($destination) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); // TODO: validate destination try { $shell = new ShellExec(); $exitcode = $shell->Execute(File::CMD_COPY, "-a " . escapeshellarg($this->filename) . " " . escapeshellarg($destination), true); } catch (Exception $e) { throw new FileException($e->getMessage(), COMMON_WARNING); } if ($exitcode != 0) { $errmsg = $shell->GetOutput(); throw new FileException($errmsg[0], COMMON_WARNING); } } /** * Moves the file to new location. * * @see Replace * @param string $destination destination location * @return void * @throws FileException, ValidationException */ function MoveTo($destination) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); // TODO: validate destination try { $shell = new ShellExec(); $exitcode = $shell->Execute(File::CMD_MOVE, escapeshellarg($this->filename) . " " . escapeshellarg($destination), true); } catch (Exception $e) { throw new FileException($e->getMessage(),COMMON_WARNING); } if ($exitcode != 0) { $errmsg = $shell->GetOutput(); throw new FileException($errmsg[0], COMMON_WARNING); } $this->filename = $destination; } /** * Replaces lines in a section of a file for Apache-style configuration files. * * Specify the (non-unique) start and end tags along with a search value that uniquely defines the section. * * @param string $start regular expression specifying the start line * @param string $end regular expression specifying the end line * @param string $search regular expression for the search string * @param string $replacement replacement line * @return void * @throws FileNotFoundException Exception (inherited from GetContentsAsArray) */ function ReplaceLinesBetween($search, $replacement, $start, $end) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); $replaced = false; $tempfile = tempnam(COMMON_TEMP_DIR, basename("$this->filename")); $lines = $this->GetContentsAsArray(); if (!($fh_t = @fopen($tempfile, "w"))) { $this->AddValidationError(FILE_LANG_ERRMSG_OPEN . $tempfile,__METHOD__,__LINE__); } else { // Find start tag $match = false; foreach ($lines as $line) { if (preg_match($start, $line)) break; fputs($fh_t, $line . "\n"); array_shift($lines); } foreach ($lines as $line) { // Bail if see the end tag if (preg_match($end, $line)) break; if (preg_match($search, $line)) { $match = true; if (strlen($replacement)) fputs($fh_t, $replacement); } else { fputs($fh_t, $line . "\n"); } array_shift($lines); } foreach ($lines as $line) fputs($fh_t, $line . "\n"); fclose($fh_t); if (! $match) { $this->AddValidationError(LOCALE_LANG_ERRMSG_NO_MATCH,__METHOD__,__LINE__); unlink($tempfile); } else { $replaced = $this->Replace($tempfile); } } return $match; } /** * Replaces a line (defined by a regular expression) with a replacement. * * @param string $search search string * @param string $replacement replacement line (or lines) * @param integer $maxreplaced maximum number of matches to make * @return integer number of replacements made * @throws FileException, ValidationException */ function ReplaceLines($search, $replacement, $maxreplaced = -1) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); // TODO: add validation $replaced = 0; $tempfile = tempnam(COMMON_TEMP_DIR, basename("$this->filename")); $lines = $this->GetContentsAsArray(); if (!($fh_t = @fopen($tempfile, "w"))) throw new FileException(FILE_LANG_ERRMSG_OPEN . " - " . $tempfile, COMMON_NOTICE); // Find start tag foreach ($lines as $line) { if (preg_match($search, $line) && (($replaced < $maxreplaced) || $maxreplaced == -1)) { fputs($fh_t, $replacement); $replaced++; } else { fputs($fh_t, $line . "\n"); } } fclose($fh_t); if ($replaced == 0) { unlink($tempfile); return 0; } else { $this->Replace($tempfile); } $this->contents = null; return $replaced; } /** * Replaces a line defined by a regular expression. * * @param string $search search string * @param string $replacement replacement line (or lines) * @return integer number of replacements made * @throws FileNotFoundException, FileException */ // TODO: deprecate function ReplaceOneLine($search, $replacement) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); return $this->ReplaceLines($search, $replacement, 1); } /** * Replaces a line defined by a regular expression. * * This method will throw a PLATFORM_EXCEPTION_LOOKUP_NO_MATCH * if a match is not found. This version differs from ReplaceOneLine * in that it uses preg_replace to do the substitution. Thus you can * use parts of a pattern match in the replacement (ie: $1, $2, etc). * * @param string $search search expression * @param string $replacement replacement expression * @return boolean true if any replacements were made * @throws FileNotFoundException Exception (inherited from GetContentsAsArray) */ function ReplaceOneLineByPattern($search, $replacement) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); $replaced = false; $tempfile = tempnam(COMMON_TEMP_DIR, basename("$this->filename")); $lines = $this->GetContentsAsArray(); if (!($fh_t = @fopen($tempfile, "w"))) { $this->AddValidationError(FILE_LANG_ERRMSG_OPEN . $tempfile,__METHOD__,__LINE__); } else { $match = false; foreach ($lines as $line) { if ((preg_match($search, $line)) && !$match) { $match = preg_replace($search, $replacement, $line); if ($match) fputs($fh_t, $match . "\n"); } else fputs($fh_t, $line . "\n"); } fclose($fh_t); if (! $match) { $this->AddValidationError(LOCALE_LANG_ERRMSG_NO_MATCH,__METHOD__,__LINE__); unlink($tempfile); } else { $replaced = $this->Replace($tempfile); } } return $replaced; } /** * Replaces all matching lines defined by a regular expression. * * This method will throw a PLATFORM_EXCEPTION_LOOKUP_NO_MATCH * if a match is not found. * * @param string $search search expression * @param string $replacement replacement expression * @return boolean true if any replacements were made * @throws FileNotFoundException Exception (inherited from GetContentsAsArray) */ function ReplaceLinesByPattern($search, $replacement) { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); $replaced = false; $tempfile = tempnam(COMMON_TEMP_DIR, basename("$this->filename")); $lines = $this->GetContentsAsArray(); if (!($fh_t = @fopen($tempfile, "w"))) { $this->AddValidationError(FILE_LANG_ERRMSG_OPEN . $tempfile,__METHOD__,__LINE__); } else { $match = false; foreach ($lines as $line) { if ((preg_match($search, $line))) { $match = preg_replace($search, $replacement, $line); if ($match) fputs($fh_t, $match . "\n"); } else fputs($fh_t, $line . "\n"); } fclose($fh_t); if (! $match) { $this->AddValidationError(LOCALE_LANG_ERRMSG_NO_MATCH,__METHOD__,__LINE__); unlink($tempfile); } else { $replaced = $this->Replace($tempfile); } } return $replaced; } /** * @access private */ function __destruct() { if (COMMON_DEBUG_MODE) $this->Log(COMMON_DEBUG, "called", __METHOD__, __LINE__); parent::__destruct(); } } // vim: syntax=php ts=4 ?>
赞赏
他的文章
- [原创]在Windows驱动中使用PCRE正则表达式 9444
- [求助]ssdt hook API造成驱动启动失败是什么原因 6077
- [求助]一个怪怪的算法. 4735
- [求助]有人能看出这是什么算法吗 6369
看原图
赞赏
雪币:
留言: