Skip to content

Commit 581560d

Browse files
Fix ChildChanged event not being triggered for BusinessListBase objects in Blazor ViewModel (#4747)
* Initial plan * Fix ChildChanged event hook to support BusinessListBase objects Co-authored-by: rockfordlhotka <2333134+rockfordlhotka@users.noreply.github.com> --------- Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com> Co-authored-by: rockfordlhotka <2333134+rockfordlhotka@users.noreply.github.com>
1 parent 366aecb commit 581560d

2 files changed

Lines changed: 103 additions & 2 deletions

File tree

Source/Csla.Blazor/ViewModel.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -114,7 +114,7 @@ protected void UnhookChangedEvents(T? model)
114114
if (model is INotifyPropertyChanged npc)
115115
npc.PropertyChanged -= OnModelPropertyChanged;
116116

117-
if (model is IBusinessBase ncc)
117+
if (model is INotifyChildChanged ncc)
118118
ncc.ChildChanged -= OnModelChildChanged;
119119

120120
if (model is INotifyCollectionChanged cc)
@@ -130,7 +130,7 @@ private void HookChangedEvents(T? model)
130130
if (model is INotifyPropertyChanged npc)
131131
npc.PropertyChanged += OnModelPropertyChanged;
132132

133-
if (model is IBusinessBase ncc)
133+
if (model is INotifyChildChanged ncc)
134134
ncc.ChildChanged += OnModelChildChanged;
135135

136136
if (model is INotifyCollectionChanged cc)
Lines changed: 101 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,101 @@
1+
using Microsoft.VisualStudio.TestTools.UnitTesting;
2+
using Csla.Blazor.Test.Fakes;
3+
using Csla.TestHelpers;
4+
using System.Threading.Tasks;
5+
using Csla.Core;
6+
7+
namespace Csla.Blazor.Test
8+
{
9+
[TestClass]
10+
public class ViewModelChildChangedEventTests
11+
{
12+
private static TestDIContext _testDIContext;
13+
14+
[ClassInitialize]
15+
public static void ClassInitialize(TestContext context)
16+
{
17+
_testDIContext = TestDIContextFactory.CreateDefaultContext();
18+
}
19+
20+
[TestCleanup]
21+
public void CleanupTests()
22+
{
23+
FakeDataStorage.ClearDataStorage();
24+
}
25+
26+
[TestMethod]
27+
public void ViewModel_WithBusinessBase_ShouldHookChildChangedEvent()
28+
{
29+
// Arrange
30+
var appContext = TestDIContextExtensions.CreateTestApplicationContext(_testDIContext);
31+
var vm = new ViewModel<FakePerson>(appContext);
32+
bool childChangedCalled = false;
33+
vm.ModelChildChanged += (sender, e) => childChangedCalled = true;
34+
35+
// Act - Create and set a FakePerson model (BusinessBase)
36+
IDataPortal<FakePerson> dataPortal = _testDIContext.CreateDataPortal<FakePerson>();
37+
var person = dataPortal.Create();
38+
vm.Model = person;
39+
40+
// Trigger child changed by modifying email addresses
41+
var emailAddress = person.EmailAddresses.AddNew();
42+
emailAddress.EmailAddress = "test@example.com";
43+
44+
// Assert
45+
Assert.IsTrue(childChangedCalled, "ModelChildChanged event should be raised for BusinessBase");
46+
}
47+
48+
[TestMethod]
49+
public void ViewModel_WithBusinessListBase_ShouldHookChildChangedEvent()
50+
{
51+
// Arrange
52+
var appContext = TestDIContextExtensions.CreateTestApplicationContext(_testDIContext);
53+
var vm = new ViewModel<FakePersonEmailAddresses>(appContext);
54+
bool childChangedCalled = false;
55+
vm.ModelChildChanged += (sender, e) => childChangedCalled = true;
56+
57+
// Act - Create and set a FakePersonEmailAddresses model (BusinessListBase)
58+
IChildDataPortal<FakePersonEmailAddresses> dataPortal = _testDIContext.CreateChildDataPortal<FakePersonEmailAddresses>();
59+
var emailAddresses = dataPortal.CreateChild();
60+
vm.Model = emailAddresses;
61+
62+
// Trigger child changed by adding an item
63+
var emailAddress = emailAddresses.AddNew();
64+
emailAddress.EmailAddress = "test@example.com";
65+
66+
// Assert
67+
Assert.IsTrue(childChangedCalled, "ModelChildChanged event should be raised for BusinessListBase");
68+
}
69+
70+
[TestMethod]
71+
public void ViewModel_WhenModelChanged_ShouldUnhookOldAndHookNewChildChangedEvent()
72+
{
73+
// Arrange
74+
var appContext = TestDIContextExtensions.CreateTestApplicationContext(_testDIContext);
75+
var vm = new ViewModel<FakePersonEmailAddresses>(appContext);
76+
int childChangedCount = 0;
77+
vm.ModelChildChanged += (sender, e) => childChangedCount++;
78+
79+
IChildDataPortal<FakePersonEmailAddresses> dataPortal = _testDIContext.CreateChildDataPortal<FakePersonEmailAddresses>();
80+
var emailAddresses1 = dataPortal.CreateChild();
81+
var emailAddresses2 = dataPortal.CreateChild();
82+
83+
// Act - Set first model
84+
vm.Model = emailAddresses1;
85+
var email1 = emailAddresses1.AddNew();
86+
email1.EmailAddress = "test1@example.com";
87+
88+
// Change model
89+
vm.Model = emailAddresses2;
90+
var email2 = emailAddresses2.AddNew();
91+
email2.EmailAddress = "test2@example.com";
92+
93+
// Modify old model - should NOT trigger event
94+
var email3 = emailAddresses1.AddNew();
95+
email3.EmailAddress = "test3@example.com";
96+
97+
// Assert
98+
Assert.AreEqual(2, childChangedCount, "ModelChildChanged should only be raised for current model");
99+
}
100+
}
101+
}

0 commit comments

Comments
 (0)