Repository.cs 12.6 KB
using Hh.Mes.Common.Infrastructure;
using Hh.Mes.Common.Request;
using Hh.Mes.POJO.Response;
using Microsoft.EntityFrameworkCore;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Reflection;
using Z.EntityFramework.Plus;

namespace WebRepository
{
    public class Repository<T> : IRepository<T> where T : SysEntity
    {
        private BaseDBContext _context;

        public LoginInfo _loginInfo { get; set; }
        public Repository(BaseDBContext context)
        {
            _context = context;
        }

        public bool IsExist(Expression<Func<T, bool>> exp)
        {
            return _context.Set<T>().Any(exp); /*1:要检查是否为空的序列。2:如果源序列包含任何元素,则为 true;否则为 false。*/
        }

        /// <summary>
        /// 查找单个,且不被上下文所跟踪
        /// </summary>
        public T FindSingle(Expression<Func<T, bool>> exp)
        {
            return _context.Set<T>().AsNoTracking().FirstOrDefault(exp);
        }

        /// <summary>
        /// 根据过滤条件,获取记录
        /// </summary>
        /// <param name="exp">The exp.</param>
        public IQueryable<T> Find(Expression<Func<T, bool>> exp = null)
        {
            return Filter(exp);
        }

        /// <summary>
        /// 得到分页记录
        /// </summary>
        /// <param name="pageindex">The pageindex.</param>
        /// <param name="pagesize">The pagesize.</param>
        /// <param name="orderby">排序,格式如:"Id"/"Id descending"</param>
        /// <param name="exp">表达式</param>
        public IQueryable<T> Find(int pageindex, int pagesize, string orderby = "", Expression<Func<T, bool>> exp = null)
        {
            if (pageindex < 1) pageindex = 1;
            if (string.IsNullOrEmpty(orderby))
                orderby = "Id descending";

            return Filter(exp).OrderBy(orderby).Skip(pagesize * (pageindex - 1)).Take(pagesize);
        }

        /// <summary>
        /// 根据过滤条件获取记录数
        /// </summary>
        public int GetCount(Expression<Func<T, bool>> exp = null)
        {
            return Filter(exp).Count();
        }

        public void Add(T entity)
        {
        
            entity.CreateBy = _loginInfo.Account;
            entity.CreateTime = DateTime.Now;

            _context.Set<T>().Add(entity);
            Save();
        }

        /// <summary>
        /// 批量添加
        /// </summary>
        /// <param name="entities">The entities.</param>
        public void BatchAdd(T[] entities)
        {
            foreach (var entity in entities)
            {
                entity.CreateBy = _loginInfo.Account;
                entity.CreateTime = DateTime.Now;
            }
            _context.Set<T>().AddRange(entities);
            Save();
        }

        public void Update(T entity)
        {
            if (string.IsNullOrEmpty(entity.CreateBy))
            {
                T oldentity = FindSingle(u => u.Id == entity.Id);
                entity.CreateBy = oldentity.CreateBy;
                entity.CreateTime = oldentity.CreateTime;
            }

            entity.UpdateBy = _loginInfo.Account;
            entity.UpdateTime = DateTime.Now;

            var entry = this._context.Entry(entity);
            entry.State = EntityState.Modified;
            //如果数据没有发生变化
            if (!this._context.ChangeTracker.HasChanges())
            {
                return;
            }

            Save();
        }

        public void UpdateS(T entity, List<dynamic> bodyEntity)
        {
            T oldentity = null;
            if (string.IsNullOrEmpty(entity.CreateBy))
            {
                oldentity = FindSingle(u => u.Id == entity.Id);
                entity.CreateBy = oldentity.CreateBy;
                entity.CreateTime = oldentity.CreateTime;
            }
            if (bodyEntity != null && bodyEntity.Count() > 0)
            {
                foreach (var item in bodyEntity)
                {
                    item.Id = oldentity.Id;
                    item.CreateBy = oldentity.CreateBy;
                    item.CreateTime = oldentity.CreateTime;

                    item.UpdateBy = _loginInfo.Account;
                    item.UpdateTime = DateTime.Now;
                }
                var entityEntry = this._context.Entry(bodyEntity);
                entityEntry.State = EntityState.Modified;
            }

            entity.UpdateBy = _loginInfo.Account;
            entity.UpdateTime = DateTime.Now;

            var entry = this._context.Entry(entity);
            entry.State = EntityState.Modified;
            //如果数据没有发生变化
            if (!this._context.ChangeTracker.HasChanges())
            {
                return;
            }

            Save();
        }

        public void UpdateByTracking(T entity)
        {
            if (string.IsNullOrEmpty(entity.CreateBy))
            {
                T oldentity = FindSingle(u => u.Id == entity.Id);
                entity.CreateBy = oldentity.CreateBy;
                entity.CreateTime = oldentity.CreateTime;
            }

            entity.UpdateBy = _loginInfo.Account;
            entity.UpdateTime = DateTime.Now;

            T entity_exist = _context.Set<T>().AsQueryable().Where(u => u.Id.Equals(entity.Id)).FirstOrDefault();

            if (entity_exist != null)
            {
                foreach (var property in entity_exist.GetType().GetProperties())
                {
                    var propertyValue = entity.GetType().GetProperty(property.Name).GetValue(entity, null);
                    if (propertyValue != null)
                    {
                        if (propertyValue.GetType().IsClass)
                        {

                        }
                        entity_exist.GetType().InvokeMember(property.Name, BindingFlags.SetProperty, null, entity_exist, new object[] { propertyValue });
                    }
                }

                foreach (var field in entity_exist.GetType().GetFields())
                {
                    var fieldValue = entity.GetType().GetField(field.Name).GetValue(entity);
                    if (fieldValue != null)
                    {
                        entity_exist.GetType().InvokeMember(field.Name, BindingFlags.SetField, null, entity_exist, new object[] { fieldValue });
                    }
                }

                var entry = this._context.Entry(entity_exist);
                entry.State = EntityState.Modified;
                //如果数据没有发生变化
                if (!this._context.ChangeTracker.HasChanges())
                {
                    return;
                }
            }
            else
            {
                var entry = this._context.Entry(entity);
                entry.State = EntityState.Modified;
                //如果数据没有发生变化
                if (!this._context.ChangeTracker.HasChanges())
                {
                    return;
                }
            }

            Save();
        }

        /// <summary>
        /// 实现按需要只更新部分更新
        /// <para>如:Update(u =>u.Id==1,u =>new User{Name="ok"});</para>
        /// </summary>
        /// <param name="where">The where.</param>
        /// <param name="entity">The entity.</param>
        public void Update(Expression<Func<T, bool>> where, Expression<Func<T, T>> entity)
        {
            _context.Set<T>().Where(where).Update(entity);
            Save();
        }

        public void Delete(T entity)
        {
            _context.Set<T>().Remove(entity);
            Save();
        }

        public void DeleteByTracking(T entity)
        {
            T entity_exist = _context.Set<T>().AsQueryable().Where(u => u.Id.Equals(entity.Id)).FirstOrDefault();
            if (entity_exist != null)
            {
                _context.Set<T>().Remove(entity_exist);
            }
            else
            {
                _context.Set<T>().Remove(entity);
            }

            Save();
        }

        public virtual void Delete(Expression<Func<T, bool>> exp)
        {
            System.Collections.Generic.List<T> entitys = _context.Set<T>().Where(exp).ToList();
            foreach (var item in entitys)
            {
                Delete(item);
            }
        }

        public void Save()
        {
            try
            {
                _context.SaveChanges();
            }
            catch (Exception ex)
            {
                string sMessage = ex.Message;
                if (ex.InnerException != null)
                {
                    sMessage = ex.InnerException.Message;

                    if (ex.InnerException.InnerException != null)
                    {
                        sMessage = ex.InnerException.InnerException.Message + $"实例{ex.ToString()}";
                    }
                }
                throw new Exception(sMessage);
            }
        }

        public int ExecuteSql(string sql)
        {
            try
            {
                return _context.Database.ExecuteSqlCommand(sql);
            }
            catch (Exception ex)
            {
                throw new Exception(ex.Message.Replace("ROLLBACK TRANSACTION 请求没有对应的 BEGIN TRANSACTION。", "", StringComparison.CurrentCulture));
            }
        }

        public Response Load(PageReq pageRequest, T entity)
        {
            var result = new Response();
            var data = Find(EntityToExpression<T>.GetExpressions(entity));

            GetData(data, result, pageRequest);
            result.Count = data.Count();

            return result;
        }

        public Response ExportData(T entity)
        {
            var result = new Response();
            var data = Find(EntityToExpression<T>.GetExpressions(entity));

            GetData(data, result);
            result.Count = data.Count();

            return result;
        }

        public void GetData(IQueryable<T> data, Response result, PageReq pageRequest = null)
        {
            int skipPage = 0;
            int takeCount = data.Count();
            string odby = "";
            string sfield = "";

            if (data.Count() == 0) return;

            if (pageRequest != null)
            {
                skipPage = (pageRequest.page - 1) * pageRequest.limit;
                takeCount = pageRequest.limit;
                odby = pageRequest.order;
                sfield = pageRequest.field;
            }

            if (string.IsNullOrEmpty(sfield))
            {
                odby = "desc";
                sfield = "Id";
            }

            bool isAsc = odby == "desc" ? false : true;

            List<T> data1;
            if (string.IsNullOrEmpty(sfield))
                data1 = data.Skip(skipPage).Take(takeCount).ToList();
            else
                data1 = data.OrderBy(sfield, isAsc).Skip(skipPage).Take(takeCount).ToList();

            result.Result = data1; 
        }

        private IQueryable<T> Filter(Expression<Func<T, bool>> exp)
        {
            var dbSet = _context.Set<T>().AsNoTracking().AsQueryable();
            if (exp != null)
                dbSet = dbSet.Where(exp);
            return dbSet;
        }
        /// <summary>
        /// 获取任务号
        /// </summary>
        /// <param name="TaskType">TaskType.</param>
        /// <param name="SeqLength">长度.</param>
        public string GetTaskNo(string TaskType, int SeqLength = 4)
        {
            string Value = "1";
            SysCount sysCount = _context.Set<SysCount>().AsNoTracking().FirstOrDefault(u => u.Type == TaskType);
            if (sysCount == null)
            {
                Value = TaskType + DateTime.Now.ToString("yyyyMMdd") + Value.PadLeft(SeqLength, '0');
                sysCount = new SysCount { Type = TaskType, Value = Value };
                _context.Set<SysCount>().Add(sysCount);
                Save();
            }
            else
            {
                string Date = sysCount.Value.Substring(TaskType.Length, 8);

                if (Date == DateTime.Now.ToString("yyyyMMdd"))
                {
                    Value = Date + (int.Parse(sysCount.Value.Substring(sysCount.Value.Length - 4, 4)) + 1).ToString().PadLeft(SeqLength, '0');
                }
                else
                {
                    Value = DateTime.Now.ToString("yyyyMMdd") + Value.PadLeft(SeqLength, '0');
                }
                Value = TaskType + Value;
                //_context.Set<SysCount>().Where(u => u.Type == TaskType).Update(u => new SysCount { Value = Value });
                Save();
            }
            return Value;
        }
    }
}