如何在同一查询/脚本中获得服务器角色和数据库角色?

时间:2018-11-22 02:23:42

标签: sql sql-server

是否可以在同一查询/脚本中获得所有数据库角色和服务器角色?如果可以,那么如何实现?

第一个查询赋予所有服务器角色,第二个查询赋予所有数据库角色,我可以使用“ Union All”将两个查询联接起来,但是第二个查询的问题是它没有显示任何数据库名称我需要。

select @@SERVERNAME AS 'ServerName',
       logins.default_database_name AS DatabaseSchemaName,
       logins.name As LoginName,
       logins.type As Type,
    logins.type_desc As Type_Desc,
       sr.[name] COLLATE DATABASE_DEFAULT AS 'Roles&Permissions'                 
from  sys.server_principals logins 
inner join sys.server_role_members srm on logins.principal_id = srm. member_principal_id
Inner join sys.server_principals sr ON role_principal_id = sr.principal_id 
where logins.is_fixed_role <>1


SELECT @@SERVERNAME as 'Server Name',
       logins.default_schema_name AS SchemaName,
       logins.name AS Name,
    logins.type As Type,
    logins.type_desc AS Type_Desc,
       db.[name] COLLATE DATABASE_DEFAULT AS 'Roles&Permissions'                 
FROM  sys.database_principals logins 
inner join sys.database_role_members drm on logins.principal_id = drm.member_principal_id
Inner join sys.database_principals db ON role_principal_id = db.principal_id

最终目标是获取具有角色(例如db_owner)的SQL Server实例中的所有数据库。这将存储在临时表中,我可以从中将其导出到excel。因此,当上述查询不起作用时,我在进行了一些阅读和在线搜索之后又写了一个查询。在下面的查询中,我将获得数据库角色以及相应的数据库,以便解决此问题,但是我也需要服务器角色,但不知道如何在此查询中添加这些角色。

DECLARE @DatabaseName SYSNAME,    
        @sql VARCHAR(1000)
DECLARE @ResultTable TABLE(DatabaseName VARCHAR(100), ServerName VARCHAR(100), Name VARCHAR(100), TypeDesc Varchar(100), DatabaseRole VARCHAR(100) )
DECLARE DatabaseCursor CURSOR 
     FOR SELECT Name FROM sys.databases
OPEN databaseCursor
FETCH NEXT FROM databaseCursor INTO @DatabaseName
WHILE (@@FETCH_STATUS = 0)
BEGIN
    SET @sql ='SELECT ''' + @DatabaseName + ''' AS [Database],
                      ''' +@@SERVERNAME +  '''AS [Server Name],
                      logins.name Name,
                      logins.type_desc TypeDesc, 
                      roles.name RoleName
               FROM '+@databaseName+'.sys.database_role_members rm
               INNER JOIN '+@databaseName +'.sys.database_principals roles ON rm.role_principal_id = roles.principal_id
               INNER JOIN '+@databaseName+'.sys.database_principals logins ON rm.member_principal_id = logins.principal_id'
    INSERT INTO @ResultTable EXEC(@sql)
    FETCH NEXT FROM databaseCursor INTO @databaseName
END
CLOSE databaseCursor 
DEALLOCATE databaseCursor 
SELECT * FROM @ResultTable;

1 个答案:

答案 0 :(得分:0)

如果确定具有服务器登录权限的成员以及数据库角色也可以满足您的要求,那么我们可以使用sys.database_principals

SELECT ROL.name AS Role_Name 
      ,MEM.name AS Member_Name 
      ,MEM.type_desc AS Member_Type 
      ,MEM.default_schema_name AS DefaultSchema 
      ,SP.name AS ServerLogin 
FROM sys.database_role_members AS DRM 
     INNER JOIN sys.database_principals AS ROL 
         ON DRM.role_principal_id = ROL.principal_id 
     INNER JOIN sys.database_principals AS MEM 
         ON DRM.member_principal_id = MEM.principal_id 
     INNER JOIN sys.server_principals AS SP 
         ON MEM.[sid] = SP.[sid] 
ORDER BY Role_Name 
        ,Member_Name;