/// <summary> /// Returns a new change record that represents the total of this change /// and the previous change. /// </summary> /// <param name="previousChange"></param> /// <returns></returns> public ChangeRecord Compound(ChangeRecord previousChange) { // assume the propertyDiffs array in both objects is aligned var resultDiffs = new PropertyDiff[_propertyDiffs.Length]; for (var i = 0; i < _propertyDiffs.Length; i++) { resultDiffs[i] = _propertyDiffs[i].Compound(previousChange.PropertyDiffs[i]); } // return a new change record that represents the accumulation of both changes // the resultant ChangeType depends on whether this change Supercedes previousChange, or vice versa return new ChangeRecord(_entity, Supercedes(previousChange) ? _changeType : previousChange._changeType, resultDiffs); }
/// <summary> /// Returns a new change record that represents the total of this change /// and the previous change. /// </summary> /// <param name="previousChange"></param> /// <returns></returns> public ChangeRecord Compound(ChangeRecord previousChange) { // assume the propertyDiffs array in both objects is aligned var resultDiffs = new PropertyDiff[_propertyDiffs.Length]; for (var i = 0; i < _propertyDiffs.Length; i++) { resultDiffs[i] = _propertyDiffs[i].Compound(previousChange.PropertyDiffs[i]); } // return a new change record that represents the accumulation of both changes // the resultant ChangeType depends on whether this change Supercedes previousChange, or vice versa return(new ChangeRecord(_entity, Supercedes(previousChange) ? _changeType : previousChange._changeType, resultDiffs)); }
/// <summary> /// Records that the specified change occured to the specified entity. /// </summary> /// <param name="entity"></param> /// <param name="changeType"></param> /// <param name="propertyDiffs"></param> internal void RecordChange(Entity entity, EntityChangeType changeType, PropertyDiff[] propertyDiffs) { var thisChange = new ChangeRecord(entity, changeType, propertyDiffs); // check if this entity was already recorded in the list // note that reference equality is used because we do not know how the Equals method of the entity may be implemented // for example, it may define equality based on a property whose value has changed, which would break this logic var prevRecordIndex = _changeRecords.FindIndex(r => ReferenceEquals(r.Entity, entity)); if (prevRecordIndex > -1) { // this entity was already marked as changed var previousChange = _changeRecords[prevRecordIndex]; // compound the previous change record with this one _changeRecords[prevRecordIndex] = thisChange.Compound(previousChange); } else { // record this change in the change set _changeRecords.Add(thisChange); } }
/// <summary> /// Checks whether this change supercedes the specified other change. This change supercedes other iff /// the <see cref="ChangeType"/> of this change is greater than the <see cref="ChangeType"/> of the other. /// </summary> /// <remarks> /// The <see cref="EntityChangeType.Create"/> value supercedes <see cref="EntityChangeType.Update"/>, and /// <see cref="EntityChangeType.Delete"/> supercedes both. In other words, a Create followed by an update /// is fundamentally a Create, and a Create or Update followed by a Delete is fundamentally a Delete. /// </remarks> /// <param name="other"></param> /// <returns></returns> private bool Supercedes(ChangeRecord other) { return _changeType > other.ChangeType; }
/// <summary> /// Checks whether this change supercedes the specified other change. This change supercedes other iff /// the <see cref="ChangeType"/> of this change is greater than the <see cref="ChangeType"/> of the other. /// </summary> /// <remarks> /// The <see cref="EntityChangeType.Create"/> value supercedes <see cref="EntityChangeType.Update"/>, and /// <see cref="EntityChangeType.Delete"/> supercedes both. In other words, a Create followed by an update /// is fundamentally a Create, and a Create or Update followed by a Delete is fundamentally a Delete. /// </remarks> /// <param name="other"></param> /// <returns></returns> private bool Supercedes(ChangeRecord other) { return(_changeType > other.ChangeType); }