private Fintrak.Shared.SystemCore.Entities.AuditTrail AuditTrailFactory(DbEntityEntry entry, string userName)
        {
            Fintrak.Shared.SystemCore.Entities.AuditTrail audit = new Fintrak.Shared.SystemCore.Entities.AuditTrail();

            audit.RevisionStamp = DateTime.Now;
            audit.TableName     = entry.Entity.GetType().Name;
            audit.UserName      = userName;
            audit.Deleted       = false;
            audit.CreatedBy     = userName;
            audit.CreatedOn     = DateTime.Now;
            audit.UpdatedBy     = userName;
            audit.UpdatedOn     = DateTime.Now;

            if (entry.State == EntityState.Added)
            {
                //entry is Added

                var model = (EntityBase)entry.Entity;
                model.CreatedBy = DataConnector.LoginName;
                model.CreatedOn = DateTime.Now;
                model.UpdatedBy = DataConnector.LoginName;
                model.UpdatedOn = DateTime.Now;

                audit.NewData = GetEntryValueInString(entry, false);
                audit.Actions = AuditAction.C;
            }
            else if (entry.State == EntityState.Deleted)
            {
                //entry in deleted
                audit.OldData = GetEntryValueInString(entry, true);
                audit.Actions = AuditAction.D;
            }
            else
            {
                //entry is modified
                var model = (EntityBase)entry.Entity;
                model.UpdatedBy = DataConnector.LoginName;
                model.UpdatedOn = DateTime.Now;

                audit.OldData = GetEntryValueInString(entry, true);
                audit.NewData = GetEntryValueInString(entry, false);
                audit.Actions = AuditAction.U;

                IEnumerable <string> modifiedProperties = entry.CurrentValues.PropertyNames;
                //assing collection of mismatched Columns name as serialized string
                audit.ChangedColumns = XMLSerializationHelper.XmlSerialize(modifiedProperties.ToArray());
            }

            return(audit);
        }
        public override int SaveChanges()
        {
            try
            {
                if (ChangeTracker.HasChanges())
                {
                    var entries = this.ChangeTracker.Entries();

                    foreach (DbEntityEntry entry in entries)
                    {
                        if (entry.Entity != null && !(entry.Entity is Fintrak.Shared.SystemCore.Entities.AuditTrail))
                        {
                            //is a normal entry, not a relationship
                            Fintrak.Shared.SystemCore.Entities.AuditTrail audit = this.AuditTrailFactory(entry, DataConnector.LoginName);
                            auditTrailList.Add(audit);
                        }
                    }
                }

                if (auditTrailList.Count > 0)
                {
                    foreach (var audit in auditTrailList)
                    {
                        //add all audits
                        AuditTrailSet.Add(audit);
                    }

                    auditTrailList.Clear();
                }

                return(base.SaveChanges());
            }
            catch (DbUpdateException e)
            {
                var innerEx = e.InnerException;
                while (innerEx.InnerException != null)
                {
                    innerEx = innerEx.InnerException;
                }

                throw new Exception(innerEx.Message);
            }
            catch (DbEntityValidationException e)
            {
                var sb = new StringBuilder();

                foreach (var entry in e.EntityValidationErrors)
                {
                    foreach (var error in entry.ValidationErrors)
                    {
                        sb.AppendLine(string.Format("{0}-{1}-{2}", entry.Entry.Entity, error.PropertyName, error.ErrorMessage));
                    }
                }

                throw new Exception(sb.ToString());
            }
            catch (Exception e)
            {
                var innerEx = e.InnerException;
                while (innerEx.InnerException != null)
                {
                    innerEx = innerEx.InnerException;
                }

                throw new Exception(innerEx.Message);
            }
        }