Sql-Server

我怎樣才能知道什麼數據庫/過程正在使用連結伺服器?

  • January 28, 2016

我有 3 台伺服器,其中一台配置了指向另一台的連結伺服器 - 我將其稱為伺服器 A。伺服器 A 有 100 多個用於各種目的的使用者數據庫。伺服器 B 正在執行我們正在嘗試消除的 SQL 2005。伺服器 C 有來自伺服器 B 的一些數據庫的副本,我們正在將應用程序從伺服器 B 的數據庫副本遷移到伺服器 C。

當我在伺服器 B 上時,我可以看到從伺服器 A 到某個數據庫的連接,但我不知道如何判斷伺服器 A 的哪些過程、任務或作業正在使用與伺服器 B 的連結伺服器連接。

為了停用伺服器 B 上的數據庫,我需要將伺服器 A 的連接重新指向伺服器 C 上的數據庫;但為了做到這一點,我需要知道伺服器 A 上的哪些過程、任務或作業正在使用該連接,以便可以更新它們。

有沒有辦法在不禁用連結伺服器的情況下查看連結伺服器上的依賴關係以查看開始失敗的原因?

好吧,您可以解析伺服器 A 上的過程(只要它們未加密)和作業,以查找連結伺服器的名稱 - 但請記住,這些請求可以通過應用程序傳入,從 ad hoc 傳入SQL,動態建構等,所以這不會擷取所有內容。如果連結的伺服器名稱是可能在程式碼或註釋中自然找到的常用術語,這也會產生誤報。

DECLARE @sql NVARCHAR(MAX) = N'', 
 @p NVARCHAR(MAX), 
 @linked_server SYSNAME = N'%linked_server_name%';

SET @p = N' UNION ALL SELECT N''$db$'', s.name,
  o.name FROM $db$.sys.sql_modules AS p
  INNER JOIN $db$.sys.objects AS o
  ON p.[object_id] = o.[object_id]
  INNER JOIN $db$.sys.schemas AS s
  ON o.[schema_id] = s.[schema_id]
 WHERE p.definition LIKE @lsn';

SELECT @sql = @sql + REPLACE(@p, N'$db$', QUOTENAME(name))
 FROM sys.databases; -- may want to filter out system dbs, offline, etc

SET @sql = STUFF(@sql, 1, 11, N'') + N';';

EXEC sys.sp_executesql @sql, N'@lsn SYSNAME', @linked_server;

SELECT j.name FROM msdb.dbo.sysjobs AS j
 INNER JOIN msdb.dbo.sysjobsteps AS s
 ON j.job_id = s.job_id
 WHERE s.command LIKE @linked_server;

當然,您可能需要先尋找同義詞:

DECLARE @sql NVARCHAR(MAX) = N'', 
 @p NVARCHAR(MAX), 
 @synonym_prefix SYSNAME = N'[linked_server_name].%';

SET @p = N' UNION ALL SELECT N''$db$'', s.name, o.name
  FROM $db$.sys.synonyms AS o
  INNER JOIN $db$.sys.schemas AS s
  ON o.[schema_id] = s.[schema_id]
 WHERE s.base_object_name LIKE @spre';

SELECT @sql = @sql + REPLACE(@p, N'$db$', QUOTENAME(name))
 FROM sys.databases; -- may want to filter out system dbs, offline, etc

SET @sql = STUFF(@sql, 1, 11, N'') + N';';

EXEC sys.sp_executesql @sql, N'@spre SYSNAME', @synonym_prefix;

然後使用這些同義詞名稱而不是'linked_server_name'上面的。

引用自:https://dba.stackexchange.com/questions/127613