Skip to content

Commit

Permalink
Fixes #41: Add & AddRange cleanup partial adds after an exception
Browse files Browse the repository at this point in the history
  • Loading branch information
akade committed Jul 11, 2023
1 parent 2f3deb0 commit b6a0290
Show file tree
Hide file tree
Showing 2 changed files with 58 additions and 4 deletions.
34 changes: 34 additions & 0 deletions Akade.IndexedSet.Tests/GeneralTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -62,4 +62,38 @@ public void Updating_immutable_key_value_updates_index()
Assert.AreEqual(_a.PrimaryKey, _indexedSet.Single(x => x.IntProperty, 42).PrimaryKey);
Assert.IsFalse(_indexedSet.Where(x => x.IntProperty, 0).Any(a => a.PrimaryKey == _a.PrimaryKey));
}

[TestMethod]
public void Adding_a_conflicting_item_should_keep_the_set_in_a_consistent_state()
{
IndexedSet<TestData> set = new[] { _a, _c, _d }.ToIndexedSet()
.WithIndex(x => x.GuidProperty)
.WithUniqueIndex(x => x.IntProperty)
.Build();

_ = Assert.ThrowsException<ArgumentException>(() => set.Add(_b));
Assert.IsFalse(set.TryGetSingle(x => x.GuidProperty, _b.GuidProperty, out _));
Assert.AreEqual(3, set.Count);
Assert.IsFalse(set.Contains(_b));
}

[TestMethod]
public void Adding_multiple_items_with_a_conflicting_item_should_keep_the_set_in_a_consistent_state()
{
IndexedSet<TestData> set = new[] { _a, _c, }.ToIndexedSet()
.WithIndex(x => x.GuidProperty)
.WithUniqueIndex(x => x.IntProperty)
.Build();
TestData[] dataToAdd = new[] { _d, _b, _e };

_ = Assert.ThrowsException<ArgumentException>(() => set.AddRange(dataToAdd));
Assert.AreEqual(2, set.Count);

foreach (TestData item in dataToAdd)
{
Assert.IsFalse(set.TryGetSingle(x => x.GuidProperty, _b.GuidProperty, out _));
Assert.IsFalse(set.Contains(item));

}
}
}
28 changes: 24 additions & 4 deletions Akade.IndexedSet/IndexedSet.cs
Original file line number Diff line number Diff line change
Expand Up @@ -43,9 +43,18 @@ public bool Add(TElement element)
return false;
}

foreach (Index<TElement> index in _indices.Values)
try
{
index.Add(element);
foreach (Index<TElement> index in _indices.Values)
{
index.Add(element);
}
}
catch
{
_ = Remove(element);

throw;
}

return true;
Expand Down Expand Up @@ -81,9 +90,20 @@ public int AddRange(IEnumerable<TElement> elements)
}
}

foreach (Index<TElement> index in _indices.Values)
try
{
index.AddRange(elementsToAdd);
foreach (Index<TElement> index in _indices.Values)
{
index.AddRange(elementsToAdd);
}
}
catch
{
foreach (TElement element in elementsToAdd)
{
_ = Remove(element);
}
throw;
}

return elementsToAdd.Count;
Expand Down

0 comments on commit b6a0290

Please sign in to comment.