Search code examples
c#testinggetsetassert

SetValue test succeeds with my Period class but fails with my Name class


So my first TestMethod went through, as expected. I tested my SetValue method.

p1 = new DateTimePeriod { From = DateTime.MinValue, To = DateTime.MaxValue };
p2 = new DateTimePeriod { From = DateTime.MaxValue, To = DateTime.MinValue };

[TestMethod]
public void SetPeriodTest()
{
   b.SetValue(ref p1, p2);
   Assert.AreEqual(DateTime.MaxValue, p1.From);
   Assert.AreEqual(DateTime.MinValue, p1.To);
}

But the next test fails. Apparently x.AName, x.Valid and x.Id are null although I clearly set them the same way I set p1.From and p1.To. Why are these properties returning null?

[TestMethod]
public void SetNameTest()
{
    var x = new Name { AName = "Jack", Valid = p1, Id = "123" };
    var y = new Name { AName = "John", Valid = p2, Id = "321" };
    b.SetValue(ref x, y);
    Assert.AreEqual("John", x.AName);
    Assert.AreEqual(p2, x.Valid);
    Assert.AreEqual("321", x.Id);
}

EDIT:

public class Name: Base
{
    private string id;
    public string Id
    {
        get { return id; }
        set { SetValue(ref id, value); }
    }
    private string aName;
    public string AName
    {
        get { return aName; }
        set { SetValue(ref aName, value); }
    }
    private DateTimePeriod valid;
    public DateTimePeriod Valid
    {
        get { return valid; }
        set { SetValue(ref valid, value); }
    }
}

public class DateTimePeriod: Period<DateTime>
{
}

public class Period<T>: Base
{
    private T from;
    private T to;
    public Period()
    {
        from = default(T);
        to = default(T);
    }
    public T From
    {
        get { return from; }
        set { SetValue(ref from, value); }
    }
    public T To
    {
        get { return to; }
        set { SetValue(ref to, value); }
    }
}

EDIT2:

public class Base: object
{
    public void SetValue<T>(ref T field, T value)
    {
        if (field == null) return;
        if (field.Equals(value)) return;
        field = value;
        DoOnChanged();
    }
    public event EventHandler OnChanged;
    protected void DoOnChanged()
    {
        if (OnChanged == null) return;
        OnChanged(this, null);
    }
}

Solution

  • If I debug your Code in the Unit test, it´s working without any Problems. I changed the setter to a normal use, because I don´t know what you are using for Base and SetValue.

    But the Unit Test are working fine with this code:

    namespace SampleUnitTest
    {
        [TestClass]
        public class Foo
        {
            [TestMethod]
            public void Bar()
            {
                var p1 = new DateTimePeriod { From = DateTime.MinValue, To = DateTime.MaxValue };
                var p2 = new DateTimePeriod { From = DateTime.MaxValue, To = DateTime.MinValue };
                var x = new Name { AName = "Jack", Valid = p1, Id = "123" };
                var y = new Name { AName = "John", Valid = p2, Id = "321" };
                Assert.AreEqual("John", x.AName);
                Assert.AreEqual(p2, x.Valid);
                Assert.AreEqual("321", x.Id);
            }
        } 
    
        public class Name
        {
            private string id;
            public string Id
            {
                get { return id; }
                set { id = value; }
            }
            private string aName;
            public string AName
            {
                get { return aName; }
                set { aName = value; ; }
            }
            private DateTimePeriod valid;
            public DateTimePeriod Valid
            {
                get { return valid; }
                set { valid = value ; }
            }
        }
    
        public class DateTimePeriod : Period<DateTime>
        {
        }
    
        public class Period<T>
        {
            private T from;
            private T to;
            public Period()
            {
                from = default(T);
                to = default(T);
            }
            public T From
            {
                get { return from; }
                set { from = value; }
            }
            public T To
            {
                get { return to; }
                set { to = value; }
            }
        }
    }
    

    I think the SetValue is also the reason why your DateTime is working and your other classes don´t.