2016-04-20 79 views
0

我通過他們的.NET官方管理驅動程序(一個Nuget包)使用Oracle。如何在.NET中處理數據庫異常?

我的應用程序從頭開始使用與數據庫相同的連接,並在多個位置使用它來執行查詢。

在某些情況下,可能存在導致異常的連接「打嗝」。問題是,我不知道在這種情況發生時重試執行查詢的最佳策略是什麼。

有沒有一種常見的方法來解決這種情況?

謝謝。

+1

這是相當廣泛的,但爲什麼你使用單一連接,爲什麼不盡可能早地使用多個連接並打開連接並儘可能早地關閉。 – Habib

回答

1

我同意來自Habib的評論。

oracle .NET Package使用連接池。即使你打開多個連接,它也會相應地管理它們,這樣你就不必保持打開。

這意味着,你的代碼可以簡化,弄成這樣的僞代碼:

using(OracleConnection conn = MakeConnection()) 
{ 
    //do stuff with connection 

    //not necessary, but I always manually close connection. Doesn't hurt. 
    conn.Close(); 
} 

如果您即使在很小的執行是不確定的連接問題,你可以在它包裝try-catch塊如下:

try 
{ 
    using(OracleConnection conn = MakeConnection()) 
    { 
     //do stuff with connection 

     //not necessary, but I always manually close connection. Doesn't hurt. 
     conn.Close(); 
    } 
} 
catch(OracleException ex) 
{ 
    //handle exception. 
} 

OracleException看起來是.NET oracle軟件包的一個主要異常。請注意,可能有其他人想要更具體地瞭解。

+0

即使在出現異常情況下,「使用」塊也會照顧到Connection.Close()和Connection.Dispose()。我們不需要在代碼中指定它。 – Gokul

1

當查詢正在進行時,動態實例化連接會更容易。我不認爲一個簡單的try/catch會幫助你,因爲即使你重新初始化catch塊的連接,你也不得不以某種方式重新執行你的查詢。

我不建議這樣做,但你可以使用,如果一個異常被捕獲的是重新初始化連接的重試類....

public class Retry 
{ 
    public static void Do(Action action, TimeSpan retryInterval, int retryCount = 3) 
    { 
     Do<object>(() => 
     { 
      action(); 
      return null; 
     }, 
     retryInterval, retryCount); 
    } 

    public static T Do<T>(Func<T> action, TimeSpan retryInterval, int retryCount = 3) 
    { 
     var exceptions = new List<Exception>(); 

     for (int retry = 0; retry < retryCount; retry++) 
     { 
      try 
      { 
       if (retry > 0) 
        Thread.Sleep(retryInterval); 
       return action(); 
      } 
      catch (ConnectionException ex) 
      { 
       // ***Handle the reconnection in here*** 

       exceptions.Add(ex); 
      } 
     } 

     throw new AggregateException(exceptions); 
    } 
} 

然後,你可以打電話給你的查詢關鍵詞,比如

Retry.Do(() => MyQueryMethod, TimeSpan.FromSeconds(5)); 

很久以前,我從這個重試代碼中得到了基礎,不記得這個線程,但它不是我原來的代碼。儘管如此,我已經使用了很多東西。