title: Perform Assert.AreMatch() to deep compare properties in two objects
body: <p>I am writing tests against our Caching mechanism and I want to be sure that what goes into the cache is the same as what comes out, ie that all properties match. Here is a fictional example of how I would like it to work</p>
  
  <pre><code>    [Test]
      public void add_client_model_member_to_cache_then_retreve()
      {
          //arrange
          MemcachedClient client = new MemcachedClient();
          Member member = GetMember();
          client.Store(StoreMode.Set, "membertest", member);
  
          // act
          var result = client.Get&lt;Member&gt;("membertest");
  
          // assert
          Assert.AreMatch(result, member);
      }
  </code></pre>
  
  <p>It is not feasible to perform Assert.AreEqual on each property as there will be many of these tests with many properties in each.</p>
  
  <p>Wow, thanks Jon. I think you answered that in under one minute. Here are my resulting solution for any interested parties. I implemented as Jon suggested (I think) however I got into a little trouble with array properties and as such my solution only handles arrays of ints (all I currently require). </p>
  
  <p>It also got to be a fairly slippery slope if I try to check deeper than one level. I am sure this can be achieved however for my purposes it is not required.</p>
  
  <pre><code>private bool AreMatch(object initial, object result)
      {
          if (initial.Equals(result)) 
              return true;
  
          foreach (var property in initial.GetType().GetProperties())
          {
              var initialPropValue = property.GetValue(initial,null);
              var resultPropValue = result.GetType().GetProperty(property.Name).GetValue(result,null);
  
              if (property.PropertyType.IsArray)
              {
                  if ((initialPropValue != null &amp;&amp; resultPropValue != null) &amp;&amp; !Enumerable.SequenceEqual((int[])initialPropValue, (int[])resultPropValue))
                          return false;                   
              }
              else if (!object.Equals(initialPropValue, resultPropValue))
              {
                  return false;
              }
              else if (initialPropValue != null &amp;&amp; property.PropertyType.IsClass)
              {
                  // Don't go deeper than one level, this got me into trouble
                  //if (!AreMatch(initialPropValue, resultPropValue))
                  //  return false;
              }
          }
          return true;
      }
  </code></pre>
  
  <p>The method above can be used in the following situations</p>
  
  <pre><code>    [Test]
      public void cached_result_is_same_as_original()
      {
          //arrange
          Member member = GetMember();
          client.Store(StoreMode.Set, "membertest", member);
  
          // act
          var result = client.Get&lt;Member&gt;("membertest");
  
          // assert
          Assert.IsTrue(AreMatch(member, result));
      }
  
      [Test]
      public void cached_result_is_same_as_original()
      {
          //arrange
          Member member = GetMember();
          client.Store(StoreMode.Set, "membertest", member);
  
          // act
          var result = client.Get&lt;Member&gt;("membertest");
          result.FirstName = "Result is different"; 
  
          // assert
          Assert.IsFalse(AreMatch(member, result));
      }
  </code></pre>