Используя T-SQL, есть ли способ показать имя базы данных, для которой выполняется резервное копирование или восстановление? - PullRequest
1 голос
/ 05 марта 2019

У меня есть некоторый код, который я использую для мониторинга резервного копирования и восстановления, дайте мне «микрософт минутку» о том, когда может сделать, как долго он работает, и несколько другие части информации. Код ниже:

WITH CTE
AS (
SELECT @@SERVERNAME AS [ServerName]
    ,db_name(r.database_id) AS DatabaseName
    ,CONVERT(NUMERIC(6, 2), r.percent_complete) AS [PercentComplete]
    ,CONVERT(VARCHAR(20), DATEADD(ms, r.estimated_completion_time, GetDate()), 20) AS [ETACompletionTime]
    ,CONVERT(NUMERIC(10, 2), r.total_elapsed_time / 1000.0 / 60.0) AS [ElapsedMinutes]
    ,CONVERT(NUMERIC(10, 2), r.total_elapsed_time / 1000.0 / 60.0 / 60.0) AS [ElapsedHours]
    ,CONVERT(NUMERIC(10, 2), r.estimated_completion_time / 1000.0 / 60.0) AS [ETAMinutes]
    ,CONVERT(NUMERIC(10, 2), r.estimated_completion_time / 1000.0 / 60.0 / 60.0) AS [ETAHours]
    ,CONVERT(VARCHAR(1000), (
            SELECT SUBSTRING(TEXT, r.statement_start_offset / 2, CASE 
                        WHEN r.statement_end_offset = - 1
                            THEN 1000
                        ELSE (r.statement_end_offset - r.statement_start_offset) / 2
                        END)
            FROM sys.dm_exec_sql_text(sql_handle) --sql_handle is a column from sys.dm_exec_requests
            )) AS [TSQLCode]
FROM sys.dm_exec_requests r
WHERE command IN (
        'RESTORE DATABASE'
        ,'BACKUP DATABASE'
        )
)
SELECT [ServerName]
,SUBSTRING([TSQLCode], CHARINDEX('DATABASE [', [TSQLCode]) + 10, CHARINDEX(']', [TSQLCode], (CHARINDEX('DATABASE [', [TSQLCode]) + 10)) - (CHARINDEX('DATABASE [', [TSQLCode]) + 10)) AS [DatabaseName]
,[PercentComplete]
,[ETACompletionTime]
,[ElapsedMinutes]
,[ElapsedHours]
,[ETAMinutes]
,[ETAHours]
,Cast(CASE 
        WHEN charindex('Rest', [TSQLCode], 0) > 0
            THEN 'Restoring'
        ELSE 'Backup'
        END AS VARCHAR(10)) AS BackupRestore
,[TSQLCode]
FROM CTE

Этот код по большей части работает ... до тех пор, пока база данных инкапсулирована в [имя_базы_данных] (квадратные скобки). Если это не так, вы получите следующую ошибку.

Invalid length error

Со всеми базами данных, которые нам нужно восстановить, с тем, что у нас есть множество заданий, которые выполняют восстановление, я не знаю, какие задания имеют или не имеют квадратных скобок. И я должен учитывать специальные задания резервного копирования \ восстановления от людей, которые могут не использовать квадратные скобки.

Поэтому я ищу способ получить базу данных, без разбора, для резервного копирования или восстановления.

1 Ответ

2 голосов
/ 05 марта 2019

замена charindex на patindex('%DATABASE[ \[]%', [TSQLCode]) испортит ваш +10, может быть проще просто заменить резервную базу данных и восстановить базу данных, ltrim и charindex '', чтобы вывести слово после. Я не тестировал «код» ниже, но мне он показался правильным. возиться по желанию!

left(ltrim(replace(replace(TSQLCode, 'backup database',''),'restore database','')),charindex(' ',ltrim(replace(replace(TSQLCode, 'backup database',''),'restore database',''))))

edit: теперь, когда передо мной sql server, попробуйте:

WITH CTE
AS (
SELECT @@SERVERNAME AS [ServerName]
    ,db_name(r.database_id) AS DatabaseName
    ,CONVERT(NUMERIC(6, 2), r.percent_complete) AS [PercentComplete]
    ,CONVERT(VARCHAR(20), DATEADD(ms, r.estimated_completion_time, GetDate()), 20) AS [ETACompletionTime]
    ,CONVERT(NUMERIC(10, 2), r.total_elapsed_time / 1000.0 / 60.0) AS [ElapsedMinutes]
    ,CONVERT(NUMERIC(10, 2), r.total_elapsed_time / 1000.0 / 60.0 / 60.0) AS [ElapsedHours]
    ,CONVERT(NUMERIC(10, 2), r.estimated_completion_time / 1000.0 / 60.0) AS [ETAMinutes]
    ,CONVERT(NUMERIC(10, 2), r.estimated_completion_time / 1000.0 / 60.0 / 60.0) AS [ETAHours]
    ,replace(replace(CONVERT(VARCHAR(1000), (
            SELECT replace(replace(replace(replace(replace(replace(SUBSTRING(TEXT, r.statement_start_offset / 2, CASE 
                        WHEN r.statement_end_offset = - 1
                            THEN 1000
                        ELSE (r.statement_end_offset - r.statement_start_offset) / 2
                        END),']',''),'[',''),char(10),' '),char(13), ' '),char(9), ' '),'  ',' ')
            FROM sys.dm_exec_sql_text(sql_handle) --sql_handle is a column from sys.dm_exec_requests
            )),'  ',' '),'  ',' ') AS [TSQLCode]
FROM sys.dm_exec_requests r
WHERE command IN (
        'RESTORE DATABASE'
        ,'BACKUP DATABASE'
        )
)
SELECT [ServerName]
,SUBSTRING([TSQLCode], CHARINDEX('DATABASE ', [TSQLCode]) + 9, CHARINDEX(' ', [TSQLCode], (CHARINDEX('DATABASE ', [TSQLCode]) + 9)) - (CHARINDEX('DATABASE ', [TSQLCode]) + 9)) AS [DatabaseName]
,[PercentComplete]
,[ETACompletionTime]
,[ElapsedMinutes]
,[ElapsedHours]
,[ETAMinutes]
,[ETAHours]
,Cast(CASE 
        WHEN charindex('Rest', [TSQLCode], 0) > 0
            THEN 'Restoring'
        ELSE 'Backup'
        END AS VARCHAR(10)) AS BackupRestore
,[TSQLCode]
FROM CTE

обновлено для удаления (\ n \ r \ t) (новая строка, возврат каретки, табуляция) и "попытка" очистить достаточно двойных пробелов, чтобы не мешать выводу.

один из многих, кто знает, что таблица ascii хороша.

удаление [] в cte, затем обработка без [], сработало в моих тестах здесь.

...