Continued:
[core.git] / framework / main / classes / iterator / file / class_FileIterator.php
index b4945aeec1dbc92110aba430fc892f027456a7b1..face6a395ece52246f7481c2551e40118d0d6d90 100644 (file)
@@ -3,16 +3,23 @@
 namespace Org\Mxchange\CoreFramework\Iterator\File;
 
 // Import framework stuff
-use Org\Mxchange\CoreFramework\Filesystem\Block;
+use Org\Mxchange\CoreFramework\Filesystem\File\BinaryFile;
+use Org\Mxchange\CoreFramework\Generic\FrameworkInterface;
 use Org\Mxchange\CoreFramework\Iterator\BaseIterator;
-use Org\Mxchange\CoreFramework\Iterator\Filesystem\SeekableWritableFileIterator;
+use Org\Mxchange\CoreFramework\Traits\File\BinaryFileTrait;
+
+// Import SPL stuff
+use \BadMethodCallException;
+use \InvalidArgumentException;
+use \OutOfBoundsException;
+use \SeekableIterator;
 
 /**
  * A file iterator
  *
  * @author             Roland Haeder <webmaster@ship-simu.org>
  * @version            0.0.0
- * @copyright  Copyright (c) 2007, 2008 Roland Haeder, 2009 - 2017 Core Developer Team
+ * @copyright  Copyright (c) 2007, 2008 Roland Haeder, 2009 - 2023 Core Developer Team
  * @license            GNU GPL 3.0 or any newer version
  * @link               http://www.ship-simu.org
  *
@@ -29,13 +36,16 @@ use Org\Mxchange\CoreFramework\Iterator\Filesystem\SeekableWritableFileIterator;
  * You should have received a copy of the GNU General Public License
  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
  */
-class FileIterator extends BaseIterator implements SeekableWritableFileIterator {
+class FileIterator extends BaseIterator implements SeekableIterator {
+       // Load traits
+       use BinaryFileTrait;
+
        /**
         * Protected constructor
         *
         * @return      void
         */
-       protected function __construct () {
+       private function __construct () {
                // Call parent constructor
                parent::__construct(__CLASS__);
        }
@@ -43,18 +53,19 @@ class FileIterator extends BaseIterator implements SeekableWritableFileIterator
        /**
         * Creates an instance of this class
         *
-        * @param       $pointerInstance        An instance of a Block class
+        * @param       $binaryFileInstance     An instance of a BinaryFile class
         * @return      $iteratorInstance       An instance of a Iterator class
         */
-       public final static function createFileIterator (Block $blockInstance) {
+       public final static function createFileIterator (BinaryFile $binaryFileInstance) {
                // Get new instance
+               //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('FILE-ITERATOR: binaryFileInstance=%s - CALLED!', $binaryFileInstance->__toString()));
                $iteratorInstance = new FileIterator();
 
                // Set the instance here
-               /* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('[%s:%d] Setting blockInstance=%s ...', __METHOD__, __LINE__, $blockInstance->__toString()));
-               $iteratorInstance->setBlockInstance($blockInstance);
+               $iteratorInstance->setBinaryFileInstance($binaryFileInstance);
 
                // Return the prepared instance
+               //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('FILE-ITERATOR: iteratorInstance=%s - EXIT!', $iteratorInstance->__toString()));
                return $iteratorInstance;
        }
 
@@ -62,30 +73,58 @@ class FileIterator extends BaseIterator implements SeekableWritableFileIterator
         * Gets currently read data
         *
         * @return      $current        Currently read data
+        * @throws      BadMethodCallException  If valid() is FALSE
         */
        public function current () {
-               // Call block instance
-               return $this->getBlockInstance()->current();
+               // Is condition given?
+               //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput('FILE-ITERATOR: CALLED!');
+               if (!$this->valid()) {
+                       // Throw BMCE
+                       throw new BadMethodCallException('Current key cannot be valid, forgot to invoke valid()?', FrameworkInterface::EXCEPTION_BAD_METHOD_CALL);
+               }
+
+               // Call file instance
+               $current = $this->getBinaryFileInstance()->current();
+
+               // Return it
+               //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('FILE-ITERATOR: current[]=%s - EXIT!', gettype($current)));
+               return $current;
        }
 
        /**
         * Gets current seek position ("key").
         *
         * @return      $key    Current key in iteration
+        * @throws      BadMethodCallException  If valid() is FALSE
         */
        public function key () {
-               // Return it
-               return $this->getBlockInstance()->determineSeekPosition();
+               // Is condition given?
+               //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput('FILE-ITERATOR: CALLED!');
+               if (!$this->valid()) {
+                       // Throw BMCE
+                       throw new BadMethodCallException('Current key cannot be valid, forgot to invoke valid()?', FrameworkInterface::EXCEPTION_BAD_METHOD_CALL);
+               }
+
+               // Get key from file instance
+               $key = $this->getBinaryFileInstance()->determineSeekPosition();
+
+               // Return key
+               //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('FILE-ITERATOR: key[%s]=%s - EXIT!', gettype($key), $key));
+               return $key;
        }
 
        /**
-        * Advances to next "block" of bytes
+        * Advances to next "file" of bytes
         *
         * @return      void
         */
        public function next () {
-               // Call block instance
-               $this->getBlockInstance()->next();
+               // Call file instance
+               //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput('FILE-ITERATOR: CALLED!');
+               $this->getBinaryFileInstance()->next();
+
+               // Trace message
+               //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput('FILE-ITERATOR: EXIT!');
        }
 
        /**
@@ -94,8 +133,12 @@ class FileIterator extends BaseIterator implements SeekableWritableFileIterator
         * @return      $status         Status of this operation
         */
        public function rewind () {
-               // Call block instance
-               return $this->getBlockInstance()->rewind();
+               // Call file instance
+               //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput('FILE-ITERATOR: CALLED!');
+               $this->getBinaryFileInstance()->rewind();
+
+               // Trace message
+               //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput('FILE-ITERATOR: EXIT!');
        }
 
        /**
@@ -105,232 +148,35 @@ class FileIterator extends BaseIterator implements SeekableWritableFileIterator
         * @return      $isValid        Whether the next entry is valid
         */
        public function valid () {
-               // Call block instance
-               return $this->getBlockInstance()->valid();
+               // Call file instance
+               //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput('FILE-ITERATOR: CALLED!');
+               $isValid = $this->getBinaryFileInstance()->valid();
+
+               // Return flag
+               //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('FILE-ITERATOR: isValid=%d - EXIT!', intval($isValid)));
+               return $isValid;
        }
 
        /**
         * Seeks to given position
         *
         * @param       $seekPosition   Seek position in file
-        * @return      $status                 Status of this operation
-        */
-       public function seek ($seekPosition) {
-               // Call block instance
-               return $this->getBlockInstance()->seek($seekPosition);
-       }
-
-       /**
-        * Size of file stack
-        *
-        * @return      $size   Size (in bytes) of file
-        */
-       public function size () {
-               // Call the block object
-               $size = $this->getBlockInstance()->size();
-
-               // Return result
-               return $size;
-       }
-
-       /**
-        * Reads given amount of bytes from file.
-        *
-        * @param       $bytes  Amount of bytes to read
-        * @return      $data   Data read from file
-        */
-       public function read ($bytes = NULL) {
-               // Call block instance
-               return $this->getBlockInstance()->read($bytes);
-       }
-
-       /**
-        * Analyzes entries in index file. This will count all found (and valid)
-        * entries, mark invalid as damaged and count gaps ("fragmentation"). If
-        * only gaps are found, the file is considered as "virgin" (no entries).
-        *
-        * @return      void
-        */
-       public function analyzeFile () {
-               // Just call the block instance
-               $this->getBlockInstance()->analyzeFile();
-       }
-
-       /**
-        * Checks whether the file header is initialized
-        *
-        * @return      $isInitialized  Whether the file header is initialized
-        */
-       public function isFileHeaderInitialized () {
-               // Just call the block instance
-               return $this->getBlockInstance()->isFileHeaderInitialized();
-       }
-
-       /**
-        * Creates the assigned file
-        *
-        * @return      void
-        */
-       public function createFileHeader () {
-               // Just call the block instance
-               $this->getBlockInstance()->createFileHeader();
-       }
-
-       /**
-        * Pre-allocates file (if enabled) with some space for later faster write access.
-        *
-        * @param       $type   Type of the file
-        * @return      void
-        */
-       public function preAllocateFile ($type) {
-               // Just call the block instance
-               $this->getBlockInstance()->preAllocateFile($type);
-       }
-
-       /**
-        * Initializes counter for valid entries, arrays for damaged entries and
-        * an array for gap seek positions. If you call this method on your own,
-        * please re-analyze the file structure. So you are better to call
-        * analyzeFile() instead of this method.
-        *
-        * @return      void
-        */
-       public function initCountersGapsArray () {
-               // Call block instance
-               $this->getBlockInstance()->initCountersGapsArray();
-       }
-
-       /**
-        * Getter for header size
-        *
-        * @return      $totalEntries   Size of file header
-        */
-       public final function getHeaderSize () {
-               // Call block instance
-               return $this->getBlockInstance()->getHeaderSize();
-       }
-
-       /**
-        * Setter for header size
-        *
-        * @param       $headerSize             Size of file header
-        * @return      void
-        */
-       public final function setHeaderSize ($headerSize) {
-               // Call block instance
-               $this->getBlockInstance()->setHeaderSize($headerSize);
-       }
-
-       /**
-        * Getter for header array
-        *
-        * @return      $totalEntries   Size of file header
-        */
-       public final function getHeader () {
-               // Call block instance
-               return $this->getBlockInstance()->getHeader();
-       }
-
-       /**
-        * Setter for header
-        *
-        * @param       $header         Array for a file header
-        * @return      void
-        */
-       public final function setHeader (array $header) {
-               // Call block instance
-               $this->getBlockInstance()->setHeader($header);
-       }
-
-       /**
-        * Updates seekPosition attribute from file to avoid to much access on file.
-        *
-        * @return      void
-        */
-       public function updateSeekPosition () {
-               // Call block instance
-               $this->getBlockInstance()->updateSeekPosition();
-       }
-
-       /**
-        * Getter for total entries
-        *
-        * @return      $totalEntries   Total entries in this file
-        */
-       public final function getCounter () {
-               // Call block instance
-               return $this->getBlockInstance()->getCounter();
-       }
-
-       /**
-        * "Getter" for file size
-        *
-        * @return      $fileSize       Size of currently loaded file
-        */
-       public function getFileSize () {
-               // Call block instance
-               return $this->getBlockInstance()->getFileSize();
-       }
-
-       /**
-        * Writes data at given position
-        *
-        * @param       $seekPosition   Seek position
-        * @param       $data                   Data to be written
-        * @param       $flushHeader    Whether to flush the header (default: flush)
         * @return      void
+        * @throws      OutOfBoundsException    If the position is not seekable
         */
-       public function writeData ($seekPosition, $data, $flushHeader = true) {
-               // Call block instance
-               $this->getBlockInstance()->writeData($seekPosition, $data, $flushHeader);
-       }
-
-       /**
-        * Getter for seek position
-        *
-        * @return      $seekPosition   Current seek position (stored here in object)
-        */
-       public function getSeekPosition () {
-               // Call block instance
-               return $this->getBlockInstance()->getSeekPosition();
-       }
-
-       /**
-        * Writes given value to the file and returns a hash and gap position for it
-        *
-        * @param       $groupId        Group identifier
-        * @param       $value          Value to be added to the stack
-        * @return      $data           Hash and gap position
-        */
-       public function writeValueToFile ($groupId, $value) {
-               // Call block instance
-               return $this->getBlockInstance()->writeValueToFile($groupId, $value);
-       }
+       public function seek (int $seekPosition) {
+               // Validate parameter
+               //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('FILE-ITERATOR: seekPosition=%d,whence=%d - CALLED!', $seekPosition, $whence));
+               if ($seekPosition < 0) {
+                       // Throw IAE
+                       throw new OutOfBoundsException(sprintf('seekPosition=%d is not valid', $seekPosition));
+               }
 
-       /**
-        * Writes given raw data to the file and returns a gap position and length
-        *
-        * @param       $groupId        Group identifier
-        * @param       $hash           Hash from encoded value
-        * @param       $encoded        Encoded value to be written to the file
-        * @return      $data           Gap position and length of the raw data
-        */
-       public function writeDataToFreeGap ($groupId, $hash, $encoded) {
-               // Call block instance
-               return $this->getBlockInstance()->writeDataToFreeGap($groupId, $hash, $encoded);
-       }
+               // Call file instance
+               $this->getBinaryFileInstance()->seek($seekPosition);
 
-       /**
-        * Searches for next suitable gap the given length of data can fit in
-        * including padding bytes.
-        *
-        * @param       $length                 Length of raw data
-        * @return      $seekPosition   Found next gap's seek position
-        */
-       public function searchNextGap ($length) {
-               // Call block instance
-               print $this->getBlockInstance()->__toString() . PHP_EOL;
-               return $this->getBlockInstance()->searchNextGap($length);
+               // Trace message
+               //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput('FILE-ITERATOR: EXIT!');
        }
 
 }