2017-02-20 10 views
0

ОК, я думаю, мне нужно прояснить что-то о моем сообщении, о котором я забыл упомянуть ранее. Мое «тестовое приложение» в Visual Studio 2010 имеет базу данных SQL Server 2008 R2 EXPRESS. Однако, база данных не с автономной установки SQL Server Express. Скорее, файл данных, т. Е. .mdf и .ldf, выбираются в VS «Project \ Add New Item \ Data \ Service-based Database». Таким образом, файл данных «BkUp_SMO.mdf».Как отправить команду резервного копирования или восстановления в окно команд

Я не уверен, что это имеет значение, но я попробовал несколько примеров использования объектов Microsoft.SqlServer.Management, SMO, но безуспешно. Я добавил необходимые .DLL, то есть Microsoft.SqlServer.ConnectionInfo, Microsoft.SqlServer.Management.Sdk.Sfc, Microsoft.SqlServer.Smo, Microsoft.SqlServer.SmoExtended.

В моем коде у меня есть «использование» операторов для Microsoft.SqlServer.Management.Common и Microsoft.SqlServer.Management.Smo. Я даже добавил «использование» для System.Deployment.Application, чтобы установить строковое значение для пути к папке развертывания ClickOnce, где находится DB и файл журнала, используя String dbPath = ApplicationDeployment.CurrentDeployment.DataDirectory;

В дополнение к статье ссылка ниже, я также попытался примеры из другой статьи, то есть, «Резервное копирование базы данных SQL в C#» Backing up an SQL Database in C#

Разве это не возможно выполнить резервное копирование и восстановление на визуал Студия создала базу данных SQL?

Я написал приложение для тестирования в C# с целью отправки команды резервного копирования или восстановления SQL Server с помощью командной строки. Я на основе некоторых из моего кода на статье под заголовком: Резервное копирование и восстановление базы данных SQL Server из командной строки

Backup and Restore Your SQL Server Database from the Command Line

Полное применение будет user_App, где я не хочу конечного пользователя нужно открыть окно команд и ввести что угодно, поэтому я пытаюсь отправить необходимые команды с помощью кода C#, как показано ниже. Моя проблема заключается в том, что код работает без исключения, окно CMD открывается и закрывается, но без какой-либо резервной копии моего файла данных SQL Server 2008 R2 (.mdf).

Пожалуйста, укажите, что мне не хватает в моем коде, или лучший способ выполнить это. Также будет ли полная резервная копия автоматически архивировать файл журнала (.ldf)?

First code attempt 
private void btnChoose_Click(object sender, EventArgs e) 
{ 
    if (optBkupCMD.Checked) 
    { 
     StringBuilder bkup = new StringBuilder(); 
     bkup.Append("SqlCmd -E -S "); 
     bkup.Append(Environment.MachineName);//servername appears to be same as computer name. 
     bkup.Append(" –Q “BACKUP DATABASE [BkUp_SMO.mdf] TO DISK=’C:\\Backups\\BkUp_SMO.bak'”"); 
     string theBackup = bkup.ToString(); 

    using (Process process = new Process()) 
    { 
     process.StartInfo.FileName = "cmd.exe"; 
     process.StartInfo.RedirectStandardInput = true; 
     process.StartInfo.RedirectStandardOutput = true; 
     process.StartInfo.CreateNoWindow = false; 
     process.StartInfo.UseShellExecute = false; 
     process.StartInfo.Arguments = @"/C"; 
     process.Start(); 
     process.StandardInput.WriteLine(theBackup); 
     process.StandardInput.Flush(); 
     process.StandardInput.Close(); 
     process.WaitForExit(); 
     Console.WriteLine(process.StandardOutput.ReadToEnd()); 
    } 
else if (optRestoreCMD.Checked) 
{ 
    StringBuilder rstr = new StringBuilder(); 
    rstr.Append("SqlCmd -E -S "); 
    rstr.Append(Environment.MachineName); 
    rstr.Append(" –Q “RESTORE DATABASE [BkUp_SMO.mdf] FROM DISK=’C:\\Backups\\BkUp_SMO.bak'”"); 
    string restore = rstr.ToString(); 

    using (Process process = new Process()) 
    { 
     process.StartInfo.FileName = "cmd.exe"; 
     process.StartInfo.RedirectStandardInput = true; 
     process.StartInfo.RedirectStandardOutput = true; 
     process.StartInfo.CreateNoWindow = false; 
     process.StartInfo.UseShellExecute = false; 
     process.StartInfo.Arguments = @"/C"; 
     process.Start(); 
     process.StandardInput.WriteLine(restore); 
     process.StandardInput.Flush(); 
     process.StandardInput.Close(); 
     process.WaitForExit(); 
     Console.WriteLine(process.StandardOutput.ReadToEnd()); 
    } 
} 

}

My 2nd code attempt. 
using System; 
using System.Collections.Generic; 
using System.ComponentModel; 
using System.Data; 
using System.Data.SqlClient; 
using System.Drawing; 
using System.Linq; 
using System.Text; 
using System.Windows.Forms; 
using System.Threading; 
using Microsoft.Win32; 
using System.Deployment.Application; 
using System.Diagnostics; 
using System.IO; 
using Microsoft.SqlServer.Management.Smo; 
using Microsoft.SqlServer.Management.Common; 

namespace DB_Bkup_using_SMO 
{ 
    public partial class Bkup_in_CSharp : Form 
    { 
     public Bkup_in_CSharp() 
     { 
      InitializeComponent(); 
     } 

    private void btnBkViaCsharp_Click(object sender, EventArgs e) 
    { 
     string filePath = ApplicationDeployment.CurrentDeployment.DataDirectory; 
     BackupDatabase(filePath); 
    } 

    private void btnRestViaCsharp_Click(object sender, EventArgs e) 
    { 
     string filePath = ApplicationDeployment.CurrentDeployment.DataDirectory; 
     RestoreDatabase(filePath); 
    } 

    ///<summary> 
    ///Backup a whole database to the specified file. 
    ///</summary> 
    ///<remarks> 
    ///The database must not be in use when backing up. 
    ///The folder holding the file must have appropriate permissions given 
    ///</remarks> 
    ///<param name="backupFile">Full path to file to hold the backup</param> 
    public static void BackupDatabase(string backupFile) 
    { 
     try 
     { 
      ServerConnection con = new ServerConnection(@"Data Source=.\SQLEXPRESS;AttachDbFilename=|DataDirectory|\BkUp_SMO.mdf;Integrated Security=True;User Instance=True"); 

      Server server = new Server(con); 
      Backup source = new Backup(); 
      source.Database = "BkUp_SMO.mdf"; 
      source.Action = BackupActionType.Database; 

      source.LogTruncation = BackupTruncateLogType.Truncate; 
      BackupDeviceItem destination = new BackupDeviceItem(backupFile, DeviceType.File); 
      source.Devices.Add(destination); 

      source.SqlBackup(server); 
      con.Disconnect(); 
     } 
     catch (Exception ex) 
     { 
      MessageBox.Show(ex.Message + " " + ex.InnerException); 
     } 
    } 

    ///<summary> 
    ///Restore a whole database from a backup file. 
    ///</summary> 
    ///<remarks> 
    ///The database must be in use when backing up. 
    ///The folder holding the file must have appropriate permissions given. 
    ///</remarks> 
    ///<param name="backupFile">Full path to file to holding the backup</param> 
    public static void RestoreDatabase(string backupFile) 
    { 
     try 
     { 
      ServerConnection con = new ServerConnection(@"Data Source=.\SQLEXPRESS;AttachDbFilename=|DataDirectory|\BkUp_SMO.mdf;Integrated Security=True;User Instance=True"); 

      Server server = new Server(con); 
      Restore destination = new Restore(); 
      destination.Database = "BkUp_SMO.mdf"; 
      destination.Action = RestoreActionType.Database; 
      destination.Action = RestoreActionType.Log; 
      BackupDeviceItem source = new BackupDeviceItem(backupFile, DeviceType.File); 
      destination.Devices.Add(source); 
      destination.ReplaceDatabase = true; 
      destination.SqlRestore(server); 
     } 
     catch (Exception ex) 
     { 
      MessageBox.Show(ex.Message + " " + ex.InnerException); 
     } 

    } 
} 
} 
+0

Вам нужно «показать» черную линию командной строки? Если нет, есть простой способ резервного копирования, как и мой. –

+0

Hello Kay Lee. Нет, мне не нужно видеть окно команд. Однако он должен предоставить конечному пользователю возможность легко выполнить резервное копирование. Пожалуйста, поделитесь своим методом или образцом кода. – CodeMann

ответ

0

Это мой код для резервного копирования также SQL Server 2008 R2.

Этот тип базовых примеров кодов можно найти везде, если вы попытаетесь выполнить поиск.

Просто попробуйте, но не стоит отмечать это как ответ, потому что здесь много.

string masterdb_ConnectionString = string.Format(@"Data Source={0};Initial Catalog=Master;Connect Timeout=79;Encrypt=False;TrustServerCertificate=True;ApplicationIntent=ReadWrite;MultiSubnetFailover=False;Integrated Security=True;", System.Environment.MachineName); 

using (SqlConnection masterdbConn = new SqlConnection()) 
{ 
    masterdbConn.ConnectionString = mastedb_rConnectionString; 
    masterdbConn.Open(); 

    using (SqlCommand multiuser_rollback_dbcomm = new SqlCommand()) 
    { 
     multiuser_rollback_dbcomm.Connection = masterdbConn; 
     multiuser_rollback_dbcomm.CommandText= @"ALTER DATABASE yourdbname SET MULTI_USER WITH ROLLBACK IMMEDIATE"; 
     multiuser_rollback_dbcomm.CommandTimeout = 79; 

     multiuser_rollback_dbcomm.ExecuteNonQuery(); 
    } 
    masterdbConn.Close(); 
} 

SqlConnection.ClearAllPools(); 

string yourdb_ConnectionString= "connectionstring for yourdb here"; 

using (SqlConnection backupConn = new SqlConnection()) 
{ 
    backupConn.ConnectionString = yourdb_ConnectionString; 
    backupConn.Open(); 

    using (SqlCommand backupcomm = new SqlCommand()) 
    { 
     backupcomm.Connection = backupConn; 
     backupcomm.CommandText = string.Format(@"BACKUP DATABASE yourdbname TO DISK='c:\yourdbname.bak'", DateTime.Today.ToString("yyyy/MM/dd")); 
     backupcomm.CommandTimeout = 79; 

     backupcomm.ExecuteNonQuery(); 
    } 
    backupConn.Close(); 
} 

Обновление- Есть ли будет SQL Server 2008 R2 установлен на клиентов (пользователей ') компьютера?

Вы уже используете «Integrated Security = True», что означает, что пользователь, использующий эту строку соединения, будет иметь все (полные) разрешения в качестве администратора.Соединение с основной базой данных, очевидно, не является проблемой.

Что касается IMMEDIATE ROLLBACK, это завершает все незавершенные транзакции, завершенные так же, как «руки от БД до резервного копирования». Другими словами, прежде чем мы закроем ресторан, если мы не объявим, что этот ресторан будет закрыт, если мы вдруг закроем ресторан, некоторые клиенты могут по-прежнему иметь продукты, хотя ресторан закрывается.

Посмотрите, ALTER DATABASE IMMEDIATE ROLLBACK, Technet

This example uses the termination option WITH ROLLBACK IMMEDIATE in the first ALTER DATABASE statement. All incomplete transactions will be rolled back and any other connections to the AdventureWorks2008R2 sample database will be immediately disconnected.

И наконец, кажется, вы пытаетесь с SMO. Я испытал трудности в течение нескольких дней с ним, но, наконец, не смог и пошел другим путем.

+0

Привет, Кей. Я не совсем понимаю ваш пример кода. Похоже, что он подключается к базе данных MASTER, а не к моей базе данных. Из того, что я прочитал, для этого могут потребоваться повышенные учетные данные пользователя. Кроме того, не понимайте свою ссылку на «multiuser_rollback» или инструкцию ALTER db. Это должно быть распределенным «однопользовательским» конечным пользователем. Пожалуйста, обратитесь к моему правлению выше об этом, являющемся Visual Studio, созданным файлом данных SQL Express, а не отдельной установкой SQL Express. Спасибо – CodeMann

+0

@CodeMann, см. Мой обновленный ответ. Извините, у меня не так много времени из-за моих важных работ. Надеюсь, что это поможет. –

+0

Кей, я попробовал ваш пример кода и, выполнив код, сделал следующее исключение: связанная с сетью или конкретная ошибка экземпляра произошел при установлении соединения с SQL Server. Сервер не найден или не был доступен. Проверьте правильность имени экземпляра и настройте SQL Server для удаленного подключения. (поставщик: поставщик Named Pipes, ошибка: 40 - не удалось открыть соединение с SQL Server) System.ComponentModel.Win32Exception (0x80004005): система не может найти указанный файл. – CodeMann

Смежные вопросы