2011-10-05 55 views
6

在SQL Server Management Studio中執行腳本時,通常會生成顯示在消息窗口中的消息。例如,運行數據庫的備份時:SQL Server消息輸出上的C#句柄

已處理10%。

處理20%。

等...

加工1722608個網頁數據庫 '樣本',文件 'SAMPE' 的文件1.

100%的處理。

耗時1頁數據庫 '樣本',文件 'Sample_Log' 上文件1.

BACKUP DATABASE成功處理在202.985 秒(66.299 MB /秒)1722609頁。

我想能夠顯示這些消息在一個C#應用程序運行SQL腳本對數據庫。但是,我無法弄清楚在生成SQL時如何獲得從SQL輸出的消息的句柄。有人知道怎麼做這個嗎?對我來說,我不得不使用哪個連接框架。我對LINQ,NHibernate,實體框架,ADO.Net,企業庫相當滿意,並且很高興能夠學習新的。

回答

6

下面是我嘗試的示例代碼,它適用於我。 http://www.dotnetcurry.com/ShowArticle.aspx?ID=344

注意你所需要的代碼實際上是這一部分:

cn.Open(); 
cn.InfoMessage += delegate(object sender, SqlInfoMessageEventArgs e) 
{          
     txtMessages.Text += "\n" + e.Message;         
}; 

這是e.Message不斷返回消息回txtMessages(可以替換爲文本框或標籤)。

您也可以參考這篇文章: Backup SQL Server Database with progress

我的代碼的一個例子是以下幾點:

//The idea of the following code is to display the progress on a progressbar using the value returning from the SQL Server message. 
//When done, it will show the final message on the textbox. 
String connectionString = "Data Source=server;Integrated Security=SSPI;"; 
SqlConnection sqlConnection = new SqlConnection(connectionString); 

public void DatabaseWork(SqlConnection con) 
{ 
    con.FireInfoMessageEventOnUserErrors = true; 
    //con.InfoMessage += OnInfoMessage; 
    con.Open(); 
    con.InfoMessage += delegate(object sender, SqlInfoMessageEventArgs e) 
    { 
     //Use textBox due to textBox has Invoke function. You can also utilize other way. 
     this.textBox.Invoke(
      (MethodInvoker)delegate() 
      { 
       int num1; 
       //Get the message from e.Message index 0 to the length of first ' ' 
       bool res = int.TryParse(e.Message.Substring(0, e.Message.IndexOf(' ')), out num1); 

       //If the substring can convert to integer 
       if (res) 
       { 
        //keep updating progressbar 
        this.progressBar.Value = int.Parse(e.Message.Substring(0, e.Message.IndexOf(' '))); 
       } 
       else 
       { 
        //Check status from message 
        int succ; 
        succ = textBox.Text.IndexOf("successfully"); 
        //or succ = e.Message.IndexOf("successfully"); //get result from e.Message directly 
        if (succ != -1) //If IndexOf find nothing, it will return -1 
        { 
         progressBar.Value = 100; 
         MessageBox.Show("Done!"); 
        } 
        else 
        { 
         progressBar.Value = 0; 
         MessageBox.Show("Error, backup failed!"); 
        } 
       } 
      } 
     ); 
    }; 
    using (var cmd = new SqlCommand(string.Format(
     "Your SQL Script"//, 
     //QuoteIdentifier(databaseName), 
     //QuoteString(Filename)//, 
     //QuoteString(backupDescription), 
     //QuoteString(backupName) 
     ), con)) 
    { 
     //Set timeout = 1200 seconds (equal 20 minutes, you can set smaller value for shoter time out. 
     cmd.CommandTimeout = 1200; 
     cmd.ExecuteNonQuery(); 
    } 
    con.Close(); 
    //con.InfoMessage -= OnInfoMessage; 
    con.FireInfoMessageEventOnUserErrors = false; 
} 

爲了得到進度工作,你需要有一個實現此backgroundworker,您的應用程序不會凍結,並突然100%完成。