Skip to content

Commit 5332d90

Browse files
authored
Improve error handling in the inmemory storage implementation. (#79)
Improve error handling in the inmemory storage This addresses a TODO, in a type that is really only used for testing. This also adds a test for a similar circumstance -- adding the same version twice -- in the SQLite storage, but it is already handled correctly.
1 parent f3445d5 commit 5332d90

File tree

2 files changed

+59
-6
lines changed

2 files changed

+59
-6
lines changed

core/src/inmemory.rs

Lines changed: 42 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -130,7 +130,6 @@ impl StorageTxn for InnerTxn<'_> {
130130
parent_version_id: Uuid,
131131
history_segment: Vec<u8>,
132132
) -> anyhow::Result<()> {
133-
// TODO: verify it doesn't exist (`.entry`?)
134133
let version = Version {
135134
version_id,
136135
parent_version_id,
@@ -143,15 +142,33 @@ impl StorageTxn for InnerTxn<'_> {
143142
snap.versions_since += 1;
144143
}
145144
} else {
146-
return Err(anyhow::anyhow!("Client {} does not exist", self.client_id));
145+
anyhow::bail!("Client {} does not exist", self.client_id);
147146
}
148147

149-
self.guard
148+
if self
149+
.guard
150150
.children
151-
.insert((self.client_id, parent_version_id), version_id);
152-
self.guard
151+
.insert((self.client_id, parent_version_id), version_id)
152+
.is_some()
153+
{
154+
anyhow::bail!(
155+
"Client {} already has a child for {}",
156+
self.client_id,
157+
parent_version_id
158+
);
159+
}
160+
if self
161+
.guard
153162
.versions
154-
.insert((self.client_id, version_id), version);
163+
.insert((self.client_id, version_id), version)
164+
.is_some()
165+
{
166+
anyhow::bail!(
167+
"Client {} already has a version {}",
168+
self.client_id,
169+
version_id
170+
);
171+
}
155172

156173
self.written = true;
157174
Ok(())
@@ -259,6 +276,25 @@ mod test {
259276
Ok(())
260277
}
261278

279+
#[test]
280+
fn test_add_version_exists() -> anyhow::Result<()> {
281+
let storage = InMemoryStorage::new();
282+
let client_id = Uuid::new_v4();
283+
let mut txn = storage.txn(client_id)?;
284+
285+
let version_id = Uuid::new_v4();
286+
let parent_version_id = Uuid::new_v4();
287+
let history_segment = b"abc".to_vec();
288+
289+
txn.new_client(parent_version_id)?;
290+
txn.add_version(version_id, parent_version_id, history_segment.clone())?;
291+
assert!(txn
292+
.add_version(version_id, parent_version_id, history_segment.clone())
293+
.is_err());
294+
txn.commit()?;
295+
Ok(())
296+
}
297+
262298
#[test]
263299
fn test_snapshots() -> anyhow::Result<()> {
264300
let storage = InMemoryStorage::new();

sqlite/src/lib.rs

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -385,6 +385,23 @@ mod test {
385385
Ok(())
386386
}
387387

388+
#[test]
389+
fn test_add_version_exists() -> anyhow::Result<()> {
390+
let tmp_dir = TempDir::new()?;
391+
let storage = SqliteStorage::new(tmp_dir.path())?;
392+
let client_id = Uuid::new_v4();
393+
let mut txn = storage.txn(client_id)?;
394+
395+
let version_id = Uuid::new_v4();
396+
let parent_version_id = Uuid::new_v4();
397+
let history_segment = b"abc".to_vec();
398+
txn.add_version(version_id, parent_version_id, history_segment.clone())?;
399+
assert!(txn
400+
.add_version(version_id, parent_version_id, history_segment.clone())
401+
.is_err());
402+
Ok(())
403+
}
404+
388405
#[test]
389406
fn test_snapshots() -> anyhow::Result<()> {
390407
let tmp_dir = TempDir::new()?;

0 commit comments

Comments
 (0)