UnitOfWork.cs 38 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Linq;
  4. using System.Text;
  5. using Bowin.Common.Data;
  6. using Bowin.Common.Linq;
  7. using Bowin.Common.Linq.Entity;
  8. using EMIS.Entities;
  9. using System.Data.SqlClient;
  10. using System.Data;
  11. using System.Data.Entity;
  12. using System.Data.Entity.Validation;
  13. using System.Diagnostics;
  14. using System.Data.Entity.Core.Objects;
  15. using System.Data.Entity.Core.Metadata.Edm;
  16. using System.Data.Entity.Infrastructure;
  17. using System.Linq.Expressions;
  18. using System.Reflection;
  19. using EMIS.Utility.Log;
  20. using System.Collections;
  21. using Bowin.Common.Linq.DB;
  22. using System.Configuration;
  23. namespace EMIS.DataLogic
  24. {
  25. public class UnitOfWork : EMISNewContext, IDisposable
  26. {
  27. public UnitOfWork()
  28. : base("EMISNewContext")
  29. {
  30. }
  31. public TEntity Add<TEntity>(TEntity entity) where TEntity : class
  32. {
  33. return Set<TEntity>().Add(entity);
  34. }
  35. public IEnumerable<TEntity> AddRange<TEntity>(IEnumerable<TEntity> entityList) where TEntity : class
  36. {
  37. return Set<TEntity>().AddRange(entityList);
  38. }
  39. public TEntity Attach<TEntity>(TEntity entity) where TEntity : class
  40. {
  41. return Set<TEntity>().Attach(entity);
  42. }
  43. /// <summary>
  44. /// 事务提交
  45. /// </summary>
  46. public void Commit()
  47. {
  48. var logs = DbLog.GetLog(this.ChangeTracker).Concat(
  49. DbLog.GetRelationshipLog(this)).ToList();
  50. try
  51. {
  52. SaveChanges();
  53. logs.ForEach(x => x.IsSuccess = true);
  54. LogUnitOfWork.WriteLogs(logs);
  55. }
  56. catch (DbEntityValidationException dbEx)
  57. {
  58. logs.ForEach(x => x.IsSuccess = false);
  59. LogUnitOfWork.WriteLogs(logs);
  60. foreach (var validationErrors in dbEx.EntityValidationErrors)
  61. {
  62. foreach (var validationError in validationErrors.ValidationErrors)
  63. {
  64. Trace.TraceInformation("Property: {0} Error: {1}", validationError.PropertyName, validationError.ErrorMessage);
  65. }
  66. }
  67. throw dbEx;
  68. }
  69. catch (Exception ex)
  70. {
  71. logs.ForEach(x => x.IsSuccess = false);
  72. LogUnitOfWork.WriteLogs(logs);
  73. throw ex;
  74. }
  75. }
  76. /// <summary>
  77. /// 创建只有ID字段的临时表
  78. /// </summary>
  79. /// <param name="TempTableName"></param>
  80. public void CreateIDTempTable(string TempTableName, List<Guid?> Id)
  81. {
  82. SqlConnection conn = GetConnection();
  83. if (conn.State == ConnectionState.Closed)
  84. {
  85. conn.Open();
  86. }
  87. string sql = "";
  88. StringBuilder sb = new StringBuilder();
  89. if (Id.Count == 0)
  90. {
  91. sb.Append(@"CREATE TABLE [" + TempTableName + "] (ID UNIQUEIDENTIFIER NOT NULL)");
  92. }
  93. else
  94. {
  95. sb.Append(@"CREATE TABLE [" + TempTableName + "] (ID UNIQUEIDENTIFIER NOT NULL) INSERT INTO [" + TempTableName + "] VALUES");
  96. foreach (var i in Id)
  97. {
  98. sb.Append("(" + "'" + i + "'" + "),");
  99. }
  100. sb.Remove(sb.Length - 1, 1);
  101. }
  102. sql = sb.ToString();
  103. try
  104. {
  105. var command = new SqlCommand(sql, conn);
  106. command.CommandTimeout = 12000;
  107. command.CommandType = System.Data.CommandType.Text;
  108. command.ExecuteNonQuery();
  109. }
  110. catch (Exception)
  111. {
  112. throw;
  113. }
  114. }
  115. /// <summary>
  116. /// 删除只有ID字段的临时表
  117. /// </summary>
  118. /// <param name="TempTableName"></param>
  119. public void DeleteTempTable(string TempTableName)
  120. {
  121. SqlConnection conn = GetConnection();
  122. if (conn.State == ConnectionState.Closed)
  123. {
  124. conn.Open();
  125. }
  126. string sql = "";
  127. StringBuilder sb = new StringBuilder();
  128. sb.Append(@"DROP TABLE [" + TempTableName + "] ");
  129. sql = sb.ToString();
  130. try
  131. {
  132. var command = new SqlCommand(sql, conn);
  133. command.CommandTimeout = 12000;
  134. command.CommandType = System.Data.CommandType.Text;
  135. command.ExecuteNonQuery();
  136. }
  137. catch (Exception)
  138. {
  139. throw;
  140. }
  141. }
  142. /// <summary>
  143. /// 批量更新
  144. /// </summary>
  145. /// <typeparam name="TEntity"></typeparam>
  146. /// <param name="data"></param>
  147. public void BatchUpdate<TEntity>(IList<TEntity> data) where TEntity : class
  148. {
  149. var logList = DbLog.GetBatchUpdateLog(data, this);
  150. string setField = "";
  151. string keyExpression = "";
  152. string tableName = typeof(TEntity).Name;
  153. var properties = typeof(TEntity).GetProperties();
  154. string tableKey = "";
  155. PropertyInfo keyProperty;
  156. try
  157. {
  158. tableKey = TableKeyDictionary.GetKeyName<TEntity>();
  159. keyProperty = typeof(TEntity).GetProperty(tableKey);
  160. }
  161. catch
  162. {
  163. throw new Exception("批量修改出错,输入的实体没有正确对应的主键,请检查输入。");
  164. }
  165. foreach (var property in properties)
  166. {
  167. if (property.PropertyType.IsPrimitive || property.PropertyType.IsValueType || property.PropertyType.Name.StartsWith("String"))
  168. {
  169. var field = property.Name;
  170. if (setField != "")
  171. {
  172. setField += ",";
  173. }
  174. setField += "[" + field + "]" + "=dest.[" + field + "]";
  175. }
  176. }
  177. if (keyProperty.PropertyType.IsPrimitive || keyProperty.PropertyType.IsValueType || keyProperty.PropertyType.Name.StartsWith("String"))
  178. {
  179. keyExpression = "source.[" + keyProperty.Name + "]" + "=dest.[" + keyProperty.Name + "]";
  180. }
  181. string tmpTableName = "##UpdateTemp" + Guid.NewGuid().ToString().Replace("-", "");
  182. SqlConnection conn = GetConnection();
  183. conn.BulkCopyToTempTable(tmpTableName, data);
  184. string sql = @"update " + tableName + @" set " + setField + @" from " + tableName + @" source inner join " + tmpTableName + @" dest on " + keyExpression;
  185. try
  186. {
  187. var command = new SqlCommand(sql, conn);
  188. command.CommandTimeout = 12000;
  189. command.CommandType = System.Data.CommandType.Text;
  190. command.ExecuteNonQuery();
  191. try
  192. {
  193. command.CommandText = "drop table " + tmpTableName;
  194. command.CommandType = System.Data.CommandType.Text;
  195. command.ExecuteNonQuery();
  196. }
  197. catch { }
  198. logList.ForEach(x => x.IsSuccess = true);
  199. LogUnitOfWork.WriteLogs(logList);
  200. }
  201. catch (Exception)
  202. {
  203. logList.ForEach(x => x.IsSuccess = false);
  204. LogUnitOfWork.WriteLogs(logList);
  205. throw;
  206. }
  207. }
  208. /// <summary>
  209. ///
  210. /// </summary>
  211. /// <typeparam name="TEntity"></typeparam>
  212. /// <param name="data"></param>
  213. public void BulkInsert<TEntity>(IList<TEntity> data) where TEntity : class
  214. {
  215. var logList = DbLog.GetBulkInsertLog(data);
  216. try
  217. {
  218. var db = GetConnection();
  219. data.ExecuteBulkCopy(db, typeof(TEntity).Name);
  220. logList.ForEach(x => x.IsSuccess = true);
  221. LogUnitOfWork.WriteLogs(logList);
  222. }
  223. catch (Exception ex)
  224. {
  225. logList.ForEach(x => x.IsSuccess = false);
  226. LogUnitOfWork.WriteLogs(logList);
  227. throw ex;
  228. }
  229. }
  230. /// <summary>
  231. ///
  232. /// </summary>
  233. /// <typeparam name="TEntity1"></typeparam>
  234. /// <typeparam name="TEntity2"></typeparam>
  235. /// <param name="data"></param>
  236. public void BulkInsert<TEntity1, TEntity2>(IList<Relation2KeyTable> data)
  237. {
  238. var tableName1 = typeof(TEntity1).Name;
  239. var tableName2 = typeof(TEntity2).Name;
  240. var metadata = ((IObjectContextAdapter)this).ObjectContext.MetadataWorkspace;
  241. var associationSet = metadata.GetItemCollection(DataSpace.SSpace)
  242. .GetItems<EntityContainer>().Single()
  243. .AssociationSets.Where(x => x.AssociationSetEnds.Any(w => w.Name == tableName1)
  244. && (x.AssociationSetEnds.Any(w => w.Name == tableName1 + tableName2) || x.AssociationSetEnds.Any(w => w.Name == tableName2 + tableName1))).FirstOrDefault();
  245. if (associationSet == null) { return; }
  246. bool isSourceSet;
  247. var targetSetProperty = typeof(AssociationSet).GetProperty("TargetSet", BindingFlags.Instance | BindingFlags.NonPublic);
  248. var sourceSetProperty = typeof(AssociationSet).GetProperty("SourceSet", BindingFlags.Instance | BindingFlags.NonPublic);
  249. var targetSet = ((System.Data.Entity.Core.Metadata.Edm.EntitySet)(targetSetProperty.GetValue(associationSet, null)));
  250. var sourceSet = ((System.Data.Entity.Core.Metadata.Edm.EntitySet)(sourceSetProperty.GetValue(associationSet, null)));
  251. var tableName = targetSet.Table;
  252. if (tableName == null)
  253. {
  254. tableName = sourceSet.Table;
  255. isSourceSet = false;
  256. if (tableName == null || tableName == tableName1)
  257. {
  258. return;
  259. }
  260. }
  261. else
  262. {
  263. isSourceSet = true;
  264. }
  265. var key1 = TableKeyDictionary.GetKeyName<TEntity1>();
  266. var key2 = TableKeyDictionary.GetKeyName<TEntity2>();
  267. var keyProperty = typeof(TEntity1).GetProperty(key1);
  268. var targetKeyPropery = typeof(TEntity2).GetProperty(key2);
  269. var resultTable = new DataTable(tableName);
  270. var db = GetConnection();
  271. var columnList = db.GetTableColumns(tableName);
  272. if (columnList.First().ToLower() == key1.ToLower())
  273. {
  274. resultTable.Columns.Add(key1, typeof(Guid));
  275. resultTable.Columns.Add(key2, typeof(Guid));
  276. }
  277. else
  278. {
  279. resultTable.Columns.Add(key2, typeof(Guid));
  280. resultTable.Columns.Add(key1, typeof(Guid));
  281. }
  282. foreach (var dataItem in data)
  283. {
  284. var row = resultTable.NewRow();
  285. row[0] = dataItem.Key1;
  286. row[1] = dataItem.Key2;
  287. resultTable.Rows.Add(row);
  288. }
  289. var logList = DbLog.GetBulkInsertLog(resultTable, tableName);
  290. try
  291. {
  292. BulkCopyExtensions.ExecuteBulkCopy(db, resultTable);
  293. logList.ForEach(x => x.IsSuccess = true);
  294. LogUnitOfWork.WriteLogs(logList);
  295. }
  296. catch (Exception ex)
  297. {
  298. logList.ForEach(x => x.IsSuccess = false);
  299. LogUnitOfWork.WriteLogs(logList);
  300. throw ex;
  301. }
  302. }
  303. /// <summary>
  304. ///
  305. /// </summary>
  306. /// <typeparam name="TEntity"></typeparam>
  307. /// <typeparam name="TProperty"></typeparam>
  308. /// <param name="data"></param>
  309. /// <param name="relationShip"></param>
  310. public void BulkInsert<TEntity, TProperty>(IList<TEntity> data, Expression<Func<TEntity, TProperty>> relationShip)
  311. {
  312. if (!typeof(TProperty).FullName.Contains("HashSet"))
  313. {
  314. return;
  315. }
  316. var tableName1 = typeof(TEntity).Name;
  317. var targetProperty = (PropertyInfo)((MemberExpression)relationShip.Body).Member;
  318. var tableName2 = targetProperty.Name;
  319. var metadata = ((IObjectContextAdapter)this).ObjectContext.MetadataWorkspace;
  320. var associationSet = metadata.GetItemCollection(DataSpace.SSpace)
  321. .GetItems<EntityContainer>().Single()
  322. .AssociationSets.Where(x => x.AssociationSetEnds.Any(w => w.Name == tableName1)
  323. && (x.AssociationSetEnds.Any(w => w.Name == tableName1 + tableName2) || x.AssociationSetEnds.Any(w => w.Name == tableName2 + tableName1))).FirstOrDefault();
  324. if (associationSet == null) { return; }
  325. bool isSourceSet;
  326. var targetSetProperty = typeof(AssociationSet).GetProperty("TargetSet", BindingFlags.Instance | BindingFlags.NonPublic);
  327. var sourceSetProperty = typeof(AssociationSet).GetProperty("SourceSet", BindingFlags.Instance | BindingFlags.NonPublic);
  328. var targetSet = ((System.Data.Entity.Core.Metadata.Edm.EntitySet)(targetSetProperty.GetValue(associationSet, null)));
  329. var sourceSet = ((System.Data.Entity.Core.Metadata.Edm.EntitySet)(sourceSetProperty.GetValue(associationSet, null)));
  330. var tableName = targetSet.Table;
  331. if (tableName == null)
  332. {
  333. tableName = sourceSet.Table;
  334. isSourceSet = false;
  335. if (tableName == null || tableName == tableName1)
  336. {
  337. return;
  338. }
  339. }
  340. else
  341. {
  342. isSourceSet = true;
  343. }
  344. var targetElementType = (typeof(TProperty)).GetGenericArguments()[0];
  345. var key1 = TableKeyDictionary.GetKeyName<TEntity>();
  346. var key2 = TableKeyDictionary.GetKeyName(targetElementType.Assembly.CreateInstance(targetElementType.FullName));
  347. var keyProperty = typeof(TEntity).GetProperty(key1);
  348. var targetKeyPropery = targetElementType.GetProperty(key2);
  349. var resultTable = new DataTable(tableName);
  350. var db = GetConnection();
  351. var columnList = db.GetTableColumns(tableName);
  352. if (columnList.First().ToLower() == key1.ToLower())
  353. {
  354. resultTable.Columns.Add(key1, typeof(Guid));
  355. resultTable.Columns.Add(key2, typeof(Guid));
  356. }
  357. else
  358. {
  359. resultTable.Columns.Add(key2, typeof(Guid));
  360. resultTable.Columns.Add(key1, typeof(Guid));
  361. }
  362. foreach (var dataItem in data)
  363. {
  364. IEnumerable targetHashset = (IEnumerable)targetProperty.GetValue(dataItem, null);
  365. foreach (var target in targetHashset)
  366. {
  367. var row = resultTable.NewRow();
  368. if (columnList.First().ToLower() == key1.ToLower())
  369. {
  370. row[0] = (Guid)keyProperty.GetValue(dataItem, null);
  371. row[1] = (Guid)targetKeyPropery.GetValue(target, null);
  372. }
  373. else
  374. {
  375. row[0] = (Guid)targetKeyPropery.GetValue(target, null);
  376. row[1] = (Guid)keyProperty.GetValue(dataItem, null);
  377. }
  378. resultTable.Rows.Add(row);
  379. }
  380. }
  381. var logList = DbLog.GetBulkInsertLog(resultTable, tableName);
  382. try
  383. {
  384. BulkCopyExtensions.ExecuteBulkCopy(db, resultTable);
  385. logList.ForEach(x => x.IsSuccess = true);
  386. LogUnitOfWork.WriteLogs(logList);
  387. }
  388. catch (Exception ex)
  389. {
  390. logList.ForEach(x => x.IsSuccess = false);
  391. LogUnitOfWork.WriteLogs(logList);
  392. throw ex;
  393. }
  394. }
  395. /// <summary>
  396. ///
  397. /// </summary>
  398. /// <returns></returns>
  399. private SqlConnection GetConnection()
  400. {
  401. //var connectionKey = typeof(EMISNewContext).Name;
  402. ////if (!SqlConnectionManager.IsGlobalConnectionStarted)
  403. ////{
  404. //// SqlConnectionManager.InitConnections();
  405. ////}
  406. //return SqlConnectionManager.GetConnection(connectionKey);
  407. return (SqlConnection)((DbContext)this).Database.Connection;
  408. }
  409. public TEntity Remove<TEntity>(TEntity entity) where TEntity : class
  410. {
  411. Set<TEntity>().Attach(entity);
  412. return Set<TEntity>().Remove(entity);
  413. }
  414. public void Remove<TEntity>(Expression<Func<TEntity, bool>> where) where TEntity : class
  415. {
  416. var entities = this.Set<TEntity>().Where(where).ToList();
  417. Set<TEntity>().RemoveRange(entities);
  418. }
  419. public void RemoveRange<TEntity>(HashSet<TEntity> entities) where TEntity : class
  420. {
  421. Set<TEntity>().RemoveRange(entities);
  422. }
  423. void IDisposable.Dispose()
  424. {
  425. Dispose();
  426. }
  427. public void Update<TEntity>(TEntity entity) where TEntity : class
  428. {
  429. Entry<TEntity>(entity).State = System.Data.Entity.EntityState.Modified;
  430. }
  431. public event Action<object> PostUpdate;
  432. public void Update<TEntity>(Expression<Func<TEntity, TEntity>> setExpression, Expression<Func<TEntity, bool>> whereExpression) where TEntity : class
  433. {
  434. var entities = this.Set<TEntity>().Where(whereExpression).ToList();
  435. entities.ForEach(x =>
  436. {
  437. foreach (var binding in ((MemberInitExpression)setExpression.Body).Bindings)
  438. {
  439. PropertyInfo property = (PropertyInfo)binding.Member;
  440. var expression = ((MemberAssignment)binding).Expression;
  441. if (expression is ConstantExpression)
  442. {
  443. property.SetValue(x, ((ConstantExpression)expression).Value, null);
  444. }
  445. else
  446. {
  447. property.SetValue(x, Expression.Lambda(expression, setExpression.Parameters.ToArray()).Compile()
  448. .DynamicInvoke(x), null);
  449. }
  450. }
  451. });
  452. var logList = DbLog.GetBatchUpdateLog(entities, this);
  453. try
  454. {
  455. EntityFramework.Extensions.BatchExtensions.Update(this.Set<TEntity>().Where(whereExpression), setExpression);
  456. logList.ForEach(x => x.IsSuccess = true);
  457. LogUnitOfWork.WriteLogs(logList);
  458. }
  459. catch (Exception ex)
  460. {
  461. logList.ForEach(x => x.IsSuccess = false);
  462. LogUnitOfWork.WriteLogs(logList);
  463. throw ex;
  464. }
  465. }
  466. public void Delete<TEntity>(Expression<Func<TEntity, bool>> whereExpression) where TEntity : class
  467. {
  468. var entities = this.Set<TEntity>().Where(whereExpression).ToList();
  469. if (entities.Count == 0) return;
  470. var logList = DbLog.GetDeleteLog(entities);
  471. try
  472. {
  473. ((DbContext)this).Delete(whereExpression);
  474. logList.ForEach(x => x.IsSuccess = true);
  475. LogUnitOfWork.WriteLogs(logList);
  476. }
  477. catch (Exception ex)
  478. {
  479. logList.ForEach(x => x.IsSuccess = false);
  480. LogUnitOfWork.WriteLogs(logList);
  481. throw ex;
  482. }
  483. //entities.ForEach(x => this.Remove(x));
  484. //this.Commit();
  485. }
  486. public void Delete<TEntity>(IList<TEntity> entityList) where TEntity : class
  487. {
  488. if (entityList.Count == 0) return;
  489. var tableName = typeof(TEntity).Name;
  490. var tableKey = TableKeyDictionary.GetKeyName<TEntity>();
  491. var logList = DbLog.GetDeleteLog(Bowin.Common.Data.ConvertToDataTable.ToTable(entityList), tableName);
  492. try
  493. {
  494. var db = GetConnection();
  495. string tmpTableName = "##DeleteTemp" + Guid.NewGuid().ToString().Replace("-", "");
  496. db.BulkCopyToTempTable(tmpTableName, entityList);
  497. string sql = @"
  498. delete t
  499. from " + tableName + @" t
  500. inner join " + tmpTableName + @" tmp on
  501. t.[" + tableKey + "]=tmp.[" + tableKey + "]";
  502. var command = new SqlCommand(sql, db);
  503. command.CommandTimeout = 12000;
  504. command.CommandType = CommandType.Text;
  505. command.ExecuteNonQuery();
  506. command.CommandText = "drop table " + tmpTableName;
  507. command.CommandType = System.Data.CommandType.Text;
  508. command.ExecuteNonQuery();
  509. logList.ForEach(x => x.IsSuccess = true);
  510. LogUnitOfWork.WriteLogs(logList);
  511. }
  512. catch (Exception ex)
  513. {
  514. logList.ForEach(x => x.IsSuccess = false);
  515. LogUnitOfWork.WriteLogs(logList);
  516. throw ex;
  517. }
  518. }
  519. public void Delete<TEntity, TProperty>(IList<TEntity> entityList, Expression<Func<TEntity, TProperty>> relationShip)
  520. {
  521. if (entityList.Count == 0) return;
  522. if (!typeof(TProperty).FullName.Contains("HashSet"))
  523. {
  524. return;
  525. }
  526. var tableName1 = typeof(TEntity).Name;
  527. var targetProperty = (PropertyInfo)((MemberExpression)relationShip.Body).Member;
  528. var tableName2 = targetProperty.Name;
  529. var metadata = ((IObjectContextAdapter)this).ObjectContext.MetadataWorkspace;
  530. var associationSet = metadata.GetItemCollection(DataSpace.SSpace)
  531. .GetItems<EntityContainer>().Single()
  532. .AssociationSets.Where(x => x.AssociationSetEnds.Any(w => w.Name == tableName1)
  533. && (x.AssociationSetEnds.Any(w => w.Name == tableName1 + tableName2) || x.AssociationSetEnds.Any(w => w.Name == tableName2 + tableName1))).FirstOrDefault();
  534. if (associationSet == null) { return; }
  535. bool isSourceSet;
  536. var targetSetProperty = typeof(AssociationSet).GetProperty("TargetSet", BindingFlags.Instance | BindingFlags.NonPublic);
  537. var sourceSetProperty = typeof(AssociationSet).GetProperty("SourceSet", BindingFlags.Instance | BindingFlags.NonPublic);
  538. var targetSet = ((System.Data.Entity.Core.Metadata.Edm.EntitySet)(targetSetProperty.GetValue(associationSet, null)));
  539. var sourceSet = ((System.Data.Entity.Core.Metadata.Edm.EntitySet)(sourceSetProperty.GetValue(associationSet, null)));
  540. var tableName = targetSet.Table;
  541. if (tableName == null)
  542. {
  543. tableName = sourceSet.Table;
  544. isSourceSet = false;
  545. if (tableName == null || tableName == tableName1)
  546. {
  547. return;
  548. }
  549. }
  550. else
  551. {
  552. isSourceSet = true;
  553. }
  554. var targetElementType = (typeof(TProperty)).GetGenericArguments()[0];
  555. var key1 = TableKeyDictionary.GetKeyName<TEntity>();
  556. var key2 = TableKeyDictionary.GetKeyName(targetElementType.Assembly.CreateInstance(targetElementType.FullName));
  557. var keyProperty = typeof(TEntity).GetProperty(key1);
  558. var targetKeyPropery = targetElementType.GetProperty(key2);
  559. var resultTable = new DataTable(tableName);
  560. if (isSourceSet)
  561. {
  562. resultTable.Columns.Add(key1, typeof(Guid));
  563. resultTable.Columns.Add(key2, typeof(Guid));
  564. }
  565. else
  566. {
  567. resultTable.Columns.Add(key2, typeof(Guid));
  568. resultTable.Columns.Add(key1, typeof(Guid));
  569. }
  570. List<Guid> keyList = new List<Guid>();
  571. foreach (var entity in entityList)
  572. {
  573. IEnumerable targetHashset = (IEnumerable)targetProperty.GetValue(entity, null);
  574. foreach (var target in targetHashset)
  575. {
  576. var row = resultTable.NewRow();
  577. if (isSourceSet)
  578. {
  579. row[0] = (Guid)keyProperty.GetValue(entity, null);
  580. row[1] = (Guid)targetKeyPropery.GetValue(target, null);
  581. }
  582. else
  583. {
  584. row[0] = (Guid)targetKeyPropery.GetValue(target, null);
  585. row[1] = (Guid)keyProperty.GetValue(entity, null);
  586. }
  587. keyList.Add((Guid)keyProperty.GetValue(entity, null));
  588. resultTable.Rows.Add(row);
  589. }
  590. }
  591. var logList = DbLog.GetDeleteLog(resultTable, tableName);
  592. try
  593. {
  594. var db = GetConnection();
  595. string tmpTableName = "##DeleteTemp" + Guid.NewGuid().ToString().Replace("-", "");
  596. db.BulkCopyToTempTable(tmpTableName, keyList, keyProperty.Name);
  597. string sql = @"
  598. delete t
  599. from " + tableName + @" t
  600. inner join " + tmpTableName + @" tmp on
  601. t.[" + keyProperty.Name + "]=tmp.[" + keyProperty.Name + "]";
  602. var command = new SqlCommand(sql, db);
  603. command.CommandTimeout = 12000;
  604. command.CommandType = CommandType.Text;
  605. command.ExecuteNonQuery();
  606. command.CommandText = "drop table " + tmpTableName;
  607. command.CommandType = System.Data.CommandType.Text;
  608. command.ExecuteNonQuery();
  609. logList.ForEach(x => x.IsSuccess = true);
  610. LogUnitOfWork.WriteLogs(logList);
  611. }
  612. catch (Exception ex)
  613. {
  614. logList.ForEach(x => x.IsSuccess = false);
  615. LogUnitOfWork.WriteLogs(logList);
  616. throw ex;
  617. }
  618. }
  619. public void Delete<TEntity, TProperty>(TEntity entity, Expression<Func<TEntity, TProperty>> relationShip)
  620. {
  621. if (entity == null) return;
  622. if (!typeof(TProperty).FullName.Contains("HashSet"))
  623. {
  624. return;
  625. }
  626. var tableName1 = typeof(TEntity).Name;
  627. var targetProperty = (PropertyInfo)((MemberExpression)relationShip.Body).Member;
  628. var tableName2 = targetProperty.Name;
  629. var metadata = ((IObjectContextAdapter)this).ObjectContext.MetadataWorkspace;
  630. var associationSet = metadata.GetItemCollection(DataSpace.SSpace)
  631. .GetItems<EntityContainer>().Single()
  632. .AssociationSets.Where(x => x.AssociationSetEnds.Any(w => w.Name == tableName1)
  633. && (x.AssociationSetEnds.Any(w => w.Name == tableName1 + tableName2) || x.AssociationSetEnds.Any(w => w.Name == tableName2 + tableName1))).FirstOrDefault();
  634. if (associationSet == null) { return; }
  635. bool isSourceSet;
  636. var targetSetProperty = typeof(AssociationSet).GetProperty("TargetSet", BindingFlags.Instance | BindingFlags.NonPublic);
  637. var sourceSetProperty = typeof(AssociationSet).GetProperty("SourceSet", BindingFlags.Instance | BindingFlags.NonPublic);
  638. var targetSet = ((System.Data.Entity.Core.Metadata.Edm.EntitySet)(targetSetProperty.GetValue(associationSet, null)));
  639. var sourceSet = ((System.Data.Entity.Core.Metadata.Edm.EntitySet)(sourceSetProperty.GetValue(associationSet, null)));
  640. var tableName = targetSet.Table;
  641. if (tableName == null)
  642. {
  643. tableName = sourceSet.Table;
  644. isSourceSet = false;
  645. if (tableName == null || tableName == tableName1)
  646. {
  647. return;
  648. }
  649. }
  650. else
  651. {
  652. isSourceSet = true;
  653. }
  654. var targetElementType = (typeof(TProperty)).GetGenericArguments()[0];
  655. var key1 = TableKeyDictionary.GetKeyName<TEntity>();
  656. var key2 = TableKeyDictionary.GetKeyName(targetElementType.Assembly.CreateInstance(targetElementType.FullName));
  657. var keyProperty = typeof(TEntity).GetProperty(key1);
  658. var targetKeyPropery = targetElementType.GetProperty(key2);
  659. var resultTable = new DataTable(tableName);
  660. if (isSourceSet)
  661. {
  662. resultTable.Columns.Add(key1, typeof(Guid));
  663. resultTable.Columns.Add(key2, typeof(Guid));
  664. }
  665. else
  666. {
  667. resultTable.Columns.Add(key2, typeof(Guid));
  668. resultTable.Columns.Add(key1, typeof(Guid));
  669. }
  670. IEnumerable targetHashset = (IEnumerable)targetProperty.GetValue(entity, null);
  671. foreach (var target in targetHashset)
  672. {
  673. var row = resultTable.NewRow();
  674. if (isSourceSet)
  675. {
  676. row[0] = (Guid)keyProperty.GetValue(entity, null);
  677. row[1] = (Guid)targetKeyPropery.GetValue(target, null);
  678. }
  679. else
  680. {
  681. row[0] = (Guid)targetKeyPropery.GetValue(target, null);
  682. row[1] = (Guid)keyProperty.GetValue(entity, null);
  683. }
  684. resultTable.Rows.Add(row);
  685. }
  686. var logList = DbLog.GetDeleteLog(resultTable, tableName);
  687. try
  688. {
  689. var db = GetConnection();
  690. db.Delete(tableName, key1, (Guid)keyProperty.GetValue(entity, null));
  691. logList.ForEach(x => x.IsSuccess = true);
  692. LogUnitOfWork.WriteLogs(logList);
  693. }
  694. catch (Exception ex)
  695. {
  696. logList.ForEach(x => x.IsSuccess = false);
  697. LogUnitOfWork.WriteLogs(logList);
  698. throw ex;
  699. }
  700. }
  701. int ExecuteSQL(string sql, params object[] parameters)
  702. {
  703. return this.Database.ExecuteSqlCommand(sql, parameters);
  704. }
  705. public void BatchUpdate<TKey>(string tableName, string columnName, object value, IList<TKey> idList)
  706. {
  707. var assembly = typeof(EMISNewContext).Assembly;
  708. var entityType = assembly.GetTypes().Where(x => x.Name.ToLower() == tableName.ToLower()).FirstOrDefault();
  709. var methodInfo = typeof(UnitOfWork).GetMethods()
  710. .Where(x => x.ContainsGenericParameters && x.GetGenericArguments().Length == 2 && x.Name == "BatchUpdate"
  711. && x.GetParameters().Length == 3).FirstOrDefault();
  712. methodInfo = methodInfo
  713. .MakeGenericMethod(entityType, typeof(TKey));
  714. methodInfo.Invoke(this, new object[] { columnName, value, idList });
  715. }
  716. public void BatchUpdate<TEntity, TKey>(string columnName, object value, IList<TKey> idList) where TEntity : class
  717. {
  718. var curUser = EMIS.Utility.FormValidate.CustomPrincipal.Current;
  719. ExpressionFactory<TEntity> factory = new ExpressionFactory<TEntity>(Set<TEntity>());
  720. var para = Expression.Parameter(typeof(TEntity));
  721. var property = typeof(TEntity).GetProperty(columnName);
  722. var modifytime = typeof(TEntity).GetProperty("ModifyTime");
  723. var modifyuser = typeof(TEntity).GetProperty("ModifyUserID");
  724. object timevalue = DateTime.Now;
  725. object uservalue = curUser.UserID;
  726. MemberInitExpression memberExpression;
  727. if (modifytime != null)
  728. {
  729. var newExpression = Expression.New(typeof(TEntity).GetConstructor(new Type[] { }));
  730. var bindExpression = Expression.Bind(property, GetValueExpression(value, property));
  731. var timebindExpression = Expression.Bind(modifytime, GetValueExpression(timevalue, modifytime));
  732. var userbindExpression = Expression.Bind(modifyuser, GetValueExpression(uservalue, modifyuser));
  733. memberExpression = Expression.MemberInit(newExpression, new MemberBinding[] { bindExpression, timebindExpression, userbindExpression });
  734. }
  735. else
  736. {
  737. var newExpression = Expression.New(typeof(TEntity).GetConstructor(new Type[] { }));
  738. var bindExpression = Expression.Bind(property, GetValueExpression(value, property));
  739. memberExpression = Expression.MemberInit(newExpression, new MemberBinding[] { bindExpression });
  740. }
  741. Expression<Func<TEntity, TEntity>> setExpression = Expression.Lambda<Func<TEntity, TEntity>>(memberExpression, para);
  742. Expression<Func<TEntity, bool>> whereExpression = factory.DynamicInExpression(TableKeyDictionary.GetKeyName<TEntity>(), idList);
  743. this.Update(setExpression, whereExpression);
  744. }
  745. public void BatchUpdate<TKey>(string tableName, IDictionary<string, object> valueList, IList<TKey> idList)
  746. {
  747. var assembly = typeof(EMISNewContext).Assembly;
  748. var entityType = assembly.GetTypes().Where(x => x.Name.ToLower() == tableName.ToLower()).FirstOrDefault();
  749. var methodInfo = typeof(UnitOfWork).GetMethods()
  750. .Where(x => x.ContainsGenericParameters && x.GetGenericArguments().Length == 2 && x.Name == "BatchUpdate"
  751. && x.GetParameters().Length == 2).FirstOrDefault();
  752. methodInfo = methodInfo
  753. .MakeGenericMethod(entityType, typeof(TKey));
  754. methodInfo.Invoke(this, new object[] { valueList, idList });
  755. }
  756. public void BatchUpdate<TEntity, TKey>(IDictionary<string, object> valueList, IList<TKey> idList) where TEntity : class
  757. {
  758. var curUser = EMIS.Utility.FormValidate.CustomPrincipal.Current;
  759. ExpressionFactory<TEntity> factory = new ExpressionFactory<TEntity>(Set<TEntity>());
  760. var para = Expression.Parameter(typeof(TEntity));
  761. var newExpression = Expression.New(typeof(TEntity).GetConstructor(new Type[] { }));
  762. var memberBindingList = new List<MemberBinding>();
  763. foreach (var keyValue in valueList)
  764. {
  765. var property = typeof(TEntity).GetProperty(keyValue.Key);
  766. var bindExpression = Expression.Bind(property, GetValueExpression(keyValue.Value, property));
  767. memberBindingList.Add(bindExpression);
  768. }
  769. var modifytime = typeof(TEntity).GetProperty("ModifyTime");
  770. var modifyuser = typeof(TEntity).GetProperty("ModifyUserID");
  771. if (modifytime != null)
  772. {
  773. object timevalue = DateTime.Now;
  774. var timebindExpression = Expression.Bind(modifytime, GetValueExpression(timevalue, modifytime));
  775. memberBindingList.Add(timebindExpression);
  776. }
  777. if (modifyuser != null)
  778. {
  779. object uservalue = curUser.UserID;
  780. var userbindExpression = Expression.Bind(modifyuser, GetValueExpression(uservalue, modifyuser));
  781. memberBindingList.Add(userbindExpression);
  782. }
  783. var memberExpression = Expression.MemberInit(newExpression, memberBindingList.ToArray());
  784. Expression<Func<TEntity, TEntity>> setExpression = Expression.Lambda<Func<TEntity, TEntity>>(memberExpression, para);
  785. Expression<Func<TEntity, bool>> whereExpression = factory.DynamicInExpression(TableKeyDictionary.GetKeyName<TEntity>(), idList);
  786. this.Update(setExpression, whereExpression);
  787. }
  788. private Expression GetValueExpression(object value, PropertyInfo property)
  789. {
  790. if (property.PropertyType == typeof(Guid) || property.PropertyType == typeof(Guid?))
  791. {
  792. return Expression.Constant(Guid.Parse(value.ToString()));
  793. }
  794. else if (property.PropertyType == typeof(int) || property.PropertyType == typeof(int?))
  795. {
  796. return Expression.Constant(int.Parse(value.ToString()));
  797. }
  798. else if (property.PropertyType == typeof(short) || property.PropertyType == typeof(short?))
  799. {
  800. return Expression.Constant(short.Parse(value.ToString()));
  801. }
  802. else if (property.PropertyType == typeof(bool) || property.PropertyType == typeof(bool?))
  803. {
  804. if (value.Equals("1") || value.Equals("0"))
  805. return Expression.Constant(value.Equals("1"));
  806. return Expression.Constant(bool.Parse(value.ToString()));
  807. }
  808. else if (property.PropertyType == typeof(decimal) || property.PropertyType == typeof(decimal?))
  809. {
  810. return Expression.Constant(decimal.Parse(value.ToString()));
  811. }
  812. else if (property.PropertyType == typeof(DateTime) || property.PropertyType == typeof(DateTime?))
  813. {
  814. return Expression.Constant(DateTime.Parse(value.ToString()));
  815. }
  816. else
  817. {
  818. return Expression.Convert(Expression.Constant(value), property.PropertyType);
  819. }
  820. }
  821. public DataSet QuerySQL(string sql,List<SqlParameter> sParams) {
  822. var db = GetConnection();
  823. if (db.State == ConnectionState.Closed)
  824. {
  825. db.Open();
  826. }
  827. DataSet ds = new DataSet();
  828. try
  829. {
  830. SqlCommand comm = new SqlCommand(sql, db);
  831. if (sParams != null && sParams.Count > 0)
  832. {
  833. sParams.ForEach(p =>
  834. {
  835. comm.Parameters.Add(p);
  836. });
  837. }
  838. SqlDataAdapter adapter = new SqlDataAdapter();
  839. adapter.SelectCommand = comm;
  840. adapter.Fill(ds);
  841. //adapter.
  842. }
  843. catch(Exception ex)
  844. {
  845. var a = ex;
  846. }
  847. return ds;
  848. }
  849. }
  850. public class Relation2KeyTable
  851. {
  852. public Guid Key1 { get; set; }
  853. public Guid Key2 { get; set; }
  854. }
  855. }