From b921231cb7820aedbcb7de4f02ea10e9a55f8c5d Mon Sep 17 00:00:00 2001 From: 28810 <28810@YEXIANGQIN> Date: Mon, 6 May 2019 21:02:15 +0800 Subject: [PATCH] =?UTF-8?q?-=20=E8=A1=A5=E5=85=85=20IFreeSql=20=E5=A2=9E?= =?UTF-8?q?=E5=8A=A0=E4=B8=8E=E5=AE=9E=E7=8E=B0=20IDisposable=20=E6=8E=A5?= =?UTF-8?q?=E5=8F=A3=EF=BC=88=E4=BE=9D=E7=84=B6=E8=A6=81=E4=BF=9D=E6=8C=81?= =?UTF-8?q?=E5=8D=95=E4=BE=8B=E7=9A=84=E4=BD=BF=E7=94=A8=E4=B9=A0=E6=83=AF?= =?UTF-8?q?=EF=BC=89=EF=BC=9B=20-=20=E5=A2=9E=E5=8A=A0=20CurdBefore?= =?UTF-8?q?=E3=80=81CurdAfter=20AOP=20=E6=96=B9=E6=B3=95=EF=BC=8C=E5=8F=AF?= =?UTF-8?q?=E7=9B=91=E6=8E=A7=E6=89=A7=E8=A1=8C=E5=A2=9E=E5=88=A0=E6=9F=A5?= =?UTF-8?q?=E6=94=B9=EF=BC=9B=20-=20=E5=A2=9E=E5=8A=A0=20SyncStructureBefo?= =?UTF-8?q?re=E3=80=81SyncStructureAfter=20AOP=20=E6=96=B9=E6=B3=95?= =?UTF-8?q?=EF=BC=8C=E5=8F=AF=E7=9B=91=E6=8E=A7CodeFirst=E8=BF=81=E7=A7=BB?= =?UTF-8?q?=EF=BC=9B?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../PostgreSQLExpression/OtherTest.cs | 4 + FreeSql/FreeSql.xml | 90 +++++--- FreeSql/Interface/IAop.cs | 176 +++++++++------ FreeSql/Internal/CommonExpression.cs | 2 +- .../Internal/CommonProvider/AopProvider.cs | 18 +- .../Internal/CommonProvider/DeleteProvider.cs | 34 ++- .../Internal/CommonProvider/InsertProvider.cs | 32 ++- .../SelectProvider/Select0Provider.cs | 210 +++++++++++++----- .../Internal/CommonProvider/UpdateProvider.cs | 40 +++- FreeSql/Internal/CommonUtils.cs | 4 +- FreeSql/MySql/Curd/MySqlDelete.cs | 31 ++- FreeSql/MySql/Curd/MySqlInsert.cs | 65 +++++- FreeSql/MySql/Curd/MySqlUpdate.cs | 37 ++- FreeSql/MySql/MySqlCodeFirst.cs | 26 ++- FreeSql/Oracle/Curd/OracleInsert.cs | 72 +++++- FreeSql/Oracle/OracleCodeFirst.cs | 26 ++- FreeSql/PostgreSQL/Curd/PostgreSQLDelete.cs | 31 ++- FreeSql/PostgreSQL/Curd/PostgreSQLInsert.cs | 101 +++++++-- FreeSql/PostgreSQL/Curd/PostgreSQLUpdate.cs | 37 ++- FreeSql/PostgreSQL/PostgreSQLCodeFirst.cs | 26 ++- FreeSql/SqlServer/Curd/SqlServerDelete.cs | 30 ++- FreeSql/SqlServer/Curd/SqlServerInsert.cs | 68 +++++- FreeSql/SqlServer/Curd/SqlServerUpdate.cs | 36 ++- FreeSql/SqlServer/SqlServerCodeFirst.cs | 26 ++- FreeSql/Sqlite/Curd/SqliteInsert.cs | 36 ++- FreeSql/Sqlite/SqliteCodeFirst.cs | 26 ++- 26 files changed, 981 insertions(+), 303 deletions(-) diff --git a/FreeSql.Tests/PostgreSQL/PostgreSQLExpression/OtherTest.cs b/FreeSql.Tests/PostgreSQL/PostgreSQLExpression/OtherTest.cs index 766d478b..aa45e936 100644 --- a/FreeSql.Tests/PostgreSQL/PostgreSQLExpression/OtherTest.cs +++ b/FreeSql.Tests/PostgreSQL/PostgreSQLExpression/OtherTest.cs @@ -6,6 +6,7 @@ using NpgsqlTypes; using System; using System.Collections; using System.Collections.Generic; +using System.Diagnostics; using System.Linq; using System.Net; using System.Net.NetworkInformation; @@ -37,6 +38,9 @@ namespace FreeSql.Tests.PostgreSQLExpression { [Fact] public void Array() { + //g.pgsql.Aop.CurdAfter = (s, e) => { + // Trace.WriteLine(e.CurdType + ": " + e.ElapsedMilliseconds + "ms " + e.Sql.Replace("\n", "")); + //}; IEnumerable testlinqlist = new List(new[] { 1, 2, 3 }); var testlinq = select.Where(a => testlinqlist.Contains(a.testFieldInt)).ToList(); diff --git a/FreeSql/FreeSql.xml b/FreeSql/FreeSql.xml index 0a68971a..515e14e5 100644 --- a/FreeSql/FreeSql.xml +++ b/FreeSql/FreeSql.xml @@ -1882,129 +1882,149 @@ 自定义实体的属性配置,方便和多个 ORM 共同使用 - + - IUpdate 执行成功后触发 + 增删查改,执行命令之前触发 - + - IInsert 执行成功后触发 + 增删查改,执行命令完成后触发 - + - IDeleted 执行成功后触发 + CodeFirst迁移,执行之前触发 - + - ISelect 执行成功后触发 + CodeFirst迁移,执行完成触发 - + 可重新装饰的引用数据 - + 可使上层不被执行这个条件 - + 内置解析功能,可辅助您进行解析 - + 需要您解析的表达式 - + 解析后的内容 - + 实体类型 - + 实体配置 - + 实体类型 - + 实体的属性 - + 实体的属性配置 - + - 更新的实体 + 标识符,可将 CurdBefore 与 CurdAfter 进行匹配 - + - 执行 ExecuteIdentity 方法时有效 + 操作类型 - + 实体类型 - + 执行的 SQL - + 参数化命令 - + - 执行 ExecuteAffrows 方法时有效 + 发生的错误 - + - 执行 ExecuteDeleted 方法时有效 + 执行SQL命令,返回的结果 - + + + 耗时(单位:Ticks) + + + + + 耗时(单位:毫秒) + + + + + 标识符,可将 SyncStructureBeforeEventArgs 与 SyncStructureAfterEventArgs 进行匹配 + + + 实体类型 - + 执行的 SQL - + - 参数化命令 + 发生的错误 - + - 查询返回的对象 + 耗时(单位:Ticks) + + + + + 耗时(单位:毫秒) diff --git a/FreeSql/Interface/IAop.cs b/FreeSql/Interface/IAop.cs index d27d2326..6fb82996 100644 --- a/FreeSql/Interface/IAop.cs +++ b/FreeSql/Interface/IAop.cs @@ -3,6 +3,7 @@ using FreeSql.DatabaseModel; using System; using System.Collections.Generic; using System.Data.Common; +using System.Diagnostics; using System.Linq.Expressions; using System.Reflection; @@ -12,47 +13,50 @@ namespace FreeSql { /// /// 监控 ToList 返回的的数据,用于拦截重新装饰 /// - EventHandler ToList { get; set; } + EventHandler ToList { get; set; } /// /// 监视 Where,包括 select/update/delete,可控制使上层不被执行。 /// - EventHandler Where { get; set; } + EventHandler Where { get; set; } /// /// 可自定义解析表达式 /// - EventHandler ParseExpression { get; set; } + EventHandler ParseExpression { get; set; } /// /// 自定义实体的配置,方便和多个 ORM 共同使用 /// - EventHandler ConfigEntity { get; set; } + EventHandler ConfigEntity { get; set; } /// /// 自定义实体的属性配置,方便和多个 ORM 共同使用 /// - EventHandler ConfigEntityProperty { get; set; } + EventHandler ConfigEntityProperty { get; set; } /// - /// IUpdate 执行成功后触发 + /// 增删查改,执行命令之前触发 /// - EventHandler OnUpdated { get; set; } + EventHandler CurdBefore { get; set; } /// - /// IInsert 执行成功后触发 + /// 增删查改,执行命令完成后触发 /// - EventHandler OnInserted { get; set; } + EventHandler CurdAfter { get; set; } + /// - /// IDeleted 执行成功后触发 + /// CodeFirst迁移,执行之前触发 /// - EventHandler OnDeleted { get; set; } + EventHandler SyncStructureBefore { get; set; } /// - /// ISelect 执行成功后触发 + /// CodeFirst迁移,执行完成触发 /// - EventHandler OnSelected { get; set; } + EventHandler SyncStructureAfter { get; set; } } +} - public class AopToListEventArgs : EventArgs { - public AopToListEventArgs(object list) { +namespace FreeSql.Aop { + public class ToListEventArgs : EventArgs { + public ToListEventArgs(object list) { this.List = list; } /// @@ -60,8 +64,8 @@ namespace FreeSql { /// public object List { get; } } - public class AopWhereEventArgs : EventArgs { - public AopWhereEventArgs(params object[] parameters) { + public class WhereEventArgs : EventArgs { + public WhereEventArgs(params object[] parameters) { this.Parameters = parameters; } public object[] Parameters { get; } @@ -70,8 +74,8 @@ namespace FreeSql { /// public bool IsCancel { get; set; } } - public class AopParseExpressionEventArgs : EventArgs { - public AopParseExpressionEventArgs(Expression expression, Func freeParse) { + public class ParseExpressionEventArgs : EventArgs { + public ParseExpressionEventArgs(Expression expression, Func freeParse) { this.Expression = expression; this.FreeParse = freeParse; } @@ -90,8 +94,8 @@ namespace FreeSql { /// public string Result { get; set; } } - public class AopConfigEntityEventArgs : EventArgs { - public AopConfigEntityEventArgs(Type entityType) { + public class ConfigEntityEventArgs : EventArgs { + public ConfigEntityEventArgs(Type entityType) { this.EntityType = entityType; this.ModifyResult = new TableAttribute(); } @@ -105,8 +109,8 @@ namespace FreeSql { /// public TableAttribute ModifyResult { get; } } - public class AopConfigEntityPropertyEventArgs : EventArgs { - public AopConfigEntityPropertyEventArgs(Type entityType, PropertyInfo property) { + public class ConfigEntityPropertyEventArgs : EventArgs { + public ConfigEntityPropertyEventArgs(Type entityType, PropertyInfo property) { this.EntityType = entityType; this.Property = property; this.ModifyResult = new ColumnAttribute(); @@ -126,38 +130,30 @@ namespace FreeSql { public ColumnAttribute ModifyResult { get; } } - public class AopOnUpdatedEventArgs : AopOnDeletedEventArgs { - public AopOnUpdatedEventArgs(Type entityType, object source, string sql, DbParameter[] dbParms, int affrows, object returning) - : base(entityType, sql, dbParms, affrows, returning) { - this.Source = source; + public class CurdBeforeEventArgs : EventArgs { + public CurdBeforeEventArgs(Type entityType, CurdType curdType, string sql, DbParameter[] dbParms) : + this(Guid.NewGuid(), new Stopwatch(), entityType, curdType, sql, dbParms) { + this.Stopwatch.Start(); } - - /// - /// 更新的实体 - /// - public object Source { get; } - } - public class AopOnInsertedEventArgs : AopOnUpdatedEventArgs { - public AopOnInsertedEventArgs(Type entityType, object source, string sql, DbParameter[] dbParms, int affrows, long identity, object returning) - : base(entityType, source, sql, dbParms, affrows, returning) { - this.Identity = identity; - } - - /// - /// 执行 ExecuteIdentity 方法时有效 - /// - public long? Identity { get; set; } - } - - public class AopOnDeletedEventArgs : EventArgs { - public AopOnDeletedEventArgs(Type entityType, string sql, DbParameter[] dbParms, int affrows, object returning) { + protected CurdBeforeEventArgs(Guid identifier, Stopwatch stopwatch, Type entityType, CurdType curdType, string sql, DbParameter[] dbParms) { + this.Identifier = identifier; + this.Stopwatch = stopwatch; this.EntityType = entityType; + this.CurdType = curdType; this.Sql = sql; this.DbParms = dbParms; - this.Affrows = affrows; - this.Returning = returning; } + /// + /// 标识符,可将 CurdBefore 与 CurdAfter 进行匹配 + /// + public Guid Identifier { get; protected set; } + protected Stopwatch Stopwatch { get; } + internal Stopwatch StopwatchInternal => Stopwatch; + /// + /// 操作类型 + /// + public CurdType CurdType { get; } /// /// 实体类型 /// @@ -170,39 +166,79 @@ namespace FreeSql { /// 参数化命令 /// public DbParameter[] DbParms { get; } - /// - /// 执行 ExecuteAffrows 方法时有效 - /// - public int Affrows { get; } - /// - /// 执行 ExecuteDeleted 方法时有效 - /// - public object Returning { get; } } - - public class AopOnSelectedEventArgs : EventArgs { - public AopOnSelectedEventArgs(Type entityType, string sql, DbParameter[] dbParms, object returnData) { - this.EntityType = entityType; - this.Sql = sql; - this.DbParms = dbParms; - this.ReturnData = returnData; + public enum CurdType { Select, Delete, Update, Insert } + public class CurdAfterEventArgs : CurdBeforeEventArgs { + public CurdAfterEventArgs(CurdBeforeEventArgs before, Exception exception, object executeResult) : + base(before.Identifier, before.StopwatchInternal, before.EntityType, before.CurdType, before.Sql, before.DbParms) { + this.Exception = exception; + this.ExecuteResult = executeResult; + this.Stopwatch.Stop(); } + /// + /// 发生的错误 + /// + public Exception Exception { get; } + /// + /// 执行SQL命令,返回的结果 + /// + public object ExecuteResult { get; set; } + /// + /// 耗时(单位:Ticks) + /// + public long ElapsedTicks => this.Stopwatch.ElapsedTicks; + /// + /// 耗时(单位:毫秒) + /// + public long ElapsedMilliseconds => this.Stopwatch.ElapsedMilliseconds; + } + + public class SyncStructureBeforeEventArgs : EventArgs { + public SyncStructureBeforeEventArgs(Type[] entityTypes) : + this(Guid.NewGuid(), new Stopwatch(), entityTypes) { + this.Stopwatch.Start(); + } + protected SyncStructureBeforeEventArgs(Guid identifier, Stopwatch stopwatch, Type[] entityTypes) { + this.Identifier = identifier; + this.Stopwatch = stopwatch; + this.EntityTypes = entityTypes; + } + + /// + /// 标识符,可将 SyncStructureBeforeEventArgs 与 SyncStructureAfterEventArgs 进行匹配 + /// + public Guid Identifier { get; protected set; } + protected Stopwatch Stopwatch { get; } + internal Stopwatch StopwatchInternal => Stopwatch; /// /// 实体类型 /// - public Type EntityType { get; } + public Type[] EntityTypes { get; } + } + public class SyncStructureAfterEventArgs : SyncStructureBeforeEventArgs { + public SyncStructureAfterEventArgs(SyncStructureBeforeEventArgs before, string sql, Exception exception) : + base(before.Identifier, before.StopwatchInternal, before.EntityTypes) { + this.Sql = sql; + this.Exception = exception; + this.Stopwatch.Stop(); + } + /// /// 执行的 SQL /// public string Sql { get; } /// - /// 参数化命令 + /// 发生的错误 /// - public DbParameter[] DbParms { get; } + public Exception Exception { get; } /// - /// 查询返回的对象 + /// 耗时(单位:Ticks) /// - public object ReturnData { get; } + public long ElapsedTicks => this.Stopwatch.ElapsedTicks; + /// + /// 耗时(单位:毫秒) + /// + public long ElapsedMilliseconds => this.Stopwatch.ElapsedMilliseconds; } -} +} \ No newline at end of file diff --git a/FreeSql/Internal/CommonExpression.cs b/FreeSql/Internal/CommonExpression.cs index b4ff8006..972b252e 100644 --- a/FreeSql/Internal/CommonExpression.cs +++ b/FreeSql/Internal/CommonExpression.cs @@ -392,7 +392,7 @@ namespace FreeSql.Internal { internal string ExpressionLambdaToSql(Expression exp, ExpTSC tsc) { if (exp == null) return ""; if (tsc.isDisableDiyParse == false && _common._orm.Aop.ParseExpression != null) { - var args = new AopParseExpressionEventArgs(exp, ukexp => ExpressionLambdaToSql(exp, tsc.CloneDisableDiyParse())); + var args = new Aop.ParseExpressionEventArgs(exp, ukexp => ExpressionLambdaToSql(exp, tsc.CloneDisableDiyParse())); _common._orm.Aop.ParseExpression?.Invoke(this, args); if (string.IsNullOrEmpty(args.Result) == false) return args.Result; } diff --git a/FreeSql/Internal/CommonProvider/AopProvider.cs b/FreeSql/Internal/CommonProvider/AopProvider.cs index 98cca135..f7a8faf7 100644 --- a/FreeSql/Internal/CommonProvider/AopProvider.cs +++ b/FreeSql/Internal/CommonProvider/AopProvider.cs @@ -6,14 +6,14 @@ using System.Text; namespace FreeSql.Internal.CommonProvider { class AopProvider : IAop { - public EventHandler ToList { get; set; } - public EventHandler Where { get; set; } - public EventHandler ParseExpression { get; set; } - public EventHandler ConfigEntity { get; set; } - public EventHandler ConfigEntityProperty { get; set; } - public EventHandler OnUpdated { get; set; } - public EventHandler OnInserted { get; set; } - public EventHandler OnDeleted { get; set; } - public EventHandler OnSelected { get; set; } + public EventHandler ToList { get; set; } + public EventHandler Where { get; set; } + public EventHandler ParseExpression { get; set; } + public EventHandler ConfigEntity { get; set; } + public EventHandler ConfigEntityProperty { get; set; } + public EventHandler CurdBefore { get; set; } + public EventHandler CurdAfter { get; set; } + public EventHandler SyncStructureBefore { get; set; } + public EventHandler SyncStructureAfter { get; set; } } } diff --git a/FreeSql/Internal/CommonProvider/DeleteProvider.cs b/FreeSql/Internal/CommonProvider/DeleteProvider.cs index 25292bf7..dfd38adb 100644 --- a/FreeSql/Internal/CommonProvider/DeleteProvider.cs +++ b/FreeSql/Internal/CommonProvider/DeleteProvider.cs @@ -51,8 +51,19 @@ namespace FreeSql.Internal.CommonProvider { var sql = this.ToSql(); if (string.IsNullOrEmpty(sql)) return 0; var dbParms = _params.ToArray(); - var affrows = _orm.Ado.ExecuteNonQuery(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnDeleted?.Invoke(this, new AopOnDeletedEventArgs(_table.Type, sql, dbParms, affrows, null)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Delete, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var affrows = 0; + Exception exception = null; + try { + affrows = _orm.Ado.ExecuteNonQuery(_connection, _transaction, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, affrows); + _orm.Aop.CurdAfter?.Invoke(this, after); + } this.ClearData(); return affrows; } @@ -60,8 +71,19 @@ namespace FreeSql.Internal.CommonProvider { var sql = this.ToSql(); if (string.IsNullOrEmpty(sql)) return 0; var dbParms = _params.ToArray(); - var affrows = await _orm.Ado.ExecuteNonQueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnDeleted?.Invoke(this, new AopOnDeletedEventArgs(_table.Type, sql, dbParms, affrows, null)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Delete, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var affrows = 0; + Exception exception = null; + try { + affrows = await _orm.Ado.ExecuteNonQueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, affrows); + _orm.Aop.CurdAfter?.Invoke(this, after); + } this.ClearData(); return affrows; } @@ -71,8 +93,8 @@ namespace FreeSql.Internal.CommonProvider { public IDelete Where(Expression> exp) => this.Where(_commonExpression.ExpressionWhereLambdaNoneForeignObject(null, _table, null, exp?.Body, null)); public IDelete Where(string sql, object parms = null) { if (string.IsNullOrEmpty(sql)) return this; - var args = new AopWhereEventArgs(sql, parms); - _orm.Aop.Where?.Invoke(this, new AopWhereEventArgs(sql, parms)); + var args = new Aop.WhereEventArgs(sql, parms); + _orm.Aop.Where?.Invoke(this, new Aop.WhereEventArgs(sql, parms)); if (args.IsCancel == true) return this; if (++_whereTimes > 1) _where.Append(" AND "); diff --git a/FreeSql/Internal/CommonProvider/InsertProvider.cs b/FreeSql/Internal/CommonProvider/InsertProvider.cs index 9935a05d..e93277b5 100644 --- a/FreeSql/Internal/CommonProvider/InsertProvider.cs +++ b/FreeSql/Internal/CommonProvider/InsertProvider.cs @@ -325,14 +325,38 @@ namespace FreeSql.Internal.CommonProvider { internal int RawExecuteAffrows() { var sql = ToSql(); - var affrows = _orm.Ado.ExecuteNonQuery(_connection, _transaction, CommandType.Text, sql, _params); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, affrows, 0, null)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + var affrows = 0; + Exception exception = null; + try { + affrows = _orm.Ado.ExecuteNonQuery(_connection, _transaction, CommandType.Text, sql, _params); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, affrows); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return affrows; } async internal Task RawExecuteAffrowsAsync() { var sql = ToSql(); - var affrows = await _orm.Ado.ExecuteNonQueryAsync(_connection, _transaction, CommandType.Text, sql, _params); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, affrows, 0, null)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + var affrows = 0; + Exception exception = null; + try { + affrows = await _orm.Ado.ExecuteNonQueryAsync(_connection, _transaction, CommandType.Text, sql, _params); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, affrows); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return affrows; } internal abstract long RawExecuteIdentity(); diff --git a/FreeSql/Internal/CommonProvider/SelectProvider/Select0Provider.cs b/FreeSql/Internal/CommonProvider/SelectProvider/Select0Provider.cs index fa7e9524..403629c5 100644 --- a/FreeSql/Internal/CommonProvider/SelectProvider/Select0Provider.cs +++ b/FreeSql/Internal/CommonProvider/SelectProvider/Select0Provider.cs @@ -217,8 +217,19 @@ namespace FreeSql.Internal.CommonProvider { return _orm.Cache.Shell(_cache.key, _cache.seconds, () => { var dbParms = _params.ToArray(); - var ret = _orm.Ado.ExecuteDataTable(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnSelected?.Invoke(this, new AopOnSelectedEventArgs(_tables[0].Table.Type, sql, dbParms, ret)); + var before = new Aop.CurdBeforeEventArgs(_tables[0].Table.Type, Aop.CurdType.Select, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + DataTable ret = null; + Exception exception = null; + try { + ret = _orm.Ado.ExecuteDataTable(_connection, _transaction, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } return ret; }); } @@ -228,8 +239,19 @@ namespace FreeSql.Internal.CommonProvider { return _orm.Cache.ShellAsync(_cache.key, _cache.seconds, async () => { var dbParms = _params.ToArray(); - var ret = await _orm.Ado.ExecuteDataTableAsync(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnSelected?.Invoke(this, new AopOnSelectedEventArgs(_tables[0].Table.Type, sql, dbParms, ret)); + var before = new Aop.CurdBeforeEventArgs(_tables[0].Table.Type, Aop.CurdType.Select, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + DataTable ret = null; + Exception exception = null; + try { + ret = await _orm.Ado.ExecuteDataTableAsync(_connection, _transaction, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } return ret; }); } @@ -239,15 +261,25 @@ namespace FreeSql.Internal.CommonProvider { if (_cache.seconds > 0 && string.IsNullOrEmpty(_cache.key)) _cache.key = sql; return _orm.Cache.Shell(_cache.key, _cache.seconds, () => { - var ret = new List(); var type = typeof(TTuple); var dbParms = _params.ToArray(); - _orm.Ado.ExecuteReader(_connection, _transaction, dr => { - var read = Utils.ExecuteArrayRowReadClassOrTuple(type, null, dr, 0, _commonUtils); - ret.Add((TTuple) read.Value); - }, CommandType.Text, sql, dbParms); - _orm.Aop.OnSelected?.Invoke(this, new AopOnSelectedEventArgs(_tables[0].Table.Type, sql, dbParms, ret)); - _orm.Aop.ToList?.Invoke(this, new AopToListEventArgs(ret)); + var before = new Aop.CurdBeforeEventArgs(_tables[0].Table.Type, Aop.CurdType.Select, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + _orm.Ado.ExecuteReader(_connection, _transaction, dr => { + var read = Utils.ExecuteArrayRowReadClassOrTuple(type, null, dr, 0, _commonUtils); + ret.Add((TTuple)read.Value); + }, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + _orm.Aop.ToList?.Invoke(this, new Aop.ToListEventArgs(ret)); _trackToList?.Invoke(ret); return ret; }); @@ -257,16 +289,26 @@ namespace FreeSql.Internal.CommonProvider { if (_cache.seconds > 0 && string.IsNullOrEmpty(_cache.key)) _cache.key = sql; return _orm.Cache.ShellAsync(_cache.key, _cache.seconds, async () => { - var ret = new List(); var type = typeof(TTuple); var dbParms = _params.ToArray(); - await _orm.Ado.ExecuteReaderAsync(_connection, _transaction, dr => { - var read = Utils.ExecuteArrayRowReadClassOrTuple(type, null, dr, 0, _commonUtils); - ret.Add((TTuple) read.Value); - return Task.CompletedTask; - }, CommandType.Text, sql, dbParms); - _orm.Aop.OnSelected?.Invoke(this, new AopOnSelectedEventArgs(_tables[0].Table.Type, sql, dbParms, ret)); - _orm.Aop.ToList?.Invoke(this, new AopToListEventArgs(ret)); + var before = new Aop.CurdBeforeEventArgs(_tables[0].Table.Type, Aop.CurdType.Select, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + await _orm.Ado.ExecuteReaderAsync(_connection, _transaction, dr => { + var read = Utils.ExecuteArrayRowReadClassOrTuple(type, null, dr, 0, _commonUtils); + ret.Add((TTuple)read.Value); + return Task.CompletedTask; + }, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + _orm.Aop.ToList?.Invoke(this, new Aop.ToListEventArgs(ret)); _trackToList?.Invoke(ret); return ret; }); @@ -276,13 +318,23 @@ namespace FreeSql.Internal.CommonProvider { if (_cache.seconds > 0 && string.IsNullOrEmpty(_cache.key)) _cache.key = $"{sql}{string.Join("|", _params.Select(a => a.Value))}"; return _orm.Cache.Shell(_cache.key, _cache.seconds, () => { - var ret = new List(); var dbParms = _params.ToArray(); - _orm.Ado.ExecuteReader(_connection, _transaction, dr => { - ret.Add(af.Read(_orm, dr)); - }, CommandType.Text, sql, dbParms); - _orm.Aop.OnSelected?.Invoke(this, new AopOnSelectedEventArgs(_tables[0].Table.Type, sql, dbParms, ret)); - _orm.Aop.ToList?.Invoke(this, new AopToListEventArgs(ret)); + var before = new Aop.CurdBeforeEventArgs(_tables[0].Table.Type, Aop.CurdType.Select, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + _orm.Ado.ExecuteReader(_connection, _transaction, dr => { + ret.Add(af.Read(_orm, dr)); + }, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + _orm.Aop.ToList?.Invoke(this, new Aop.ToListEventArgs(ret)); _trackToList?.Invoke(ret); return ret; }); @@ -292,14 +344,24 @@ namespace FreeSql.Internal.CommonProvider { if (_cache.seconds > 0 && string.IsNullOrEmpty(_cache.key)) _cache.key = $"{sql}{string.Join("|", _params.Select(a => a.Value))}"; return await _orm.Cache.ShellAsync(_cache.key, _cache.seconds, async () => { - var ret = new List(); var dbParms = _params.ToArray(); - await _orm.Ado.ExecuteReaderAsync(_connection, _transaction, dr => { - ret.Add(af.Read(_orm, dr)); - return Task.CompletedTask; - }, CommandType.Text, sql, dbParms); - _orm.Aop.OnSelected?.Invoke(this, new AopOnSelectedEventArgs(_tables[0].Table.Type, sql, dbParms, ret)); - _orm.Aop.ToList?.Invoke(this, new AopToListEventArgs(ret)); + var before = new Aop.CurdBeforeEventArgs(_tables[0].Table.Type, Aop.CurdType.Select, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + await _orm.Ado.ExecuteReaderAsync(_connection, _transaction, dr => { + ret.Add(af.Read(_orm, dr)); + return Task.CompletedTask; + }, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + _orm.Aop.ToList?.Invoke(this, new Aop.ToListEventArgs(ret)); _trackToList?.Invoke(ret); return ret; }); @@ -325,15 +387,25 @@ namespace FreeSql.Internal.CommonProvider { if (_cache.seconds > 0 && string.IsNullOrEmpty(_cache.key)) _cache.key = $"{sql}{string.Join("|", _params.Select(a => a.Value))}"; return _orm.Cache.Shell(_cache.key, _cache.seconds, () => { - var ret = new List(); var type = typeof(TReturn); var dbParms = _params.ToArray(); - _orm.Ado.ExecuteReader(_connection, _transaction, dr => { - var index = -1; - ret.Add((TReturn) _commonExpression.ReadAnonymous(af.map, dr, ref index, false)); - }, CommandType.Text, sql, dbParms); - _orm.Aop.OnSelected?.Invoke(this, new AopOnSelectedEventArgs(_tables[0].Table.Type, sql, dbParms, ret)); - _orm.Aop.ToList?.Invoke(this, new AopToListEventArgs(ret)); + var before = new Aop.CurdBeforeEventArgs(_tables[0].Table.Type, Aop.CurdType.Select, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + _orm.Ado.ExecuteReader(_connection, _transaction, dr => { + var index = -1; + ret.Add((TReturn)_commonExpression.ReadAnonymous(af.map, dr, ref index, false)); + }, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + _orm.Aop.ToList?.Invoke(this, new Aop.ToListEventArgs(ret)); _trackToList?.Invoke(ret); return ret; }); @@ -343,16 +415,26 @@ namespace FreeSql.Internal.CommonProvider { if (_cache.seconds > 0 && string.IsNullOrEmpty(_cache.key)) _cache.key = $"{sql}{string.Join("|", _params.Select(a => a.Value))}"; return await _orm.Cache.ShellAsync(_cache.key, _cache.seconds, async () => { - var ret = new List(); var type = typeof(TReturn); var dbParms = _params.ToArray(); - await _orm.Ado.ExecuteReaderAsync(_connection, _transaction, dr => { - var index = -1; - ret.Add((TReturn) _commonExpression.ReadAnonymous(af.map, dr, ref index, false)); - return Task.CompletedTask; - }, CommandType.Text, sql, dbParms); - _orm.Aop.OnSelected?.Invoke(this, new AopOnSelectedEventArgs(_tables[0].Table.Type, sql, dbParms, ret)); - _orm.Aop.ToList?.Invoke(this, new AopToListEventArgs(ret)); + var before = new Aop.CurdBeforeEventArgs(_tables[0].Table.Type, Aop.CurdType.Select, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + await _orm.Ado.ExecuteReaderAsync(_connection, _transaction, dr => { + var index = -1; + ret.Add((TReturn)_commonExpression.ReadAnonymous(af.map, dr, ref index, false)); + return Task.CompletedTask; + }, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + _orm.Aop.ToList?.Invoke(this, new Aop.ToListEventArgs(ret)); _trackToList?.Invoke(ret); return ret; }); @@ -680,8 +762,8 @@ namespace FreeSql.Internal.CommonProvider { public TSelect Where(string sql, object parms = null) => this.WhereIf(true, sql, parms); public TSelect WhereIf(bool condition, string sql, object parms = null) { if (condition == false || string.IsNullOrEmpty(sql)) return this as TSelect; - var args = new AopWhereEventArgs(sql, parms); - _orm.Aop.Where?.Invoke(this, new AopWhereEventArgs(sql, parms)); + var args = new Aop.WhereEventArgs(sql, parms); + _orm.Aop.Where?.Invoke(this, new Aop.WhereEventArgs(sql, parms)); if (args.IsCancel == true) return this as TSelect; _where.Append(" AND (").Append(sql).Append(")"); @@ -732,15 +814,37 @@ namespace FreeSql.Internal.CommonProvider { protected DataTable InternalToDataTable(Expression select) { var sql = this.InternalToSql(select); var dbParms = _params.ToArray(); - var ret = _orm.Ado.ExecuteDataTable(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnSelected?.Invoke(this, new AopOnSelectedEventArgs(_tables[0].Table.Type, sql, dbParms, ret)); + var before = new Aop.CurdBeforeEventArgs(_tables[0].Table.Type, Aop.CurdType.Select, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + DataTable ret = null; + Exception exception = null; + try { + ret = _orm.Ado.ExecuteDataTable(_connection, _transaction, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } return ret; } async protected Task InternalToDataTableAsync(Expression select) { var sql = this.InternalToSql(select); var dbParms = _params.ToArray(); - var ret = await _orm.Ado.ExecuteDataTableAsync(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnSelected?.Invoke(this, new AopOnSelectedEventArgs(_tables[0].Table.Type, sql, dbParms, ret)); + var before = new Aop.CurdBeforeEventArgs(_tables[0].Table.Type, Aop.CurdType.Select, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + DataTable ret = null; + Exception exception = null; + try { + ret = await _orm.Ado.ExecuteDataTableAsync(_connection, _transaction, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } return ret; } diff --git a/FreeSql/Internal/CommonProvider/UpdateProvider.cs b/FreeSql/Internal/CommonProvider/UpdateProvider.cs index f4822b1b..9fea958f 100644 --- a/FreeSql/Internal/CommonProvider/UpdateProvider.cs +++ b/FreeSql/Internal/CommonProvider/UpdateProvider.cs @@ -240,18 +240,42 @@ namespace FreeSql.Internal.CommonProvider { var sql = this.ToSql(); if (string.IsNullOrEmpty(sql)) return 0; var dbParms = _params.Concat(_paramsSource).ToArray(); - var affrows = _orm.Ado.ExecuteNonQuery(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnUpdated?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, null, sql, dbParms, affrows, 0, null)); - ValidateVersionAndThrow(affrows); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Update, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var affrows = 0; + Exception exception = null; + try { + affrows = _orm.Ado.ExecuteNonQuery(_connection, _transaction, CommandType.Text, sql, dbParms); + ValidateVersionAndThrow(affrows); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, affrows); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return affrows; } async internal Task RawExecuteAffrowsAsync() { var sql = this.ToSql(); if (string.IsNullOrEmpty(sql)) return 0; var dbParms = _params.Concat(_paramsSource).ToArray(); - var affrows = await _orm.Ado.ExecuteNonQueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnUpdated?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, null, sql, dbParms, affrows, 0, null)); - ValidateVersionAndThrow(affrows); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Update, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var affrows = 0; + Exception exception = null; + try { + affrows = await _orm.Ado.ExecuteNonQueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); + ValidateVersionAndThrow(affrows); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, affrows); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return affrows; } internal abstract List RawExecuteUpdated(); @@ -343,8 +367,8 @@ namespace FreeSql.Internal.CommonProvider { public IUpdate Where(Expression> expression) => this.Where(_commonExpression.ExpressionWhereLambdaNoneForeignObject(null, _table, null, expression?.Body, null)); public IUpdate Where(string sql, object parms = null) { if (string.IsNullOrEmpty(sql)) return this; - var args = new AopWhereEventArgs(sql, parms); - _orm.Aop.Where?.Invoke(this, new AopWhereEventArgs(sql, parms)); + var args = new Aop.WhereEventArgs(sql, parms); + _orm.Aop.Where?.Invoke(this, new Aop.WhereEventArgs(sql, parms)); if (args.IsCancel == true) return this; _where.Append(" AND (").Append(sql).Append(")"); diff --git a/FreeSql/Internal/CommonUtils.cs b/FreeSql/Internal/CommonUtils.cs index 91f32308..540f7c19 100644 --- a/FreeSql/Internal/CommonUtils.cs +++ b/FreeSql/Internal/CommonUtils.cs @@ -61,7 +61,7 @@ namespace FreeSql.Internal { internal TableAttribute GetEntityTableAttribute(Type type) { TableAttribute attr = null; if (_orm.Aop.ConfigEntity != null) { - var aope = new AopConfigEntityEventArgs(type); + var aope = new Aop.ConfigEntityEventArgs(type); _orm.Aop.ConfigEntity(_orm, aope); attr = aope.ModifyResult; } @@ -87,7 +87,7 @@ namespace FreeSql.Internal { internal ColumnAttribute GetEntityColumnAttribute(Type type, PropertyInfo proto) { ColumnAttribute attr = null; if (_orm.Aop.ConfigEntityProperty != null) { - var aope = new AopConfigEntityPropertyEventArgs(type, proto); + var aope = new Aop.ConfigEntityPropertyEventArgs(type, proto); _orm.Aop.ConfigEntityProperty(_orm, aope); attr = aope.ModifyResult; } diff --git a/FreeSql/MySql/Curd/MySqlDelete.cs b/FreeSql/MySql/Curd/MySqlDelete.cs index 9157b521..db2eaa24 100644 --- a/FreeSql/MySql/Curd/MySqlDelete.cs +++ b/FreeSql/MySql/Curd/MySqlDelete.cs @@ -1,4 +1,5 @@ using FreeSql.Internal; +using System; using System.Collections.Generic; using System.Data; using System.Text; @@ -26,8 +27,19 @@ namespace FreeSql.MySql.Curd { } sql = sb.ToString(); var dbParms = _params.ToArray(); - var ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnDeleted?.Invoke(this, new AopOnDeletedEventArgs(_table.Type, sql, dbParms, 0, ret)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Delete, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } this.ClearData(); return ret; } @@ -46,8 +58,19 @@ namespace FreeSql.MySql.Curd { } sql = sb.ToString(); var dbParms = _params.ToArray(); - var ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnDeleted?.Invoke(this, new AopOnDeletedEventArgs(_table.Type, sql, dbParms, 0, ret)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Delete, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } this.ClearData(); return ret; } diff --git a/FreeSql/MySql/Curd/MySqlInsert.cs b/FreeSql/MySql/Curd/MySqlInsert.cs index 29560a7d..3eeb3c9a 100644 --- a/FreeSql/MySql/Curd/MySqlInsert.cs +++ b/FreeSql/MySql/Curd/MySqlInsert.cs @@ -1,4 +1,5 @@ using FreeSql.Internal; +using System; using System.Collections.Generic; using System.Data; using System.Text; @@ -24,8 +25,20 @@ namespace FreeSql.MySql.Curd { if (string.IsNullOrEmpty(sql)) return 0; sql = string.Concat(sql, "; SELECT LAST_INSERT_ID();"); - var ret = long.TryParse(string.Concat(_orm.Ado.ExecuteScalar(_connection, _transaction, CommandType.Text, sql, _params)), out var trylng) ? trylng : 0; - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, ret, null)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + long ret = 0; + Exception exception = null; + try { + ret = long.TryParse(string.Concat(_orm.Ado.ExecuteScalar(_connection, _transaction, CommandType.Text, sql, _params)), out var trylng) ? trylng : 0; + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return ret; } async internal override Task RawExecuteIdentityAsync() { @@ -33,8 +46,20 @@ namespace FreeSql.MySql.Curd { if (string.IsNullOrEmpty(sql)) return 0; sql = string.Concat(sql, "; SELECT LAST_INSERT_ID();"); - var ret = long.TryParse(string.Concat(await _orm.Ado.ExecuteScalarAsync(_connection, _transaction, CommandType.Text, sql, _params)), out var trylng) ? trylng : 0; - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, ret, null)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + long ret = 0; + Exception exception = null; + try { + ret = long.TryParse(string.Concat(await _orm.Ado.ExecuteScalarAsync(_connection, _transaction, CommandType.Text, sql, _params)), out var trylng) ? trylng : 0; + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return ret; } internal override List RawExecuteInserted() { @@ -51,8 +76,20 @@ namespace FreeSql.MySql.Curd { ++colidx; } sql = sb.ToString(); - var ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, _params); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, 0, ret)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, _params); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return ret; } async internal override Task> RawExecuteInsertedAsync() { @@ -69,8 +106,20 @@ namespace FreeSql.MySql.Curd { ++colidx; } sql = sb.ToString(); - var ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, _params); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, 0, ret)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, _params); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return ret; } } diff --git a/FreeSql/MySql/Curd/MySqlUpdate.cs b/FreeSql/MySql/Curd/MySqlUpdate.cs index 2b2dfb55..b319276a 100644 --- a/FreeSql/MySql/Curd/MySqlUpdate.cs +++ b/FreeSql/MySql/Curd/MySqlUpdate.cs @@ -1,5 +1,6 @@ using FreeSql.Internal; using FreeSql.Internal.Model; +using System; using System.Collections.Generic; using System.Data; using System.Linq; @@ -35,9 +36,21 @@ namespace FreeSql.MySql.Curd { } sql = sb.ToString(); var dbParms = _params.Concat(_paramsSource).ToArray(); - var ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnUpdated?.Invoke(this, new AopOnUpdatedEventArgs(_table.Type, _source, sql, dbParms, 0, ret)); - ValidateVersionAndThrow(ret.Count); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Update, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, dbParms); + ValidateVersionAndThrow(ret.Count); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return ret; } async internal override Task> RawExecuteUpdatedAsync() { @@ -55,9 +68,21 @@ namespace FreeSql.MySql.Curd { } sql = sb.ToString(); var dbParms = _params.Concat(_paramsSource).ToArray(); - var ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnUpdated?.Invoke(this, new AopOnUpdatedEventArgs(_table.Type, _source, sql, dbParms, 0, ret)); - ValidateVersionAndThrow(ret.Count); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Update, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); + ValidateVersionAndThrow(ret.Count); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return ret; } diff --git a/FreeSql/MySql/MySqlCodeFirst.cs b/FreeSql/MySql/MySqlCodeFirst.cs index 25b10793..b3a6087d 100644 --- a/FreeSql/MySql/MySqlCodeFirst.cs +++ b/FreeSql/MySql/MySqlCodeFirst.cs @@ -292,15 +292,27 @@ where a.constraint_schema IN ({0}) and a.table_name IN ({1})".FormatMySql(tboldn if (entityTypes == null) return true; var syncTypes = entityTypes.Where(a => dicSyced.ContainsKey(a.FullName) == false).ToArray(); if (syncTypes.Any() == false) return true; - lock (syncStructureLock) { - var ddl = this.GetComparisonDDLStatements(syncTypes); - if (string.IsNullOrEmpty(ddl)) { + var before = new Aop.SyncStructureBeforeEventArgs(entityTypes); + _orm.Aop.SyncStructureBefore?.Invoke(this, before); + Exception exception = null; + string ddl = null; + try { + lock (syncStructureLock) { + ddl = this.GetComparisonDDLStatements(syncTypes); + if (string.IsNullOrEmpty(ddl)) { + foreach (var syncType in syncTypes) dicSyced.TryAdd(syncType.FullName, true); + return true; + } + var affrows = _orm.Ado.ExecuteNonQuery(CommandType.Text, ddl); foreach (var syncType in syncTypes) dicSyced.TryAdd(syncType.FullName, true); - return true; + return affrows > 0; } - var affrows = _orm.Ado.ExecuteNonQuery(CommandType.Text, ddl); - foreach (var syncType in syncTypes) dicSyced.TryAdd(syncType.FullName, true); - return affrows > 0; + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.SyncStructureAfterEventArgs(before, ddl, exception); + _orm.Aop.SyncStructureAfter?.Invoke(this, after); } } public ICodeFirst ConfigEntity(Action> entity) => _commonUtils.ConfigEntity(entity); diff --git a/FreeSql/Oracle/Curd/OracleInsert.cs b/FreeSql/Oracle/Curd/OracleInsert.cs index 943c3210..2eb55b77 100644 --- a/FreeSql/Oracle/Curd/OracleInsert.cs +++ b/FreeSql/Oracle/Curd/OracleInsert.cs @@ -84,9 +84,23 @@ namespace FreeSql.Oracle.Curd { var sql = this.ToSql(); if (string.IsNullOrEmpty(sql)) return 0; + long ret = 0; + Exception exception = null; + Aop.CurdBeforeEventArgs before = null; + if (_identCol == null || _source.Count > 1) { - _orm.Ado.ExecuteNonQuery(_connection, _transaction, CommandType.Text, sql, _params); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, 0, null)); + before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + try { + ret = _orm.Ado.ExecuteNonQuery(_connection, _transaction, CommandType.Text, sql, _params); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return 0; } var identColName = _commonUtils.QuoteSqlName(_identCol.Attribute.Name); @@ -94,18 +108,42 @@ namespace FreeSql.Oracle.Curd { identParam.Direction = ParameterDirection.Output; sql = $"{sql} RETURNING {identColName} INTO {identParam.ParameterName}"; var dbParms = _params.Concat(new[] { identParam }).ToArray(); - _orm.Ado.ExecuteNonQuery(_connection, _transaction, CommandType.Text, sql, dbParms); - long.TryParse(string.Concat(identParam.Value), out var trylng); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, dbParms, 0, trylng, null)); - return trylng; + before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + try { + _orm.Ado.ExecuteNonQuery(_connection, _transaction, CommandType.Text, sql, dbParms); + long.TryParse(string.Concat(identParam.Value), out ret); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); + return ret; } async internal override Task RawExecuteIdentityAsync() { var sql = this.ToSql(); if (string.IsNullOrEmpty(sql)) return 0; + long ret = 0; + Exception exception = null; + Aop.CurdBeforeEventArgs before = null; + if (_identCol == null || _source.Count > 1) { - await _orm.Ado.ExecuteNonQueryAsync(_connection, _transaction, CommandType.Text, sql, _params); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, 0, null)); + before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + try { + ret = await _orm.Ado.ExecuteNonQueryAsync(_connection, _transaction, CommandType.Text, sql, _params); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return 0; } var identColName = _commonUtils.QuoteSqlName(_identCol.Attribute.Name); @@ -113,10 +151,20 @@ namespace FreeSql.Oracle.Curd { identParam.Direction = ParameterDirection.Output; sql = $"{sql} RETURNING {identColName} INTO {identParam.ParameterName}"; var dbParms = _params.Concat(new[] { identParam }).ToArray(); - await _orm.Ado.ExecuteNonQueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); - long.TryParse(string.Concat(identParam.Value), out var trylng); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, dbParms, 0, trylng, null)); - return trylng; + before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + try { + await _orm.Ado.ExecuteNonQueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); + long.TryParse(string.Concat(identParam.Value), out ret); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); + return ret; } internal override List RawExecuteInserted() { diff --git a/FreeSql/Oracle/OracleCodeFirst.cs b/FreeSql/Oracle/OracleCodeFirst.cs index 78087953..ce650f9b 100644 --- a/FreeSql/Oracle/OracleCodeFirst.cs +++ b/FreeSql/Oracle/OracleCodeFirst.cs @@ -339,15 +339,27 @@ and a.owner in ({0}) and a.table_name in ({1})".FormatMySql(tboldname ?? tbname) if (entityTypes == null) return true; var syncTypes = entityTypes.Where(a => dicSyced.ContainsKey(a.FullName) == false).ToArray(); if (syncTypes.Any() == false) return true; - lock (syncStructureLock) { - var ddl = this.GetComparisonDDLStatements(syncTypes); - if (string.IsNullOrEmpty(ddl)) { + var before = new Aop.SyncStructureBeforeEventArgs(entityTypes); + _orm.Aop.SyncStructureBefore?.Invoke(this, before); + Exception exception = null; + string ddl = null; + try { + lock (syncStructureLock) { + ddl = this.GetComparisonDDLStatements(syncTypes); + if (string.IsNullOrEmpty(ddl)) { + foreach (var syncType in syncTypes) dicSyced.TryAdd(syncType.FullName, true); + return true; + } + var affrows = _orm.Ado.ExecuteNonQuery(CommandType.Text, ddl); foreach (var syncType in syncTypes) dicSyced.TryAdd(syncType.FullName, true); - return true; + return affrows > 0; } - var affrows = _orm.Ado.ExecuteNonQuery(CommandType.Text, ddl); - foreach (var syncType in syncTypes) dicSyced.TryAdd(syncType.FullName, true); - return affrows > 0; + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.SyncStructureAfterEventArgs(before, ddl, exception); + _orm.Aop.SyncStructureAfter?.Invoke(this, after); } } public ICodeFirst ConfigEntity(Action> entity) => _commonUtils.ConfigEntity(entity); diff --git a/FreeSql/PostgreSQL/Curd/PostgreSQLDelete.cs b/FreeSql/PostgreSQL/Curd/PostgreSQLDelete.cs index f685812b..e7011753 100644 --- a/FreeSql/PostgreSQL/Curd/PostgreSQLDelete.cs +++ b/FreeSql/PostgreSQL/Curd/PostgreSQLDelete.cs @@ -1,4 +1,5 @@ using FreeSql.Internal; +using System; using System.Collections.Generic; using System.Data; using System.Text; @@ -26,8 +27,19 @@ namespace FreeSql.PostgreSQL.Curd { } sql = sb.ToString(); var dbParms = _params.ToArray(); - var ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnDeleted?.Invoke(this, new AopOnDeletedEventArgs(_table.Type, sql, dbParms, 0, ret)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Delete, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } this.ClearData(); return ret; } @@ -46,8 +58,19 @@ namespace FreeSql.PostgreSQL.Curd { } sql = sb.ToString(); var dbParms = _params.ToArray(); - var ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnDeleted?.Invoke(this, new AopOnDeletedEventArgs(_table.Type, sql, dbParms, 0, ret)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Delete, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } this.ClearData(); return ret; } diff --git a/FreeSql/PostgreSQL/Curd/PostgreSQLInsert.cs b/FreeSql/PostgreSQL/Curd/PostgreSQLInsert.cs index 0bdc836a..549c7ace 100644 --- a/FreeSql/PostgreSQL/Curd/PostgreSQLInsert.cs +++ b/FreeSql/PostgreSQL/Curd/PostgreSQLInsert.cs @@ -1,4 +1,5 @@ using FreeSql.Internal; +using System; using System.Collections.Generic; using System.Data; using System.Linq; @@ -24,31 +25,79 @@ namespace FreeSql.PostgreSQL.Curd { var sql = this.ToSql(); if (string.IsNullOrEmpty(sql)) return 0; + long ret = 0; + Exception exception = null; + Aop.CurdBeforeEventArgs before = null; + var identCols = _table.Columns.Where(a => a.Value.Attribute.IsIdentity == true); if (identCols.Any() == false) { - _orm.Ado.ExecuteNonQuery(_connection, _transaction, CommandType.Text, sql, _params); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, 0, null)); + before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + try { + ret = _orm.Ado.ExecuteNonQuery(_connection, _transaction, CommandType.Text, sql, _params); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return 0; } sql = string.Concat(sql, " RETURNING ", _commonUtils.QuoteSqlName(identCols.First().Value.Attribute.Name)); - long.TryParse(string.Concat(_orm.Ado.ExecuteScalar(_connection, _transaction, CommandType.Text, sql, _params)), out var trylng); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, trylng, null)); - return trylng; + before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + try { + long.TryParse(string.Concat(_orm.Ado.ExecuteScalar(_connection, _transaction, CommandType.Text, sql, _params)), out ret); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); + return ret; } async internal override Task RawExecuteIdentityAsync() { var sql = this.ToSql(); if (string.IsNullOrEmpty(sql)) return 0; + long ret = 0; + Exception exception = null; + Aop.CurdBeforeEventArgs before = null; + var identCols = _table.Columns.Where(a => a.Value.Attribute.IsIdentity == true); if (identCols.Any() == false) { - await _orm.Ado.ExecuteNonQueryAsync(_connection, _transaction, CommandType.Text, sql, _params); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, 0, null)); + before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + try { + ret = await _orm.Ado.ExecuteNonQueryAsync(_connection, _transaction, CommandType.Text, sql, _params); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return 0; } sql = string.Concat(sql, " RETURNING ", _commonUtils.QuoteSqlName(identCols.First().Value.Attribute.Name)); - long.TryParse(string.Concat(await _orm.Ado.ExecuteScalarAsync(_connection, _transaction, CommandType.Text, sql, _params)), out var trylng); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, trylng, null)); - return trylng; + before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + try { + long.TryParse(string.Concat(await _orm.Ado.ExecuteScalarAsync(_connection, _transaction, CommandType.Text, sql, _params)), out ret); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); + return ret; } internal override List RawExecuteInserted() { @@ -65,8 +114,20 @@ namespace FreeSql.PostgreSQL.Curd { ++colidx; } sql = sb.ToString(); - var ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, _params); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, 0, ret)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, _params); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return ret; } async internal override Task> RawExecuteInsertedAsync() { @@ -83,8 +144,20 @@ namespace FreeSql.PostgreSQL.Curd { ++colidx; } sql = sb.ToString(); - var ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, _params); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, 0, ret)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, _params); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return ret; } } diff --git a/FreeSql/PostgreSQL/Curd/PostgreSQLUpdate.cs b/FreeSql/PostgreSQL/Curd/PostgreSQLUpdate.cs index 09bcf447..87c66a05 100644 --- a/FreeSql/PostgreSQL/Curd/PostgreSQLUpdate.cs +++ b/FreeSql/PostgreSQL/Curd/PostgreSQLUpdate.cs @@ -1,5 +1,6 @@ using FreeSql.Internal; using FreeSql.Internal.Model; +using System; using System.Collections.Generic; using System.Data; using System.Linq; @@ -35,9 +36,21 @@ namespace FreeSql.PostgreSQL.Curd { } sql = sb.ToString(); var dbParms = _params.Concat(_paramsSource).ToArray(); - var ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnUpdated?.Invoke(this, new AopOnUpdatedEventArgs(_table.Type, _source, sql, dbParms, 0, ret)); - ValidateVersionAndThrow(ret.Count); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Update, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, dbParms); + ValidateVersionAndThrow(ret.Count); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return ret; } async internal override Task> RawExecuteUpdatedAsync() { @@ -55,9 +68,21 @@ namespace FreeSql.PostgreSQL.Curd { } sql = sb.ToString(); var dbParms = _params.Concat(_paramsSource).ToArray(); - var ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnUpdated?.Invoke(this, new AopOnUpdatedEventArgs(_table.Type, _source, sql, dbParms, 0, ret)); - ValidateVersionAndThrow(ret.Count); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Update, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); + ValidateVersionAndThrow(ret.Count); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return ret; } diff --git a/FreeSql/PostgreSQL/PostgreSQLCodeFirst.cs b/FreeSql/PostgreSQL/PostgreSQLCodeFirst.cs index 5ea16289..38403a6c 100644 --- a/FreeSql/PostgreSQL/PostgreSQLCodeFirst.cs +++ b/FreeSql/PostgreSQL/PostgreSQLCodeFirst.cs @@ -344,15 +344,27 @@ where pg_namespace.nspname={0} and pg_class.relname={1} and pg_constraint.contyp if (entityTypes == null) return true; var syncTypes = entityTypes.Where(a => dicSyced.ContainsKey(a.FullName) == false).ToArray(); if (syncTypes.Any() == false) return true; - lock (syncStructureLock) { - var ddl = this.GetComparisonDDLStatements(syncTypes); - if (string.IsNullOrEmpty(ddl)) { + var before = new Aop.SyncStructureBeforeEventArgs(entityTypes); + _orm.Aop.SyncStructureBefore?.Invoke(this, before); + Exception exception = null; + string ddl = null; + try { + lock (syncStructureLock) { + ddl = this.GetComparisonDDLStatements(syncTypes); + if (string.IsNullOrEmpty(ddl)) { + foreach (var syncType in syncTypes) dicSyced.TryAdd(syncType.FullName, true); + return true; + } + var affrows = _orm.Ado.ExecuteNonQuery(CommandType.Text, ddl); foreach (var syncType in syncTypes) dicSyced.TryAdd(syncType.FullName, true); - return true; + return affrows > 0; } - var affrows = _orm.Ado.ExecuteNonQuery(CommandType.Text, ddl); - foreach (var syncType in syncTypes) dicSyced.TryAdd(syncType.FullName, true); - return affrows > 0; + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.SyncStructureAfterEventArgs(before, ddl, exception); + _orm.Aop.SyncStructureAfter?.Invoke(this, after); } } public ICodeFirst ConfigEntity(Action> entity) => _commonUtils.ConfigEntity(entity); diff --git a/FreeSql/SqlServer/Curd/SqlServerDelete.cs b/FreeSql/SqlServer/Curd/SqlServerDelete.cs index c1f48a42..f604a4f2 100644 --- a/FreeSql/SqlServer/Curd/SqlServerDelete.cs +++ b/FreeSql/SqlServer/Curd/SqlServerDelete.cs @@ -32,8 +32,19 @@ namespace FreeSql.SqlServer.Curd { sql = sb.ToString(); var dbParms = _params.ToArray(); - var ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnDeleted?.Invoke(this, new AopOnDeletedEventArgs(_table.Type, sql, dbParms, 0, ret)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Delete, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } this.ClearData(); return ret; } @@ -57,8 +68,19 @@ namespace FreeSql.SqlServer.Curd { sql = sb.ToString(); var dbParms = _params.ToArray(); - var ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnDeleted?.Invoke(this, new AopOnDeletedEventArgs(_table.Type, sql, dbParms, 0, ret)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Delete, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } this.ClearData(); return ret; } diff --git a/FreeSql/SqlServer/Curd/SqlServerInsert.cs b/FreeSql/SqlServer/Curd/SqlServerInsert.cs index b934852d..71991e41 100644 --- a/FreeSql/SqlServer/Curd/SqlServerInsert.cs +++ b/FreeSql/SqlServer/Curd/SqlServerInsert.cs @@ -27,18 +27,42 @@ namespace FreeSql.SqlServer.Curd { if (string.IsNullOrEmpty(sql)) return 0; sql = string.Concat(sql, "; SELECT SCOPE_IDENTITY();"); - long.TryParse(string.Concat(_orm.Ado.ExecuteScalar(_connection, _transaction, CommandType.Text, sql, _params)), out var trylng); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, trylng, null)); - return trylng; + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + long ret = 0; + Exception exception = null; + try { + long.TryParse(string.Concat(_orm.Ado.ExecuteScalar(_connection, _transaction, CommandType.Text, sql, _params)), out ret); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); + return ret; } async internal override Task RawExecuteIdentityAsync() { var sql = this.ToSql(); if (string.IsNullOrEmpty(sql)) return 0; sql = string.Concat(sql, "; SELECT SCOPE_IDENTITY();"); - long.TryParse(string.Concat(await _orm.Ado.ExecuteScalarAsync(_connection, _transaction, CommandType.Text, sql, _params)), out var trylng); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, trylng, null)); - return trylng; + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + long ret = 0; + Exception exception = null; + try { + long.TryParse(string.Concat(await _orm.Ado.ExecuteScalarAsync(_connection, _transaction, CommandType.Text, sql, _params)), out ret); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); + return ret; } internal override List RawExecuteInserted() { @@ -60,8 +84,20 @@ namespace FreeSql.SqlServer.Curd { sb.Append(sql.Substring(validx + 1)); sql = sb.ToString(); - var ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, _params); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, 0, ret)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, _params); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return ret; } async internal override Task> RawExecuteInsertedAsync() { @@ -83,8 +119,20 @@ namespace FreeSql.SqlServer.Curd { sb.Append(sql.Substring(validx + 1)); sql = sb.ToString(); - var ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, _params); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, 0, ret)); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, _params); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return ret; } } diff --git a/FreeSql/SqlServer/Curd/SqlServerUpdate.cs b/FreeSql/SqlServer/Curd/SqlServerUpdate.cs index b9268e7a..9f3403f8 100644 --- a/FreeSql/SqlServer/Curd/SqlServerUpdate.cs +++ b/FreeSql/SqlServer/Curd/SqlServerUpdate.cs @@ -41,9 +41,21 @@ namespace FreeSql.SqlServer.Curd { sql = sb.ToString(); var dbParms = _params.Concat(_paramsSource).ToArray(); - var ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnUpdated?.Invoke(this, new AopOnUpdatedEventArgs(_table.Type, _source, sql, dbParms, 0, ret)); - ValidateVersionAndThrow(ret.Count); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Update, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = _orm.Ado.Query(_connection, _transaction, CommandType.Text, sql, dbParms); + ValidateVersionAndThrow(ret.Count); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return ret; } async internal override Task> RawExecuteUpdatedAsync() { @@ -66,9 +78,21 @@ namespace FreeSql.SqlServer.Curd { sql = sb.ToString(); var dbParms = _params.Concat(_paramsSource).ToArray(); - var ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); - _orm.Aop.OnUpdated?.Invoke(this, new AopOnUpdatedEventArgs(_table.Type, _source, sql, dbParms, 0, ret)); - ValidateVersionAndThrow(ret.Count); + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Update, sql, dbParms); + _orm.Aop.CurdBefore?.Invoke(this, before); + var ret = new List(); + Exception exception = null; + try { + ret = await _orm.Ado.QueryAsync(_connection, _transaction, CommandType.Text, sql, dbParms); + ValidateVersionAndThrow(ret.Count); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); return ret; } diff --git a/FreeSql/SqlServer/SqlServerCodeFirst.cs b/FreeSql/SqlServer/SqlServerCodeFirst.cs index 3dad8044..6335a9d0 100644 --- a/FreeSql/SqlServer/SqlServerCodeFirst.cs +++ b/FreeSql/SqlServer/SqlServerCodeFirst.cs @@ -333,15 +333,27 @@ use " + database, tboldname ?? tbname); if (entityTypes == null) return true; var syncTypes = entityTypes.Where(a => dicSyced.ContainsKey(a.FullName) == false).ToArray(); if (syncTypes.Any() == false) return true; - lock (syncStructureLock) { - var ddl = this.GetComparisonDDLStatements(syncTypes); - if (string.IsNullOrEmpty(ddl)) { + var before = new Aop.SyncStructureBeforeEventArgs(entityTypes); + _orm.Aop.SyncStructureBefore?.Invoke(this, before); + Exception exception = null; + string ddl = null; + try { + lock (syncStructureLock) { + ddl = this.GetComparisonDDLStatements(syncTypes); + if (string.IsNullOrEmpty(ddl)) { + foreach (var syncType in syncTypes) dicSyced.TryAdd(syncType.FullName, true); + return true; + } + var affrows = _orm.Ado.ExecuteNonQuery(CommandType.Text, ddl); foreach (var syncType in syncTypes) dicSyced.TryAdd(syncType.FullName, true); - return true; + return affrows > 0; } - var affrows = _orm.Ado.ExecuteNonQuery(CommandType.Text, ddl); - foreach (var syncType in syncTypes) dicSyced.TryAdd(syncType.FullName, true); - return affrows > 0; + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.SyncStructureAfterEventArgs(before, ddl, exception); + _orm.Aop.SyncStructureAfter?.Invoke(this, after); } } public ICodeFirst ConfigEntity(Action> entity) => _commonUtils.ConfigEntity(entity); diff --git a/FreeSql/Sqlite/Curd/SqliteInsert.cs b/FreeSql/Sqlite/Curd/SqliteInsert.cs index 2244021b..f10f1ff4 100644 --- a/FreeSql/Sqlite/Curd/SqliteInsert.cs +++ b/FreeSql/Sqlite/Curd/SqliteInsert.cs @@ -26,18 +26,42 @@ namespace FreeSql.Sqlite.Curd { if (string.IsNullOrEmpty(sql)) return 0; sql = string.Concat(sql, "; SELECT last_insert_rowid();"); - long.TryParse(string.Concat(_orm.Ado.ExecuteScalar(_connection, _transaction, CommandType.Text, sql, _params)), out var trylng); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, trylng, null)); - return trylng; + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + long ret = 0; + Exception exception = null; + try { + long.TryParse(string.Concat(_orm.Ado.ExecuteScalar(_connection, _transaction, CommandType.Text, sql, _params)), out ret); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); + return ret; } async internal override Task RawExecuteIdentityAsync() { var sql = this.ToSql(); if (string.IsNullOrEmpty(sql)) return 0; sql = string.Concat(sql, "; SELECT last_insert_rowid();"); - long.TryParse(string.Concat(await _orm.Ado.ExecuteScalarAsync(_connection, _transaction, CommandType.Text, sql, _params)), out var trylng); - _orm.Aop.OnInserted?.Invoke(this, new AopOnInsertedEventArgs(_table.Type, _source, sql, _params, 0, trylng, null)); - return trylng; + var before = new Aop.CurdBeforeEventArgs(_table.Type, Aop.CurdType.Insert, sql, _params); + _orm.Aop.CurdBefore?.Invoke(this, before); + long ret = 0; + Exception exception = null; + try { + long.TryParse(string.Concat(await _orm.Ado.ExecuteScalarAsync(_connection, _transaction, CommandType.Text, sql, _params)), out ret); + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.CurdAfterEventArgs(before, exception, ret); + _orm.Aop.CurdAfter?.Invoke(this, after); + } + this.ClearData(); + return ret; } internal override List RawExecuteInserted() { var sql = this.ToSql(); diff --git a/FreeSql/Sqlite/SqliteCodeFirst.cs b/FreeSql/Sqlite/SqliteCodeFirst.cs index ee275641..ce503cc8 100644 --- a/FreeSql/Sqlite/SqliteCodeFirst.cs +++ b/FreeSql/Sqlite/SqliteCodeFirst.cs @@ -256,15 +256,27 @@ namespace FreeSql.Sqlite { if (entityTypes == null) return true; var syncTypes = entityTypes.Where(a => dicSyced.ContainsKey(a.FullName) == false).ToArray(); if (syncTypes.Any() == false) return true; - lock (syncStructureLock) { - var ddl = this.GetComparisonDDLStatements(syncTypes); - if (string.IsNullOrEmpty(ddl)) { + var before = new Aop.SyncStructureBeforeEventArgs(entityTypes); + _orm.Aop.SyncStructureBefore?.Invoke(this, before); + Exception exception = null; + string ddl = null; + try { + lock (syncStructureLock) { + ddl = this.GetComparisonDDLStatements(syncTypes); + if (string.IsNullOrEmpty(ddl)) { + foreach (var syncType in syncTypes) dicSyced.TryAdd(syncType.FullName, true); + return true; + } + var affrows = _orm.Ado.ExecuteNonQuery(CommandType.Text, ddl); foreach (var syncType in syncTypes) dicSyced.TryAdd(syncType.FullName, true); - return true; + return affrows > 0; } - var affrows = _orm.Ado.ExecuteNonQuery(CommandType.Text, ddl); - foreach (var syncType in syncTypes) dicSyced.TryAdd(syncType.FullName, true); - return affrows > 0; + } catch (Exception ex) { + exception = ex; + throw ex; + } finally { + var after = new Aop.SyncStructureAfterEventArgs(before, ddl, exception); + _orm.Aop.SyncStructureAfter?.Invoke(this, after); } } public ICodeFirst ConfigEntity(Action> entity) => _commonUtils.ConfigEntity(entity);