public function next()
 {
     $this->current = null;
     if (($restore = $this->statement->fetch(\PDO::FETCH_ASSOC)) !== false) {
         $this->current = clone $this->storable;
         $this->current->schema()->validate($restore);
         if (isset($restore['guid'])) {
             $this->current->guid($restore['guid']);
             $this->storage->register($this->current);
         }
         $this->current->restore($restore);
     }
 }
 /**
  * @param IStorable $storable
  *
  * @return IStorable
  * @throws StorageException
  */
 public function load(IStorable $storable)
 {
     if ($this->hasStorable($guid = $storable->guid())) {
         return $this->storable($guid);
     }
     $selectQuery = new SelectQuery();
     $guid = $storable->guid();
     $selectQuery->select(new AsteriskFragment())->from(new SelectTable($storable->schema()->getName()))->where($this->whereIdentifier($guid));
     if (($one = $this->select($selectQuery, $storable)->storable()) === null) {
         throw new StorageException(sprintf('Storable [%s (%s)] not found by given guid [%s].', get_class($storable), $storable->schema()->getName(), $guid));
     }
     $this->register($one);
     return $one;
 }
 public function save(IStorable $storable)
 {
     $this->createSchema($schema = $storable->schema());
     $schema->validate($store = $storable->store($this));
     /**
      * exactly empty arrays are unmodified state; otherwise NULL is delete state
      */
     if (is_array($store) && empty($store)) {
         return $storable;
     }
     $guid = $this->hasStorable($guid = $storable->guid()) ? $guid : null;
     $this->register($storable);
     if (empty($store) && $guid !== null) {
         $this->delete($storable);
     } else {
         if (!empty($store) && $guid === null) {
             $this->create($storable, $store);
         } else {
             if (!empty($store) && $guid !== null) {
                 $this->update($storable, $store);
             }
         }
     }
     return $storable;
 }