為什麼不允許組的數據庫所有權?哪個使用者應該擁有數據庫?
根據微軟“SQL Server 數據庫的 ALTER AUTHORIZATION”:
對新主人的要求:
新的所有者主體必須是以下之一:
- SQL Server 身份驗證登錄。
- 代表 Windows 使用者(不是組)的 Windows 身份驗證登錄名。
- 通過代表 Windows 組的 Windows 身份驗證登錄進行身份驗證的 Windows 使用者。
顯然,一個組不能擁有一個數據庫。確實在呼叫
alter authorization on database::MyDatabase to [domainname\SQLServerAdminGroup]
導致消息
數據庫類型的實體不能由角色、組、approle 或映射到證書或非對稱密鑰的主體擁有。
讓一個 SQL 管理員的 Windows 安全組的單個成員成為數據庫所有者似乎很容易受到該帳戶被廢棄的影響。這似乎是在這個問題中擁有員工離開公司時發生的事情。 這個答案總結了數據庫所有權是 NT 主要主體的問題,如下所示:
將數據庫所有權預設設置為 NT 主要主體會產生包含問題(所有者是由 AD 管理的 NT SID,並且不與數據庫文件一起旅行,NT 帳戶可以是拇指石等)。
我是 SQL Server 管理的新手,與例如文件的所有權相比,只有主要主體才能成為所有者的限制比較突出。根據微軟“如何分配和更改所有者”:
預設情況下,新對象的所有者是在附加到創建過程的訪問令牌中標識為預設所有者的安全主體。…當使用者是管理員組或域管理員組的成員時,會出現唯一的例外情況。在這兩種情況下,使用者訪問令牌中的 Owner 欄位都包含組的 SID,而不是單個使用者帳戶的 SID。假設是管理帳戶僅用於管理系統,而不用於任何個人目的。因此,由一個管理員創建的對象可以由同一組中的其他管理員管理。
換句話說,
- 對於管理員創建的文件,文件的**預設所有者是組,而
- 對於數據庫,所有者不能是組。
這給我留下了以下問題:
- 數據庫不能由次要委託人擁有是否存在根本原因?
- 哪個主體應該擁有數據庫?有最佳實踐嗎?如果是這樣,最佳實踐背後的原因是什麼?
老實說,
sa
或者俱有絕對最低權限的禁用 SQL Server 帳戶是最佳選擇。至於為什麼?好吧,我可以寫三到四段,或者我可以分享我最喜歡的文章,關於什麼帳戶應該擁有數據庫以及為什麼。涵蓋所有基礎的非常徹底的解釋。強烈推薦。這是核心摘錄:(編輯以添加此 2020 年 1 月 9 日)
好吧,那sa呢?它已經可以做它想做的任何事情,所以它不像我們在授予額外的權限,它不能退出或被解僱,無論如何也不應該有人使用它。哎呀,你可能有殘疾,對吧?你知道嗎?這實際上是完全合理的!事實上,sa 是一個非常常見的 id,可用作數據庫所有者。
唯一的風險是如果數據庫變得可信。然後,您可以創建可以充當 sa 的儲存過程。老實說,即使那樣,這也不是一個巨大的風險,因為您必須具有模擬權限才能使用 EXECUTE AS 子句創建過程。這意味著為了創建該儲存過程,您已被明確授予模擬 db_owner 角色成員的能力(請,請,請不要這樣做)或自己成為 db_owner 的成員。這確實意味著擁有 db_owner 的人可以成為系統管理員,但風險也很小。TRUSTWORTHY 並不常見,希望如果您使用它,您會了解風險並避免危險的權限。
但是,風險就是風險。因此,如果我們感覺特別偏執和/或有一個非常敏感的系統,最簡單的解決方案是創建一個 SQL 登錄(使用一個愚蠢複雜的密碼,因為沒有人會用它登錄),禁用它,然後使用它作為所有者。
- 數據庫不能由次要委託人擁有是否存在根本原因?
我不是 100% 確定這個限制的原因,儘管我懷疑它與模仿(即成為)那個 SID 的能力有關。某些操作可以到達實例之外(例如作業系統、文件系統等),其邏輯通常是模擬 Windows 登錄,或使用 SQL Server 服務帳戶進行 SQL 登錄。一個程序不能模擬一個組。但是,如果 SID 是 Windows 組,我猜邏輯也可以使用 SQL Server 服務帳戶,不是嗎?我不知道,除了它只是武斷之外,想不出任何半途而廢的合理解釋。
不過,我可以說,我不同意不應將 Windows 登錄用作數據庫所有者的概念/建議,至少出於上述原因。在將數據庫備份和還原到不同的伺服器上、在 SQL Server 中創建的 SID 或來自 Windows 或 AD 的 SID 之間沒有太大區別。在任何一種情況下,您都可以很容易地恢復到不知道數據庫所有者 SID 的實例上。編寫腳本並傳輸登錄以在新實例上重新創建可能會稍微容易一些,這樣它就可以
dbo
在恢復時匹配數據庫中使用者的 SID。但是,所有者 SID 最初將是執行的 SID,RESTORE
並且無論如何都需要更新某些內容(除非您使用sa
因為這保證在新實例上,但這並不是一個好的選擇;稍後會詳細介紹)。最後,在數據庫本身中更改所有者和使用者都相當容易,或者在還原後簡單地將數據庫中使用者的 SID 更新為sys.databases
新實例上的現有 SID。有幾種選擇,沒有一個是那麼困難的。dbo``dbo
並且對 SID 不“與數據庫文件一起旅行”的擔憂不應該適用於物理 MDF、NDF、LDF 文件,因為這些文件應該由 SQL Server 服務帳戶擁有,而不是數據庫所有者。
- 哪個主體應該擁有數據庫?有最佳實踐嗎?如果是這樣,最佳實踐背後的原因是什麼?
這裡的答案歸結為優先事項:便利性xor安全性?選一個。
一個問題是數據庫所有者用於確定某些操作的權限。就其本質而言,該
sa
帳戶不受任何限制(除了可能對其自身施加限制,但現在我們只是傻了)。我不確定該操作列表是什麼,但使用低特權 SQL Server 登錄作為所有者絕對是人們發現這些操作是什麼的一種方式;-)(因此為什麼這麼多人更喜歡使用sa
,即使這是一個糟糕的選擇;稍後會詳細介紹)。該問題與執行其中包含的程式碼時可能發生的特權升級問題是分開的
EXECUTE AS...
。如果對像有效地由(直接或存在於-owned 模式中)擁有,它是否執行owner
或dbo
不產生影響。從技術上講,這實際上與使用if是固定伺服器角色成員的登錄名創建的 proc 相同。在這些情況下,如果啟用了數據庫屬性,則執行模組(儲存過程、觸發器、標量 UDF、表值函式等)的任何人都將承擔這些實例級權限。Laughing Vergil 連結到的文章提到需要獲得許可dbo``dbo``EXECUTE AS [bob]``[bob]``sysadmin``TRUSTWORTHY``IMPERSONATE``EXECUTE AS
,但那是誤導。IMPERSONATE
僅在使用EXECUTE AS ...
. _ 但是,IMPERSONATE
在執行使用. _ 因此,這不是一扇完全敞開的門,但是如果數據庫所有者登錄名是固定伺服器角色的成員,並且在該數據庫中啟用,則任何對創建的 proc 具有 EXEC 權限的人都將以系統管理員身份執行該模組中的程式碼.EXECUTE AS...``EXECUTE AS 'dbo'
sysadmin
TRUSTWORTHY
太棒了:
- 如果您想要無需考慮任何事情的便利,或者可能需要幾分鐘來設置適當的安全性,那麼
sa
它會盡可能方便。- 如果您想要適當的安全性並且可以接受偶爾遇到權限錯誤,這會導致一些額外的小工作(雖然不多)來設置模組簽名(並且在初始設置之後,根據需要更快/更容易地添加額外的權限,如果需要)然後使用低權限的 SQL Server 登錄。
就個人而言,我使用第二個選項(低權限 SQL Server 登錄)進行生產,並且為了方便我使用的測試/展示
sa
或其他一些sysadmin
登錄。