Beispiel #1
0
        public void replay_all_should_load_aggregate_from_history()
        {
            // arrange
            var id       = NewGuid();
            var birthday = Now.AddYears(-3);
            var person   = new Person(id, "Jane", "Smith", birthday);
            var spouse   = new Person(NewGuid(), "John", "Doe", Now);
            var version  = 0;

            person.Marry(spouse, Now);
            person.ChangeLastName("Doe");

            foreach (var @event in person.UncommittedEvents)
            {
                @event.Version = version++;
            }

            var lifeExperiences = person.UncommittedEvents.ToArray();
            var twin            = new Person();

            person.AcceptChanges();

            // act
            twin.ReplayAll(lifeExperiences);

            // assert
            twin.Equals(person).Should().BeTrue();
            twin.Version.Should().Be(2);
        }
Beispiel #2
0
        public void ChangeTracking_EntitySubPropertyTracking()
        {
            var p = new Person
            {
                Address = new Address()
            };

            p.AcceptChanges();
            p.TrackChanges();

            p.Address.City = "Bardon";

            Assert.IsTrue(p.IsChanged);
            Assert.AreEqual(new System.Collections.Specialized.StringCollection {
                "Address"
            }, p.ChangeTracking);
            Assert.IsTrue(p.Address.IsChanged);
            Assert.AreEqual(new System.Collections.Specialized.StringCollection {
                "City"
            }, p.Address.ChangeTracking);
        }
Beispiel #3
0
        public void accept_changes_should_update_state()
        {
            // arrange
            var person  = new Person(NewGuid(), "Jane", "Smith", Now.AddYears(-3));
            var spouse  = new Person(NewGuid(), "John", "Doe", Now);
            var version = 0;

            person.Marry(spouse, Now);
            person.ChangeLastName("Doe");

            foreach (var @event in person.UncommittedEvents)
            {
                @event.Version = version++;
            }

            // act
            person.AcceptChanges();

            // assert
            person.IsChanged.Should().BeFalse();
            person.UncommittedEvents.Should().BeEmpty();
            person.Version.Should().Be(2);
        }
        private Person AttachWithRelations(Person entity, InsertMode insertMode = InsertMode.Attach, MergeOption mergeOption = MergeOption.AppendOnly, List <object> referenceTrackingList = null)
        {
            #region iteration tracking

            if (ReferenceEquals(null, referenceTrackingList))
            {
                referenceTrackingList = new List <object>();
            }

            if (referenceTrackingList.Contains(entity))
            {
                return(_people.GetExisting(entity));
            }
            else
            {
                referenceTrackingList.Add(entity);
            }

            #endregion

            #region add/attach entity

            Person existingEntity = null;

            switch (insertMode)
            {
            case InsertMode.Add:
                existingEntity = _people.Add(entity);
                break;

            case InsertMode.Attach:
                existingEntity = _people.Attach(entity);
                break;

            default:
                throw new Exception(string.Format("Implementation Exception: missing action for {0}", insertMode));
            }

            if (!ReferenceEquals(null, existingEntity) && ReferenceEquals(existingEntity, entity))
            {
                return(existingEntity);
            }

            #endregion

            #region attach relations recursively

            // register entity's property changed event if entity is new to context
            if (ReferenceEquals(null, existingEntity))
            {
                entity.PropertyChanged += On_person_propertyChanged;
            }

            // attach related entity to context
            if (!ReferenceEquals(null, entity.Address1))
            {
                var existingRelatedEntity = AttachWithRelations(entity.Address1, insertMode, mergeOption, referenceTrackingList);

                // update relation if entity is new to context or relation is new to entity
                if (ReferenceEquals(null, existingEntity) || !entity.Address1.Equals(existingEntity.Address1))
                {
                    if (!ReferenceEquals(null, existingRelatedEntity) && !ReferenceEquals(existingRelatedEntity, entity.Address1))
                    {
                        // check merge options
                        if (!(mergeOption == MergeOption.PreserveChanges && existingRelatedEntity.ChangeTracker.OriginalValues.ContainsKey("People")))
                        {
                            using (entity.ChangeTrackingPrevention())
                            {
                                entity.Address1 = existingRelatedEntity;
                            }

                            using (existingRelatedEntity.ChangeTrackingPrevention())
                            {
                                var entityToReplace = existingRelatedEntity.People.FirstOrDefault(e => e.Equals(entity));
                                if (!ReferenceEquals(null, entityToReplace))
                                {
                                    using (entityToReplace.ChangeTrackingPrevention())
                                    {
                                        existingRelatedEntity.People.Remove(entityToReplace);
                                    }
                                }

                                existingRelatedEntity.People.Add(entity);
                            }
                        }
                    }
                }
            }

            #endregion

            #region refresh existing entity based on merge options

            if (!ReferenceEquals(null, existingEntity) && !ReferenceEquals(existingEntity, entity))
            {
                if (People.MergeOption == MergeOption.OverwriteChanges)
                {
                    Invoke(delegate
                    {
                        existingEntity.Refresh(entity, trackChanges: false);
                        existingEntity.AcceptChanges();
                    });
                }
                else if (People.MergeOption == MergeOption.PreserveChanges)
                {
                    Invoke(delegate
                    {
                        existingEntity.Refresh(entity, trackChanges: false, preserveExistingChanges: true);
                    });
                }
            }

            #endregion

            return(existingEntity);
        }