diff --git a/UndoRedo.Test/UndoRedoStackTests.cs b/UndoRedo.Test/UndoRedoStackTests.cs index fd42f6e..2fecb17 100644 --- a/UndoRedo.Test/UndoRedoStackTests.cs +++ b/UndoRedo.Test/UndoRedoStackTests.cs @@ -882,6 +882,46 @@ public async Task UndoToSaveBoundary_BoundaryRemovedByBranching_ReturnsFalse() Assert.IsEmpty(stack.GetCommandsToUndo(removedBoundary)); } + [TestMethod] + public void GetCommandsToUndo_EnumeratedAfterBranching_ReflectsStateAtCall() + { + // Arrange + UndoRedoService stack = CreateService(); + stack.MarkAsSaved(); + stack.Execute(new DelegateCommand("A", () => { }, () => { })); + stack.Execute(new DelegateCommand("B", () => { }, () => { })); + SaveBoundary boundary = stack.SaveBoundaries[0]; + + // Act + IEnumerable commandsToUndo = stack.GetCommandsToUndo(boundary); + stack.Undo(); + stack.Execute(new DelegateCommand("C", () => { }, () => { })); // Replaces B in the live stack + + // Assert + string descriptions = string.Join(",", commandsToUndo.Select(c => c.Description)); + Assert.AreEqual("A,B", descriptions, "The result should be a snapshot of the stack when it was requested"); + } + + [TestMethod] + public void GetChangeVisualizations_EnumeratedAfterExecute_ReflectsStateAtCall() + { + // Arrange + UndoRedoService stack = CreateService(); + stack.Execute(new DelegateCommand("A", () => { }, () => { })); + + // Act + IEnumerable visualizations = stack.GetChangeVisualizations(); + stack.MarkAsSaved(); + stack.Execute(new DelegateCommand("C", () => { }, () => { })); + + // Assert + List snapshot = [.. visualizations]; + Assert.HasCount(1, snapshot, "Commands executed after the call should not appear"); + Assert.AreEqual("A", snapshot[0].Command.Description); + Assert.IsTrue(snapshot[0].IsExecuted); + Assert.IsFalse(snapshot[0].HasSaveBoundary, "A save boundary created after the call should not appear"); + } + [TestMethod] public async Task UndoToSaveBoundary_WhenAlreadyAtPosition_ReturnsFalse() { diff --git a/UndoRedo/Services/SaveBoundaryManager.cs b/UndoRedo/Services/SaveBoundaryManager.cs index 3d92029..d9d4ba0 100644 --- a/UndoRedo/Services/SaveBoundaryManager.cs +++ b/UndoRedo/Services/SaveBoundaryManager.cs @@ -97,9 +97,10 @@ public IEnumerable GetCommandsToUndo(SaveBoundary saveBoundary, int cu Ensure.NotNull(saveBoundary); Ensure.NotNull(commands); + // Materialize so the result is a snapshot, not a view that changes with the live stack return currentPosition <= saveBoundary.Position ? [] - : commands.Skip(saveBoundary.Position + 1).Take(currentPosition - saveBoundary.Position); + : [.. commands.Skip(saveBoundary.Position + 1).Take(currentPosition - saveBoundary.Position)]; } ///