Added Null datatype
rkinyon [Tue, 28 Nov 2006 05:07:30 +0000 (05:07 +0000)]
lib/DBM/Deep/Engine3.pm
t/02_hash.t

index f817897..2d1a916 100644 (file)
@@ -150,10 +150,19 @@ sub write_value {
     });
     die "How did this fail (no blist)?!\n" unless $blist;
 
-    my $value_sector = DBM::Deep::Engine::Sector::Scalar->new({
-        engine => $self,
-        data   => $value,
-    });
+    my $value_sector;
+    if ( !defined $value ) {
+        $value_sector = DBM::Deep::Engine::Sector::Null->new({
+            engine => $self,
+            data   => $value,
+        });
+    }
+    else {
+        $value_sector = DBM::Deep::Engine::Sector::Scalar->new({
+            engine => $self,
+            data   => $value,
+        });
+    }
 
     $blist->write_md5( $key_md5, $value_sector->offset );
 }
@@ -359,6 +368,20 @@ sub _load_sector {
             offset => $offset,
         });
     }
+    elsif ( $type eq $self->SIG_NULL ) {
+        return DBM::Deep::Engine::Sector::Null->new({
+            engine => $self,
+            type   => $type,
+            offset => $offset,
+        });
+    }
+    elsif ( $type eq $self->SIG_DATA ) {
+        return DBM::Deep::Engine::Sector::Scalar->new({
+            engine => $self,
+            type   => $type,
+            offset => $offset,
+        });
+    }
 
     die "Don't know what to do with type '$type' at offset '$offset'\n";
 }
@@ -449,6 +472,35 @@ sub data {
     );
 }
 
+package DBM::Deep::Engine::Sector::Null;
+
+our @ISA = qw( DBM::Deep::Engine::Sector::Data );
+
+sub type { $_[0]{engine}->SIG_NULL }
+sub data_length { 0 }
+sub data { return }
+
+sub _init {
+    my $self = shift;
+
+    my $engine = $self->engine;
+
+    unless ( $self->offset ) {
+        my $leftover = $self->size - 3 - 1 * $engine->byte_size;
+
+        $self->{offset} = $engine->storage->request_space( $self->size );
+        $engine->storage->print_at( $self->offset,
+            $self->type,                          # Sector type
+            pack( $StP{1}, 0 ),                   # Recycled counter
+            pack( $StP{$engine->byte_size}, 0 ),  # Chain loc
+            pack( $StP{1}, $self->data_length ),  # Data length
+            chr(0) x $leftover,                   # Zero-fill the rest
+        );
+
+        return;
+    }
+}
+
 package DBM::Deep::Engine::Sector::Reference;
 
 our @ISA = qw( DBM::Deep::Engine::Sector::Data );
@@ -568,10 +620,7 @@ sub get_data_for {
         $self->offset + 2 + $self->engine->hash_size, $self->engine->byte_size,
     );
     $location = unpack( $StP{$self->engine->byte_size}, $location );
-    return DBM::Deep::Engine::Sector::Scalar->new({
-        engine => $self->engine,
-        offset => $location,
-    });
+    return $self->engine->_load_sector( $location );
 }
 
 1;
index a71273f..cdaf0c9 100644 (file)
@@ -16,7 +16,6 @@ my $db = DBM::Deep->new( $filename );
 ##
 $db->{key1} = "value1";
 is( $db->get("key1"), "value1", "get() works with hash assignment" );
-__END__
 is( $db->fetch("key1"), "value1", "... fetch() works with hash assignment" );
 is( $db->{key1}, "value1", "... and hash-access also works" );
 $db->put("key2", undef);
@@ -28,6 +27,7 @@ $db->store( "key3", "value3" );
 is( $db->get("key3"), "value3", "get() works with store()" );
 is( $db->fetch("key3"), "value3", "... fetch() works with put()" );
 is( $db->{key3}, 'value3', "... and hash-access also works" );
+__END__
 
 ok( $db->exists("key1"), "exists() function works" );
 ok( exists $db->{key2}, "exists() works against tied hash" );