首页 > 代码库 > 从零开始,搭建博客系统MVC5+EF6搭建框架(1),EF Code frist、实现泛型数据仓储以及业务逻辑

从零开始,搭建博客系统MVC5+EF6搭建框架(1),EF Code frist、实现泛型数据仓储以及业务逻辑

前言

     从上篇30岁找份程序员的工作(伪程序员的独白)文章开始,我说过我要用我自学的技术,来搭建一个博客系统,也希望大家给点意见,另外我很感谢博客园的各位朋友们,对我那篇算是自我阶段总结文章的评论,在里面能看出有很多种声音,有支持的我的朋友给我加油打气,有分享自己工作经历的朋友,有提出忠肯意见的朋友,有对记事本写代码吐槽的朋友,也有希望让我换个行业的,觉得我可能不适合这个行业朋友,不管怎样,我都接受,都是大家同行的一些忠告,谢谢大家。

     首先我要在这里感谢很多博客园里面的大牛,写了很多系列,很多学习资料,让我受益很多,有机会找个时间,我会把我浏览器中收藏的资源都整理出来,分享给大家,其实我会的这些都是自己在博客园看到的文章、在某宝买的视频、QQ群里看群主的分享公开课学的,希望大家多提宝贵意见。

一、框架搭建

技术分享

首先创建几个文件夹:

01Data用来放链接数据的EF以及创建表的类;

02Core存放数据仓储一些跟数据库链接实现数据操作的部分:

03Services 用于存放业务逻辑处理;

04Common用于放公共应用的工具之类;

05UI mvc页面展示的就放在这里 以及web相关的核心代码

 

其中除了Wchl.CRM.WebUI创建的是MVC5应用程序,其他的都是创建类库

二、创建数据库

1.创建一个空的EF code frist环境,输入的名字为WMBlogDB

技术分享

2、选择空的Code Frist模型

技术分享

3、创建一个models文件存放所有表的类,这里先创建一个用户信息表的类sysUserInfo

sysUserInfo类:

技术分享
  1 namespace Wchl.WMBlog.Model.Models  2 {  3      public class sysUserInfo  4     {  5         /// <summary>  6         /// 用户ID  7         /// </summary>  8         public int uID { get; set; }  9         /// <summary> 10         /// 登录账号 11         /// </summary> 12         public string uLoginName { get; set; } 13         /// <summary> 14         /// 登录密码 15         /// </summary> 16         public string uLoginPWD { get; set; } 17         /// <summary> 18         /// 真实姓名 19         /// </summary> 20         public string uRealName { get; set; } 21         /// <summary> 22         /// 状态 23         /// </summary> 24         public int uStatus { get; set; } 25         /// <summary> 26         /// 备注 27         /// </summary> 28         public string uRemark { get; set; } 29         /// <summary> 30         /// 创建时间 31         /// </summary> 32         public System.DateTime uCreateTime { get; set; } 33         /// <summary> 34         /// 更新时间 35         /// </summary> 36         public System.DateTime uUpdateTime { get; set; } 37     } 38 }
View Code

4、创建一个maps文件夹,主要是用来放对表字段进行约束的类sysUserInfoMap

sysUserInfoMap类:

技术分享
  1 namespace Wchl.WMBlog.Model.Maps  2 {  3     public class sysUserInfoMap:EntityTypeConfiguration<sysUserInfo>  4     {  5         public sysUserInfoMap()  6         {  7             this.HasKey(u => u.uID);  8             this.Property(u => u.uLoginName).HasMaxLength(60);  9             this.Property(u => u.uLoginPWD).HasMaxLength(60); 10             this.Property(u => u.uRealName).HasMaxLength(60); 11         } 12     } 13 }
View Code

关于EntityTypeConfiguration类的用法,大家可以去看看博客园里面一些介绍文章,HasKey设置主键,HasMaxLength字段最大长度。

5、在控制台中创建数据库脚本 Enable-Migrations

技术分享

6、修改Configuration类配置

技术分享

7、在WMBlogDB类中重写OnModelCreating方法

技术分享

重写OnModelCreating方法:

技术分享
  1         protected override void OnModelCreating(DbModelBuilder modelBuilder)  2         {  3             //移除表名为复数  4             modelBuilder.Conventions.Remove<PluralizingTableNameConvention>();  5             //自动添加实现EntityTypeConfiguration的类  6             modelBuilder.Configurations.AddFromAssembly(Assembly.GetExecutingAssembly());  7             base.OnModelCreating(modelBuilder);  8         }
View Code

二、仓储层建设

1、在Wchl.WMBlog.IRepository中创建一个类,做为操作数据的父接口IBaseRepository,这里使用泛型来创建

IBaseRepository接口

技术分享
  1 namespace Wchl.WMBlog.IRepository.Base  2 {  3     public interface IBaseRepository<TEntity> where TEntity:class  4     {  5         #region 查询  6         /// <summary>  7         /// 单表查询  8         /// </summary>  9         /// <param name="predicate"></param> 10         /// <returns></returns> 11         List<TEntity> QueryWhere(Expression<Func<TEntity, bool>> predicate); 12  13         /// <summary> 14         /// 多表关联查询 15         /// </summary> 16         /// <param name="predicate"></param> 17         /// <param name="tableNames"></param> 18         /// <returns></returns> 19         List<TEntity> QueryJoin(Expression<Func<TEntity, bool>> predicate, string[] tableNames); 20         /// <summary> 21         /// 升序查询还是降序查询 22         /// </summary> 23         /// <typeparam name="TKey"></typeparam> 24         /// <param name="predicate"></param> 25         /// <param name="keySelector"></param> 26         /// <param name="IsQueryOrderBy"></param> 27         /// <returns></returns> 28         List<TEntity> QueryOrderBy<TKey>(Expression<Func<TEntity, bool>> predicate, Expression<Func<TEntity, TKey>> keySelector, bool IsQueryOrderBy); 29  30         /// <summary> 31         /// 升序分页查询还是降序分页 32         /// </summary> 33         /// <typeparam name="TKey"></typeparam> 34         /// <param name="pageIndex">第几页</param> 35         /// <param name="pagesize">一页多少条</param> 36         /// <param name="rowcount">返回共多少条</param> 37         /// <param name="predicate">查询条件</param> 38         /// <param name="keySelector">排序字段</param> 39         /// <param name="IsQueryOrderBy">true为升序 false为降序</param> 40         /// <returns></returns> 41         List<TEntity> QueryByPage<TKey>(int pageIndex, int pagesize, out int rowcount, Expression<Func<TEntity, bool>> predicate, Expression<Func<TEntity, TKey>> keySelector, bool IsQueryOrderBy); 42         #endregion 43  44         #region 编辑 45         /// <summary> 46         /// 通过传入的model加需要修改的字段来更改数据 47         /// </summary> 48         /// <param name="model"></param> 49         /// <param name="propertys"></param> 50         void Edit(TEntity model, string[] propertys); 51  52         /// <summary> 53         /// 直接查询之后再修改 54         /// </summary> 55         /// <param name="model"></param> 56         void Edit(TEntity model); 57         #endregion 58  59         #region 删除 60         void Delete(TEntity model, bool isadded); 61         #endregion 62  63         #region 新增 64         void Add(TEntity model); 65         #endregion 66  67         #region 统一提交 68         int SaverChanges(); 69         #endregion 70  71         #region 调用存储过程返回一个指定的TResult 72         List<TResult> RunProc<TResult>(string sql, params object[] pamrs); 73         #endregion 74     } 75 }
View Code

2、然后实现IBaseRepository接口,在Wchl.WMBlog.Repository程序集中创建BaseRepository类来实现对数据操作的查询、增加、删除、编辑等。

BaseRepository

技术分享
  1 namespace Wchl.WMBlog.Repository.Base  2 {  3     public class BaseRepository<TEntity>: IBaseRepository<TEntity> where TEntity:class  4     {  5         WMBlogDB db = new WMBlogDB();  6   7         DbSet<TEntity> _dbSet;  8   9         public BaseRepository() 10         { 11             _dbSet = db.Set<TEntity>(); 12         } 13  14         #region 查询 15         /// <summary> 16         /// 单表查询 17         /// </summary> 18         /// <param name="predicate"></param> 19         /// <returns></returns> 20         public List<TEntity> QueryWhere(Expression<Func<TEntity, bool>> predicate) 21         { 22            return _dbSet.Where(predicate).ToList(); 23         } 24  25         /// <summary> 26         /// 多表关联查询 27         /// </summary> 28         /// <param name="predicate"></param> 29         /// <param name="tableNames"></param> 30         /// <returns></returns> 31         public List<TEntity> QueryJoin(Expression<Func<TEntity, bool>> predicate, string[] tableNames) 32         { 33             if (tableNames == null && tableNames.Any() == false) 34             { 35                 throw new Exception("缺少连表名称"); 36             } 37  38             DbQuery<TEntity> query = _dbSet; 39  40             foreach (var table in tableNames) 41             { 42                 query = query.Include(table); 43             } 44  45             return query.Where(predicate).ToList(); 46         } 47  48         /// <summary> 49         /// 升序查询还是降序查询 50         /// </summary> 51         /// <typeparam name="TKey"></typeparam> 52         /// <param name="predicate"></param> 53         /// <param name="keySelector"></param> 54         /// <param name="IsQueryOrderBy"></param> 55         /// <returns></returns> 56         public List<TEntity> QueryOrderBy<TKey>(Expression<Func<TEntity, bool>> predicate, Expression<Func<TEntity, TKey>> keySelector,bool IsQueryOrderBy) 57         { 58             if (IsQueryOrderBy) 59             { 60                 return _dbSet.Where(predicate).OrderBy(keySelector).ToList(); 61             } 62             return _dbSet.Where(predicate).OrderByDescending(keySelector).ToList(); 63  64         } 65  66         /// <summary> 67         /// 升序分页查询还是降序分页 68         /// </summary> 69         /// <typeparam name="TKey"></typeparam> 70         /// <param name="pageIndex">第几页</param> 71         /// <param name="pagesize">一页多少条</param> 72         /// <param name="rowcount">返回共多少条</param> 73         /// <param name="predicate">查询条件</param> 74         /// <param name="keySelector">排序字段</param> 75         /// <param name="IsQueryOrderBy">true为升序 false为降序</param> 76         /// <returns></returns> 77         public List<TEntity> QueryByPage<TKey>(int pageIndex,int pagesize,out int rowcount,Expression<Func<TEntity, bool>> predicate, Expression<Func<TEntity, TKey>> keySelector, bool IsQueryOrderBy) 78         { 79             rowcount = _dbSet.Count(predicate); 80             if (IsQueryOrderBy) 81             { 82                 return _dbSet.Where(predicate).OrderBy(keySelector).Skip((pageIndex - 1) * pagesize).Take(pagesize).ToList(); 83             } 84             else 85             { 86                 return _dbSet.Where(predicate).OrderByDescending(keySelector).Skip((pageIndex - 1) * pagesize).Take(pagesize).ToList(); 87             } 88         } 89         #endregion 90  91         #region 编辑 92         /// <summary> 93         /// 通过传入的model加需要修改的字段来更改数据 94         /// </summary> 95         /// <param name="model"></param> 96         /// <param name="propertys"></param> 97         public void Edit(TEntity model, string[] propertys) 98         { 99             if (model == null)100             {101                 throw new Exception("实体不能为空");102             }103 104             if (propertys.Any() == false)105             {106                 throw new Exception("要修改的属性至少要有一个");107             }108 109             //将model追击到EF容器110             DbEntityEntry entry = db.Entry(model);111 112             entry.State = EntityState.Unchanged;113 114             foreach (var item in propertys)115             {116                 entry.Property(item).IsModified = true;117             }118 119             //关闭EF对于实体的合法性验证参数120             db.Configuration.ValidateOnSaveEnabled = false;121         }122 123         /// <summary>124         /// 直接查询之后再修改125         /// </summary>126         /// <param name="model"></param>127         public void Edit(TEntity model)128         {129             db.Entry(model).State = EntityState.Modified;130         }131         #endregion132 133         #region 删除134         public void Delete(TEntity model, bool isadded)135         {136             if (!isadded) {137                 _dbSet.Attach(model);138             }139             _dbSet.Remove(model);140         }141         #endregion142 143         #region 新增144         public void Add(TEntity model)145         {146             _dbSet.Add(model);147         }148         #endregion149 150         #region 统一提交151         public int SaverChanges()152         {153             return db.SaveChanges();154         }155         #endregion156 157         #region 调用存储过程返回一个指定的TResult158         public List<TResult> RunProc<TResult>(string sql, params object[] pamrs)159         {160             return db.Database.SqlQuery<TResult>(sql, pamrs).ToList();161         }162         #endregion163     }164 }
View Code

三、业务逻辑层父接口和父类创建

1、在Wchl.WMBlog.IServices程序集中创建IBaseServices接口

IBaseServices接口:

技术分享
  1 namespace Wchl.WMBlog.IServices.Base  2 {  3     public interface IBaseServices<TEntity> where TEntity:class  4     {  5         #region 查询  6         /// <summary>  7         /// 单表查询  8         /// </summary>  9         /// <param name="predicate"></param> 10         /// <returns></returns> 11         List<TEntity> QueryWhere(Expression<Func<TEntity, bool>> predicate); 12  13         /// <summary> 14         /// 多表关联查询 15         /// </summary> 16         /// <param name="predicate"></param> 17         /// <param name="tableNames"></param> 18         /// <returns></returns> 19         List<TEntity> QueryJoin(Expression<Func<TEntity, bool>> predicate, string[] tableNames); 20         /// <summary> 21         /// 升序查询还是降序查询 22         /// </summary> 23         /// <typeparam name="TKey"></typeparam> 24         /// <param name="predicate"></param> 25         /// <param name="keySelector"></param> 26         /// <param name="IsQueryOrderBy"></param> 27         /// <returns></returns> 28         List<TEntity> QueryOrderBy<TKey>(Expression<Func<TEntity, bool>> predicate, Expression<Func<TEntity, TKey>> keySelector, bool IsQueryOrderBy); 29  30         /// <summary> 31         /// 升序分页查询还是降序分页 32         /// </summary> 33         /// <typeparam name="TKey"></typeparam> 34         /// <param name="pageIndex">第几页</param> 35         /// <param name="pagesize">一页多少条</param> 36         /// <param name="rowcount">返回共多少条</param> 37         /// <param name="predicate">查询条件</param> 38         /// <param name="keySelector">排序字段</param> 39         /// <param name="IsQueryOrderBy">true为升序 false为降序</param> 40         /// <returns></returns> 41         List<TEntity> QueryByPage<TKey>(int pageIndex, int pagesize, out int rowcount, Expression<Func<TEntity, bool>> predicate, Expression<Func<TEntity, TKey>> keySelector, bool IsQueryOrderBy); 42         #endregion 43  44         #region 编辑 45         /// <summary> 46         /// 通过传入的model加需要修改的字段来更改数据 47         /// </summary> 48         /// <param name="model"></param> 49         /// <param name="propertys"></param> 50         void Edit(TEntity model, string[] propertys); 51  52         /// <summary> 53         /// 直接查询之后再修改 54         /// </summary> 55         /// <param name="model"></param> 56         void Edit(TEntity model); 57         #endregion 58  59         #region 删除 60         void Delete(TEntity model, bool isadded); 61         #endregion 62  63         #region 新增 64         void Add(TEntity model); 65         #endregion 66  67         #region 统一提交 68         int SaverChanges(); 69         #endregion 70  71         #region 调用存储过程返回一个指定的TResult 72         List<TResult> RunProc<TResult>(string sql, params object[] pamrs); 73         #endregion 74     } 75 }
View Code

2、在Wchl.WMBlog.Services程序集创建BaseServices类

BaseServices类

技术分享
  1 namespace Wchl.WMBlog.Services.Base  2 {  3    public class BaseServices<TEntity>: IBaseServices<TEntity> where TEntity:class  4     {  5         public IBaseRepository<TEntity> baseDal = new BaseRepository<TEntity>();  6   7         #region 查询  8         /// <summary>  9         /// 单表查询 10         /// </summary> 11         /// <param name="predicate"></param> 12         /// <returns></returns> 13         public List<TEntity> QueryWhere(Expression<Func<TEntity, bool>> predicate) 14         { 15             return baseDal.QueryWhere(predicate); 16         } 17  18         /// <summary> 19         /// 多表关联查询 20         /// </summary> 21         /// <param name="predicate"></param> 22         /// <param name="tableNames"></param> 23         /// <returns></returns> 24         public List<TEntity> QueryJoin(Expression<Func<TEntity, bool>> predicate, string[] tableNames) 25         { 26             return baseDal.QueryJoin(predicate, tableNames); 27  28         } 29  30         /// <summary> 31         /// 升序查询还是降序查询 32         /// </summary> 33         /// <typeparam name="TKey"></typeparam> 34         /// <param name="predicate"></param> 35         /// <param name="keySelector"></param> 36         /// <param name="IsQueryOrderBy"></param> 37         /// <returns></returns> 38         public List<TEntity> QueryOrderBy<TKey>(Expression<Func<TEntity, bool>> predicate, Expression<Func<TEntity, TKey>> keySelector, bool IsQueryOrderBy) 39         { 40             return baseDal.QueryOrderBy(predicate, keySelector, IsQueryOrderBy); 41         } 42  43         /// <summary> 44         /// 升序分页查询还是降序分页 45         /// </summary> 46         /// <typeparam name="TKey"></typeparam> 47         /// <param name="pageIndex">第几页</param> 48         /// <param name="pagesize">一页多少条</param> 49         /// <param name="rowcount">返回共多少条</param> 50         /// <param name="predicate">查询条件</param> 51         /// <param name="keySelector">排序字段</param> 52         /// <param name="IsQueryOrderBy">true为升序 false为降序</param> 53         /// <returns></returns> 54         public List<TEntity> QueryByPage<TKey>(int pageIndex, int pagesize, out int rowcount, Expression<Func<TEntity, bool>> predicate, Expression<Func<TEntity, TKey>> keySelector, bool IsQueryOrderBy) 55         { 56  57             return baseDal.QueryByPage(pageIndex, pagesize,out rowcount, predicate, keySelector, IsQueryOrderBy); 58  59         } 60         #endregion 61  62         #region 编辑 63         /// <summary> 64         /// 通过传入的model加需要修改的字段来更改数据 65         /// </summary> 66         /// <param name="model"></param> 67         /// <param name="propertys"></param> 68         public void Edit(TEntity model, string[] propertys) 69         { 70             baseDal.Edit(model, propertys); 71         } 72  73         /// <summary> 74         /// 直接查询之后再修改 75         /// </summary> 76         /// <param name="model"></param> 77         public void Edit(TEntity model) 78         { 79             baseDal.Edit(model); 80         } 81         #endregion 82  83         #region 删除 84         public void Delete(TEntity model, bool isadded) 85         { 86             baseDal.Delete(model, isadded); 87         } 88         #endregion 89  90         #region 新增 91         public void Add(TEntity model) 92         { 93             baseDal.Add(model); 94         } 95         #endregion 96  97         #region 统一提交 98         public int SaverChanges() 99         {100            return baseDal.SaverChanges();101         }102         #endregion103 104         #region 调用存储过程返回一个指定的TResult105         public List<TResult> RunProc<TResult>(string sql, params object[] pamrs)106         {107            return baseDal.RunProc<TResult>(sql, pamrs);108         }109         #endregion110     }111 }
View Code

   到目前为止数据库、仓储层、业务逻辑层的父类和父接口都实现了,下一篇博文就在UI层怎么调用,测试看,成功写成功没。

 

谢谢大家的支持,多提宝贵意见。

从零开始,搭建博客系统MVC5+EF6搭建框架(1),EF Code frist、实现泛型数据仓储以及业务逻辑