3

次の SMO コードを使用して、SQL Server データベースを復元しようとしています。

Server _server;
ServerConnection _conn;

public void Restore(string destinationPath)
{
   Restore res = new Restore();
   _conn = new ServerConnection { ServerInstance = "." };
   _server = new Server(_conn);

   try
   {
       string fileName = destinationPath;
       const string databaseName = "RelationAtOffice";

       res.Database = databaseName;
       res.Action = RestoreActionType.Database;
       res.Devices.AddDevice(fileName, DeviceType.File);

       res.PercentCompleteNotification = 10;
       res.ReplaceDatabase = true;
       res.PercentComplete += new PercentCompleteEventHandler(ProgressEventHandler);
       res.SqlRestore(_server);

       System.Windows.Forms.MessageBox.Show("Restore of " + databaseName + " Complete!", "Restore", MessageBoxButtons.OK, MessageBoxIcon.Information);
    }
    catch (SmoException exSMO)
    {
       System.Windows.Forms.MessageBox.Show(exSMO.ToString());
    }
    catch (Exception ex)
    {
        System.Windows.Forms.MessageBox.Show(ex.ToString());
    }
}

次のコードを正しい答えにリンクする理由。しかし、私のコードは機能していませんか? 一緒に好きなコード。私はwpfを使用し、次のリンクユーザーはwinappを使用しました

リンク

SMO エラー:

Microsoft.SqlServer.Management.Smo.FailedOperationException: サーバー 'MORTEZA' の復元に失敗しました。
---> Microsoft.SqlServer.Management.Smo.SmoException:
System.Data.SqlClient.SqlError: データベースが使用中のため、排他アクセスを取得できませんでした。
Microsoft.SqlServer.Management.Smo.ExecutionManager.ExecuteNonQueryWithMessage (StringCollection クエリ、ServerMessageEventHandler dbccMessageHandler、Boolean errorsAsMessages)
で Microsoft.SqlServer.Management.Smo.BackupRestoreBase.ExecuteSql (サーバー サーバー、StringCollection クエリ)
で Microsoft.SqlServer.Management.Smo. Restore.SqlRestore(サーバーサーバー)
E:\prozhe\RelationAtOfficeApp\RelationAtOfficeApp\RelationAtOfficeApp\Admin\AdministratorMainPage.xaml.cs:line 268 の RelationAtOfficeApp.Admin.AdministratorMainPage.Restore (String destinationPath) で

4

2 に答える 2

7

最も可能性の高い原因は次のとおりです。

  • サーバーからバックアップを取得しました -ファイルにData.mdfandData_Log.ldfをバックアップしましたBackup.bak

  • 同じ(サーバー)マシンで、同じデータベースを復元しようとしています

この場合、.mdfand.ldfを上書きする必要がありますが、SQL Server はまだそのデータベースを制御下に置いているため、そうはなりません。データとログ ファイルを上書きできないため、復元は失敗します。

これを解決するには、次の 2 つの方法があります。

  1. 「ファイルの再配置」を定義します。たとえば、復元時に新しいデータとログ ファイル名を定義します。これにより、データベースが復元され、ファイルが新しい名前で SQL Server データ ディレクトリに配置されます。

    これには、次のようなコードが必要です。

    ....  
    res.Devices.AddDevice(fileName, DeviceType.File);
    
    // define "file relocation" - for all "logical" files in a SQL Server database,
    // define a new physical location where the file will end up at          
    RelocateFile relocateDataFile = new RelocateFile("Data", @"(your data dir)\RestoredData.mdf");
    RelocateFile relocateLogFile = new RelocateFile("Log", @"(your log dir)\Data\RestoredData_log.ldf");
    
    res.RelocateFiles.Add(relocateDataFile);
    res.RelocateFiles.Add(relocateLogFile);
    
  2. 新しいファイルを作成したくない場合は、次のように設定して、既存のデータベースを復元操作で置き換えることを SMO 復元に指定できます。

    res.ReplaceDatabase = true;
    

    電話する前に

    res.SqlRestore(_server);
    

更新:サンプルで使用した論理ファイル名はもちろん単なるサンプルです。この場合、バックアップ ファイルには他の論理ファイル名が含まれている可能性が高く、コードでそれらのファイル名を使用する必要があります。

データベースに含まれる論理ファイル名は、基本的に次の 2 つの方法で確認できます。

  1. エラー メッセージに明確に記載されているように、SQL Server Management StudioFILELISTONLYのコマンドでオプションを使用して、ファイルを復元する前に検査することができます。次のようなことを試してください:RESTORE.bak

    RESTORE FILELISTONLY
    FROM DISK = N'path-and-full-file-name-of-your-bak-file-here.bak'
    

    これにより、ファイルに含まれる論理ファイル名と物理ファイル名を示す小さなグリッドが表示され.bakます。

  2. データベースがまだサーバーに接続されている場合はObject Explorer、SQL Server Management Studio で を使用して、データベースの論理ファイル名を確認できます。選択したデータベースを右クリックすると、このダイアログ ボックスが表示され、Filesセクションに探している情報が表示されます。

ここに画像の説明を入力

于 2012-10-14T20:32:39.330 に答える