框架搭建与EF常用基类实现
程序员文章站
2022-06-07 12:20:33
前两篇简单谈了一些.Net Core的优势以及机构设计的一些思路,这一篇开始,我们将从零开始搭建架构,底层我们将采用EF来访问数据库,所以这篇我们将贴一下EF常用操作的基类。 简单介绍下一些类库将要实现的功能: Business:业务实现层 Domains:实体(Model) Service:接口 ......
前两篇简单谈了一些.net core的优势以及机构设计的一些思路,这一篇开始,我们将从零开始搭建架构,底层我们将采用ef来访问数据库,所以这篇我们将贴一下ef常用操作的基类。
简单介绍下一些类库将要实现的功能:
business:业务实现层
domains:实体(model)
service:接口
data:数据库访问(ef或其他)
easycacheing:开源缓存管理
tools:工具类库
其他的我们用到的时候再说;
接着说ef常用操作基类,我们将基类放在data下,具体目录结构如下:
baseentity:实体基类,基础共有的放在这里面:
1 using system; 2 using system.collections.generic; 3 using system.text; 4 5 namespace data 6 { 7 /// <summary> 8 /// base class for entities 9 /// </summary> 10 ///[serializable] 11 public abstract partial class baseentity 12 { 13 /// <summary> 14 /// gets or sets the entity identifier 15 /// </summary> 16 public string id { get; set; } 17 public virtual nullable<datetime> createtime { get; set; } 18 public virtual string createperson { get; set; } 19 public virtual nullable<datetime> updatetime { get; set; } 20 public virtual string updateperson { get; set; } 21 22 public baseentity() 23 { 24 this.id = getidentifier(); 25 this.createtime = datetime.now; 26 this.updatetime = datetime.now; 27 } 28 29 private string getidentifier() 30 { 31 return guid.newguid().tostring(); 32 } 33 34 public override bool equals(object obj) 35 { 36 return equals(obj as baseentity); 37 } 38 39 private static bool istransient(baseentity obj) 40 { 41 return obj != null && equals(obj.id, default(string)); 42 } 43 44 private type getunproxiedtype() 45 { 46 return gettype(); 47 } 48 49 public virtual bool equals(baseentity other) 50 { 51 if (other == null) 52 return false; 53 54 if (referenceequals(this, other)) 55 return true; 56 57 if (!istransient(this) && 58 !istransient(other) && 59 equals(id, other.id)) 60 { 61 var othertype = other.getunproxiedtype(); 62 var thistype = getunproxiedtype(); 63 return thistype.isassignablefrom(othertype) || 64 othertype.isassignablefrom(thistype); 65 } 66 67 return false; 68 } 69 70 public static bool operator ==(baseentity x, baseentity y) 71 { 72 return equals(x, y); 73 } 74 75 public static bool operator !=(baseentity x, baseentity y) 76 { 77 return !(x == y); 78 } 79 } 80 }
dbcontextextensions:数据库操作扩展
1 using microsoft.entityframeworkcore; 2 using microsoft.entityframeworkcore.infrastructure; 3 using system; 4 using system.collections.generic; 5 using system.data; 6 using system.data.common; 7 using system.data.sqlclient; 8 using system.reflection; 9 using system.text; 10 11 namespace data 12 { 13 public static class dbcontextextensions 14 { 15 private static void combineparams(ref dbcommand command, params object[] parameters) 16 { 17 if (parameters != null) 18 { 19 foreach (sqlparameter parameter in parameters) 20 { 21 if (!parameter.parametername.contains("@")) 22 parameter.parametername = $"@{parameter.parametername}"; 23 command.parameters.add(parameter); 24 } 25 } 26 } 27 28 29 private static dbcommand createcommand(databasefacade facade, string sql, out dbconnection dbconn, params object[] parameters) 30 { 31 dbconnection conn = facade.getdbconnection(); 32 dbconn = conn; 33 conn.open(); 34 dbcommand cmd = conn.createcommand(); 35 if (facade.issqlserver()) 36 { 37 cmd.commandtext = sql; 38 combineparams(ref cmd, parameters); 39 } 40 return cmd; 41 } 42 43 public static datatable sqlquery(this databasefacade facade, string sql, params object[] parameters) 44 { 45 dbcommand cmd = createcommand(facade, sql, out dbconnection conn, parameters); 46 dbdatareader reader = cmd.executereader(); 47 datatable dt = new datatable(); 48 dt.load(reader); 49 reader.close(); 50 conn.close(); 51 return dt; 52 } 53 54 public static ienumerable<t> sqlquery<t>(this databasefacade facade, string sql, params object[] parameters) where t : class, new() 55 { 56 datatable dt = sqlquery(facade, sql, parameters); 57 return dt.toenumerable<t>(); 58 } 59 60 public static ienumerable<t> toenumerable<t>(this datatable dt) where t : class, new() 61 { 62 propertyinfo[] propertyinfos = typeof(t).getproperties(); 63 t[] ts = new t[dt.rows.count]; 64 int i = 0; 65 foreach (datarow row in dt.rows) 66 { 67 t t = new t(); 68 foreach (propertyinfo p in propertyinfos) 69 { 70 if (dt.columns.indexof(p.name) != -1 && row[p.name] != dbnull.value) 71 p.setvalue(t, row[p.name], null); 72 } 73 ts[i] = t; 74 i++; 75 } 76 return ts; 77 } 78 } 79 }
ipagedlist:分页接口
1 using system; 2 using system.collections.generic; 3 using system.text; 4 5 namespace data 6 { 7 public interface ipagedlist<t> : ilist<t> 8 { 9 int pageindex { get; } 10 int pagesize { get; } 11 int totalcount { get; } 12 int totalpages { get; } 13 bool haspreviouspage { get; } 14 bool hasnextpage { get; } 15 } 16 }
pagedlist:分页接口的实现
1 using system; 2 using system.collections.generic; 3 using system.linq; 4 using system.text; 5 6 namespace data 7 { 8 /// <summary> 9 /// paged list 10 /// </summary> 11 /// <typeparam name="t">t</typeparam> 12 public class pagedlist<t> : list<t>, ipagedlist<t> 13 { 14 /// <summary> 15 /// ctor 16 /// </summary> 17 /// <param name="source">source</param> 18 /// <param name="pageindex">page index</param> 19 /// <param name="pagesize">page size</param> 20 public pagedlist(iqueryable<t> source, int pageindex, int pagesize) 21 { 22 int total = source.count(); 23 this.totalcount = total; 24 this.totalpages = total / pagesize; 25 26 if (total % pagesize > 0) 27 totalpages++; 28 29 this.pagesize = pagesize; 30 this.pageindex = pageindex; 31 this.addrange(source.skip((pageindex - 1) * pagesize).take(pagesize).tolist()); 32 } 33 34 /// <summary> 35 /// ctor 36 /// </summary> 37 /// <param name="source">source</param> 38 /// <param name="pageindex">page index</param> 39 /// <param name="pagesize">page size</param> 40 public pagedlist(ilist<t> source, int pageindex, int pagesize) 41 { 42 totalcount = source.count(); 43 totalpages = totalcount / pagesize; 44 45 if (totalcount % pagesize > 0) 46 totalpages++; 47 48 this.pagesize = pagesize; 49 this.pageindex = pageindex; 50 this.addrange(source.skip((pageindex - 1) * pagesize).take(pagesize).tolist()); 51 } 52 53 /// <summary> 54 /// ctor 55 /// </summary> 56 /// <param name="source">source</param> 57 /// <param name="pageindex">page index</param> 58 /// <param name="pagesize">page size</param> 59 /// <param name="totalcount">total count</param> 60 public pagedlist(ienumerable<t> source, int pageindex, int pagesize, int totalcount) 61 { 62 totalcount = totalcount; 63 totalpages = totalcount / pagesize; 64 65 if (totalcount % pagesize > 0) 66 totalpages++; 67 68 this.pagesize = pagesize; 69 this.pageindex = pageindex; 70 this.addrange(source); 71 } 72 73 public int pageindex { get; private set; } 74 public int pagesize { get; private set; } 75 public int totalcount { get; private set; } 76 public int totalpages { get; private set; } 77 78 public bool haspreviouspage 79 { 80 get { return (pageindex > 0); } 81 } 82 public bool hasnextpage 83 { 84 get { return (pageindex + 1 < totalpages); } 85 } 86 } 87 }
ienumerableextensions:ienumerable分页的扩展
1 using system.collections.generic; 2 using system.linq; 3 4 namespace data 5 { 6 public static class ienumerableextensions 7 { 8 public static pagedlist<tsource> topagelist<tsource>(this ienumerable<tsource> source, int pageindex, int pagesize) 9 { 10 if (pageindex < 1) 11 pageindex = 1; 12 int totalcount = 0; 13 list<tsource> resultlist = new list<tsource>(); 14 resultlist = source.skip((pageindex - 1) * pagesize).take(pagesize).tolist(); ; 15 totalcount = source.count(); 16 return new pagedlist<tsource>(resultlist, pageindex, pagesize, totalcount); 17 } 18 } 19 }
irepository:数据库仓库访问接口
1 using system; 2 using system.collections.generic; 3 using system.linq; 4 using system.linq.expressions; 5 6 namespace data 7 { 8 public interface irepository<t> where t : baseentity 9 { 10 /// <summary> 11 /// 通过id获取单个实体 12 /// </summary> 13 /// <param name="id"></param> 14 /// <returns></returns> 15 t getbyid(object id); 16 /// <summary> 17 /// 插入单个实体 18 /// </summary> 19 /// <param name="entity">实体</param> 20 /// <returns></returns> 21 bool insert(t entity); 22 /// <summary> 23 /// 插入单个实体并返回id 24 /// </summary> 25 /// <param name="entity"></param> 26 /// <returns></returns> 27 object insertandgetid(t entity); 28 /// <summary> 29 /// 批量插入数据集 30 /// </summary> 31 /// <param name="entities">数据集</param> 32 void insert(ienumerable<t> entities); 33 /// <summary> 34 /// 更新单个实体 35 /// </summary> 36 /// <param name="entity">实体</param> 37 /// <returns></returns> 38 bool update(t entity); 39 /// <summary> 40 /// 批量更新数据集 41 /// </summary> 42 /// <param name="entities"></param> 43 void update(ienumerable<t> entities); 44 /// <summary> 45 /// 删除单个实体 46 /// </summary> 47 /// <param name="entity"></param> 48 /// <returns></returns> 49 bool delete(t entity); 50 /// <summary> 51 /// 批量删除 52 /// </summary> 53 /// <param name="entities">删除的数据集</param> 54 void delete(ienumerable<t> entities); 55 /// <summary> 56 /// 通过id删除实体 57 /// </summary> 58 /// <param name="id"></param> 59 /// <returns></returns> 60 bool deletebyid(object id); 61 /// <summary> 62 /// 通过id(逗号分隔id)批量删除 63 /// </summary> 64 /// <param name="ids"></param> 65 /// <returns></returns> 66 bool deletebyids(object ids); 67 /// <summary> 68 /// 通过id列表批量删除 69 /// </summary> 70 /// <param name="list"></param> 71 /// <returns></returns> 72 bool deletebyidlist(list<object> list); 73 /// <summary> 74 /// 分页查询 75 /// </summary> 76 /// <param name="pageindex">当前页</param> 77 /// <param name="pagesize">每页条数</param> 78 /// <param name="condition">lambda查询条件where</param> 79 /// <param name="ordername">排序字段 默认createtime</param> 80 /// <param name="sortorder">排序方式 asc desc,默认createtime desc</param> 81 /// <returns></returns> 82 ipagedlist<t> getlistforpaging(int pageindex, int pagesize, expression<func<t, bool>> condition = null, string ordername = null, string sortorder = null); 83 /// <summary> 84 /// linq连表查询专用,获取单表所有数据请使用getlist 85 /// </summary> 86 iqueryable<t> table { get; } 87 /// <summary> 88 /// 根据条件查找 89 /// </summary> 90 /// <param name="condition">lambda查询条件where</param> 91 /// <returns></returns> 92 t getentity(expression<func<t, bool>> condition); 93 /// <summary> 94 /// 分页查询(linq分页方式) 95 /// </summary> 96 /// <param name="pageindex">当前页</param> 97 /// <param name="pagesize">页码</param> 98 /// <param name="condition">lambda查询条件where</param> 99 /// <<param name="sort">排序key:排序字段,value:bool,true-desc,false-asc 默认:createtime desc</param> 100 /// <returns></returns> 101 ipagedlist<t> getlistforpaging(int pageindex, int pagesize, expression<func<t, bool>> condition = null, dictionary<string, bool> sort = null); 102 /// <summary> 103 /// 执行原始sql命令 104 /// </summary> 105 /// <param name="commandtext">sql命令</param> 106 /// <param name="parameters">参数</param> 107 /// <returns>影响的记录数</returns> 108 ienumerable<telement> sqlquery<telement>(string sql, params object[] parameters) where telement : class, new(); 109 /// <summary> 110 /// 执行sqlcommand 111 /// </summary> 112 /// <param name="sql">sql</param> 113 /// <param name="parameters">参数</param> 114 /// <returns></returns> 115 int executesqlcommand(string sql, params object[] parameters); 116 /// <summary> 117 /// 查询列表,默认返回整个表数据 118 /// </summary> 119 /// <param name="condition">lambda查询条件where</param> 120 /// <returns></returns> 121 list<t> getlist(expression<func<t, bool>> condition = null); 122 } 123 }
efrepository:iefrepository接口实现
1 using microsoft.entityframeworkcore; 2 using system; 3 using system.collections.generic; 4 using system.data; 5 using system.linq; 6 using system.linq.expressions; 7 using system.reflection; 8 using tools.cache; 9 10 namespace data 11 { 12 public class efrepository<t> : irepository<t> where t : baseentity 13 { 14 private dbcontext _context; 15 private dbset<t> _entities; 16 private istaticcachemanager _cachemanager; 17 public efrepository(dbcontext context, istaticcachemanager cachemanager) 18 { 19 this._context = context; 20 _cachemanager = cachemanager; 21 } 22 23 private dbset<t> entities 24 { 25 get 26 { 27 if (_entities == null) 28 { 29 _entities = this._context.set<t>(); 30 } 31 return _entities; 32 } 33 } 34 /// <summary> 35 /// linq连表查询专用,获取单表所有数据请使用getlist 36 /// </summary> 37 public virtual iqueryable<t> table 38 { 39 get { 40 return this.entities; 41 } 42 } 43 /// <summary> 44 /// 通过id获取单个实体 45 /// </summary> 46 /// <param name="id"></param> 47 /// <returns></returns> 48 public virtual t getbyid(object id) 49 { 50 var cachekey = typeof(t).name+".getbyid."+id; 51 return _cachemanager.get(cachekey, ()=>this.entities.find(id)); 52 } 53 /// <summary> 54 /// 插入单个实体 55 /// </summary> 56 /// <param name="entity">实体</param> 57 /// <returns></returns> 58 public virtual bool insert(t entity) 59 { 60 if (entity == null) 61 throw new argumentnullexception(nameof(entity)); 62 63 try 64 { 65 entities.add(entity); 66 _context.savechanges(); 67 var cachecontain = typeof(t).name; 68 _cachemanager.removebycontain(cachecontain); 69 } 70 catch (dbupdateexception exception) 71 { 72 //ensure that the detailed error text is saved in the log 73 throw new exception(getfullerrortextandrollbackentitychanges(exception), exception); 74 } 75 return true; 76 } 77 /// <summary> 78 /// 插入单个实体并返回id 79 /// </summary> 80 /// <param name="entity"></param> 81 /// <returns></returns> 82 public virtual object insertandgetid(t entity) 83 { 84 if (entity == null) 85 throw new argumentnullexception(nameof(entity)); 86 try 87 { 88 this.entities.add(entity); 89 this._context.savechanges(); 90 var cachecontain = typeof(t).name; 91 _cachemanager.removebycontain(cachecontain); 92 } 93 catch (dbupdateexception exception) 94 { 95 //ensure that the detailed error text is saved in the log 96 throw new exception(getfullerrortextandrollbackentitychanges(exception), exception); 97 } 98 return entity.id; 99 } 100 /// <summary> 101 /// 批量插入数据集 102 /// </summary> 103 /// <param name="entities">数据集</param> 104 public virtual void insert(ienumerable<t> entities) 105 { 106 if (entities == null) 107 throw new argumentnullexception(nameof(entities)); 108 109 try 110 { 111 entities.addrange(entities); 112 _context.savechanges(); 113 var cachecontain = typeof(t).name; 114 _cachemanager.removebycontain(cachecontain); 115 } 116 catch (dbupdateexception exception) 117 { 118 //ensure that the detailed error text is saved in the log 119 throw new exception(getfullerrortextandrollbackentitychanges(exception), exception); 120 } 121 } 122 /// <summary> 123 /// 更新单个实体 124 /// </summary> 125 /// <param name="entity">实体</param> 126 /// <returns></returns> 127 public virtual bool update(t entity) 128 { 129 if (entity == null) 130 throw new argumentnullexception(nameof(entity)); 131 try 132 { 133 this._context.set<t>().attach(entity); 134 type _type = typeof(t); 135 propertyinfo[] _properties = _type.getproperties(); 136 var entry = _context.entry(entity); 137 foreach (propertyinfo item in _properties) 138 { 139 if ("id" == item.name || "createtime" == item.name || "createperson" == item.name) 140 { 141 continue; 142 } 143 144 entry.property(item.name).ismodified = true; 145 } 146 this._context.savechanges(); 147 var cachecontain = typeof(t).name; 148 _cachemanager.removebycontain(cachecontain); 149 } 150 catch (dbupdateexception exception) 151 { 152 //ensure that the detailed error text is saved in the log 153 throw new exception(getfullerrortextandrollbackentitychanges(exception), exception); 154 } 155 return true; 156 } 157 /// <summary> 158 /// 批量更新数据集 159 /// </summary> 160 /// <param name="entities"></param> 161 public virtual void update(ienumerable<t> entities) 162 { 163 if (entities == null) 164 throw new argumentnullexception(nameof(entities)); 165 166 try 167 { 168 // entities.updaterange(entities); 169 this._context.set<t>().attachrange(entities); 170 foreach (var entity in entities) 171 { 172 type _type = typeof(t); 173 propertyinfo[] _properties = _type.getproperties(); 174 var entry = _context.entry(entity); 175 foreach (propertyinfo item in _properties) 176 { 177 if ("id" == item.name || "createtime" == item.name || "createperson" == item.name) 178 { 179 continue; 180 } 181 182 entry.property(item.name).ismodified = true; 183 } 184 } 185 186 _context.savechanges(); 187 var cachecontain = typeof(t).name; 188 _cachemanager.removebycontain(cachecontain); 189 } 190 catch (dbupdateexception exception) 191 { 192 //ensure that the detailed error text is saved in the log 193 throw new exception(getfullerrortextandrollbackentitychanges(exception), exception); 194 } 195 } 196 /// <summary> 197 /// 删除单个实体 198 /// </summary> 199 /// <param name="entity"></param> 200 /// <returns></returns> 201 public virtual bool delete(t entity) 202 { 203 if (entity == null) 204 throw new argumentnullexception(nameof(entity)); 205 206 try 207 { 208 entities.remove(entity); 209 _context.savechanges(); 210 var cachecontain = typeof(t).name; 211 _cachemanager.removebycontain(cachecontain); 212 } 213 catch (dbupdateexception exception) 214 { 215 //ensure that the detailed error text is saved in the log 216 throw new exception(getfullerrortextandrollbackentitychanges(exception), exception); 217 } 218 return true; 219 } 220 /// <summary> 221 /// 批量删除 222 /// </summary> 223 /// <param name="entities">删除的数据集</param> 224 public virtual void delete(ienumerable<t> entities) 225 { 226 if (entities == null) 227 throw new argumentnullexception(nameof(entities)); 228 229 try 230 { 231 entities.removerange(entities); 232 _context.savechanges(); 233 var cachecontain = typeof(t).name; 234 _cachemanager.removebycontain(cachecontain); 235 } 236 catch (dbupdateexception exception) 237 { 238 //ensure that the detailed error text is saved in the log 239 throw new exception(getfullerrortextandrollbackentitychanges(exception), exception); 240 } 241 } 242 /// <summary> 243 /// 通过id删除实体 244 /// </summary> 245 /// <param name="id"></param> 246 /// <returns></returns> 247 public virtual bool deletebyid(object id) 248 { 249 try 250 { 251 var item = this.entities.find(id); 252 if (item == null) 253 { 254 return false; 255 } 256 this.entities.remove(item); 257 this._context.savechanges(); 258 var cachecontain = typeof(t).name; 259 _cachemanager.removebycontain(cachecontain); 260 } 261 catch (dbupdateexception exception) 262 { 263 //ensure that the detailed error text is saved in the log 264 throw new exception(getfullerrortextandrollbackentitychanges(exception), exception); 265 } 266 return true; 267 } 268 /// <summary> 269 /// 通过id(逗号分隔id)批量删除 270 /// </summary> 271 /// <param name="ids"></param> 272 /// <returns></returns> 273 public virtual bool deletebyids(object ids) 274 { 275 try 276 { 277 var idarray = ids.tostring().split(','); 278 for (int i = 0; i < idarray.length; i++) 279 { 280 var item = this.entities.find(idarray[i]); 281 if (item == null) 282 { 283 continue; 284 } 285 this.entities.remove(item); 286 } 287 this._context.savechanges(); 288 var cachecontain = typeof(t).name; 289 _cachemanager.removebycontain(cachecontain); 290 } 291 catch (dbupdateexception exception) 292 { 293 //ensure that the detailed error text is saved in the log 294 throw new exception(getfullerrortextandrollbackentitychanges(exception), exception); 295 } 296 return true; 297 } 298 /// <summary> 299 /// 通过id列表批量删除 300 /// </summary> 301 /// <param name="list"></param> 302 /// <returns></returns> 303 public virtual bool deletebyidlist(list<object> list) 304 { 305 try 306 { 307 for (int i = 0; i < list.count; i++) 308 { 309 var item = this.entities.find(list[i]); 310 if (item == null) 311 { 312 continue; 313 } 314 this.entities.remove(item); 315 } 316 this._context.savechanges(); 317 var cachecontain = typeof(t).name; 318 _cachemanager.removebycontain(cachecontain); 319 } 320 catch (dbupdateexception exception) 321 { 322 //ensure that the detailed error text is saved in the log 323 throw new exception(getfullerrortextandrollbackentitychanges(exception), exception); 324 } 325 return true; 326 } 327 328 /// <summary> 329 /// 根据条件查找 330 /// </summary> 331 /// <param name="condition">lambda查询条件where</param> 332 /// <returns></returns> 333 public virtual t getentity(expression<func<t, bool>> condition) 334 { 335 var cachekey = typeof(t) + "getsingleordefault.condition."+ condition.tostring(); 336 return _cachemanager.get(cachekey,()=>this.entities.where(condition).singleordefault()); 337 } 338 /// <summary> 339 /// 分页查询(linq分页方式) 340 /// </summary> 341 /// <param name="pageindex">当前页</param> 342 /// <param name="pagesize">页码</param> 343 /// <param name="condition">lambda查询条件where</param> 344 /// <param name="sort">排序key:排序字段,value:bool,true-desc,false-asc,默认:createtime desc</param> 345 /// <returns></returns> 346 public virtual ipagedlist<t> getlistforpaging(int pageindex, int pagesize, expression<func<t, bool>> condition = null, dictionary<string, bool> sort = null) 347 { 348 if (pageindex < 1) 349 pageindex = 1; 350 var cachekey = typeof(t).name; 351 cachekey = cachekey + ".getlist"; 352 list<t> data = null; 353 354 if (condition != null) 355 { 356 cachekey = cachekey+ ".condition." + condition.tostring(); 357 } 358 359 data = _cachemanager.get<list<t>>(cachekey); 360 361 if(data != null) 362 { 363 if (sort != null) 364 { 365 foreach (var item in sort) 366 { 367 data = data.asqueryable().orderby(item.key, item.value).tolist(); 368 } 369 } 370 else 371 { 372 data = data.asqueryable().orderbydescending(x => x.createtime).tolist(); 373 } 374 } 375 else 376 { 377 if(condition!=null) 378 { 379 data = this.entities.where(condition).tolist(); 380 } 381 else 382 { 383 data = this.entities.tolist(); 384 } 385 _cachemanager.set(cachekey, data, 60); 386 387 data = data.asqueryable().orderbydescending(x => x.createtime).tolist();//无缓存默认返回排序后数据 388 } 389 390 return new pagedlist<t>(data, pageindex, pagesize); 391 } 392 393 /// <summary> 394 /// 执行原始sql命令 395 /// </summary> 396 /// <param name="commandtext">sql命令</param> 397 /// <param name="parameters">参数</param> 398 /// <returns>影响的记录数</returns> 399 public virtual ienumerable<telement> sqlquery<telement>(string sql, params object[] parameters) where telement : class, new() 400 { 401 datatable dt = this._context.database.sqlquery(sql, parameters); 402 return dt.toenumerable<telement>(); 403 404 } 405 /// <summary> 406 /// 分页查询 407 /// </summary> 408 /// <param name="pageindex">当前页</param> 409 /// <param name="pagesize">每页条数</param> 410 /// <param name="condition">lambda查询条件where</param> 411 /// <param name="ordername">排序字段 默认createtime</param> 412 /// <param name="sortorder">排序方式 asc desc,默认createtime desc</param> 413 /// <returns></returns> 414 public virtual ipagedlist<t> getlistforpaging(int pageindex, int pagesize, expression<func<t, bool>> condition = null, string ordername = null, string sortorder = null) 415 { 416 var cachekey = typeof(t).name; 417 if (pageindex < 1) 418 pageindex = 1; 419 if (ordername == null) 420 { 421 ordername = "createtime"; 422 } 423 bool isdesc = true; 424 if(sortorder!=null&&sortorder.tolower() == "asc") 425 { 426 isdesc = false; 427 } 428 429 cachekey = cachekey + ".getlist"; 430 431 if(condition!=null) 432 { 433 cachekey = cachekey + ".condition." + condition.tostring(); 434 } 435 436 list<t> resultlist = null; 437 438 var cachedata = _cachemanager.get<list<t>>(cachekey); 439 if (cachedata != null) 440 { 441 resultlist = cachedata.asqueryable().orderby(ordername, isdesc).tolist(); 442 } 443 else 444 { 445 if (condition == null) 446 { 447 resultlist = entities.tolist(); 448 } 449 else 450 { 451 resultlist = entities.where(condition).tolist(); 452 } 453 _cachemanager.set(cachekey, resultlist, 60); 454 } 455 456 return new pagedlist<t>(resultlist, pageindex, pagesize); 457 } 458 /// <summary> 459 /// 执行sqlcommand 460 /// </summary> 461 /// <param name="sql">sql</param> 462 /// <param name="parameters">参数</param> 463 /// <returns></returns> 464 public virtual int executesqlcommand(string sql, params object[] parameters) 465 { 466 var result = this._context.database.executesqlcommand(sql, parameters); 467 return result; 468 } 469 /// <summary> 470 /// 查询列表,默认返回整个表数据 471 /// </summary> 472 /// <param name="condition">lambda查询条件where</param> 473 /// <returns></returns> 474 public virtual list<t> getlist(expression<func<t, bool>> condition = null) 475 { 476 var cachekey = typeof(t).name+ ".getlist"; 477 list<t> entities = null; 478 if (condition != null) 479 { 480 cachekey = cachekey + ".condition." + condition.tostring(); 481 entities = _cachemanager.get(cachekey,()=>this.entities.where(condition).tolist()); 482 } 483 else 484 { 485 entities = _cachemanager.get(cachekey,()=>this.entities.tolist()); 486 } 487 return entities; 488 } 489 #region utilities 490 491 /// <summary> 492 /// rollback of entity changes and return full error message 493 /// </summary> 494 /// <param name="exception">exception</param> 495 /// <returns>error message</returns> 496 protected string getfullerrortextandrollbackentitychanges(dbupdateexception exception) 497 { 498 //rollback entity changes 499 if (_context is dbcontext dbcontext) 500 { 501 var entries = dbcontext.changetracker.entries() 502 .where(e => e.state == entitystate.added || e.state == entitystate.modified).tolist(); 503 504 entries.foreach(entry => 505 { 506 try 507 { 508 entry.state = entitystate.unchanged; 509 } 510 catch (invalidoperationexception) 511 { 512 // ignored 513 } 514 }); 515 } 516 517 try 518 { 519 _context.savechanges(); 520 return exception.tostring(); 521 } 522 catch (exception ex) 523 { 524 //if after the rollback of changes the context is still not saving, 525 //return the full text of the exception that occurred when saving 526 return ex.tostring(); 527 } 528 } 529 530 #endregion 531 532 } 533 } 534 public static class queryableextensions 535 { 536 public static iqueryable<t> orderby<t>(this iqueryable<t> queryable, string propertyname) 537 { 538 return queryablehelper<t>.orderby(queryable, propertyname, false); 539 } 540 public static iqueryable<t> orderby<t>(this iqueryable<t> queryable, string propertyname, bool desc) 541 { 542 return queryablehelper<t>.orderby(queryable, propertyname, desc); 543 } 544 static class queryablehelper<t> 545 { 546 private static dictionary<string, lambdaexpression> cache = new dictionary<string, lambdaexpression>(); 547 public static iqueryable<t> orderby(iqueryable<t> queryable, string propertyname, bool desc) 548 { 549 dynamic keyselector = getlambdaexpression(propertyname); 550 return desc ? queryable.orderbydescending(queryable, keyselector) : queryable.orderby(queryable, keyselector); 551 } 552 private static lambdaexpression getlambdaexpression(string propertyname) 553 { 554 if (cache.containskey(propertyname)) return cache[propertyname]; 555 var param = expression.parameter(typeof(t)); 556 var body = expression.property(param, propertyname); 557 var keyselector = expression.lambda(body, param); 558 cache[propertyname] = keyselector; 559 return keyselector; 560 } 561 } 562 }
_cachemanager下篇我们讲到缓存管理的时候再来讲,包括依赖注入也放到下篇,今天就先到这里了!
上一篇: 有钱人的心境就是很平和