Wie verschiebe ich SQL Server-Datenbankdateien?


103

Ich habe eine Datenbank und möchte die Dateien .mdfund .ldfan einen anderen Ort verschieben. Ich möchte den MSSQLSERVERDienst jedoch nicht beenden und nicht auf einen anderen Server exportieren.

Wie kann ich das machen?

Antworten:


154

Sie müssen den SQL Server-Dienst nicht beenden, um Datenbankdateien zu verschieben, aber Sie müssen die bestimmte Datenbank offline schalten. Dies liegt daran, dass Sie keine Dateien verschieben können, während auf sie zugegriffen wird, und die Datenbank offline geschaltet wird, um zu verhindern, dass die Dateien von der SQL Server-Anwendung verwendet werden.

Der Vorgang zum Verschieben ist ziemlich einfach. Detach / Attach wurde bereits beschrieben, ist aber bei weitem nicht so komplex.

Ändern Sie die Dateispeicherorte mit einem ALTER DATABASEBefehl:

USE master; --do this all from the master
ALTER DATABASE foo
MODIFY FILE (name='DB_Data1'
             ,filename='X:\NewDBFile\DB_Data1.mdf'); --Filename is new location

Beachten Sie, dass Sie den alten Speicherort in diesem Befehl nicht deklarieren müssen. Das Ändern dieses Pfads wird nicht sofort wirksam, sondern beim nächsten Start der Datenbank verwendet.

Setzen Sie die Datenbank offline

(Ich verwende WITH ROLLBACK IMMEDIATE, um alle derzeit offenen Transaktionen auszuschließen und zurückzusetzen.)

ALTER DATABASE foo SET OFFLINE WITH ROLLBACK IMMEDIATE;

Verschieben / Kopieren Sie die Dateien an den neuen Speicherort

Kopieren Sie einfach die Dateien mit Ihrer bevorzugten Methode (Click 'n Drag, XCopy, Copy-Item, Robocopy)

Schalten Sie die Datenbank online

ALTER DATABASE foo SET ONLINE;

Sie können sehen , diese im Detail beschrieben hier .


13
Das hat bei mir funktioniert. In meinem Fall musste ich auch die LDF-Datei mit dem ersten Befehl verschieben: zB USE master; --do this all from the master ALTER DATABASE foo MODIFY FILE (name='DB_Data1_log' ,filename='X:\NewDBFile\DB_Data1_log.ldf'); --Filename is new location
Dewi Rees

1
Kann auch zum Verschieben der Volltextindexdateien verwendet werden, indem der Dateiname so aktualisiert wird, dass er mit dem im Dialogfeld "Dateien" angezeigten übereinstimmt.
DShook

24
Stellen Sie nach dem Verschieben der Datenbankdatei (en) sicher, dass der Benutzer "NT SERVICE \ MSSQLSERVER" über Berechtigungen verfügt. Andernfalls wird beim Versuch, die Datenbank wieder online zu schalten, eine Fehlermeldung angezeigt.
Demonslay335

Was soll "Name" sein? In der Dokumentation hat es "logischer_name". Was meinen sie?
Johnny

2
@mlhDev Eigentlich ist in meinem Fall die MODIFY FILEReihenfolge änderbar. Wenn Sie zuerst MODIFY FILE ausführen, wird Ihnen mitgeteilt, dass der Befehl erfolgreich ausgeführt wurde und der Speicherort nach einer Offline-Online-Operation geändert wird (der Wortlaut ist anders, aber Sie haben die Idee). Die Reihenfolge Offline-> Dateien verschieben-> Online ist jedoch aus offensichtlichen Gründen von Bedeutung. Markieren Sie auch die Notiz von Demonslay335. Dateiberechtigung ist wichtig.
Lionet Chen

50

MDF- und LDF-Dateien sind geschützt und können nicht verschoben werden, solange die Datenbank online ist.

Wenn es Ihnen nichts ausmacht, die Datenbank zu stoppen, können Sie DETACHsie verschieben und dann verschieben ATTACH.

  • Klicken Sie mit der rechten Maustaste auf den Namen der Datenbank
  • Wählen Properties
  • Gehen Sie zur FilesRegisterkarte
  • Notieren Sie sich die Pathund FileNameMDF- und LDF-Dateien . Dieser Schritt ist wichtig, wenn Sie nicht nach fehlenden Dateien suchen möchten ...
  • Klicken Sie mit der rechten Maustaste auf den Datenbanknamen
  • Wählen Tasks -> Detach
  • Verschieben Sie die Dateien, wo Sie möchten
  • Klicken Sie mit der rechten Maustaste auf den DatabasesKnoten Ihres Servers
  • Wählen Attach
  • Klicken Sie auf die AddSchaltfläche
  • Zeigen Sie auf den neuen Speicherort
  • Klicken OK

Du solltest jetzt in Ordnung sein. Infos zum DETACH- ATTACHProzess finden Sie hier .

In dem Link zu DETACH- ATTACHwird die using- ALTER DATABASEAnweisung empfohlen, wenn die Datenbank auf derselben Instanz von SQL Server verbleibt. Weitere Informationen finden Sie unter Benutzerdatenbanken verschieben .

Wenn Sie es in Bewegung halten möchten, führen Sie einen BACKUP- aus RESTORE. Während des Wiederherstellungsprozesses können Sie den neuen Speicherort der Datenbankdateien definieren.


3
Ich empfehle, SQL Management Studio als Administrator zu öffnen, um Dateizugriffsprobleme beim
erneuten Anhängen

6

Führen Sie die folgenden Schritte aus, um Systemdatenbankdateien zu verschieben:

  1. Melden Sie sich als ein Benutzer in SSMS an

  2. Erstellen Sie aus Sicherheitsgründen eine Sicherungskopie der vom Benutzer erstellten Datenbank.

  3. Beenden Sie alle Sitzungen, die über SSMS mit dem Server verbunden sind.

  4. Führen Sie den folgenden Befehl aus, um den aktuellen Speicherort der Systemdatenbanken zu überprüfen:

    USE master;
    SELECT * FROM sys.master_files;

Ermitteln Sie den Pfad und notieren Sie den aktuellen Pfad der Dateien.

  1. Verwenden Sie TSQL, um den Dateipfad für alle Datenbanken außer master zu ändern:

    ALTER DATABASE database_name MODIFY FILE ( NAME = logical_name , FILENAME = 'new_path\os_file_name' )

Z.B:

ALTER DATABASE tempdb
MODIFY FILE ( NAME = tempdev
, FILENAME = "DestinationPath\tempdb.mdf");

ALTER DATABASE tempdb
MODIFY FILE ( NAME = templog
, FILENAME = "DestinationPath\templog.ldf");

ALTER DATABASE model
MODIFY FILE ( NAME = modeldev
, FILENAME = "DestinationPath\model.mdf");

ALTER DATABASE model
MODIFY FILE ( NAME = modellog
, FILENAME = "DestinationPath\modellog.ldf");

ALTER DATABASE msdb
    MODIFY FILE ( NAME = MSDBData
, FILENAME = "DestinationPath\msdbdata.mdf");

ALTER DATABASE msdb
    MODIFY FILE ( NAME = MSDBLog
, FILENAME = "DestinationPath\msdblog.ldf");

Nun wurde der Speicherort der Datei geändert.

Stellen Sie sicher, dass Sie sowohl ldf- als auch mdf-Dateien verschieben

  1. Klicken Sie in SSMS mit der rechten Maustaste auf den Server und wählen Sie Eigenschaften aus. Innerhalb der Eigenschaften gehen Sie zu den Datenbankeinstellungen. Ändern Sie die Datenbank-Standardspeicherorte für Daten und Protokoll in den Zielpfad. Melden Sie sich vom Server ab.

    ZB: wechseln C:\Program Files\Microsoft SQL Server\MSSQL12.SQLEXPRESS\MSSQL\DATA\zuE:\projects\DataBaseFiles\MSSQL\DATA\

  2. Beenden Sie die Instanz von SQL Server.

  3. Kopieren Sie die Datei oder die Dateien an den neuen Speicherort. Verschieben Sie die Dateien mit Robocopy, um die Zugriffsberechtigungen in den Zielordner zu kopieren. Öffnen Sie cmd, führen Sie es als Administrator aus und verwenden Sie den folgenden Befehl:

    robocopy / sec sourceFolder destinationFolder

Es ist besser, zum Quellspeicherort zu gehen, um den Befehl auszuführen. Löschen Sie andere Dateien als die kopierten Systemdatenbankdateien. Z.B:

 robocopy /sec .\DATA E:\projects\DataBaseFiles\MSSQL\DATA\

(Hier verschieben wir alle Systemdatenbankdateien an einen neuen Speicherort.)

  1. Zeigen Sie im Startmenü auf Alle Programme, zeigen Sie auf Microsoft SQL Server, zeigen Sie auf Konfigurationstools, und klicken Sie dann auf SQL Server-Konfigurations-Manager.

Führen Sie die folgenden Schritte in SQL Server Configuration Manager aus:

Klicken Sie im Knoten SQL Server-Dienste mit der rechten Maustaste auf die Instanz von SQL Server (z. B. SQL Server (MSSQLSERVER)), und wählen Sie Eigenschaften aus. Klicken Sie im Dialogfeld Eigenschaften von SQL Server (Instanzname) auf die Registerkarte Startparameter. Wählen Sie im Feld Vorhandene Parameter den Parameter –d aus, um die Stammdatendatei zu verschieben. Klicken Sie auf Aktualisieren, um die Änderung zu speichern. Ändern Sie im Feld Startparameter angeben den Parameter in den neuen Pfad der master-Datenbank. Wählen Sie im Feld Vorhandene Parameter den Parameter –l aus, um die Master-Protokolldatei zu verschieben. Klicken Sie auf Aktualisieren, um die Änderung zu speichern. Ändern Sie im Feld Startparameter angeben den Parameter in den neuen Pfad der master-Datenbank.

Der Parameterwert für die Datendatei muss dem Parameter -d und der Wert für die Protokolldatei dem Parameter -l folgen. Das folgende Beispiel zeigt die Parameterwerte für den Standardspeicherort der Stammdatendatei.

-dC:\Program Files\Microsoft SQL Server\MSSQL12.SQLEXPRESS\MSSQL\DATA\master.mdf
-lC:\Program Files\Microsoft SQL Server\MSSQL12.SQLEXPRESS\MSSQL\DATA\mastlog.ldf

Wenn der geplante Umzug für die Stammdatendatei E: \ SQLData lautet, werden die Parameterwerte wie folgt geändert:

-dE:\projects\DataBaseFiles\MSSQL\DATA\master.mdf
-lE:\projects\DataBaseFiles\MSSQL\DATA\mastlog.ldf

Beenden Sie die Instanz von SQL Server, indem Sie mit der rechten Maustaste auf den Instanznamen klicken und Beenden wählen. Starten Sie die Instanz von SQL Server neu.

  1. saMelden Sie sich als Benutzer in SSMS an und überprüfen Sie den Speicherort der Datenbankdateien, indem Sie die folgende Abfrage ausführen:

    USE master;
    SELECT * FROM sys.master_files;

Alles erledigt.


Mit der SQL-Funktion können Sie die Aufgabe für alle Datenbanken automatisieren: stackoverflow.com/a/19505918/439524
amuliar

3

Sie machen Schritt für Schritt:

  1. Alle Verbindungen schließen
    ALTER DATABASE MyDB SET SINGLE_USER WITH ROLLBACK IMMEDIATE

  2. Datenbank mit Status offline setzen
    ALTER DATABASE MyDB SET OFFLINE

  3. Zum neuen Pfad
    ALTER DATABASE MyDB MODIFY FILE (Name = MyDB, Filename = 'N: \ DATA \ MyDB.MDF')

  4. Datenbank mit Status online setzen
    ALTER DATABASE MyDB SET ONLINE


  5. Setze Multi-User ALTER DATABASE MyDB SET MULTI_USER


3

Es gibt eine Möglichkeit, Datenbankdatendateien zu verschieben (noch nicht sicher, ob dies für Protokolldateien möglich ist), ohne die Datenbank offline zu schalten.

Dejan Nakarada-Kordic hat eine Erklärung + Skripte für diese Methode hier: https://www.itprotoday.com/sql-server/move-database-fileses-without-taking-database-offline

In der Kurzversion fügen Sie am neuen Speicherort eine weitere Datenbankdatei hinzu und verwenden dann DBCC Shrinkfile mit der Option EMPTYFILE, um die Daten aus der alten Datei in die neue Datei zu verschieben. In diesem Fall können Sie die alte Datendatei entfernen.

Nicht meine Lösung, ich habe selbst nach dieser Lösung gesucht und fand sie für unsere Produktionsumgebung sehr nützlich.

Thorfinn


1

Befolgen Sie diese einfachen 4 Schritte:

  1. Öffnen Sie SSMS und wählen Sie oben im Fenster die Option Neue Abfrage . Kopieren Sie dann die folgende Abfrage und führen Sie sie aus, um den Pfad der Datenbank zu suchen, den wir auf einen neuen Pfad verschieben möchten, und notieren Sie den Pfad, den Sie in der CurrentLocationSpalte anzeigen.

SELECT name, physical_name AS CurrentLocation FROM sys.master_files WHERE database_id = DB_ID('DATABASE_NAME');

  1. Gehen Sie nun zu diesem Pfad und notieren Sie den Namen der Dateien " Database_Name.mdf" und " Database_Name_log.ldf" . Führen Sie dann die folgenden zwei Abfragen aus, um die Datenbank an einen bestimmten Speicherort zu verschieben.

ALTER DATABASE DATABASE_NAME MODIFY FILE ( NAME = DATABASE_FILE_NAME , FILENAME = 'NEW_PATH\DATABASE_NAME.mdf');

ALTER DATABASE DATABASE_NAME MODIFY FILE ( NAME = DATABASE_FILE_NAME_log , FILENAME = 'NEW_PATH\DATABASE_FILE_NAME_log.ldf');

  1. Nun, stoppen Sie den Server durch Rechtsklick auf Server_Namedie Sie im Objekt - Explorer (linke Seite) sehen.

    Bildbeschreibung hier eingeben

  2. Dann bewegen Sie beiden Dateien aus altem Pfad zu Neuem Pfad und den Server neu starten , indem Sie einen Rechtsklick auf Server_Name. Bestätigen Sie den neuen Datenbankpfad, indem Sie erneut die Abfrage des ersten Schritts ausführen.


0

Ich bin mir nicht sicher, ob dies der beste Weg ist (ich würde mich über Kommentare freuen, wenn Sie mir mitteilen, wie es nicht ist), aber es ist sehr einfach (und schnell, wenn Sie eine kleine Datenbank haben):

Sichern Sie zunächst die Datenbank in einer .bak-Datei. Stellen Sie dann die Datenbank aus derselben .bak-Datei wieder her, und wählen Sie die neuen Speicherorte für .mdf- und .ldf-Dateien unter den Dateioptionen für die Wiederherstellungsaufgabe aus.

Ich würde es nicht in einer Produktionsumgebung außerhalb eines Wartungsfensters tun, da Sie während der Wiederherstellung nicht auf die Datenbank zugreifen können. Andere Methoden, die ich oben gesehen habe, hätten jedoch ähnliche Nachteile. Nachdem die Wiederherstellungsaufgabe abgeschlossen ist, müssen Sie die alte Datei nicht löschen. Es ist automatisch erledigt.


1
Dieses Szenario hat einige Nachteile. Beim Wiederherstellen muss der ursprüngliche DB überschrieben oder umbenannt werden. Bei großen Datenbanken verursacht die Methode einen erheblichen E / A-Aufwand. Das Verschieben von Dateien, wie in Methoden zum Trennen von Anhängen oder Ändern von DB- Methoden beschrieben, ist viel schneller. Wenn die Dateien innerhalb derselben NTFS-Partition verschoben werden, handelt es sich nur um eine Metadatenoperation.
vonPryz

@Ali - Sichern und Wiederherstellen. Kann länger dauern, ist aber im Allgemeinen ein sicherer Weg. Siehe Aaron Bertrands Analyse unter: blogs.sqlsentry.com/aaronbertrand/bad-habits-file-backups Auch: sqlmag.com/blog/should-i-be-using-san-snapshots-backup-solution
RLF

Bei sehr großen Datenbanken führt dieser Ansatz (und der Detach / Attach-Ansatz) zu erheblichen Ausfallzeiten. Um dies zu vermeiden, versetzen Sie die Quellendatenbank in den vollständigen Wiederherstellungsmodus und führen Sie dann die erste Sicherungswiederherstellung mit nicht betriebsfähiger Ziel-DB durch. Sichern / Wiederherstellen Sie anschließend ein oder mehrere Transaktionsprotokolle. Die Datenbank muss nur während der letzten Sicherung / Wiederherstellung des Transaktionsprotokolls inaktiv sein, was eine beliebig kleine Zeit und Größe beinhalten kann. Natürlich müssen Sie auch einen anderen Namen wiederherstellen und anschließend einen Namenstausch durchführen. Dieser Ansatz entspricht in etwa dem Protokollversand.
Brian

0

So ergänzen Sie die vorhandenen Antworten: Hier ist ein Skript zum Erstellen der ALTER DATABASE ... MOVE ...Anweisungen für alle Datenbanken:

SELECT 'ALTER DATABASE ' + QUOTENAME(d.name) + 
       ' MODIFY FILE (name=' + QUOTENAME(f.name, '''') +
       ', filename=' + QUOTENAME(REPLACE(f.physical_name, 'C:\', 'D:\'), '''') +
       ');'
  FROM sys.master_files AS f 
       INNER JOIN sys.databases AS d ON f.database_id = d.database_id
 WHERE d.name <> 'master';

Hinweis:

  • Ersetzen Sie sie REPLACE(f.physical_name, 'C:\', 'D:\')durch die gewünschte Umwandlung der Dateipfade.

  • masterist ausgenommen, da sein Pfad durch die Startoptionen von SQL Server bestimmt wird ( Details finden Sie beispielsweise in dieser Antwort ).

Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.