我有两个数据库,都属于sa
. 两个数据库中的所有对象都在 schema 中dbo
。
我有一个用户需要从连接来自和的表的视图bob
中进行选择。我不想向中的那些表授予直接权限,因为它们包含我不想看到的列。dbSafe
dbSafe
dbRestricted
bob
dbRestricted
bob
我已经授予bob
SELECT
了视图和SET DB_CHAINING ON
两个数据库的权限,但我仍然收到错误消息:
服务器主体“bob”无法在当前安全上下文中访问数据库“dbRestricted”。
我误解了跨数据库链接的作用吗?
如果源数据库中的源对象和目标数据库中的目标对象属于同一登录帐户,则 SQL Server 不会检查目标对象的权限。
数据库链接可以在这种情况下使用数据库所有者sa
和模式dbo
吗?或者它是否必须是显式登录帐户/非默认架构?
这个问题的公认答案建议在 中创建视图dbRestricted
并向 分配直接权限bob
,这在这种情况下可行吗?如果向该数据库添加视图对我来说不是一个选项(由于开发人员/供应商限制)怎么办?这不是跨数据库链接的目的吗?
您需要在 中为 bob 创建一个用户
dbRestricted
。您不需要授予 bob 访问dbRestricted
.这个最低限度完整的可验证示例显示了这一点:
如果我们删除跨数据库所有权链接,我们会看到失败:
之后使用它进行清理:
bob
如果您的用户可以从多语句表值函数 (TVF) 中选择或执行存储过程而不是视图,那么这可以更安全地完成(即无需在任一数据库上启用跨数据库所有权链接,并且没有为bob
in创建用户dbRestricted
)。跨数据库所有权链接的主要问题是您只能通过不创建等效用户来限制它
dbRestricted
(即模拟导致您发布此问题的情况)。但是两个数据库中的任何用户现在都可以在这个数据库中拥有对象访问对象dbRestricted
。假设大多数(如果不是全部)对象都在dbo
架构中,或者属于 的架构dbo
,那么这几乎就是一切。而且,即使这个 View 是dbRestricted
今天唯一可以访问的对象,您也无法阻止其他人在将来访问dbRestricted
.您可以使用模块签名来尽可能安全地实现此目标,而不是在您的系统中创建两个潜在的安全漏洞。我有示例代码显示如何在以下答案中,也在 DBA.SE 上:
基于另一个数据库中的表访问视图,而没有该其他数据库中的帐户