脚本恢复使用xp_DirTree进行瞬态逻辑BAK文件名SQL Server

时间:2016-01-29 10:31:36

标签: sql sql-server sql-server-2008 tsql

您好我正在尝试将数据库从一台服务器恢复到另一台服务器,其中.bak文件的逻辑名称每天都会更改新的时间戳,到目前为止,我已成功使用Jeff提供的以下SQL脚本确定此名称现在在这里:http://www.sqlservercentral.com/Forums/Topic1200360-391-1.aspx

            --===== Create a holding table for the file names
             CREATE TABLE #File
                    (
                    FileName    SYSNAME,
                    Depth       TINYINT,
                    IsFile      TINYINT
                    )
            ;
            --===== Capture the names in the desired directory
                 -- (Change "C:\Temp" to the directory of your choice)
             INSERT INTO #File
                    (FileName, Depth, IsFile)
             EXEC xp_DirTree '\\filepath\',1,1
            ;
            --===== Find the latest file using the "constant" characters
                 -- in the file name and the ISO style date.
             SELECT TOP 1 
                    FileName
               FROM #File
              WHERE IsFile = 1
                AND FileName LIKE '%.bak' ESCAPE '_'
              ORDER BY FileName DESC
            ;
            DROP TABLE #File

现在我的问题是如何使用它作为脚本还原操作的基础?任何帮助将非常感谢!

2 个答案:

答案 0 :(得分:0)

通过扩展上面的内容来缓存目录路径并按时间顺序排序bak文件以确定使用哪个文件,然后将恢复操作与日志移动相结合,我找到了成功。

--==CHECK IF DB EXISTS IF IT DOES DROP IT
USE [master]
IF EXISTS(SELECT * FROM sys.databases where name='insert db name')
DROP DATABASE [insert db name]

--==START THE RESTORE PROCESS
DECLARE @FileName varchar(255), @PathToBackup varchar(255), @RestoreFilePath varchar(1000)
DECLARE @Files TABLE (subdirectory varchar(255), depth int, [file] int)
SET NOCOUNT ON

--==SET THE FILEPATH
SET @PathToBackup = '\\insert path to back up'

 --insert into memory table using dirtree at a single file level
 INSERT INTO @Files
 EXEC master.dbo.xp_DirTree @PathToBackup,1,1
     SELECT TOP 1 
        @FileName = [subdirectory]
     FROM 
        @Files
     WHERE
        -- get where it is a file
        [file] = 1
     AND 
     --==FIND THE LOGICAL NAME OF THE BAK FILE FROM THE CHRONILOGICALLY ORDERED LIST   
        subdirectory LIKE '%.bak'
     ORDER BY
        -- order descending so newest file will be first by naming convention
     subdirectory DESC

IF LEFT(REVERSE(@PathToBackup), 1) != '\'
BEGIN
    SET @PathToBackup = @PathToBackup + '\'
END
SET @RestoreFilePath = @PathToBackup + @FileName

--Grab the file path to restore from
SELECT @RestoreFilePath

--BEGIN THE RESTORE TO THE DESIGNATED SERVER
RESTORE DATABASE [insert name of database to restore] 
FROM DISK = @RestoreFilePath
WITH
FILE = 1,
--Create transactional log files on target
MOVE 'mdf_file_name' TO 'file_path\file.mdf',
MOVE 'log_file_name' TO 'file_path\file.ldf', REPLACE;

答案 1 :(得分:0)

这是我部分编写和部分收集的脚本。 功能包括:

  1. 仅导入一个备份文件,该备份文件的任何文件名都带有.bak 结尾。如果有更多文件,则仅导入一个文件,不导入任何文件 错误。
  2. 如果没有文件,则显示错误。
  3. 从数据库中踢出用户。
  4. 删除备份文件

    DECLARE @DBName nvarchar(255), @FileName nvarchar(255), @PathToBackup nvarchar(255), @RestoreFilePath nvarchar(1000)
    DECLARE @Files TABLE (subdirectory nvarchar(255), depth int, [file] int)
    SET XACT_ABORT, NOCOUNT ON
    
    SET @PathToBackup = N'I:\Folder'
    
    -- insert into our memory table using dirtree and a single file level
    INSERT INTO @Files
    EXEC master.dbo.xp_DirTree @PathToBackup,1,1
    
    SELECT 
    @FileName = [subdirectory]
    FROM 
    @Files
    WHERE
    -- get where it is a file
    [file] = 1
    AND    
    subdirectory LIKE N'%.bak'
    ORDER BY
    -- order descending so newest file will be first by naming convention
    subdirectory DESC
    
    IF LEFT(REVERSE(@PathToBackup), 1) != N'\'
    BEGIN
        SET @PathToBackup = @PathToBackup + N'\'
    END
    
    SET @RestoreFilePath = @PathToBackup + @FileName
    SET @DBName = LEFT(@FileName, LEN(@FileName)-4)
    --  SELECT 'Replace AdventureWorks2016CTP3 in this script with @DBName'
    
    SELECT @RestoreFilePath
    BEGIN TRY
    -- You can try to check if this command works "already":
    --  ALTER DATABASE  [@DBName] SET SINGLE_USER WITH ROLLBACK IMMEDIATE;
        ALTER DATABASE  [AdventureWorks2016CTP3] SET SINGLE_USER WITH ROLLBACK IMMEDIATE;
    
    -- You can try to check if this command works "already":
    --    RESTORE DATABASE [@DBName] 
        RESTORE DATABASE [AdventureWorks2016CTP3] 
        FROM DISK = @RestoreFilePath
        WITH FILE = 1,  NOUNLOAD,  REPLACE,  STATS = 10
    END TRY
    BEGIN CATCH
    -- You can try to check if this command works "already":
    --  ALTER DATABASE  [@DBName] SET MULTI_USER;
        ALTER DATABASE  [AdventureWorks2016CTP3] SET MULTI_USER;
        ; THROW
    END CATCH
    
    -- You can try to check if this command works "already":
    --  ALTER DATABASE  [@DBName] SET MULTI_USER;
        ALTER DATABASE  [AdventureWorks2016CTP3] SET MULTI_USER;
    
    -- This script is especially for the case where you replication from one location to another using backup and restore. 
    -- Typically you don't need transaction log backups as all changes will be wiped out on next transfer.
    -- You can try to check if this command works "already":
    --  ALTER DATABASE  [@DBName] SET RECOVERY SIMPLE;
        ALTER DATABASE  [AdventureWorks2016CTP3] SET RECOVERY SIMPLE;
    
    -- Delete file(s)
    -- NOTE: This works only if you give deletion permissions as defined in https://docs.microsoft.com/en-us/sql/database-engine/configure-windows/xp-cmdshell-server-configuration-option?view=sql-server-2017
    -- EXAMPLE: exec xp_cmdshell 'del "I:\Directory\AdventureWorks2016CTP3___.bak"'
    -- exec xp_cmdshell 'del "' + '@PathToBackup + ''\'' + @FileName + ''"''
    DECLARE @cmd NVARCHAR(MAX) = 'xp_cmdshell ''del "' + @PathToBackup + @FileName + '"''';
    -- SELECT @cmd
    EXEC (@cmd)