From: Roland Häder Date: Sat, 31 May 2008 15:13:56 +0000 (+0000) Subject: Renamed a folder, database client added X-Git-Url: https://git.mxchange.org/?a=commitdiff_plain;h=b1583f59560e2878c10df2c485cc3a63a309ac3c;p=shipsimu.git Renamed a folder, database client added --- diff --git a/.gitattributes b/.gitattributes index 332a418..d919845 100644 --- a/.gitattributes +++ b/.gitattributes @@ -151,6 +151,8 @@ inc/classes/exceptions/container/class_ContainerMaybeDamagedException.php -text inc/classes/exceptions/controller/.htaccess -text inc/classes/exceptions/controller/class_DefaultControllerException.php -text inc/classes/exceptions/database/.htaccess -text +inc/classes/exceptions/database/clients/.htaccess -text +inc/classes/exceptions/database/clients/class_ClientUserNameNotFoundException.php -text inc/classes/exceptions/database/local_file/.htaccess -text inc/classes/exceptions/database/local_file/class_SavePathIsEmptyException.php -text inc/classes/exceptions/database/local_file/class_SavePathIsNoDirectoryException.php -text @@ -282,9 +284,13 @@ inc/classes/main/controller/default/class_WebDefaultNewsController.php -text inc/classes/main/controller/form/.htaccess -text inc/classes/main/controller/form/class_WebDoFormController.php -text inc/classes/main/database/.htaccess -text +inc/classes/main/database/class_ -text +inc/classes/main/database/class_BaseDatabaseClient.php -text inc/classes/main/database/class_BaseDatabaseFrontend.php -text -inc/classes/main/database/classes/.htaccess -text -inc/classes/main/database/classes/class_LocalFileDatabase.php -text +inc/classes/main/database/clients/.htaccess -text +inc/classes/main/database/clients/class_UserDatabaseClient.php -text +inc/classes/main/database/databases/.htaccess -text +inc/classes/main/database/databases/class_LocalFileDatabase.php -text inc/classes/main/debug/.htaccess -text inc/classes/main/debug/class_DebugConsoleOutput.php -text inc/classes/main/debug/class_DebugErrorLogOutput.php -text diff --git a/inc/classes/exceptions/database/clients/.htaccess b/inc/classes/exceptions/database/clients/.htaccess new file mode 100644 index 0000000..3a42882 --- /dev/null +++ b/inc/classes/exceptions/database/clients/.htaccess @@ -0,0 +1 @@ +Deny from all diff --git a/inc/classes/exceptions/database/clients/class_ClientUserNameNotFoundException.php b/inc/classes/exceptions/database/clients/class_ClientUserNameNotFoundException.php new file mode 100644 index 0000000..d6fe7ed --- /dev/null +++ b/inc/classes/exceptions/database/clients/class_ClientUserNameNotFoundException.php @@ -0,0 +1,47 @@ + + * @version 0.0.0 + * @copyright Copyright(c) 2007, 2008 Roland Haeder, this is free software + * @license GNU GPL 3.0 or any newer version + * @link http://www.ship-simu.org + * + * 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 3 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, see . + */ +class ClientUserNameNotFoundException extends FrameworkException { + /** + * The constructor + * + * @param $msgArray Message from the exception + * @param $code Code number for the exception + * @return void + */ + public function __construct (array $msgArray, $code) { + // Add a message around the missing class + $message = sprintf("[%s:%d] Username %s was not found. Requesting class: %s", + $msgArray[0]->__toString(), + $this->getLine(), + $msgArray[1]->getUserName(), + $msgArray[1]->__toString() + ); + + // Call parent constructor + parent::__construct($message, $code); + } +} + +// [EOF] +?> diff --git a/inc/classes/main/database/class_ b/inc/classes/main/database/class_ new file mode 100644 index 0000000..661b38f --- /dev/null +++ b/inc/classes/main/database/class_ @@ -0,0 +1,48 @@ + + * @version 0.0.0 + * @copyright Copyright(c) 2007, 2008 Roland Haeder, this is free software + * @license GNU GPL 3.0 or any newer version + * @link http://www.ship-simu.org + * + * 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 3 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, see . + */ +class extends BaseDatabaseFrontend { + /** + * Protected constructor + * + * @return void + */ + protected function __construct($class) { + // Call parent constructor + parent::constructor(__CLASS__); + + // Set part description + $this->setObjectDescription(""); + + // Create unique ID number + $this->createUniqueID(); + + // Clean up a little + $this->removeNumberFormaters(); + $this->removeSystemArray(); + } +} + +// [EOF] +?> diff --git a/inc/classes/main/database/class_BaseDatabaseClient.php b/inc/classes/main/database/class_BaseDatabaseClient.php new file mode 100644 index 0000000..8117c38 --- /dev/null +++ b/inc/classes/main/database/class_BaseDatabaseClient.php @@ -0,0 +1,41 @@ + + * @version 0.0.0 + * @copyright Copyright(c) 2007, 2008 Roland Haeder, this is free software + * @license GNU GPL 3.0 or any newer version + * @link http://www.ship-simu.org + * + * 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 3 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, see . + */ +class BaseDatabaseClient extends BaseFrameworkSystem { + /** + * Protected constructor + * + * @return void + */ + protected function __construct($class) { + // Call parent constructor + parent::__construct($class); + + // Clean up a little + $this->removeNumberFormaters(); + $this->removeSystemArray(); + } +} + +// [EOF] +?> diff --git a/inc/classes/main/database/classes/.htaccess b/inc/classes/main/database/classes/.htaccess deleted file mode 100644 index 3a42882..0000000 --- a/inc/classes/main/database/classes/.htaccess +++ /dev/null @@ -1 +0,0 @@ -Deny from all diff --git a/inc/classes/main/database/classes/class_LocalFileDatabase.php b/inc/classes/main/database/classes/class_LocalFileDatabase.php deleted file mode 100644 index 432a168..0000000 --- a/inc/classes/main/database/classes/class_LocalFileDatabase.php +++ /dev/null @@ -1,465 +0,0 @@ - - * @version 0.0.0 - * @copyright Copyright(c) 2007, 2008 Roland Haeder, this is free software - * @license GNU GPL 3.0 or any newer version - * @link http://www.ship-simu.org - * - * 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 3 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, see . - */ -class LocalFileDatabase extends BaseDatabaseFrontend implements DatabaseFrontendInterface { - /** - * Save path for "file database" - */ - private $savePath = ""; - - /** - * The file's extension - */ - private $fileExtension = "serialized"; - - /** - * The last read file's name - */ - private $lastFile = ""; - - /** - * The last read file's content including header information - */ - private $lastContents = array(); - - /** - * The private constructor. Do never instance from outside! - * You need to set a local file path. The class will then validate it. - * - * @return void - */ - protected function __construct() { - // Call parent constructor - parent::__construct(__CLASS__); - - // Set description - $this->setObjectDescription("Class for local file databases"); - - // Create unique ID - $this->createUniqueID(); - - // Clean up a little - $this->removeSystemArray(); - } - - /** - * Create an object of LocalFileDatabase and set the save path for local files. - * This method also validates the given file path. - * - * @param $savePath The local file path string - * @param $ioInstance The input/output handler. This - * should be FileIoHandler - * @return $dbInstance An instance of LocalFileDatabase - * @throws SavePathIsEmptyException If the given save path is an - * empty string - * @throws SavePathIsNoDirectoryException If the save path is no - * path (e.g. a file) - * @throws SavePathReadProtectedException If the save path is read- - * protected - * @throws SavePathWriteProtectedException If the save path is write- - * protected - */ - public final static function createLocalFileDatabase ($savePath, FileIoHandler $ioInstance) { - // Get an instance - $dbInstance = new LocalFileDatabase(); - - if (empty($savePath)) { - // Empty string - throw new SavePathIsEmptyException($dbInstance, self::EXCEPTION_UNEXPECTED_EMPTY_STRING); - } elseif (!is_dir($savePath)) { - // Is not a dir - throw new SavePathIsNoDirectoryException($savePath, self::EXCEPTION_INVALID_PATH_NAME); - } elseif (!is_readable($savePath)) { - // Path not readable - throw new SavePathReadProtectedException($savePath, self::EXCEPTION_READ_PROTECED_PATH); - } elseif (!is_writeable($savePath)) { - // Path not writeable - throw new SavePathWriteProtectedException($savePath, self::EXCEPTION_WRITE_PROTECED_PATH); - } - - // Set save path and IO instance - $dbInstance->setSavePath($savePath); - $dbInstance->setFileIoInstance($ioInstance); - - // Return database instance - return $dbInstance; - } - - /** - * Setter for save path - * - * @param $savePath The local save path where we shall put our serialized classes - * @return void - */ - public final function setSavePath ($savePath) { - // Secure string - $savePath = (string) $savePath; - - // Set save path - $this->savePath = $savePath; - } - - /** - * Getter for save path - * - * @return $savePath The local save path where we shall put our serialized classes - */ - public final function getSavePath () { - return $this->savePath; - } - - /** - * Saves a given object to the local file system by serializing and - * transparently compressing it - * - * @param $object The object we shall save to the local file system - * @return void - * @throws NullPointerException If the object instance is null - * @throws NoObjectException If the parameter $object is not - * an object - */ - public final function saveObject ($object) { - // Some tests on the parameter... - if (is_null($object)) { - // Is null, throw exception - throw new NullPointerException($object, self::EXCEPTION_IS_NULL_POINTER); - } elseif (!is_object($object)) { - // Is not an object, throw exception - throw new NoObjectException($object, self::EXCEPTION_IS_NO_OBJECT); - } elseif (!method_exists($object, '__toString')) { - // A highly required method was not found... :-( - throw new MissingMethodException(array($object, '__toString'), self::EXCEPTION_MISSING_METHOD); - } - - // Get a string containing the serialized object. We cannot exchange - // $this and $object here because $object does not need to worry - // about it's limitations... ;-) - $serialized = $this->serializeObject($object); - - // Get a path name plus file name and append the extension - $fqfn = $this->getSavePath() . $object->getPathFileNameFromObject() . "." . $this->getFileExtension(); - - // Save the file to disc we don't care here if the path is there, - // this must be done in later methods. - $this->getFileIoInstance()->saveFile($fqfn, array($this->getCompressorChannel()->getCompressorExtension(), $serialized)); - } - - /** - * Get a serialized string from the given object - * - * @param $object The object we want to serialize and transparently - * compress - * @return $serialized A string containing the serialzed/compressed object - * @see ObjectLimits An object holding limition information - * @see SerializationContainer A special container class for e.g. - * attributes from limited objects - */ - private function serializeObject ($object) { - // If there is no limiter instance we serialize the whole object - // otherwise only in the limiter object (ObjectLimits) specified - // attributes summarized in a special container class - if ($this->getLimitInstance() === null) { - // Serialize the whole object. This tribble call is the reason - // why we need a fall-back implementation in CompressorChannel - // of the methods compressStream() and decompressStream(). - $serialized = $this->getCompressorChannel()->getCompressor()->compressStream(serialize($object)); - } else { - // Serialize only given attributes in a special container - $container = SerializationContainer::createSerializationContainer($this->getLimitInstance(), $object); - - // Serialize the container - $serialized = $this->getCompressorChannel()->getCompressor()->compressStream(serialize($container)); - } - - // Return the serialized object string - return $serialized; - } - - /** - * Analyses if a unique ID has already been used or not by search in the - * local database folder. - * - * @param $uniqueID A unique ID number which shall be checked - * before it will be used - * @param $inConstructor If we got called in a de/con-structor or - * from somewhere else - * @return $isUnused true = The unique ID was not found in the database, - * false = It is already in use by an other object - * @throws NoArrayCreatedException If explode() fails to create an array - * @throws InvalidArrayCountException If the array contains less or - * more than two elements - */ - public function isUniqueIdUsed ($uniqueID, $inConstructor = false) { - // Currently not used... ;-) - $isUsed = false; - - // Split the unique ID up in path and file name - $pathFile = explode("@", $uniqueID); - - // Are there two elements? Index 0 is the path, 1 the file name + global extension - if (!is_array($pathFile)) { - // No array found - if ($inConstructor) { - return false; - } else { - throw new NoArrayCreatedException(array($this, "pathFile"), self::EXCEPTION_ARRAY_EXPECTED); - } - } elseif (count($pathFile) != 2) { - // Invalid ID returned! - if ($inConstructor) { - return false; - } else { - throw new InvalidArrayCountException(array($this, "pathFile", count($pathFile), 2), self::EXCEPTION_ARRAY_HAS_INVALID_COUNT); - } - } - - // Create full path name - $pathName = $this->getSavePath() . $pathFile[0]; - - // Check if the file is there with a file handler - if ($inConstructor) { - // No exceptions in constructors and destructors! - $dirInstance = FrameworkDirectoryPointer::createFrameworkDirectoryPointer($pathName, true); - - // Has an object being created? - if (!is_object($dirInstance)) return false; - } else { - // Outside a constructor - try { - $dirInstance = FrameworkDirectoryPointer::createFrameworkDirectoryPointer($pathName); - } catch (PathIsNoDirectoryException $e) { - // Okay, path not found - return false; - } - } - - // Initialize the search loop - $isValid = false; - while ($dataFile = $dirInstance->readDirectoryExcept(array(".", ".."))) { - // Generate FQFN for testing - $fqfn = sprintf("%s/%s", $pathName, $dataFile); - $this->setLastFile($fqfn); - - // Get instance for file handler - $inputHandler = $this->getFileIoInstance(); - - // Try to read from it. This makes it sure that the file is - // readable and a valid database file - $this->setLastFileContents($inputHandler->loadFileContents($fqfn)); - - // Extract filename (= unique ID) from it - $ID = substr(basename($fqfn), 0, -(strlen($this->getFileExtension()) + 1)); - - // Is this the required unique ID? - if ($ID == $pathFile[1]) { - // Okay, already in use! - $isUsed = true; - } - } - - // Close the directory handler - $dirInstance->closeDirectory(); - - // Now the same for the file... - return $isUsed; - } - - /** - * Setter for the last read file - * - * @param $fqfn The FQFN of the last read file - * @return void - */ - private final function setLastFile ($fqfn) { - // Cast string - $fqfn = (string) $fqfn; - $this->lastFile = $fqfn; - } - - /** - * Getter for last read file - * - * @return $lastFile The last read file's name with full path - */ - public final function getLastFile () { - return $this->lastFile; - } - - /** - * Setter for contents of the last read file - * - * @param $contents An array with header and data elements - * @return void - */ - private final function setLastFileContents ($contents) { - // Cast array - $contents = (array) $contents; - $this->lastContents = $contents; - } - - /** - * Getter for last read file's content as an array - * - * @return $lastContent The array with elements 'header' and 'data'. - */ - public final function getLastContents () { - return $this->lastContents; - } - - /** - * Getter for file extension - * - * @return $fileExtension The array with elements 'header' and 'data'. - */ - public final function getFileExtension () { - return $this->fileExtension; - } - - /** - * Get cached (last fetched) data from the local file database - * - * @param $uniqueID The ID number for looking up the data - * @return $object The restored object from the maybe compressed - * serialized data - * @throws MismatchingCompressorsException If the compressor from - * the loaded file - * mismatches with the - * current used one. - * @throws NullPointerException If the restored object - * is null - * @throws NoObjectException If the restored "object" - * is not an object instance - * @throws MissingMethodException If the required method - * toString() is missing - */ - public final function getObjectFromCachedData ($uniqueID) { - // Get instance for file handler - $inputHandler = $this->getFileIoInstance(); - - // Get last file's name and contents - $fqfn = $this->repairFQFN($this->getLastFile(), $uniqueID); - $contents = $this->repairContents($this->getLastContents(), $fqfn); - - // Let's decompress it. First we need the instance - $compressInstance = $this->getCompressorChannel(); - - // Is the compressor's extension the same as the one from the data? - if ($compressInstance->getCompressorExtension() != $contents['header'][0]) { - /** - * @todo For now we abort here but later we need to make this a little more dynamic. - */ - throw new MismatchingCompressorsException(array($this, $contents['header'][0], $fqfn, $compressInstance->getCompressorExtension()), self::EXCEPTION_MISMATCHING_COMPRESSORS); - } - - // Decompress the data now - $serialized = $compressInstance->getCompressor()->decompressStream($contents['data']); - - // And unserialize it... - $object = unserialize($serialized); - - // This must become a valid object, so let's check it... - if (is_null($object)) { - // Is null, throw exception - throw new NullPointerException($object, self::EXCEPTION_IS_NULL_POINTER); - } elseif (!is_object($object)) { - // Is not an object, throw exception - throw new NoObjectException($object, self::EXCEPTION_IS_NO_OBJECT); - } elseif (!method_exists($object, '__toString')) { - // A highly required method was not found... :-( - throw new MissingMethodException(array($object, '__toString'), self::EXCEPTION_MISSING_METHOD); - } - - // And return the object - return $object; - } - - /** - * Private method for re-gathering (repairing) the FQFN - * - * @param $fqfn The current FQFN we shall validate - * @param $uniqueID The unique ID number - * @return $fqfn The repaired FQFN when it is empty - * @throws NoArrayCreatedException If explode() has not - * created an array - * @throws InvalidArrayCountException If the array count is not - * as the expected - */ - private function repairFQFN ($fqfn, $uniqueID) { - // Cast both strings - $fqfn = (string) $fqfn; - $uniqueID = (string) $uniqueID; - - // Is there pre-cached data available? - if (empty($fqfn)) { - // Split the unique ID up in path and file name - $pathFile = explode("@", $uniqueID); - - // Are there two elements? Index 0 is the path, 1 the file name + global extension - if (!is_array($pathFile)) { - // No array found - throw new NoArrayCreatedException(array($this, "pathFile"), self::EXCEPTION_ARRAY_EXPECTED); - } elseif (count($pathFile) != 2) { - // Invalid ID returned! - throw new InvalidArrayCountException(array($this, "pathFile", count($pathFile), 2), self::EXCEPTION_ARRAY_HAS_INVALID_COUNT); - } - - // Create full path name - $pathName = $this->getSavePath() . $pathFile[0]; - - // Nothing cached, so let's create a FQFN first - $fqfn = sprintf("%s/%s.%s", $pathName, $pathFile[1], $this->getFileExtension()); - $this->setLastFile($fqfn); - } - - // Return repaired FQFN - return $fqfn; - } - - /** - * Private method for re-gathering the contents of a given file - * - * @param $contents The (maybe) already cached contents as an array - * @param $fqfn The current FQFN we shall validate - * @return $contents The repaired contents from the given file - */ - private function repairContents ($contents, $fqfn) { - // Is there some content and header (2 indexes) in? - if ((!is_array($contents)) || (count($contents) != 2) || (!isset($contents['header'])) || (!isset($contents['data']))) { - // No content found so load the file again - $contents = $inputHandler->loadFileContents($fqfn); - - // And remember all data for later usage - $this->setLastContents($contents); - } - - // Return the repaired contents - return $contents; - } - - /* DUMMY */ public final function loadObject () {} -} - -// [EOF] -?> diff --git a/inc/classes/main/database/clients/.htaccess b/inc/classes/main/database/clients/.htaccess new file mode 100644 index 0000000..3a42882 --- /dev/null +++ b/inc/classes/main/database/clients/.htaccess @@ -0,0 +1 @@ +Deny from all diff --git a/inc/classes/main/database/clients/class_UserDatabaseClient.php b/inc/classes/main/database/clients/class_UserDatabaseClient.php new file mode 100644 index 0000000..2790d85 --- /dev/null +++ b/inc/classes/main/database/clients/class_UserDatabaseClient.php @@ -0,0 +1,72 @@ + + * @version 0.0.0 + * @copyright Copyright(c) 2007, 2008 Roland Haeder, this is free software + * @license GNU GPL 3.0 or any newer version + * @link http://www.ship-simu.org + * + * 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 3 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, see . + */ +class UserDatabaseClient extends BaseDatabaseClient { + // Constants + const EXCEPTION_CLIENT_USERNAME_NOT_FOUND = 0xe00; + + /** + * Protected constructor + * + * @return void + */ + protected function __construct() { + // Call parent constructor + parent::__construct(__CLASS__); + + // Set part description + $this->setObjectDescription("Database client for user objects"); + + // Create unique ID number + $this->createUniqueID(); + } + + /** + * Creates an instance of this database client by a provided user class + * + * @param $userInstance An instance of a user class + * @return $clientInstance An instance of the created client class + * @throws ClientUserNameNotFoundException If the supplied username + * does not exist + */ + public final static function createUserDatabaseClient (ManageableUser $userInstance) { + // Get a new instance + $clientInstance = new UserDatabaseClient(); + + // Does the username exists? + if (!$clientInstance->ifUserNameExists($userInstance->getUserName())) { + // Throw an exception here + throw new ClientUserNameNotFoundException (array($clientInstance, $userInstance), self::EXCEPTION_CLIENT_USERNAME_NOT_FOUND); + } + + // The user exists + $clientInstance->partialStub("Add loading of full user details"); + + // Return the instance + return $clientInstance; + } +} + +// [EOF] +?> diff --git a/inc/classes/main/database/databases/.htaccess b/inc/classes/main/database/databases/.htaccess new file mode 100644 index 0000000..3a42882 --- /dev/null +++ b/inc/classes/main/database/databases/.htaccess @@ -0,0 +1 @@ +Deny from all diff --git a/inc/classes/main/database/databases/class_LocalFileDatabase.php b/inc/classes/main/database/databases/class_LocalFileDatabase.php new file mode 100644 index 0000000..432a168 --- /dev/null +++ b/inc/classes/main/database/databases/class_LocalFileDatabase.php @@ -0,0 +1,465 @@ + + * @version 0.0.0 + * @copyright Copyright(c) 2007, 2008 Roland Haeder, this is free software + * @license GNU GPL 3.0 or any newer version + * @link http://www.ship-simu.org + * + * 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 3 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, see . + */ +class LocalFileDatabase extends BaseDatabaseFrontend implements DatabaseFrontendInterface { + /** + * Save path for "file database" + */ + private $savePath = ""; + + /** + * The file's extension + */ + private $fileExtension = "serialized"; + + /** + * The last read file's name + */ + private $lastFile = ""; + + /** + * The last read file's content including header information + */ + private $lastContents = array(); + + /** + * The private constructor. Do never instance from outside! + * You need to set a local file path. The class will then validate it. + * + * @return void + */ + protected function __construct() { + // Call parent constructor + parent::__construct(__CLASS__); + + // Set description + $this->setObjectDescription("Class for local file databases"); + + // Create unique ID + $this->createUniqueID(); + + // Clean up a little + $this->removeSystemArray(); + } + + /** + * Create an object of LocalFileDatabase and set the save path for local files. + * This method also validates the given file path. + * + * @param $savePath The local file path string + * @param $ioInstance The input/output handler. This + * should be FileIoHandler + * @return $dbInstance An instance of LocalFileDatabase + * @throws SavePathIsEmptyException If the given save path is an + * empty string + * @throws SavePathIsNoDirectoryException If the save path is no + * path (e.g. a file) + * @throws SavePathReadProtectedException If the save path is read- + * protected + * @throws SavePathWriteProtectedException If the save path is write- + * protected + */ + public final static function createLocalFileDatabase ($savePath, FileIoHandler $ioInstance) { + // Get an instance + $dbInstance = new LocalFileDatabase(); + + if (empty($savePath)) { + // Empty string + throw new SavePathIsEmptyException($dbInstance, self::EXCEPTION_UNEXPECTED_EMPTY_STRING); + } elseif (!is_dir($savePath)) { + // Is not a dir + throw new SavePathIsNoDirectoryException($savePath, self::EXCEPTION_INVALID_PATH_NAME); + } elseif (!is_readable($savePath)) { + // Path not readable + throw new SavePathReadProtectedException($savePath, self::EXCEPTION_READ_PROTECED_PATH); + } elseif (!is_writeable($savePath)) { + // Path not writeable + throw new SavePathWriteProtectedException($savePath, self::EXCEPTION_WRITE_PROTECED_PATH); + } + + // Set save path and IO instance + $dbInstance->setSavePath($savePath); + $dbInstance->setFileIoInstance($ioInstance); + + // Return database instance + return $dbInstance; + } + + /** + * Setter for save path + * + * @param $savePath The local save path where we shall put our serialized classes + * @return void + */ + public final function setSavePath ($savePath) { + // Secure string + $savePath = (string) $savePath; + + // Set save path + $this->savePath = $savePath; + } + + /** + * Getter for save path + * + * @return $savePath The local save path where we shall put our serialized classes + */ + public final function getSavePath () { + return $this->savePath; + } + + /** + * Saves a given object to the local file system by serializing and + * transparently compressing it + * + * @param $object The object we shall save to the local file system + * @return void + * @throws NullPointerException If the object instance is null + * @throws NoObjectException If the parameter $object is not + * an object + */ + public final function saveObject ($object) { + // Some tests on the parameter... + if (is_null($object)) { + // Is null, throw exception + throw new NullPointerException($object, self::EXCEPTION_IS_NULL_POINTER); + } elseif (!is_object($object)) { + // Is not an object, throw exception + throw new NoObjectException($object, self::EXCEPTION_IS_NO_OBJECT); + } elseif (!method_exists($object, '__toString')) { + // A highly required method was not found... :-( + throw new MissingMethodException(array($object, '__toString'), self::EXCEPTION_MISSING_METHOD); + } + + // Get a string containing the serialized object. We cannot exchange + // $this and $object here because $object does not need to worry + // about it's limitations... ;-) + $serialized = $this->serializeObject($object); + + // Get a path name plus file name and append the extension + $fqfn = $this->getSavePath() . $object->getPathFileNameFromObject() . "." . $this->getFileExtension(); + + // Save the file to disc we don't care here if the path is there, + // this must be done in later methods. + $this->getFileIoInstance()->saveFile($fqfn, array($this->getCompressorChannel()->getCompressorExtension(), $serialized)); + } + + /** + * Get a serialized string from the given object + * + * @param $object The object we want to serialize and transparently + * compress + * @return $serialized A string containing the serialzed/compressed object + * @see ObjectLimits An object holding limition information + * @see SerializationContainer A special container class for e.g. + * attributes from limited objects + */ + private function serializeObject ($object) { + // If there is no limiter instance we serialize the whole object + // otherwise only in the limiter object (ObjectLimits) specified + // attributes summarized in a special container class + if ($this->getLimitInstance() === null) { + // Serialize the whole object. This tribble call is the reason + // why we need a fall-back implementation in CompressorChannel + // of the methods compressStream() and decompressStream(). + $serialized = $this->getCompressorChannel()->getCompressor()->compressStream(serialize($object)); + } else { + // Serialize only given attributes in a special container + $container = SerializationContainer::createSerializationContainer($this->getLimitInstance(), $object); + + // Serialize the container + $serialized = $this->getCompressorChannel()->getCompressor()->compressStream(serialize($container)); + } + + // Return the serialized object string + return $serialized; + } + + /** + * Analyses if a unique ID has already been used or not by search in the + * local database folder. + * + * @param $uniqueID A unique ID number which shall be checked + * before it will be used + * @param $inConstructor If we got called in a de/con-structor or + * from somewhere else + * @return $isUnused true = The unique ID was not found in the database, + * false = It is already in use by an other object + * @throws NoArrayCreatedException If explode() fails to create an array + * @throws InvalidArrayCountException If the array contains less or + * more than two elements + */ + public function isUniqueIdUsed ($uniqueID, $inConstructor = false) { + // Currently not used... ;-) + $isUsed = false; + + // Split the unique ID up in path and file name + $pathFile = explode("@", $uniqueID); + + // Are there two elements? Index 0 is the path, 1 the file name + global extension + if (!is_array($pathFile)) { + // No array found + if ($inConstructor) { + return false; + } else { + throw new NoArrayCreatedException(array($this, "pathFile"), self::EXCEPTION_ARRAY_EXPECTED); + } + } elseif (count($pathFile) != 2) { + // Invalid ID returned! + if ($inConstructor) { + return false; + } else { + throw new InvalidArrayCountException(array($this, "pathFile", count($pathFile), 2), self::EXCEPTION_ARRAY_HAS_INVALID_COUNT); + } + } + + // Create full path name + $pathName = $this->getSavePath() . $pathFile[0]; + + // Check if the file is there with a file handler + if ($inConstructor) { + // No exceptions in constructors and destructors! + $dirInstance = FrameworkDirectoryPointer::createFrameworkDirectoryPointer($pathName, true); + + // Has an object being created? + if (!is_object($dirInstance)) return false; + } else { + // Outside a constructor + try { + $dirInstance = FrameworkDirectoryPointer::createFrameworkDirectoryPointer($pathName); + } catch (PathIsNoDirectoryException $e) { + // Okay, path not found + return false; + } + } + + // Initialize the search loop + $isValid = false; + while ($dataFile = $dirInstance->readDirectoryExcept(array(".", ".."))) { + // Generate FQFN for testing + $fqfn = sprintf("%s/%s", $pathName, $dataFile); + $this->setLastFile($fqfn); + + // Get instance for file handler + $inputHandler = $this->getFileIoInstance(); + + // Try to read from it. This makes it sure that the file is + // readable and a valid database file + $this->setLastFileContents($inputHandler->loadFileContents($fqfn)); + + // Extract filename (= unique ID) from it + $ID = substr(basename($fqfn), 0, -(strlen($this->getFileExtension()) + 1)); + + // Is this the required unique ID? + if ($ID == $pathFile[1]) { + // Okay, already in use! + $isUsed = true; + } + } + + // Close the directory handler + $dirInstance->closeDirectory(); + + // Now the same for the file... + return $isUsed; + } + + /** + * Setter for the last read file + * + * @param $fqfn The FQFN of the last read file + * @return void + */ + private final function setLastFile ($fqfn) { + // Cast string + $fqfn = (string) $fqfn; + $this->lastFile = $fqfn; + } + + /** + * Getter for last read file + * + * @return $lastFile The last read file's name with full path + */ + public final function getLastFile () { + return $this->lastFile; + } + + /** + * Setter for contents of the last read file + * + * @param $contents An array with header and data elements + * @return void + */ + private final function setLastFileContents ($contents) { + // Cast array + $contents = (array) $contents; + $this->lastContents = $contents; + } + + /** + * Getter for last read file's content as an array + * + * @return $lastContent The array with elements 'header' and 'data'. + */ + public final function getLastContents () { + return $this->lastContents; + } + + /** + * Getter for file extension + * + * @return $fileExtension The array with elements 'header' and 'data'. + */ + public final function getFileExtension () { + return $this->fileExtension; + } + + /** + * Get cached (last fetched) data from the local file database + * + * @param $uniqueID The ID number for looking up the data + * @return $object The restored object from the maybe compressed + * serialized data + * @throws MismatchingCompressorsException If the compressor from + * the loaded file + * mismatches with the + * current used one. + * @throws NullPointerException If the restored object + * is null + * @throws NoObjectException If the restored "object" + * is not an object instance + * @throws MissingMethodException If the required method + * toString() is missing + */ + public final function getObjectFromCachedData ($uniqueID) { + // Get instance for file handler + $inputHandler = $this->getFileIoInstance(); + + // Get last file's name and contents + $fqfn = $this->repairFQFN($this->getLastFile(), $uniqueID); + $contents = $this->repairContents($this->getLastContents(), $fqfn); + + // Let's decompress it. First we need the instance + $compressInstance = $this->getCompressorChannel(); + + // Is the compressor's extension the same as the one from the data? + if ($compressInstance->getCompressorExtension() != $contents['header'][0]) { + /** + * @todo For now we abort here but later we need to make this a little more dynamic. + */ + throw new MismatchingCompressorsException(array($this, $contents['header'][0], $fqfn, $compressInstance->getCompressorExtension()), self::EXCEPTION_MISMATCHING_COMPRESSORS); + } + + // Decompress the data now + $serialized = $compressInstance->getCompressor()->decompressStream($contents['data']); + + // And unserialize it... + $object = unserialize($serialized); + + // This must become a valid object, so let's check it... + if (is_null($object)) { + // Is null, throw exception + throw new NullPointerException($object, self::EXCEPTION_IS_NULL_POINTER); + } elseif (!is_object($object)) { + // Is not an object, throw exception + throw new NoObjectException($object, self::EXCEPTION_IS_NO_OBJECT); + } elseif (!method_exists($object, '__toString')) { + // A highly required method was not found... :-( + throw new MissingMethodException(array($object, '__toString'), self::EXCEPTION_MISSING_METHOD); + } + + // And return the object + return $object; + } + + /** + * Private method for re-gathering (repairing) the FQFN + * + * @param $fqfn The current FQFN we shall validate + * @param $uniqueID The unique ID number + * @return $fqfn The repaired FQFN when it is empty + * @throws NoArrayCreatedException If explode() has not + * created an array + * @throws InvalidArrayCountException If the array count is not + * as the expected + */ + private function repairFQFN ($fqfn, $uniqueID) { + // Cast both strings + $fqfn = (string) $fqfn; + $uniqueID = (string) $uniqueID; + + // Is there pre-cached data available? + if (empty($fqfn)) { + // Split the unique ID up in path and file name + $pathFile = explode("@", $uniqueID); + + // Are there two elements? Index 0 is the path, 1 the file name + global extension + if (!is_array($pathFile)) { + // No array found + throw new NoArrayCreatedException(array($this, "pathFile"), self::EXCEPTION_ARRAY_EXPECTED); + } elseif (count($pathFile) != 2) { + // Invalid ID returned! + throw new InvalidArrayCountException(array($this, "pathFile", count($pathFile), 2), self::EXCEPTION_ARRAY_HAS_INVALID_COUNT); + } + + // Create full path name + $pathName = $this->getSavePath() . $pathFile[0]; + + // Nothing cached, so let's create a FQFN first + $fqfn = sprintf("%s/%s.%s", $pathName, $pathFile[1], $this->getFileExtension()); + $this->setLastFile($fqfn); + } + + // Return repaired FQFN + return $fqfn; + } + + /** + * Private method for re-gathering the contents of a given file + * + * @param $contents The (maybe) already cached contents as an array + * @param $fqfn The current FQFN we shall validate + * @return $contents The repaired contents from the given file + */ + private function repairContents ($contents, $fqfn) { + // Is there some content and header (2 indexes) in? + if ((!is_array($contents)) || (count($contents) != 2) || (!isset($contents['header'])) || (!isset($contents['data']))) { + // No content found so load the file again + $contents = $inputHandler->loadFileContents($fqfn); + + // And remember all data for later usage + $this->setLastContents($contents); + } + + // Return the repaired contents + return $contents; + } + + /* DUMMY */ public final function loadObject () {} +} + +// [EOF] +?> diff --git a/inc/classes/main/filter/validator/class_UserNameValidatorFilter.php b/inc/classes/main/filter/validator/class_UserNameValidatorFilter.php index 1c7c54a..165a9ef 100644 --- a/inc/classes/main/filter/validator/class_UserNameValidatorFilter.php +++ b/inc/classes/main/filter/validator/class_UserNameValidatorFilter.php @@ -117,9 +117,6 @@ class UserNameValidatorFilter extends BaseFrameworkSystem implements Filterable } catch (UsernameMissingException $e) { // Okay, this user is missing! $alreadyTaken = false; - } catch (FrameworkException $e) { - // Something bad happend - ApplicationEntryPoint::app_die(sprintf("Exception: %s", $e->__toString())); } // Return the result diff --git a/inc/classes/main/user/class_User.php b/inc/classes/main/user/class_User.php index 53e8b46..3a31883 100644 --- a/inc/classes/main/user/class_User.php +++ b/inc/classes/main/user/class_User.php @@ -92,11 +92,33 @@ class User extends BaseFrameworkSystem implements ManageableUser { /** * Getter for username * - * @return $userName The username to set + * @return $userName The username to get */ public final function getUsername () { return $this->userNane; } + + /** + * Determines wether the username exists or not + * + * @return $exists Wether the username exists + */ + protected function ifUsernameExists () { + // By default the username does exist + $exists = true; + + // Try to get a UserDatabaseClient object back + try { + // Get the instance by providing this class + $this->userClient = UserDatabaseClient::createUserDatabaseClient($this); + } catch (ClientUserNameNotFoundException $e) { + // Does not exist! + $exists = false; + } + + // Return the status + return $exists; + } } // [EOF]