mirror of
				https://github.com/nsnail/FreeSql.git
				synced 2025-11-04 17:20:49 +08:00 
			
		
		
		
	源代码改用vs默认格式化
This commit is contained in:
		@@ -7,55 +7,64 @@ using System.Data.Common;
 | 
			
		||||
using System.Text;
 | 
			
		||||
using System.Threading;
 | 
			
		||||
 | 
			
		||||
namespace FreeSql.Oracle {
 | 
			
		||||
	class OracleAdo : FreeSql.Internal.CommonProvider.AdoProvider {
 | 
			
		||||
		public OracleAdo() : base(DataType.Oracle) { }
 | 
			
		||||
		public OracleAdo(CommonUtils util, string masterConnectionString, string[] slaveConnectionStrings) : base(DataType.Oracle) {
 | 
			
		||||
			base._util = util;
 | 
			
		||||
			if (!string.IsNullOrEmpty(masterConnectionString))
 | 
			
		||||
				MasterPool = new OracleConnectionPool("主库", masterConnectionString, null, null);
 | 
			
		||||
			if (slaveConnectionStrings != null) {
 | 
			
		||||
				foreach (var slaveConnectionString in slaveConnectionStrings) {
 | 
			
		||||
					var slavePool = new OracleConnectionPool($"从库{SlavePools.Count + 1}", slaveConnectionString, () => Interlocked.Decrement(ref slaveUnavailables), () => Interlocked.Increment(ref slaveUnavailables));
 | 
			
		||||
					SlavePools.Add(slavePool);
 | 
			
		||||
				}
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
		static DateTime dt1970 = new DateTime(1970, 1, 1);
 | 
			
		||||
		public override object AddslashesProcessParam(object param, Type mapType) {
 | 
			
		||||
			if (param == null) return "NULL";
 | 
			
		||||
			if (mapType != null && mapType != param.GetType())
 | 
			
		||||
				param = Utils.GetDataReaderValue(mapType, param);
 | 
			
		||||
			if (param is bool || param is bool?)
 | 
			
		||||
				return (bool)param ? 1 : 0;
 | 
			
		||||
			else if (param is string || param is char)
 | 
			
		||||
				return string.Concat("'", param.ToString().Replace("'", "''"), "'");
 | 
			
		||||
			else if (param is Enum)
 | 
			
		||||
				return ((Enum)param).ToInt64();
 | 
			
		||||
			else if (decimal.TryParse(string.Concat(param), out var trydec))
 | 
			
		||||
				return param;
 | 
			
		||||
			else if (param is DateTime || param is DateTime?)
 | 
			
		||||
				return string.Concat("to_timestamp('", ((DateTime)param).ToString("yyyy-MM-dd HH:mm:ss.ffffff"), "','YYYY-MM-DD HH24:MI:SS.FF6')");
 | 
			
		||||
			else if (param is TimeSpan || param is TimeSpan?)
 | 
			
		||||
				return $"numtodsinterval({((TimeSpan)param).Ticks * 1.0 / 10000000},'second')";
 | 
			
		||||
			else if (param is IEnumerable) {
 | 
			
		||||
				var sb = new StringBuilder();
 | 
			
		||||
				var ie = param as IEnumerable;
 | 
			
		||||
				foreach (var z in ie) sb.Append(",").Append(AddslashesProcessParam(z, mapType));
 | 
			
		||||
				return sb.Length == 0 ? "(NULL)" : sb.Remove(0, 1).Insert(0, "(").Append(")").ToString();
 | 
			
		||||
			}
 | 
			
		||||
			return string.Concat("'", param.ToString().Replace("'", "''"), "'");
 | 
			
		||||
			//if (param is string) return string.Concat('N', nparms[a]);
 | 
			
		||||
		}
 | 
			
		||||
namespace FreeSql.Oracle
 | 
			
		||||
{
 | 
			
		||||
    class OracleAdo : FreeSql.Internal.CommonProvider.AdoProvider
 | 
			
		||||
    {
 | 
			
		||||
        public OracleAdo() : base(DataType.Oracle) { }
 | 
			
		||||
        public OracleAdo(CommonUtils util, string masterConnectionString, string[] slaveConnectionStrings) : base(DataType.Oracle)
 | 
			
		||||
        {
 | 
			
		||||
            base._util = util;
 | 
			
		||||
            if (!string.IsNullOrEmpty(masterConnectionString))
 | 
			
		||||
                MasterPool = new OracleConnectionPool("主库", masterConnectionString, null, null);
 | 
			
		||||
            if (slaveConnectionStrings != null)
 | 
			
		||||
            {
 | 
			
		||||
                foreach (var slaveConnectionString in slaveConnectionStrings)
 | 
			
		||||
                {
 | 
			
		||||
                    var slavePool = new OracleConnectionPool($"从库{SlavePools.Count + 1}", slaveConnectionString, () => Interlocked.Decrement(ref slaveUnavailables), () => Interlocked.Increment(ref slaveUnavailables));
 | 
			
		||||
                    SlavePools.Add(slavePool);
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        static DateTime dt1970 = new DateTime(1970, 1, 1);
 | 
			
		||||
        public override object AddslashesProcessParam(object param, Type mapType)
 | 
			
		||||
        {
 | 
			
		||||
            if (param == null) return "NULL";
 | 
			
		||||
            if (mapType != null && mapType != param.GetType())
 | 
			
		||||
                param = Utils.GetDataReaderValue(mapType, param);
 | 
			
		||||
            if (param is bool || param is bool?)
 | 
			
		||||
                return (bool)param ? 1 : 0;
 | 
			
		||||
            else if (param is string || param is char)
 | 
			
		||||
                return string.Concat("'", param.ToString().Replace("'", "''"), "'");
 | 
			
		||||
            else if (param is Enum)
 | 
			
		||||
                return ((Enum)param).ToInt64();
 | 
			
		||||
            else if (decimal.TryParse(string.Concat(param), out var trydec))
 | 
			
		||||
                return param;
 | 
			
		||||
            else if (param is DateTime || param is DateTime?)
 | 
			
		||||
                return string.Concat("to_timestamp('", ((DateTime)param).ToString("yyyy-MM-dd HH:mm:ss.ffffff"), "','YYYY-MM-DD HH24:MI:SS.FF6')");
 | 
			
		||||
            else if (param is TimeSpan || param is TimeSpan?)
 | 
			
		||||
                return $"numtodsinterval({((TimeSpan)param).Ticks * 1.0 / 10000000},'second')";
 | 
			
		||||
            else if (param is IEnumerable)
 | 
			
		||||
            {
 | 
			
		||||
                var sb = new StringBuilder();
 | 
			
		||||
                var ie = param as IEnumerable;
 | 
			
		||||
                foreach (var z in ie) sb.Append(",").Append(AddslashesProcessParam(z, mapType));
 | 
			
		||||
                return sb.Length == 0 ? "(NULL)" : sb.Remove(0, 1).Insert(0, "(").Append(")").ToString();
 | 
			
		||||
            }
 | 
			
		||||
            return string.Concat("'", param.ToString().Replace("'", "''"), "'");
 | 
			
		||||
            //if (param is string) return string.Concat('N', nparms[a]);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
		protected override DbCommand CreateCommand() {
 | 
			
		||||
			return new OracleCommand();
 | 
			
		||||
		}
 | 
			
		||||
        protected override DbCommand CreateCommand()
 | 
			
		||||
        {
 | 
			
		||||
            return new OracleCommand();
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
		protected override void ReturnConnection(ObjectPool<DbConnection> pool, Object<DbConnection> conn, Exception ex) {
 | 
			
		||||
			(pool as OracleConnectionPool).Return(conn, ex);
 | 
			
		||||
		}
 | 
			
		||||
        protected override void ReturnConnection(ObjectPool<DbConnection> pool, Object<DbConnection> conn, Exception ex)
 | 
			
		||||
        {
 | 
			
		||||
            (pool as OracleConnectionPool).Return(conn, ex);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
		protected override DbParameter[] GetDbParamtersByObject(string sql, object obj) => _util.GetDbParamtersByObject(sql, obj);
 | 
			
		||||
	}
 | 
			
		||||
        protected override DbParameter[] GetDbParamtersByObject(string sql, object obj) => _util.GetDbParamtersByObject(sql, obj);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -9,183 +9,226 @@ using System.Text;
 | 
			
		||||
using System.Text.RegularExpressions;
 | 
			
		||||
using System.Threading.Tasks;
 | 
			
		||||
 | 
			
		||||
namespace FreeSql.Oracle {
 | 
			
		||||
namespace FreeSql.Oracle
 | 
			
		||||
{
 | 
			
		||||
 | 
			
		||||
	class OracleConnectionPool : ObjectPool<DbConnection> {
 | 
			
		||||
    class OracleConnectionPool : ObjectPool<DbConnection>
 | 
			
		||||
    {
 | 
			
		||||
 | 
			
		||||
		internal Action availableHandler;
 | 
			
		||||
		internal Action unavailableHandler;
 | 
			
		||||
		internal string UserId { get; set; }
 | 
			
		||||
        internal Action availableHandler;
 | 
			
		||||
        internal Action unavailableHandler;
 | 
			
		||||
        internal string UserId { get; set; }
 | 
			
		||||
 | 
			
		||||
		public OracleConnectionPool(string name, string connectionString, Action availableHandler, Action unavailableHandler) : base(null) {
 | 
			
		||||
			var userIdMatch = Regex.Match(connectionString, @"User\s+Id\s*=\s*([^;]+)", RegexOptions.IgnoreCase);
 | 
			
		||||
			if (userIdMatch.Success == false) throw new Exception(@"从 ConnectionString 中无法匹配 User\s+Id\s+=([^;]+)");
 | 
			
		||||
			this.UserId = userIdMatch.Groups[1].Value.Trim().ToUpper();
 | 
			
		||||
        public OracleConnectionPool(string name, string connectionString, Action availableHandler, Action unavailableHandler) : base(null)
 | 
			
		||||
        {
 | 
			
		||||
            var userIdMatch = Regex.Match(connectionString, @"User\s+Id\s*=\s*([^;]+)", RegexOptions.IgnoreCase);
 | 
			
		||||
            if (userIdMatch.Success == false) throw new Exception(@"从 ConnectionString 中无法匹配 User\s+Id\s+=([^;]+)");
 | 
			
		||||
            this.UserId = userIdMatch.Groups[1].Value.Trim().ToUpper();
 | 
			
		||||
 | 
			
		||||
			var policy = new OracleConnectionPoolPolicy {
 | 
			
		||||
				_pool = this,
 | 
			
		||||
				Name = name
 | 
			
		||||
			};
 | 
			
		||||
			this.Policy = policy;
 | 
			
		||||
			policy.ConnectionString = connectionString;
 | 
			
		||||
            var policy = new OracleConnectionPoolPolicy
 | 
			
		||||
            {
 | 
			
		||||
                _pool = this,
 | 
			
		||||
                Name = name
 | 
			
		||||
            };
 | 
			
		||||
            this.Policy = policy;
 | 
			
		||||
            policy.ConnectionString = connectionString;
 | 
			
		||||
 | 
			
		||||
			this.availableHandler = availableHandler;
 | 
			
		||||
			this.unavailableHandler = unavailableHandler;
 | 
			
		||||
		}
 | 
			
		||||
            this.availableHandler = availableHandler;
 | 
			
		||||
            this.unavailableHandler = unavailableHandler;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
		public void Return(Object<DbConnection> obj, Exception exception, bool isRecreate = false) {
 | 
			
		||||
			if (exception != null && exception is OracleException) {
 | 
			
		||||
        public void Return(Object<DbConnection> obj, Exception exception, bool isRecreate = false)
 | 
			
		||||
        {
 | 
			
		||||
            if (exception != null && exception is OracleException)
 | 
			
		||||
            {
 | 
			
		||||
 | 
			
		||||
				if (exception is System.IO.IOException) {
 | 
			
		||||
                if (exception is System.IO.IOException)
 | 
			
		||||
                {
 | 
			
		||||
 | 
			
		||||
					base.SetUnavailable(exception);
 | 
			
		||||
                    base.SetUnavailable(exception);
 | 
			
		||||
 | 
			
		||||
				} else if (obj.Value.Ping() == false) {
 | 
			
		||||
                }
 | 
			
		||||
                else if (obj.Value.Ping() == false)
 | 
			
		||||
                {
 | 
			
		||||
 | 
			
		||||
					base.SetUnavailable(exception);
 | 
			
		||||
				}
 | 
			
		||||
			}
 | 
			
		||||
			base.Return(obj, isRecreate);
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
                    base.SetUnavailable(exception);
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
            base.Return(obj, isRecreate);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
	class OracleConnectionPoolPolicy : IPolicy<DbConnection> {
 | 
			
		||||
    class OracleConnectionPoolPolicy : IPolicy<DbConnection>
 | 
			
		||||
    {
 | 
			
		||||
 | 
			
		||||
		internal OracleConnectionPool _pool;
 | 
			
		||||
		public string Name { get; set; } = "Oracle Connection 对象池";
 | 
			
		||||
		public int PoolSize { get; set; } = 100;
 | 
			
		||||
		public TimeSpan SyncGetTimeout { get; set; } = TimeSpan.FromSeconds(10);
 | 
			
		||||
		public TimeSpan IdleTimeout { get; set; } = TimeSpan.Zero;
 | 
			
		||||
		public int AsyncGetCapacity { get; set; } = 10000;
 | 
			
		||||
		public bool IsThrowGetTimeoutException { get; set; } = true;
 | 
			
		||||
		public int CheckAvailableInterval { get; set; } = 5;
 | 
			
		||||
        internal OracleConnectionPool _pool;
 | 
			
		||||
        public string Name { get; set; } = "Oracle Connection 对象池";
 | 
			
		||||
        public int PoolSize { get; set; } = 100;
 | 
			
		||||
        public TimeSpan SyncGetTimeout { get; set; } = TimeSpan.FromSeconds(10);
 | 
			
		||||
        public TimeSpan IdleTimeout { get; set; } = TimeSpan.Zero;
 | 
			
		||||
        public int AsyncGetCapacity { get; set; } = 10000;
 | 
			
		||||
        public bool IsThrowGetTimeoutException { get; set; } = true;
 | 
			
		||||
        public int CheckAvailableInterval { get; set; } = 5;
 | 
			
		||||
 | 
			
		||||
		static ConcurrentDictionary<string, int> dicConnStrIncr = new ConcurrentDictionary<string, int>(StringComparer.CurrentCultureIgnoreCase);
 | 
			
		||||
		private string _connectionString;
 | 
			
		||||
		public string ConnectionString {
 | 
			
		||||
			get => _connectionString;
 | 
			
		||||
			set {
 | 
			
		||||
				_connectionString = value ?? "";
 | 
			
		||||
        static ConcurrentDictionary<string, int> dicConnStrIncr = new ConcurrentDictionary<string, int>(StringComparer.CurrentCultureIgnoreCase);
 | 
			
		||||
        private string _connectionString;
 | 
			
		||||
        public string ConnectionString
 | 
			
		||||
        {
 | 
			
		||||
            get => _connectionString;
 | 
			
		||||
            set
 | 
			
		||||
            {
 | 
			
		||||
                _connectionString = value ?? "";
 | 
			
		||||
 | 
			
		||||
				var pattern = @"Max\s*pool\s*size\s*=\s*(\d+)";
 | 
			
		||||
				Match m = Regex.Match(_connectionString, pattern, RegexOptions.IgnoreCase);
 | 
			
		||||
				if (m.Success == false || int.TryParse(m.Groups[1].Value, out var poolsize) == false || poolsize <= 0) poolsize = 100;
 | 
			
		||||
				var connStrIncr = dicConnStrIncr.AddOrUpdate(_connectionString, 1, (oldkey, oldval) => oldval + 1);
 | 
			
		||||
				PoolSize = poolsize + connStrIncr;
 | 
			
		||||
				_connectionString = m.Success ?
 | 
			
		||||
					Regex.Replace(_connectionString, pattern, $"Max pool size={PoolSize}", RegexOptions.IgnoreCase) :
 | 
			
		||||
					$"{_connectionString};Max pool size={PoolSize}";
 | 
			
		||||
                var pattern = @"Max\s*pool\s*size\s*=\s*(\d+)";
 | 
			
		||||
                Match m = Regex.Match(_connectionString, pattern, RegexOptions.IgnoreCase);
 | 
			
		||||
                if (m.Success == false || int.TryParse(m.Groups[1].Value, out var poolsize) == false || poolsize <= 0) poolsize = 100;
 | 
			
		||||
                var connStrIncr = dicConnStrIncr.AddOrUpdate(_connectionString, 1, (oldkey, oldval) => oldval + 1);
 | 
			
		||||
                PoolSize = poolsize + connStrIncr;
 | 
			
		||||
                _connectionString = m.Success ?
 | 
			
		||||
                    Regex.Replace(_connectionString, pattern, $"Max pool size={PoolSize}", RegexOptions.IgnoreCase) :
 | 
			
		||||
                    $"{_connectionString};Max pool size={PoolSize}";
 | 
			
		||||
 | 
			
		||||
				pattern = @"Connection\s*LifeTime\s*=\s*(\d+)";
 | 
			
		||||
				m = Regex.Match(_connectionString, pattern, RegexOptions.IgnoreCase);
 | 
			
		||||
				if (m.Success) {
 | 
			
		||||
					IdleTimeout = TimeSpan.FromSeconds(int.Parse(m.Groups[1].Value));
 | 
			
		||||
					_connectionString = Regex.Replace(_connectionString, pattern, "", RegexOptions.IgnoreCase);
 | 
			
		||||
				}
 | 
			
		||||
                pattern = @"Connection\s*LifeTime\s*=\s*(\d+)";
 | 
			
		||||
                m = Regex.Match(_connectionString, pattern, RegexOptions.IgnoreCase);
 | 
			
		||||
                if (m.Success)
 | 
			
		||||
                {
 | 
			
		||||
                    IdleTimeout = TimeSpan.FromSeconds(int.Parse(m.Groups[1].Value));
 | 
			
		||||
                    _connectionString = Regex.Replace(_connectionString, pattern, "", RegexOptions.IgnoreCase);
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
				var minPoolSize = 0;
 | 
			
		||||
				pattern = @"Min\s*pool\s*size\s*=\s*(\d+)";
 | 
			
		||||
				m = Regex.Match(_connectionString, pattern, RegexOptions.IgnoreCase);
 | 
			
		||||
				if (m.Success) {
 | 
			
		||||
					minPoolSize = int.Parse(m.Groups[1].Value);
 | 
			
		||||
					_connectionString = Regex.Replace(_connectionString, pattern, "", RegexOptions.IgnoreCase);
 | 
			
		||||
				}
 | 
			
		||||
                var minPoolSize = 0;
 | 
			
		||||
                pattern = @"Min\s*pool\s*size\s*=\s*(\d+)";
 | 
			
		||||
                m = Regex.Match(_connectionString, pattern, RegexOptions.IgnoreCase);
 | 
			
		||||
                if (m.Success)
 | 
			
		||||
                {
 | 
			
		||||
                    minPoolSize = int.Parse(m.Groups[1].Value);
 | 
			
		||||
                    _connectionString = Regex.Replace(_connectionString, pattern, "", RegexOptions.IgnoreCase);
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
				FreeSql.Internal.CommonUtils.PrevReheatConnectionPool(_pool, minPoolSize);
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
                FreeSql.Internal.CommonUtils.PrevReheatConnectionPool(_pool, minPoolSize);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
		public bool OnCheckAvailable(Object<DbConnection> obj) {
 | 
			
		||||
			if (obj.Value.State == ConnectionState.Closed) obj.Value.Open();
 | 
			
		||||
			return obj.Value.Ping(true);
 | 
			
		||||
		}
 | 
			
		||||
        public bool OnCheckAvailable(Object<DbConnection> obj)
 | 
			
		||||
        {
 | 
			
		||||
            if (obj.Value.State == ConnectionState.Closed) obj.Value.Open();
 | 
			
		||||
            return obj.Value.Ping(true);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
		public DbConnection OnCreate() {
 | 
			
		||||
			var conn = new OracleConnection(_connectionString);
 | 
			
		||||
			return conn;
 | 
			
		||||
		}
 | 
			
		||||
        public DbConnection OnCreate()
 | 
			
		||||
        {
 | 
			
		||||
            var conn = new OracleConnection(_connectionString);
 | 
			
		||||
            return conn;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
		public void OnDestroy(DbConnection obj) {
 | 
			
		||||
			if (obj.State != ConnectionState.Closed) obj.Close();
 | 
			
		||||
			obj.Dispose();
 | 
			
		||||
		}
 | 
			
		||||
        public void OnDestroy(DbConnection obj)
 | 
			
		||||
        {
 | 
			
		||||
            if (obj.State != ConnectionState.Closed) obj.Close();
 | 
			
		||||
            obj.Dispose();
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
		public void OnGet(Object<DbConnection> obj) {
 | 
			
		||||
        public void OnGet(Object<DbConnection> obj)
 | 
			
		||||
        {
 | 
			
		||||
 | 
			
		||||
			if (_pool.IsAvailable) {
 | 
			
		||||
            if (_pool.IsAvailable)
 | 
			
		||||
            {
 | 
			
		||||
 | 
			
		||||
				if (obj.Value.State != ConnectionState.Open || DateTime.Now.Subtract(obj.LastReturnTime).TotalSeconds > 60 && obj.Value.Ping() == false) {
 | 
			
		||||
                if (obj.Value.State != ConnectionState.Open || DateTime.Now.Subtract(obj.LastReturnTime).TotalSeconds > 60 && obj.Value.Ping() == false)
 | 
			
		||||
                {
 | 
			
		||||
 | 
			
		||||
					try {
 | 
			
		||||
						obj.Value.Open();
 | 
			
		||||
					} catch (Exception ex) {
 | 
			
		||||
						if (_pool.SetUnavailable(ex) == true)
 | 
			
		||||
							throw new Exception($"【{this.Name}】状态不可用,等待后台检查程序恢复方可使用。{ex.Message}");
 | 
			
		||||
					}
 | 
			
		||||
				}
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
                    try
 | 
			
		||||
                    {
 | 
			
		||||
                        obj.Value.Open();
 | 
			
		||||
                    }
 | 
			
		||||
                    catch (Exception ex)
 | 
			
		||||
                    {
 | 
			
		||||
                        if (_pool.SetUnavailable(ex) == true)
 | 
			
		||||
                            throw new Exception($"【{this.Name}】状态不可用,等待后台检查程序恢复方可使用。{ex.Message}");
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
		async public Task OnGetAsync(Object<DbConnection> obj) {
 | 
			
		||||
        async public Task OnGetAsync(Object<DbConnection> obj)
 | 
			
		||||
        {
 | 
			
		||||
 | 
			
		||||
			if (_pool.IsAvailable) {
 | 
			
		||||
            if (_pool.IsAvailable)
 | 
			
		||||
            {
 | 
			
		||||
 | 
			
		||||
				if (obj.Value.State != ConnectionState.Open || DateTime.Now.Subtract(obj.LastReturnTime).TotalSeconds > 60 && (await obj.Value.PingAsync()) == false) {
 | 
			
		||||
                if (obj.Value.State != ConnectionState.Open || DateTime.Now.Subtract(obj.LastReturnTime).TotalSeconds > 60 && (await obj.Value.PingAsync()) == false)
 | 
			
		||||
                {
 | 
			
		||||
 | 
			
		||||
					try {
 | 
			
		||||
						await obj.Value.OpenAsync();
 | 
			
		||||
					} catch (Exception ex) {
 | 
			
		||||
						if (_pool.SetUnavailable(ex) == true)
 | 
			
		||||
							throw new Exception($"【{this.Name}】状态不可用,等待后台检查程序恢复方可使用。{ex.Message}");
 | 
			
		||||
					}
 | 
			
		||||
				}
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
                    try
 | 
			
		||||
                    {
 | 
			
		||||
                        await obj.Value.OpenAsync();
 | 
			
		||||
                    }
 | 
			
		||||
                    catch (Exception ex)
 | 
			
		||||
                    {
 | 
			
		||||
                        if (_pool.SetUnavailable(ex) == true)
 | 
			
		||||
                            throw new Exception($"【{this.Name}】状态不可用,等待后台检查程序恢复方可使用。{ex.Message}");
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
		public void OnGetTimeout() {
 | 
			
		||||
        public void OnGetTimeout()
 | 
			
		||||
        {
 | 
			
		||||
 | 
			
		||||
		}
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
		public void OnReturn(Object<DbConnection> obj) {
 | 
			
		||||
        public void OnReturn(Object<DbConnection> obj)
 | 
			
		||||
        {
 | 
			
		||||
 | 
			
		||||
		}
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
		public void OnAvailable() {
 | 
			
		||||
			_pool.availableHandler?.Invoke();
 | 
			
		||||
		}
 | 
			
		||||
        public void OnAvailable()
 | 
			
		||||
        {
 | 
			
		||||
            _pool.availableHandler?.Invoke();
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
		public void OnUnavailable() {
 | 
			
		||||
			_pool.unavailableHandler?.Invoke();
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
        public void OnUnavailable()
 | 
			
		||||
        {
 | 
			
		||||
            _pool.unavailableHandler?.Invoke();
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
	static class DbConnectionExtensions {
 | 
			
		||||
    static class DbConnectionExtensions
 | 
			
		||||
    {
 | 
			
		||||
 | 
			
		||||
		static DbCommand PingCommand(DbConnection conn) {
 | 
			
		||||
			var cmd = conn.CreateCommand();
 | 
			
		||||
			cmd.CommandTimeout = 5;
 | 
			
		||||
			cmd.CommandText = "select 1 from dual";
 | 
			
		||||
			return cmd;
 | 
			
		||||
		}
 | 
			
		||||
		public static bool Ping(this DbConnection that, bool isThrow = false) {
 | 
			
		||||
			try {
 | 
			
		||||
				PingCommand(that).ExecuteNonQuery();
 | 
			
		||||
				return true;
 | 
			
		||||
			} catch {
 | 
			
		||||
				if (that.State != ConnectionState.Closed) try { that.Close(); } catch { }
 | 
			
		||||
				if (isThrow) throw;
 | 
			
		||||
				return false;
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
		async public static Task<bool> PingAsync(this DbConnection that, bool isThrow = false) {
 | 
			
		||||
			try {
 | 
			
		||||
				await PingCommand(that).ExecuteNonQueryAsync();
 | 
			
		||||
				return true;
 | 
			
		||||
			} catch {
 | 
			
		||||
				if (that.State != ConnectionState.Closed) try { that.Close(); } catch { }
 | 
			
		||||
				if (isThrow) throw;
 | 
			
		||||
				return false;
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
        static DbCommand PingCommand(DbConnection conn)
 | 
			
		||||
        {
 | 
			
		||||
            var cmd = conn.CreateCommand();
 | 
			
		||||
            cmd.CommandTimeout = 5;
 | 
			
		||||
            cmd.CommandText = "select 1 from dual";
 | 
			
		||||
            return cmd;
 | 
			
		||||
        }
 | 
			
		||||
        public static bool Ping(this DbConnection that, bool isThrow = false)
 | 
			
		||||
        {
 | 
			
		||||
            try
 | 
			
		||||
            {
 | 
			
		||||
                PingCommand(that).ExecuteNonQuery();
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            catch
 | 
			
		||||
            {
 | 
			
		||||
                if (that.State != ConnectionState.Closed) try { that.Close(); } catch { }
 | 
			
		||||
                if (isThrow) throw;
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        async public static Task<bool> PingAsync(this DbConnection that, bool isThrow = false)
 | 
			
		||||
        {
 | 
			
		||||
            try
 | 
			
		||||
            {
 | 
			
		||||
                await PingCommand(that).ExecuteNonQueryAsync();
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            catch
 | 
			
		||||
            {
 | 
			
		||||
                if (that.State != ConnectionState.Closed) try { that.Close(); } catch { }
 | 
			
		||||
                if (isThrow) throw;
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user