EF架构~一个规范,两个实现
在EF环境里,我们的数据上下文对象通常是有两个版本,一个是DbContext对象,另一个是ObjectContext,个人觉得前者是轻量级的,对于code first模式中使用比较多,而后者是原生态的,最初的EDM(entity Data Model)就是以这个为基类的,它的实现与linq to sql很类似,也是分部方法,lambda表达式等元素的产物。
看看我的一个规范,两个实现吧!
一个规范:
1 namespace Commons.Data 2 { 3 /// <summary> 4 /// data repository interface 5 /// </summary> 6 /// <typeparam name="T"></typeparam> 7 public interface IRepository 8 { 9 /// <summary> 10 /// 添加 11 /// </summary> 12 /// <param name="entity"></param> 13 void Insert<TEntity>(TEntity entity, bool isSubmit) where TEntity : class; 14 /// <summary> 15 /// 添加并提交 16 /// </summary> 17 /// <typeparam name="TEntity"></typeparam> 18 /// <param name="entity"></param> 19 void Insert<TEntity>(TEntity entity) where TEntity : class; 20 /// <summary> 21 /// 批量添加并提交 22 /// </summary> 23 /// <typeparam name="TEntity"></typeparam> 24 /// <param name="entity"></param> 25 void Insert<TEntity>(List<TEntity> list) where TEntity : class; 26 /// <summary> 27 /// 更新 28 /// </summary> 29 /// <param name="entity"></param> 30 void Update<TEntity>(TEntity entity, bool isSubmit) where TEntity : class; 31 /// <summary> 32 /// 更新并提交 33 /// </summary> 34 /// <typeparam name="TEntity"></typeparam> 35 /// <param name="entity"></param> 36 void Update<TEntity>(TEntity entity) where TEntity : class; 37 /// <summary> 38 /// 更新列表 39 /// </summary> 40 /// <typeparam name="TEntity"></typeparam> 41 /// <param name="list"></param> 42 void Update<TEntity>(List<TEntity> list) where TEntity : class; 43 /// <summary> 44 /// 更新指定字段 45 /// </summary> 46 /// <typeparam name="T"></typeparam> 47 /// <param name="entity"></param> 48 void Update<TEntity>(Expression<Action<TEntity>> entity, bool isSubmit) where TEntity : class; 49 /// <summary> 50 /// 更新指定字段并提交 51 /// </summary> 52 /// <typeparam name="TEntity"></typeparam> 53 /// <param name="entity"></param> 54 void Update<TEntity>(Expression<Action<TEntity>> entity) where TEntity : class; 55 /// <summary> 56 /// 删除 57 /// </summary> 58 /// <param name="entity"></param> 59 void Delete<TEntity>(TEntity entity, bool isSubmit) where TEntity : class; 60 /// <summary> 61 /// 删除并提交 62 /// </summary> 63 /// <typeparam name="TEntity"></typeparam> 64 /// <param name="entity"></param> 65 void Delete<TEntity>(TEntity entity) where TEntity : class; 66 /// <summary> 67 /// 根据主键取一个 68 /// </summary> 69 /// <param name="id"></param> 70 /// <returns></returns> 71 TEntity GetEntity<TEntity>(params object[] id) where TEntity : class; 72 /// <summary> 73 /// 根据条件取一个 74 /// </summary> 75 /// <param name="predicate"></param> 76 /// <returns></returns> 77 TEntity GetEntity<TEntity>(Expression<Func<TEntity, bool>> predicate) where TEntity : class; 78 /// <summary> 79 /// 实体集对象的可查询结果集 80 /// </summary> 81 IQueryable<TEntity> GetEntities<TEntity>() where TEntity : class; 82 /// <summary> 83 /// 统计数量 84 /// </summary> 85 /// <param name="predicate"></param> 86 /// <returns></returns> 87 int Count<TEntity>(Expression<Func<TEntity, bool>> predicate) where TEntity : class; 88 /// <summary> 89 /// 返回结果集 90 /// </summary> 91 /// <param name="predicate"></param> 92 /// <returns></returns> 93 IEnumerable<TEntity> GetEntities<TEntity>(Expression<Func<TEntity, bool>> predicate) where TEntity : class; 94 /// <summary> 95 /// 带有排序的结果集 96 /// </summary> 97 /// <param name="predicate"></param> 98 /// <param name="order"></param> 99 /// <returns></returns> 100 IEnumerable<TEntity> GetEntities<TEntity>(Expression<Func<TEntity, bool>> predicate, Action<Orderable<TEntity>> order) where TEntity : class; 101 /// <summary> 102 /// 带分页和排序的结果集 103 /// </summary> 104 /// <param name="predicate"></param> 105 /// <param name="order"></param> 106 /// <param name="skip"></param> 107 /// <param name="count"></param> 108 /// <returns></returns> 109 IEnumerable<TEntity> GetEntities<TEntity>(Expression<Func<TEntity, bool>> predicate, Action<Orderable<TEntity>> order, int skip, int count) where TEntity : class; 110 111 } 112 }
两个实现:
一 DbContext作为基类的实现:
1 namespace Commons.Data 2 { 3 /// <summary> 4 /// EF数据结构实现 5 /// </summary> 6 /// <typeparam name="T"></typeparam> 7 public abstract class RepositoryBase : IRepository 8 { 9 #region Properties 10 /// <summary> 11 /// 日志对象 12 /// </summary> 13 public VLog.IVLog _iVlog { get; set; } 14 /// <summary> 15 /// 数据上下文,对子类公开 16 /// </summary> 17 protected readonly DbContext _db; 18 #endregion 19 20 #region Constructors 21 /// <summary> 22 /// 通过具体子类建立DbContext对象,并提供日志对象的实现 23 /// </summary> 24 /// <param name="db"></param> 25 /// <param name="logger"></param> 26 public RepositoryBase(DbContext db, VLog.IVLog logger) 27 { 28 try 29 { 30 _db = db; 31 _iVlog = logger; 32 } 33 catch (Exception) 34 { 35 36 throw new Exception("EF底层数据出现问题,请检查..."); 37 } 38 39 } 40 41 public RepositoryBase(DbContext db) 42 : this(db, null) 43 { 44 45 } 46 47 #endregion 48 49 #region IRepository<T> 成员 50 51 #region Create,Update,Delete --Virtual Methods 52 53 #region 简单调用 54 public virtual void Insert<TEntity>(TEntity entity) where TEntity : class 55 { 56 this.Insert(entity, true); 57 } 58 59 public void Insert<TEntity>(List<TEntity> list) where TEntity : class 60 { 61 BulkInsertAll<TEntity>(list); 62 } 63 64 public void Update<TEntity>(TEntity entity) where TEntity : class 65 { 66 this.Update<TEntity>(entity, true); 67 } 68 69 public void Update<TEntity>(List<TEntity> list) where TEntity : class 70 { 71 list.ForEach(entity => 72 { 73 this.Update<TEntity>(entity, false); 74 }); 75 this.SaveChanges(); 76 } 77 78 public virtual void Update<TEntity>(Expression<Action<TEntity>> entity) where TEntity : class 79 { 80 this.Update<TEntity>(entity, true); 81 } 82 83 public virtual void Delete<TEntity>(TEntity entity) where TEntity : class 84 { 85 this.Delete<TEntity>(entity, true); 86 } 87 #endregion 88 89 #region GUID操作实现 90 public void Insert<TEntity>(TEntity entity, bool isSubmit) where TEntity : class 91 { 92 //Logger.InfoLog("Create 表名:{0},内容:{1}", entity, ToJson(entity)); 93 _db.Entry<TEntity>(entity); 94 _db.Set<TEntity>().Add(entity); 95 if (isSubmit) 96 this.SaveChanges(); 97 } 98 99 public void Update<TEntity>(TEntity entity, bool isSubmit) where TEntity : class 100 { 101 _db.Set<TEntity>().Attach(entity); 102 _db.Entry(entity).State = EntityState.Modified; 103 if (isSubmit) 104 this.SaveChanges(); 105 } 106 107 public void Update<TEntity>(Expression<Action<TEntity>> entity, bool isSubmit) where TEntity : class 108 { 109 TEntity newEntity = typeof(TEntity).GetConstructor(Type.EmptyTypes).Invoke(null) as TEntity;//建立指定类型的实例 110 List<string> propertyNameList = new List<string>(); 111 MemberInitExpression param = entity.Body as MemberInitExpression; 112 foreach (var item in param.Bindings) 113 { 114 string propertyName = item.Member.Name; 115 object propertyValue; 116 var memberAssignment = item as MemberAssignment; 117 if (memberAssignment.Expression.NodeType == ExpressionType.Constant) 118 { 119 propertyValue = (memberAssignment.Expression as ConstantExpression).Value; 120 } 121 else 122 { 123 propertyValue = Expression.Lambda(memberAssignment.Expression, null).Compile().DynamicInvoke(); 124 } 125 typeof(TEntity).GetProperty(propertyName).SetValue(newEntity, propertyValue, null); 126 propertyNameList.Add(propertyName); 127 } 128 _db.Set<TEntity>().Attach(newEntity); 129 _db.Configuration.ValidateOnSaveEnabled = false; 130 var ObjectStateEntry = ((IObjectContextAdapter)_db).ObjectContext.ObjectStateManager.GetObjectStateEntry(newEntity); 131 propertyNameList.ForEach(x => ObjectStateEntry.SetModifiedProperty(x.Trim())); 132 if (isSubmit) 133 this.SaveChanges(); 134 } 135 136 public void Delete<TEntity>(TEntity entity, bool isSubmit) where TEntity : class 137 { 138 _db.Set<TEntity>().Attach(entity); 139 _db.Set<TEntity>().Remove(entity); 140 if (isSubmit) 141 this.SaveChanges(); 142 } 143 #endregion 144 145 #endregion 146 147 #region Get --Virtual Methods 148 public virtual int Count<TEntity>(Expression<Func<TEntity, bool>> predicate) where TEntity : class 149 { 150 return GetEntities(predicate).Count(); 151 } 152 153 public virtual TEntity GetEntity<TEntity>(params object[] id) where TEntity : class 154 { 155 return _db.Set<TEntity>().Find(id); 156 } 157 public virtual TEntity GetEntity<TEntity>(Expression<Func<TEntity, bool>> predicate) where TEntity : class 158 { 159 return GetEntities(predicate).SingleOrDefault(); 160 } 161 162 public virtual IQueryable<TEntity> GetEntities<TEntity>() where TEntity : class 163 { 164 return _db.Set<TEntity>(); 165 } 166 public virtual IEnumerable<TEntity> GetEntities<TEntity>(Expression<Func<TEntity, bool>> predicate) where TEntity : class 167 { 168 return this.GetEntities<TEntity>().Where(predicate); 169 } 170 171 public virtual IEnumerable<TEntity> GetEntities<TEntity>(Expression<Func<TEntity, bool>> predicate, Action<Orderable<TEntity>> order) where TEntity : class 172 { 173 var orderable = new Orderable<TEntity>(GetEntities(predicate).AsQueryable()); 174 order(orderable); 175 return orderable.Queryable; 176 } 177 178 public virtual IEnumerable<TEntity> GetEntities<TEntity>(Expression<Func<TEntity, bool>> predicate, Action<Orderable<TEntity>> order, int skip, int count) where TEntity : class 179 { 180 return GetEntities(predicate, order).Skip(skip).Take(count); 181 } 182 #endregion 183 184 #endregion 185 186 #region Methods 187 /// <summary> 188 /// 提交动作 189 /// 当程序中出现SaveChanges开始与数据库进行通讯 190 /// </summary> 191 protected virtual void SaveChanges() 192 { 193 try 194 { 195 _db.SaveChanges(); //在有 196 } 197 catch (Exception ex) 198 { 199 string Message = "error:"; 200 if (ex.InnerException == null) 201 Message += ex.Message + ","; 202 else if (ex.InnerException.InnerException == null) 203 Message += ex.InnerException.Message + ","; 204 else if (ex.InnerException.InnerException.InnerException == null) 205 Message += ex.InnerException.InnerException.Message + ","; 206 throw new Exception(Message); 207 } 208 } 209 /// <summary> 210 /// 批量插入 211 /// </summary> 212 /// <typeparam name="T"></typeparam> 213 /// <param name="entities"></param> 214 void BulkInsertAll<T>(IEnumerable<T> entities) where T : class 215 { 216 entities = entities.ToArray(); 217 218 string cs = _db.Database.Connection.ConnectionString; 219 var conn = new SqlConnection(cs); 220 conn.Open(); 221 222 Type t = typeof(T); 223 224 var bulkCopy = new SqlBulkCopy(conn) 225 { 226 DestinationTableName = string.Format("[{0}]", t.Name) 227 }; 228 229 var properties = t.GetProperties().Where(EventTypeFilter).ToArray(); 230 var table = new DataTable(); 231 232 foreach (var property in properties) 233 { 234 Type propertyType = property.PropertyType; 235 if (propertyType.IsGenericType && 236 propertyType.GetGenericTypeDefinition() == typeof(Nullable<>)) 237 { 238 propertyType = Nullable.GetUnderlyingType(propertyType); 239 } 240 241 table.Columns.Add(new DataColumn(property.Name, propertyType)); 242 } 243 244 foreach (var entity in entities) 245 { 246 table.Rows.Add(properties.Select( 247 property => GetPropertyValue( 248 property.GetValue(entity, null))).ToArray()); 249 } 250 251 bulkCopy.WriteToServer(table); 252 conn.Close(); 253 } 254 255 private bool EventTypeFilter(System.Reflection.PropertyInfo p) 256 { 257 var attribute = Attribute.GetCustomAttribute(p, 258 typeof(AssociationAttribute)) as AssociationAttribute; 259 260 if (attribute == null) return true; 261 if (attribute.IsForeignKey == false) return true; 262 263 return false; 264 } 265 266 private object GetPropertyValue(object o) 267 { 268 if (o == null) 269 return DBNull.Value; 270 return o; 271 } 272 #endregion 273 274 } 275 276 }
二 ObjectContext作为基类的实现:
1 namespace Commons.Data 2 { 3 /// <summary> 4 /// EF数据结构实现 5 /// </summary> 6 /// <typeparam name="T"></typeparam> 7 public abstract class ObjectContextRepositoryBase : IRepository 8 { 9 #region PropertiesObjectContext 10 /// <summary> 11 /// 日志对象 12 /// </summary> 13 public VLog.IVLog _iVlog { get; set; } 14 /// <summary> 15 /// 数据上下文,对子类公开 16 /// </summary> 17 protected readonly ObjectContext _db; 18 #endregion 19 20 #region Constructors 21 /// <summary> 22 /// 通过具体子类建立DbContext对象,并提供日志对象的实现 23 /// </summary> 24 /// <param name="db"></param> 25 /// <param name="logger"></param> 26 public ObjectContextRepositoryBase(ObjectContext db, VLog.IVLog logger) 27 { 28 try 29 { 30 _db = db; 31 _iVlog = logger; 32 } 33 catch (Exception) 34 { 35 36 throw new Exception("EF底层数据出现问题,请检查..."); 37 } 38 39 } 40 41 public ObjectContextRepositoryBase(ObjectContext db) 42 : this(db, null) 43 { 44 45 } 46 47 #endregion 48 49 #region IRepository<T> 成员 50 51 #region Create,Update,Delete --Virtual Methods 52 53 #region 简单调用 54 public virtual void Insert<TEntity>(TEntity entity) where TEntity : class 55 { 56 this.Insert(entity, true); 57 } 58 59 public void Insert<TEntity>(List<TEntity> list) where TEntity : class 60 { 61 // BulkInsertAll<TEntity>(list); 62 list.ForEach(entity => 63 { 64 Insert(entity, false); 65 }); 66 this.SaveChanges(); 67 } 68 69 public void Update<TEntity>(TEntity entity) where TEntity : class 70 { 71 // this.Update<TEntity>(entity, true); 72 UpdateEntity<TEntity>(entity); 73 } 74 75 public void Update<TEntity>(List<TEntity> list) where TEntity : class 76 { 77 list.ForEach(entity => 78 { 79 this.Update<TEntity>(entity, false); 80 }); 81 this.SaveChanges(); 82 } 83 84 public virtual void Update<TEntity>(Expression<Action<TEntity>> entity) where TEntity : class 85 { 86 this.Update<TEntity>(entity, true); 87 } 88 89 public virtual void Delete<TEntity>(TEntity entity) where TEntity : class 90 { 91 this.Delete<TEntity>(entity, true); 92 } 93 #endregion 94 95 #region GUID操作实现 96 public void Insert<TEntity>(TEntity entity, bool isSubmit) where TEntity : class 97 { 98 //Logger.InfoLog("Create 表名:{0},内容:{1}", entity, ToJson(entity)); 99 _db.CreateObjectSet<TEntity>().AddObject(entity); 100 if (isSubmit) 101 this.SaveChanges(); 102 } 103 104 public void Update<TEntity>(TEntity entity, bool isSubmit) where TEntity : class 105 { 106 _db.Attach(entity as EntityObject); 107 _db.ObjectStateManager.ChangeObjectState(entity, EntityState.Modified); 108 if (isSubmit) 109 this.SaveChanges(); 110 } 111 112 public void Update<TEntity>(Expression<Action<TEntity>> entity, bool isSubmit) where TEntity : class 113 { 114 TEntity newEntity = typeof(TEntity).GetConstructor(Type.EmptyTypes).Invoke(null) as TEntity;//建立指定类型的实例 115 List<string> propertyNameList = new List<string>(); 116 MemberInitExpression param = entity.Body as MemberInitExpression; 117 foreach (var item in param.Bindings) 118 { 119 string propertyName = item.Member.Name; 120 object propertyValue; 121 var memberAssignment = item as MemberAssignment; 122 if (memberAssignment.Expression.NodeType == ExpressionType.Constant) 123 { 124 propertyValue = (memberAssignment.Expression as ConstantExpression).Value; 125 } 126 else 127 { 128 propertyValue = Expression.Lambda(memberAssignment.Expression, null).Compile().DynamicInvoke(); 129 } 130 typeof(TEntity).GetProperty(propertyName).SetValue(newEntity, propertyValue, null); 131 propertyNameList.Add(propertyName); 132 } 133 _db.Attach(newEntity as EntityObject); 134 // _db.Configuration.ValidateOnSaveEnabled = false; 135 var ObjectStateEntry = ((IObjectContextAdapter)_db).ObjectContext.ObjectStateManager.GetObjectStateEntry(newEntity); 136 propertyNameList.ForEach(x => ObjectStateEntry.SetModifiedProperty(x.Trim())); 137 if (isSubmit) 138 this.SaveChanges(); 139 } 140 141 public void Delete<TEntity>(TEntity entity, bool isSubmit) where TEntity : class 142 { 143 _db.Attach(entity as EntityObject); 144 _db.ObjectStateManager.ChangeObjectState(entity, EntityState.Deleted); 145 if (isSubmit) 146 this.SaveChanges(); 147 } 148 #endregion 149 150 #endregion 151 152 #region Get --Virtual Methods 153 public virtual int Count<TEntity>(Expression<Func<TEntity, bool>> predicate) where TEntity : class 154 { 155 return GetEntities(predicate).Count(); 156 } 157 158 public virtual TEntity GetEntity<TEntity>(params object[] id) where TEntity : class 159 { 160 //new NotImplementedException("this method don't implement by zzl !"); 161 return null; 162 } 163 public virtual TEntity GetEntity<TEntity>(Expression<Func<TEntity, bool>> predicate) where TEntity : class 164 { 165 return GetEntities(predicate).SingleOrDefault(); 166 } 167 168 public virtual IQueryable<TEntity> GetEntities<TEntity>() where TEntity : class 169 { 170 return _db.CreateObjectSet<TEntity>(); 171 } 172 public virtual IEnumerable<TEntity> GetEntities<TEntity>(Expression<Func<TEntity, bool>> predicate) where TEntity : class 173 { 174 return this.GetEntities<TEntity>().Where(predicate); 175 } 176 177 public virtual IEnumerable<TEntity> GetEntities<TEntity>(Expression<Func<TEntity, bool>> predicate, Action<Orderable<TEntity>> order) where TEntity : class 178 { 179 var orderable = new Orderable<TEntity>(GetEntities(predicate).AsQueryable()); 180 order(orderable); 181 return orderable.Queryable; 182 } 183 184 public virtual IEnumerable<TEntity> GetEntities<TEntity>(Expression<Func<TEntity, bool>> predicate, Action<Orderable<TEntity>> order, int skip, int count) where TEntity : class 185 { 186 return GetEntities(predicate, order).Skip(skip).Take(count); 187 } 188 #endregion 189 190 #endregion 191 192 #region Methods 193 /// <summary> 194 /// 提交动作 195 /// 当程序中出现SaveChanges开始与数据库进行通讯 196 /// </summary> 197 protected virtual void SaveChanges() 198 { 199 try 200 { 201 _db.SaveChanges(); //在有 202 } 203 catch (Exception ex) 204 { 205 string Message = "error:"; 206 if (ex.InnerException == null) 207 Message += ex.Message + ","; 208 else if (ex.InnerException.InnerException == null) 209 Message += ex.InnerException.Message + ","; 210 else if (ex.InnerException.InnerException.InnerException == null) 211 Message += ex.InnerException.InnerException.Message + ","; 212 throw new Exception(Message); 213 } 214 } 215 /// <summary> 216 /// 批量插入 217 /// </summary> 218 /// <typeparam name="T"></typeparam> 219 /// <param name="entities"></param> 220 void BulkInsertAll<T>(IEnumerable<T> entities) where T : class 221 { 222 entities = entities.ToArray(); 223 224 string cs = _db.Connection.ConnectionString; 225 var conn = new SqlConnection(cs); 226 conn.Open(); 227 228 Type t = typeof(T); 229 230 var bulkCopy = new SqlBulkCopy(conn) 231 { 232 DestinationTableName = string.Format("[{0}]", t.Name) 233 }; 234 235 var properties = t.GetProperties().Where(EventTypeFilter).ToArray(); 236 var table = new DataTable(); 237 238 foreach (var property in properties) 239 { 240 Type propertyType = property.PropertyType; 241 if (propertyType.IsGenericType && 242 propertyType.GetGenericTypeDefinition() == typeof(Nullable<>)) 243 { 244 propertyType = Nullable.GetUnderlyingType(propertyType); 245 } 246 247 table.Columns.Add(new DataColumn(property.Name, propertyType)); 248 } 249 250 foreach (var entity in entities) 251 { 252 table.Rows.Add(properties.Select( 253 property => GetPropertyValue( 254 property.GetValue(entity, null))).ToArray()); 255 } 256 257 bulkCopy.WriteToServer(table); 258 conn.Close(); 259 } 260 261 private bool EventTypeFilter(System.Reflection.PropertyInfo p) 262 { 263 var attribute = Attribute.GetCustomAttribute(p, 264 typeof(AssociationAttribute)) as AssociationAttribute; 265 266 if (attribute == null) return true; 267 if (attribute.IsForeignKey == false) return true; 268 269 return false; 270 } 271 272 private object GetPropertyValue(object o) 273 { 274 if (o == null) 275 return DBNull.Value; 276 return o; 277 } 278 279 private void UpdateEntity<TEntity>(TEntity entity) where TEntity : class 280 { 281 Type entityType = entity.GetType(); 282 var table = entityType.GetProperties().Where(i => i.PropertyType != typeof(EntityKey) && i.PropertyType != typeof(EntityState)).ToArray(); 283 var primaryKeyColumns = (entity as EntityObject).GetPK(); 284 List<object> arguments = new List<object>(); 285 StringBuilder builder = new StringBuilder(); 286 287 foreach (var change in table) 288 { 289 if (change == primaryKeyColumns) 290 continue; 291 292 if (arguments.Count != 0) 293 builder.Append(", "); 294 295 if (change.GetValue(entity, null) != null) 296 { 297 builder.Append(change.Name + " = {" + arguments.Count + "}"); 298 arguments.Add(change.GetValue(entity, null)); 299 } 300 else 301 { 302 builder.Append(change.Name + " = NULL, "); 303 } 304 } 305 306 if (builder.Length == 0) 307 return; 308 309 builder.Insert(0, "UPDATE " + string.Format("[{0}]", entityType.Name) + " SET "); 310 311 builder.Append(" WHERE "); 312 bool firstPrimaryKey = true; 313 314 foreach (var primaryField in table) 315 { 316 if (firstPrimaryKey) 317 firstPrimaryKey = false; 318 else 319 builder.Append(" AND "); 320 321 object val = entityType.GetProperty(primaryField.Name).GetValue(entity, null); 322 builder.Append(GetEqualStatment(primaryField.Name, arguments.Count)); 323 arguments.Add(val); 324 } 325 326 327 328 try 329 { 330 _db.ExecuteStoreCommand(builder.ToString(), arguments.ToArray()); 331 } 332 catch (Exception) 333 { 334 throw; 335 } 336 } 337 338 private static string GetEqualStatment(string fieldName, int paramId) 339 { 340 return string.Format("{0} = {1}", fieldName, GetParamTag(paramId)); 341 342 } 343 344 private static string GetParamTag(int paramId) 345 { 346 return "{" + paramId + "}"; 347 348 } 349 #endregion 350 351 } 352 353 354 /// <summary> 355 /// ObjectContext扩展 356 /// </summary> 357 public static class ObjectContextExtension 358 { 359 /// <summary> 360 /// 得到主键 361 /// </summary> 362 public static PropertyInfo GetPK(this EntityObject value) 363 { 364 PropertyInfo[] properties = value.GetType().GetProperties(); 365 foreach (PropertyInfo pI in properties) 366 { 367 System.Object[] attributes = pI.GetCustomAttributes(true); 368 foreach (object attribute in attributes) 369 { 370 if (attribute is EdmScalarPropertyAttribute) 371 { 372 if ((attribute as EdmScalarPropertyAttribute).EntityKeyProperty && !(attribute as EdmScalarPropertyAttribute).IsNullable) 373 return pI; 374 } 375 376 } 377 } 378 return null; 379 } 380 381 /// <summary> 382 /// 把所有属性都标为已修改 383 /// </summary> 384 /// <param name="objectContext"></param> 385 /// <param name="item"></param> 386 public static void SetAllModified<TEntity>(this ObjectContext objectContext, TEntity item) 387 { 388 ObjectStateEntry stateEntry = objectContext.ObjectStateManager.GetObjectStateEntry(item) as ObjectStateEntry; 389 IEnumerable propertyNameList = stateEntry.CurrentValues.DataRecordInfo.FieldMetadata.Select(pn => pn.FieldType.Name); 390 foreach (string propName in propertyNameList) 391 { 392 stateEntry.SetModifiedProperty(propName); 393 } 394 stateEntry.SetModified(); 395 } 396 } 397 398 399 400 }
这一个规范,两个实现,在我们实际开发过程中,如果出现问题,请及时与我联系!
大家一起讨论,共同进步!