@@ -92,6 +92,13 @@ impl BlobStore {
92
92
Ok ( ( ) )
93
93
}
94
94
95
+ fn insert < K : Serialize , V : Serialize > ( & mut self , k : K , v : V ) -> Result < ( ) , BlobError > {
96
+
97
+ self . remove ( & k) . ok ( ) ;
98
+ self . insert_only ( k, v)
99
+ }
100
+
101
+
95
102
fn insert_only < K : Serialize , V : Serialize > ( & mut self , k : K , v : V ) -> Result < ( ) , BlobError > {
96
103
let blob = Blob :: from ( & k, & v) . unwrap ( ) ;
97
104
if blob. len ( ) > self . block_size {
@@ -114,6 +121,7 @@ impl BlobStore {
114
121
// add pointer immediately after data ends
115
122
write_u64 ( f, 0 ) ?;
116
123
write_u64 ( f, ( vlen - blob. len ( ) ) -16 ) ?;
124
+ self . inc_elems ( 1 ) ?;
117
125
return Ok ( ( ) ) ;
118
126
}
119
127
pos = f. seek ( SeekFrom :: Start ( pos + 16 + klen + vlen) ) ?;
@@ -149,7 +157,43 @@ impl BlobStore {
149
157
150
158
}
151
159
160
+ pub fn remove < K : Serialize > ( & mut self , k : & K ) -> Result < ( ) , BlobError > {
161
+ let s_blob = Blob :: from ( k, & 0 ) ?;
162
+ let bucket = s_blob. k_hash ( self . hseed ) % self . nblocks ;
163
+ let b_start = self . b_start ( bucket) ;
164
+ let b_end = self . b_start ( bucket+1 ) ;
165
+
166
+ let f = & mut self . file ;
167
+ let mut pos = f. seek ( SeekFrom :: Start ( b_start) ) ?;
168
+ loop {
169
+ if pos >= b_end {
170
+ return Ok ( ( ) ) ;
171
+ }
172
+
173
+ let b = Blob :: read ( f) ?;
174
+ if b. key_match ( & s_blob) {
175
+ let l = b. len ( ) ;
176
+ if pos + l < b_end {
177
+ if read_u64 ( f) ? == 0 {
178
+ let nlen = read_u64 ( f) ?;
179
+ f. seek ( SeekFrom :: Start ( pos) ) ?;
180
+ write_u64 ( f, 0 ) ?;
181
+ write_u64 ( f, l + nlen + 16 ) ?;
182
+ return Ok ( ( ) ) ;
183
+ }
184
+ }
185
+ f. seek ( SeekFrom :: Start ( pos) ) ?;
186
+ write_u64 ( f, 0 ) ?;
187
+ write_u64 ( f, l -16 ) ?;
188
+ self . inc_elems ( -1 ) ;
189
+ return Ok ( ( ) ) ;
190
+
191
+ }
192
+
193
+ pos = f. seek ( SeekFrom :: Start ( pos + b. len ( ) ) ) ?;
152
194
195
+ }
196
+ }
153
197
154
198
}
155
199
@@ -178,5 +222,9 @@ mod test {
178
222
let mut b3 = BlobStore :: open ( fs) . unwrap ( ) ;
179
223
assert_eq ! ( b3. get( & "green" ) . unwrap( ) . get_v:: <String >( ) . unwrap( ) , "wats up, im a green" . to_string( ) ) ;
180
224
225
+ b3. remove ( & "green" ) . ok ( ) ;
226
+ assert ! ( b3. get( & "green" ) . is_err( ) ) ;
227
+ assert ! ( b3. get( & "fish" ) . is_ok( ) ) ;
228
+
181
229
}
182
230
}
0 commit comments