Пример #1
0
        /// <summary>
        ///     this method needs to be handled with much care.
        ///     First, the input list must not stem from a request finishing with a call to AsNoTracking method.
        ///     Second, the query from which the input stems must be closed properly.
        ///     This means that the result of a query must be cast to any kind of IEnumerable (List, Array)
        ///     which will close the preceding query.
        /// </summary>
        /// <param name="dbAccess"></param>
        /// <param name="entities"></param>
        /// <returns></returns>
        public static DbResults <T> Delete <T, TId>(this DbContext dbAccess, IEnumerable <T> entities)
            where T : BaseAuditable <TId>
        {
            var results = new DbResults <T>();

            if (null != entities)
            {
                using var transaction = dbAccess.Database.BeginTransaction();
                foreach (var entity in entities)
                {
                    var result = new DbResult <T> {
                        Entity = entity
                    };

                    if (null == entity)
                    {
                        result.ResultCode = DbResultCode.EntityIsNull;
                        continue;
                    }

                    // Check 1: model has no unique key - skip
                    if (EqualityComparer <TId> .Default.Equals(entity.Id, default))
                    {
                        result.ResultCode = DbResultCode.Impractical;
                        continue;
                    }

                    // Check 2: model can be deleted
                    dbAccess.Entry(entity).State = EntityState.Deleted;
                    var changes = dbAccess.SaveChanges();
                    if (0 == changes || dbAccess.Entry(entity).State != EntityState.Detached)
                    {
                        result.ResultCode = DbResultCode.SaveFailed;
                    }

                    results.Results.Add(result);
                }

                if (results.Success)
                {
                    transaction.Commit();
                }
                else
                {
                    transaction.Rollback();
                }
            }

            return(results);
        }
Пример #2
0
        public static void ValidateEntity <T, TId>(T entity, DbResult <T> result)
            where T : IAuditable <TId>
        {
            entity.CreatedAt = EqualityComparer <DateTime> .Default.Equals(entity.CreatedAt, default)
                ? DateTime.UtcNow
                : entity.CreatedAt;

            entity.CreatedBy ??= Requestor;

            var validationContext = new ValidationContext(entity);

            if (!Validator.TryValidateObject(entity, validationContext, result.ValidationResults, true))
            {
                result.ResultCode |= DbResultCode.ValidationFailed;
            }
        }
Пример #3
0
        public static DbResult <T> CheckUpdateEntity <T, TId>(this DbContext dbContext, T entity)
            where T : BaseAuditable <TId>
        {
            var result = new DbResult <T> {
                Entity = entity
            };

            // Check 0: entity is NULL
            if (null == entity)
            {
                result.ResultCode = DbResultCode.EntityIsNull;
                return(result);
            }

            // Check 1: entity has no unique key - skip
            if (EqualityComparer <TId> .Default.Equals(entity.Id, default))
            {
                result.ResultCode |= DbResultCode.Impractical;
            }

            // Check 2: entity does not pass validation - skip
            ValidateEntity <T, TId>(entity, result);

            // Check 3: entity violates UK constraint - skip
            if (entity is IUniqueAuditable uniqueEntity)
            {
                var baseAuditables = dbContext.Set <T>().AsEnumerable() ?? new List <T>();
                if (baseAuditables.Any(q => uniqueEntity.HasSameUniqueKey(q) &&
                                       !EqualityComparer <TId> .Default.Equals(entity.Id, q.Id)))
                {
                    result.ResultCode |= DbResultCode.Duplicate;
                }
            }

            return(result);
        }