使用SQL CLR的VS2013数据库项目 - 未解析的对象引用[servername \ username](数据库所有者)

时间:2015-03-29 10:16:10

标签: sql-server visual-studio sqlclr

我正在使用VS2013中的一个包含C#SQL CLR存储过程的数据库项目。

程序集所有者是[servername \ User123]
数据库所有者也是[servername \ User123](作为数据库所有者,该用户显然已经存在于服务器上。我通过在SQL CLR过程中注释掉代码并发布来成功发布数据库,以下情况发生在我取消注释掉那段代码。)

如果我尝试在VS中构建项目,我会收到错误:

Error   1   SQL71501: Assembly: [DatabaseProject] has an unresolved reference to object [servername\User123].   

...由...引起:

CREATE ASSEMBLY [DatabaseProject] AUTHORIZATION [servername\User123]
FROM 0x4D5A90000300000004000000FFFF0000B8000etcetcetcetc
WITH PERMISSION_SET = EXTERNAL_ACCESS
GO

因此,如果在VS中我在\ Security文件夹中添加了一个创建用户脚本:

CREATE USER [servername\User123] FOR LOGIN [servername\User123] WITH DEFAULT_SCHEMA = dbo
GO
GRANT CONNECT TO [servername\User123]

然后我可以构建项目。

但是,如果我尝试发布数据库,我会收到错误:

Creating [servername\User123]...
(47,1): SQL72014: .Net SqlClient Data Provider: Msg 15063, Level 16, State 1, Line 1 The login already has an account under a different user name.
(47,0): SQL72045: Script execution error.  The executed script:
CREATE USER [servername\User123] FOR LOGIN [servername\User123];
An error occurred while the batch was being executed.

是否有"权利"这样做的方法?

1 个答案:

答案 0 :(得分:1)

这个问题是由于对SQL Server如何将数据库的“所有者”作为数据库“主体”处理的简单误解所致。 “数据库所有者”的概念以两种不同的方式显示:

  1. 作为数据库级用户,其名称为dboprincipal_id1。现在,哪个服务器级登录映射到此特定用户(即“主体”)只是SID字段sys.database_principals字段中的值的问题。 1}}:

    SELECT sdp.*
    FROM   [sys].[database_principals] sdp
    WHERE  sdp.[principal_id] = 1;
    

    此字段将映射到SID中的sys.server_principals字段:

    SELECT sdp.*, '---' AS [---], ssp.*
    FROM   [sys].[database_principals] sdp
    INNER JOIN [sys].[server_principals] ssp
            ON ssp.[sid] = sdp.[sid]
    WHERE  sdp.[principal_id] = 1;
    

    请注意sys.database_principals中的以下字段:

    • type_desc
    • authentication_type
    • authentication_type_desc

    看看您的数据库当前是如何由Windows登录拥有的,请立即运行查询(第二个查询 - 包含两个表的查询)。接下来,将数据库更改为sa所有。接下来,打开一个新的查询选项卡。最后,在这个新窗口中运行相同的查询(以便您可以轻松地比较“之前”和“之后”结果),确保密切关注上面提到的4个字段以及sid领域。 (请注意,可以在没有登录的情况下创建用户,并且这些内容显然不会显示在加入{{1}的查询中},但这个问题专门处理登录 s )。

    从这一切中你应该看到,指定登录作为数据库的“所有者”,实际上,创建用户< / strong>对于登录:它只是更新了sys.server_principals 用户的定义。因此,拥有数据库的登录在该数据库中存在技术,但始终使用dbo的名称而不是其实际名称。这就是您收到以下错误的原因:

      

    登录已拥有不同用户名下的帐户。

  2. 作为数据库角色,可以添加数据库中的任何用户,以便获得这些权限。

  3. 修复:

    • \ Security 文件夹中删除dbo脚本。
    • 请改用CREATE USER