Beispiel #1
0
        static async Task Main(string[] args)
        {
            Console.WriteLine("Start");

            var order = new Order();

            using (var audit = AuditScope.Create("Order:Update", () => order, new { UserName = "******" }))
            {
                Console.WriteLine("Audit");
                order.Status = EnumStatus.Finish;

                audit.Comment("commit");
            }

            AuditScope auditScope = null;

            try
            {
                auditScope = await AuditScope.CreateAsync("Test:Identity", () => order, new { user = "******" });

                {
                    order.Status = EnumStatus.Start;
                }
                auditScope.Comment("01");
            }
            finally
            {
                if (auditScope != null)
                {
                    await auditScope.DisposeAsync();
                }
            }

            Console.ReadKey();
        }
        /// <inheritdoc />
        public virtual async Task DeleteAsync(TEntity item, CancellationToken cancellationToken = default)
        {
            AuditScope auditScope = null;
            TKey       id         = item.Id;
            await DecoratedService.DeleteAsync(item, cancellationToken);

            try
            {
                auditScope = await AuditScope.CreateAsync($"{EntityName}:Delete", () => item);

                auditScope.Event.Environment.UserName = UserContext.CurrentUser;
                auditScope.Event.Target.Type          = $"{EntityFullName}";

                // Set the deleted item to null. This prevents Audit.NET from replicating the audit details of the
                // "Old" object into "New".
                // ReSharper disable once RedundantAssignment
                item = default;
            }
            catch (Exception e)
            {
                Logger.Warning(e, "Auditing failed for DeleteAsync of type {Entity} with ID {Id}.", EntityName, id);
            }
            finally
            {
                if (auditScope != null)
                {
                    await auditScope.DisposeAsync();
                }
            }
        }
        /// <inheritdoc />
        public virtual async Task <IEnumerable <TEntity> > RetrieveAsync(
            Expression <Func <TEntity, bool> > filter = null,
            PagingContext pagingContext = null,
            Func <IQueryable <TEntity>, IOrderedQueryable <TEntity> > sortCondition = null,
            CancellationToken cancellationToken = default,
            params Expression <Func <TEntity, object> >[] includes)
        {
            IEnumerable <TEntity> entities = await DecoratedService.RetrieveAsync(
                filter,
                pagingContext,
                sortCondition,
                cancellationToken,
                includes);

            IEnumerable <TEntity> retrieved  = entities.ToList();
            AuditScope            auditScope = null;

            try
            {
                // Due to size constraints, only audit the number of objects retrieved rather than the objects
                // themselves.
                var options = new AuditScopeOptions
                {
                    EventType   = $"{EntityName}:Retrieve+",
                    ExtraFields = new { Count = retrieved.Count() },
                    AuditEvent  = new AuditEvent {
                        Target = new AuditTarget()
                    }
                };

                auditScope = await AuditScope.CreateAsync(options);

                auditScope.Event.Environment.UserName = UserContext.CurrentUser;
                auditScope.Event.Target.Type          = $"{EntityFullName}";
            }
            catch (Exception e)
            {
                Logger.Warning(e, "Auditing failed for RetrieveAsync+ of type {Entity}.", EntityName);
            }
            finally
            {
                if (auditScope != null)
                {
                    await auditScope.DisposeAsync();
                }
            }

            return(retrieved);
        }
        /// <inheritdoc />
        public virtual async Task UpdateAsync(TEntity item, CancellationToken cancellationToken = default)
        {
            AuditScope auditScope         = null;
            var        isServiceException = false;
            TKey       id       = item.Id;
            TEntity    original = await ReadOnlyRepository.RetrieveAsync(id, cancellationToken);

            try
            {
                auditScope = await AuditScope.CreateAsync($"{EntityName}:Update", () => original);

                auditScope.Event.Environment.UserName = UserContext.CurrentUser;
                auditScope.Event.Target.Type          = $"{EntityFullName}";

                try
                {
                    await DecoratedService.UpdateAsync(item, cancellationToken);
                }
                catch
                {
                    isServiceException = true;
                    auditScope.Discard();
                    throw;
                }

                // Assign the updated item back to the original. This allows Audit.NET to determine what was changed.
                // ReSharper disable once RedundantAssignment
                original = item;
            }
            catch (Exception e)
            {
                if (isServiceException)
                {
                    throw;
                }

                Logger.Warning(e, "Auditing failed for UpdateAsync of type {Entity} with ID {Id}.", EntityName, id);
            }
            finally
            {
                if (auditScope != null)
                {
                    await auditScope.DisposeAsync();
                }
            }
        }
        /// <inheritdoc />
        public virtual async Task <TEntity> RetrieveAsync(
            TKey id,
            CancellationToken cancellationToken = default,
            params Expression <Func <TEntity, object> >[] includes)
        {
            TEntity    retrieved          = default;
            AuditScope auditScope         = null;
            var        isServiceException = false;

            try
            {
                auditScope = await AuditScope.CreateAsync($"{EntityName}:Retrieve", () => retrieved);

                auditScope.Event.Environment.UserName = UserContext.CurrentUser;
                auditScope.Event.Target.Type          = $"{EntityFullName}";

                try
                {
                    retrieved = await DecoratedService.RetrieveAsync(id, cancellationToken, includes);
                }
                catch
                {
                    isServiceException = true;
                    auditScope.Discard();
                    throw;
                }
            }
            catch (Exception e)
            {
                if (isServiceException)
                {
                    throw;
                }

                Logger.Warning(e, "Auditing failed for RetrieveAsync of type {Entity} with ID {Id}.", EntityName, id);
            }
            finally
            {
                if (auditScope != null)
                {
                    await auditScope.DisposeAsync();
                }
            }

            return(retrieved);
        }
        /// <inheritdoc />
        public virtual async Task <TEntity> CreateAsync(
            TEntity item,
            CancellationToken cancellationToken = default)
        {
            TEntity    created            = default;
            AuditScope auditScope         = null;
            var        isServiceException = false;

            try
            {
                auditScope = await AuditScope.CreateAsync($"{EntityName}:Create", () => created);

                auditScope.Event.Environment.UserName = UserContext.CurrentUser;
                auditScope.Event.Target.Type          = $"{EntityFullName}";

                try
                {
                    created = await DecoratedService.CreateAsync(item, cancellationToken);
                }
                catch
                {
                    isServiceException = true;
                    auditScope.Discard();
                    throw;
                }
            }
            catch (Exception e)
            {
                if (isServiceException)
                {
                    throw;
                }

                Logger.Warning(e, "Auditing failed for CreateAsync of type {Entity}.", EntityName);
            }
            finally
            {
                if (auditScope != null)
                {
                    await auditScope.DisposeAsync();
                }
            }

            return(created);
        }
        /// <inheritdoc />
        public virtual async Task <int> CountAsync(
            Expression <Func <TEntity, bool> > filter = null,
            CancellationToken cancellationToken       = default)
        {
            int count = await DecoratedService.CountAsync(filter, cancellationToken);

            AuditScope auditScope = null;

            try
            {
                var options = new AuditScopeOptions
                {
                    EventType   = $"{EntityName}:Count",
                    ExtraFields = new { Count = count },
                    AuditEvent  = new AuditEvent {
                        Target = new AuditTarget()
                    }
                };

                auditScope = await AuditScope.CreateAsync(options);

                auditScope.Event.Environment.UserName = UserContext.CurrentUser;
                auditScope.Event.Target.Type          = $"{EntityFullName}";
            }
            catch (Exception e)
            {
                Logger.Warning(e, "Auditing failed for CountAsync of type {Entity}.", EntityName);
            }
            finally
            {
                if (auditScope != null)
                {
                    await auditScope.DisposeAsync();
                }
            }

            return(count);
        }
        /// <inheritdoc />
        public virtual async Task <bool> ExistsAsync(TKey id, CancellationToken cancellationToken = default)
        {
            bool exists = await DecoratedService.ExistsAsync(id, cancellationToken);

            AuditScope auditScope = null;

            try
            {
                var options = new AuditScopeOptions
                {
                    EventType   = $"{EntityName}:Exists",
                    ExtraFields = new { Id = id, Exists = exists },
                    AuditEvent  = new AuditEvent {
                        Target = new AuditTarget()
                    }
                };

                auditScope = await AuditScope.CreateAsync(options);

                auditScope.Event.Environment.UserName = UserContext.CurrentUser;
                auditScope.Event.Target.Type          = $"{EntityFullName}";
            }
            catch (Exception e)
            {
                Logger.Warning(e, "Auditing failed for ExistsAsync of type {Entity} with ID {Id}.", EntityName, id);
            }
            finally
            {
                if (auditScope != null)
                {
                    await auditScope.DisposeAsync();
                }
            }

            return(exists);
        }