Entity Framework泛型封装

Entity Framework本身的增删改查其实 已经很方便了,不过做项目的时候用的多了也就觉得有点累了,每个业务实体基本上都涉及到到了增删改查这四个基本的要素,至于封装每个公司可能都不一样,接口,设计模式都用的眼花缭乱,我闲来没事就搞个简单的封装Helper,Github上也有关于EF的扩展Libray,具体没有用过,公司的有自己的封装,自己也没怎么弄,具体地址:https://github.com/loresoft/EntityFramework.Extended.

首先来看段代码,model和context是从数据中直接生成,你可以选择自己习惯的方式:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
//新增
  User addUser = new User();
  addUser.PersonID = 3;
  addUser.UserName = "keso";
  dbContext.Entry<User>(addUser).State = EntityState.Added;
  dbContext.SaveChanges();
  //修改
  User updateUser = new User();
  dbContext.Users.Where(item => item.ID == 2).OrderBy(item => item.ID);
  updateUser.UserName = updateUser.UserName + "测试";
  dbContext.Entry<User>(updateUser).State = EntityState.Modified;
  dbContext.SaveChanges();
  //删除
  User delUser = dbContext.Users.Where(item => item.ID == 2).First();
  dbContext.Entry<User>(delUser).State = EntityState.Deleted;
  dbContext.SaveChanges();

 如果每个业务实体都这么写一遍,估计公司水准有待提高,而且开发的也该跳起来骂人,本人只是简单封装下新建一个EFHelper,实际开发会封装的更多,不过底层处理是不变的

1
2
3
4
class EFHelpler<T> where T : class
   {
       //...
   }       

 新增

方法:

1
2
3
4
5
6
7
8
9
10
11
12
/// <summary>
      /// 实体新增
      /// </summary>
      /// <param name="model"></param>
      public void add(params T[] paramList)
      {
          foreach (var model in paramList)
          {
              dbContext.Entry<T>(model).State = EntityState.Added;
          }
          dbContext.SaveChanges();
      }

 调用:

1
2
3
4
5
6
7
8
9
10
11
12
13
EFHelpler<User> helper = new EFHelpler<User>();
         BaseContext dbContext = new BaseContext();
         //新增
         List<User> listUser = new List<User>();
         for (int i = 0; i < 2; i++)
         {
             User user = new User();
             user.PersonID = i;
             user.UserName = "FlyElehant" + i;
             listUser.Add(user);
         }
         helper.add(listUser.ToArray());
         Console.WriteLine("新增成功");

 查询

查询分了两种,一种是简单的查询,一种是分页的:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
/// <summary>
     /// 实体查询
     /// </summary>
     public IEnumerable<T> getSearchList(System.Linq.Expressions.Expression<Func<T, bool>> where)
     {
         return dbContext.Set<T>().Where(where);
     }
     /// <summary>
     /// 实体分页查询
     /// </summary>
     /// <typeparam name="TKey"></typeparam>
     /// <param name="where"></param>
     /// <param name="orderBy"></param>
     /// <param name="pageSize"></param>
     /// <param name="pageIndex"></param>
     /// <returns></returns>
     public IEnumerable<T> getSearchListByPage<TKey>(Expression<Func<T, bool>> where, Expression<Func<T, TKey>> orderBy, int pageSize, int pageIndex)
     {
         return dbContext.Set<T>().Where(where).OrderByDescending(orderBy).Skip((pageIndex - 1) * pageSize).Take(pageSize);
     }

 简单调用,第二个方式除了分页之外,主要是查询的时候指定一定OrderBy的类型,也就是TKey:

1
2
3
4
5
6
7
var query = helper.getSearchList(item => item.UserName.Contains("keso"));
       var queryMulti = helper.getSearchListByPage<int>(item => item.UserName.Contains("FlyElehant"), order => order.PersonID, 2, 1);
       query = queryMulti;
       foreach (User user in query)
       {
           Console.WriteLine(user.UserName);
       }

 修改

修改代码稍微读了几行,主要是用到了一下反射:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
/// <summary>
    /// 按照条件修改数据
    /// </summary>
    /// <param name="where"></param>
    /// <param name="dic"></param>
    public void update(Expression<Func<T, bool>> where, Dictionary<string, object> dic)
    {
        IEnumerable<T> result = dbContext.Set<T>().Where(where).ToList();
        Type type = typeof(T);
        List<PropertyInfo> propertyList = type.GetProperties(System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.Instance).ToList();
        //遍历结果集
        foreach (T entity in result)
        {
            foreach (PropertyInfo propertyInfo in propertyList)
            {
                string propertyName = propertyInfo.Name;
                if (dic.ContainsKey(propertyName))
                {
                    //设置值
                    propertyInfo.SetValue(entity, dic[propertyName], null);
                }
            }
        }
        dbContext.SaveChanges();
    }

 调用:

1
2
3
4
5
Dictionary<string,object> dic=new Dictionary<string,object>();
         dic.Add("PersonID",2);
         dic.Add("UserName","keso");
         helper.update(item => item.UserName.Contains("keso"), dic);
         Console.WriteLine("修改成功");

删除

方法:

1
2
3
4
5
6
7
8
9
10
11
12
/// <summary>
    /// 实体删除
    /// </summary>
    /// <param name="model"></param>
    public void delete(params T[] paramList)
    {
        foreach (var model in paramList)
        {
            dbContext.Entry<T>(model).State = EntityState.Deleted;
        }
        dbContext.SaveChanges();
    }

  调用:

1
2
var query = helper.getSearchList(item => item.UserName.Contains("keso"));
       helper.delete(query.ToArray());

 完整的EFHelper:

 个人Demo难免有表达不当或者技术失误的地方,如有不当,请多多指出,感激不尽~

posted @   Fly_Elephant  阅读(4930)  评论(14编辑  收藏  举报
编辑推荐:
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
阅读排行:
· 地球OL攻略 —— 某应届生求职总结
· 周边上新:园子的第一款马克杯温暖上架
· Open-Sora 2.0 重磅开源!
· .NET周刊【3月第1期 2025-03-02】
· [AI/GPT/综述] AI Agent的设计模式综述
点击右上角即可分享
微信分享提示