添加Ef Core 连接 Seq Service

Posted wjhxx

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了添加Ef Core 连接 Seq Service相关的知识,希望对你有一定的参考价值。

 

在以下涉及到的项目中增加以下包

技术图片


新建项目CoreWebLibrary.DBEntity-数据库表对应的实体类

1.增加实体类基类接口

    public interface IBaseEntity : IBaseEntity<Guid>  //id为guid的基类接口
    {
    }
    public interface IBaseEntity<Tkey> //基类接口
    {
        public Tkey Id { get; set; }
    }
2.增加实体域接口
    public interface IAggregateRoot : IAggregateRoot<Guid>,IBaseEntity
    {
    }
    public interface IAggregateRoot<Tkey> : IBaseEntity<Tkey>
    {
    }
3.实现实体域接口
    public class BaseEntity : BaseEntity<Guid>, IAggregateRoot
    {
    }
    public class BaseEntity<Tkey> : IAggregateRoot<Tkey>
    {
        public Tkey Id { get; set; }
    }
4.给所有实体类继承创建类和更新类
   //创建类
    public class CreateEntity : BaseEntity, IAggregateRoot
    {
        public DateTime CreateTime { get; set; }
        public int CreateUserId { get; set; }
    }
    public class CreateEntity<TKey> : BaseEntity<TKey>, IAggregateRoot<TKey>
    {
        public DateTime CreateTime { get; set; }
        public int CreateUserId { get; set; }
    }
  //更新类
    public class UpdateEntity : CreateEntity
    {
        public DateTime? UpdateTime { get; set; }
        public int? UpdateUserId { get; set; }
    }
    public class UpdateEntity<TKey> : CreateEntity<TKey>, IAggregateRoot<TKey>
    {
        public DateTime? UpdateTime { get; set; }
        public int? UpdateUserId { get; set; }
    }

新建项目 CoreWebLibrary.DB-数据库Database和操作封装类
1新增数据库UnitOfWorkDbContext 继承 DbContext
    public class UnitOfWorkDbContext : DbContext
    {
        public DbSet<SystemUser> SystemUser { get; set; } //数据库表
        public UnitOfWorkDbContext (DbContextOptions<UnitOfWorkDbContext> options) : base(options)
        {
        }
        protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
        {
            optionsBuilder.UseLazyLoadingProxies(false);
        }
        //读取所有CoreWebLibrary.DBEntity dll下的继承了IEntityTypeConfiguration 接口的类的实体关系(FluatApi)
        protected override void OnModelCreating(ModelBuilder modelBuilder)
        {
            base.OnModelCreating(modelBuilder);
            Assembly assembly = Assembly.Load("CoreWebLibrary.DBEntity");
            var typesToRegister = assembly.GetTypes().Where(q => q.GetInterface(typeof(IEntityTypeConfiguration<>).FullName) != null);
            foreach (var type in typesToRegister)
            {
                dynamic configurationInstance = Activator.CreateInstance(type);
                modelBuilder.ApplyConfiguration(configurationInstance);
            }
        }
    }
2 创建IUnitOfWork 接口和 UnitOfWork<T> 实现类
    public interface IUnitOfWork
    {
        int SaveChanges();
        Task<int> SaveChangesAsync();
        void CreateTransaction();
        Task CommitAsync();
        void Commit();
        void Rollback();
        Task RollbackAsync();
        void Dispose();
        Task DisposeAsync();
    }
    public class UnitOfWork<TDbContext> : IUnitOfWork where TDbContext : DbContext
    {
        private readonly TDbContext _dbContext;
        private IDbContextTransaction dbContextTransaction;
        public UnitOfWork(TDbContext context)
        {
            _dbContext = context ?? throw new ArgumentNullException(nameof(context));
        }
        public void CreateTransaction()
        {
            dbContextTransaction = _dbContext.Database.BeginTransaction();
        }
        public int SaveChanges()
        {
            return _dbContext.SaveChanges();
        }
        public async Task<int> SaveChangesAsync()
        {
            return await _dbContext.SaveChangesAsync();
        }
        public async Task CommitAsync()
        {
            if (dbContextTransaction != null)
            {
                await dbContextTransaction.CommitAsync();
            }
        }
        public void Commit()
        {
            if (dbContextTransaction != null)
            {
                dbContextTransaction.Commit();
            }
        }
        public void Rollback()
        {
            if (dbContextTransaction != null)
            {
                dbContextTransaction.Rollback();
            }
        }
        public async Task RollbackAsync()
        {
            if (dbContextTransaction != null)
            {
                await dbContextTransaction.RollbackAsync();
            }
        }
        public void Dispose()
        {
            if (dbContextTransaction != null)
            {
               dbContextTransaction.Dispose();
               dbContextTransaction = null;
            }
        }
        public async Task DisposeAsync()
        {
            if (dbContextTransaction != null)
            {
                await dbContextTransaction.DisposeAsync();
                dbContextTransaction = null;
            }
        }
    }
3.创建数据库操作仓库接口和实现类
public interface IRepository<TEntity> : IRepository<TEntity,Guid>  where TEntity : class, IAggregateRoot, IBaseEntity
    {
    }
    public interface IRepository<TEntity,Tkey> where TEntity : class, IAggregateRoot<Tkey>,IBaseEntity<Tkey>
    {
        TEntity Add(TEntity t);
        int Count();
        Task<int> CountAsync();
        void Delete(TEntity entity);
        TEntity Find(Expression<Func<TEntity, bool>> match);
        IEnumerable<TEntity> FindAll(Expression<Func<TEntity, bool>> match);
        Task<IEnumerable<TEntity>> FindAllAsync(Expression<Func<TEntity, bool>> match);
        Task<TEntity> FindAsync(Expression<Func<TEntity, bool>> match);
        TEntity Get(int id);
        IEnumerable<TEntity> GetAll();
        Task<List<TEntity>> GetAllAsyn();
        Task<TEntity> GetAsync(int id);
        void Update(TEntity PoEntity, TEntity VoEntity);
    }
 
public class Repository<TEntity> : Repository<TEntity, Guid>,IRepository<TEntity> where TEntity : class, IAggregateRoot, IBaseEntity
    {
        public Repository(UnitOfWorkDbContext dbDbContext) : base(dbDbContext)
        {
        }
    }
    public class Repository<TEntity, Tkey> : IRepository<TEntity, Tkey> where TEntity : class, IAggregateRoot<Tkey>, IBaseEntity<Tkey>
    {
        private readonly UnitOfWorkDbContext _dbContext;
        public virtual DbSet<TEntity> Table => _dbContext.Set<TEntity>();
        public Repository(UnitOfWorkDbContext dbDbContext)
        {
            _dbContext = dbDbContext;
        }
        public IEnumerable<TEntity> GetAll()
        {
            return Table.AsNoTracking().ToList();
        }
        public virtual async Task<IEnumerable<TEntity>> GetAllAsyn(CancellationToken cancellationToken = default(CancellationToken))
        {
            return await Table.AsNoTracking().ToListAsync(cancellationToken);
        }
        public virtual TEntity Get(int id)
        {
            return Table.Find(id);
        }
        public virtual async Task<TEntity> GetAsync(int id)
        {
            return await Table.FindAsync(id);
        }
        public virtual TEntity Add(TEntity entity)
        {
            return Table.Add(entity).Entity;
        }
        public virtual TEntity Find(Expression<Func<TEntity, bool>> match)
        {
            return Table.SingleOrDefault(match);
        }
        public virtual async Task<TEntity> FindAsync(Expression<Func<TEntity, bool>> match)
        {
            return await Table.SingleOrDefaultAsync(match);
        }
        public IEnumerable<TEntity> FindAll(Expression<Func<TEntity, bool>> match)
        {
            return Table.Where(match).ToList();
        }
        public async Task<IEnumerable<TEntity>> FindAllAsync(Expression<Func<TEntity, bool>> match)
        {
            return await Table.Where(match).ToListAsync();
        }
        public virtual void Delete(TEntity entity)
        {
            Table.Remove(entity);
        }

        public virtual void Update(TEntity PoEntity, TEntity VoEntity)
        {
            _dbContext.Entry(PoEntity).CurrentValues.SetValues(VoEntity);
        }
        public int Count()
        {
            return Table.Count();
        }
        public async Task<int> CountAsync()
        {
            return await Table.CountAsync();
        }
        public Task<List<TEntity>> GetAllAsyn()
        {
            return Table.AsNoTracking().ToListAsync();
        }
    }

在appsettings 中增加数据库配置字符串
  "ConnectionStrings": {
    "SqlServerConnection": "Data source=LocalHost;Initial Catalog=MyWebData;Integrated Security=True"
  }
在 web api 中Startup注入DbContext
            services.AddDbContext<UnitOfWorkDbContext>(
                    options => options.UseSqlServer(
                    Configuration.GetConnectionString("SqlServerConnection"),p=>p.MigrationsAssembly("CoreWebLibrary.DB")));
 
注入 操作仓库等
public static void AddService(this IServiceCollection serviceCollection)
        {
            serviceCollection.AddTransient<IUserService, UserService>();  //逻辑层
            serviceCollection.AddScoped<IUnitOfWork, UnitOfWork<UnitOfWorkDbContext>>();
            //注入泛型仓储
            serviceCollection.AddTransient(typeof(IRepository<>), typeof(Repository<>));
            serviceCollection.AddTransient(typeof(IRepository<,>), typeof(Repository<,>));
            AutoMapperHelp.InitAutoMapper(); //实例化AutoMapper
        }
services.AddService()

增加一个实体类 和 对应表的关系
public enum Gender
    {
        男,
        女
    }
    public enum MaritalStatus
    {
        未婚,
        已婚,
        离异
    }
    public class SystemUser : UpdateEntity<int>
    {
        /// <summary>
        /// 名称
        /// </summary>
        public string Name { get; set; }
        /// <summary>
        /// 性别
        /// </summary>
        public Gender Gender { get; set; }
        /// <summary>
        /// 年龄
        /// </summary>
        public ushort Age { get; set; }
        /// <summary>
        /// 名族
        /// </summary>
        public string Race { get; set; }
        /// <summary>
        /// 员工编号
        /// </summary>
        public string EmployeeNumber {get;set;}
        /// <summary>
        /// 婚姻状态
        /// </summary>
        public MaritalStatus MaritalStatus { get; set; }
        /// <summary>
        /// 国籍
        /// </summary>
        public string Nationality { get; set; }
    }
 
    public class SystemUserConfig : IEntityTypeConfiguration<SystemUser>
    {
        public void Configure(EntityTypeBuilder<SystemUser> systemUser)
        {
            systemUser.ToTable("Sys_User");
            systemUser.Property(x => x.Name).IsRequired();
            systemUser.Property(x => x.Gender).IsRequired();
            systemUser.Property(x => x.Age).IsRequired();
            systemUser.Property(x => x.Race).IsRequired();
            systemUser.Property(x => x.EmployeeNumber).IsRequired().HasMaxLength(20);
            systemUser.Property(x => x.MaritalStatus).IsRequired();
            systemUser.Property(x => x.Nationality).IsRequired();
        }
    }
 在控制台中输入以下命令
Add-Migration Init
update-Database Init
就会创建实例对应的表

如何使用
增加CoreWebLibrary.Service 项目
增加IUserService 和 UserService 逻辑层
    public interface IUserService
    {
        Task<int> AddUser(SystemUser systemUser);
    }
 
    public class UserService : IUserService
    {
        IUnitOfWork unitOfWork;
        IRepository<SystemUser, int> repository;
        ILogger<UserService> log;
        public UserService (IUnitOfWork unitOfWork, IRepository<SystemUser,int> repository,ILogger<UserService> log)
        {
            this.unitOfWork = unitOfWork;
            this.repository = repository;
            this.log = log;
        }
        public async Task<int> AddUser(SystemUser systemUser)
        {
            SystemUser user = repository.Add(systemUser);
            int index = await unitOfWork.SaveChangesAsync();
            log.Log(LogLevel.Information,$"Create User by id {user.Id}");
            return index;
        }
    }
 
在web Api的控制器中增加操作方法
        [MyActionFilter]
        [HttpPost("AddUser")]
        public async Task<IActionResult> AddUser([FromServices] IUserService userService,[FromBody] VUser vUser)
        {
            SystemUser systemUser = AutoMapperHelp.Map.Map<SystemUser>(vUser);
            int index = await userService.AddUser(systemUser);
            return Json(new VReturnMessage<int>
            {
                Message = "保存成功",
                ReturnCode = 200,
                Data = index
            });
        }
 

以上是关于添加Ef Core 连接 Seq Service的主要内容,如果未能解决你的问题,请参考以下文章

在 EF Core 3 中重命名 IdentityRole 表

Asp.net Core 6.0 使用EF Model First 连接mysql

Asp.net Core 6.0 使用EF Model First 连接mysql

使用 LINQ 查询语法 EF Core C# 的左外连接

EF Core 基础知识

在带有 EF7 的 ASP.NET5.0 中添加连接字符串以使用 dll 存储库库(基于 EF6)