/// <summary>Audits and saves all changes made in this context to the underlying database.</summary>
        /// <param name="context">The context used to audits and saves all changes made.</param>
        /// <param name="audit">The audit to use to add changes made to the context.</param>
        /// <returns>The number of objects written to the underlying database.</returns>
        public static int SaveChanges(this DbContext context, Audit audit)
        {
            AuditStateEntry.PreSaveChanges(audit, context);
            var result = context.SaveChanges();

            AuditStateEntry.PostSaveChanges(audit);

            if (audit.Configuration.AutoSaveAction != null)
            {
                audit.Configuration.AutoSaveAction(context, audit);
                context.SaveChanges();
            }

            return(result);
        }
        /// <summary>A DbContext extension method that saves the changes asynchronous.</summary>
        /// <param name="context">The context used to audits and saves all changes made.</param>
        /// <param name="audit">The audit to use to add changes made to the context.</param>
        /// <param name="cancellationToken">A CancellationToken to observe while waiting for the task to complete.</param>
        /// <returns>
        ///     A task that represents the asynchronous save operation. The task result contains the number of objects written
        ///     to the underlying database
        /// </returns>
        public static Task <int> SaveChangesAsync(this DbContext context, Audit audit, CancellationToken cancellationToken)
        {
            AuditStateEntry.PreSaveChanges(audit, context);
            var result = context.SaveChangesAsync(cancellationToken);

            AuditStateEntry.PostSaveChanges(audit);

            if (audit.Configuration.AutoSaveAsyncAction != null)
            {
                result.ContinueWith(x =>
                {
                    audit.Configuration.AutoSaveAsyncAction(context, audit, cancellationToken);
                    return(x.Result);
                }, cancellationToken).ConfigureAwait(false);
            }

            return(result);
        }