tSQLtを既存のデータベースにインストールしようとすると、次のエラーが発生します。
マスターデータベースに記録されているデータベース所有者SIDは、データベース ''に記録されているデータベース所有者SIDとは異なります。ALTER AUTHORIZATIONステートメントを使用してデータベース ''の所有者をリセットすることにより、この状況を修正する必要があります。
回答:
この問題は、データベースがバックアップから復元され、データベース所有者のSIDがマスターデータベースにリストされている所有者のSIDと一致しない場合に発生する可能性があります。エラーメッセージで推奨されている「ALTERAUTHORIZATION」ステートメントを使用するソリューションは次のとおりです。
DECLARE @Command VARCHAR(MAX) = 'ALTER AUTHORIZATION ON DATABASE::[<<DatabaseName>>] TO
[<<LoginName>>]'
SELECT @Command = REPLACE(REPLACE(@Command
, '<<DatabaseName>>', SD.Name)
, '<<LoginName>>', SL.Name)
FROM master..sysdatabases SD
JOIN master..syslogins SL ON SD.SID = SL.SID
WHERE SD.Name = DB_NAME()
PRINT @Command
EXEC(@Command)
これをtSQLt.class.sqlスクリプトの先頭に追加しました
declare @user varchar(50)
SELECT @user = quotename(SL.Name)
FROM master..sysdatabases SD inner join master..syslogins SL
on SD.SID = SL.SID
Where SD.Name = DB_NAME()
exec('exec sp_changedbowner ' + @user)
tSQLt Version: 1.0.5873.27393
、より簡単な解決策のようです。MS SQL Serverの2019 DeveloperとSSMS 18を使用して
ネクロマニング:
SQL-Server 2000ビュー(非推奨)を使用したくない場合は、次を使用します。
-- Restore sid when db restored from backup...
DECLARE @Command NVARCHAR(MAX)
SET @Command = N'ALTER AUTHORIZATION ON DATABASE::<<DatabaseName>> TO <<LoginName>>'
SELECT @Command = REPLACE
(
REPLACE(@Command, N'<<DatabaseName>>', QUOTENAME(SD.Name))
, N'<<LoginName>>'
,
QUOTENAME
(
COALESCE
(
SL.name
,(SELECT TOP 1 name FROM sys.server_principals WHERE type_desc = 'SQL_LOGIN' AND is_disabled = 'false' ORDER BY principal_id ASC )
)
)
)
FROM sys.databases AS SD
LEFT JOIN sys.server_principals AS SL
ON SL.SID = SD.owner_sid
WHERE SD.Name = DB_NAME()
PRINT @command
EXECUTE(@command)
GO
また、奇妙な名前のデータベースまたはユーザーのバグを防ぎ、ユーザーが関連付けられていない場合のバグを修正します(saログインを使用)。
私もこの問題に遭遇し、ターゲットデータベースの所有者がマスターデータベースに存在しないことがわかりました。そのユーザーをマスターデータベースにマッピングすると、問題が解決しました。