You are not Logged in
Would you like to Login or Register

Today is: 04 July 2009
Check this months hot topics

GRANT Permissions on all of your Stored Procedures using a query

Permissions are an essential security feature, and you'll often create Roles and Users when you copy your Database live. Rather than using the permissions dialog boxes in Enterprise Manager you can write some T-SQL to perform the GRANTS in Query Analyzer. This is relatively simple process.

Use dbo.sysobjects to get a list of your Stored Procedures

SELECT name
FROM dbo.sysobjects
WHERE type = 'P' AND category = 0

In the WHERE clause setting type to 'P' will only return the Stored Procedures from dbo.sysobjects. Of these records those with a category value of 0 are user stored procedures, you'll notice that I have added this to the WHERE clause.

Don't be tempted to use a CURSOR to get to all your stored procs

CURSORs utilise loads of resource, they're slow, and this only increases as table size increases. Try and use a simple loop to iterate rows in a table, I normally drive this using a MIN() on Unique field, selecting the next lowest value in the table, this is much faster than a cursor. See below.

DECLARE @ID    integer,
       @LAST_ID integer,

--Initialise the variable
SET @LAST_ID = 0

--Loop until we've returned all the records
WHILE @LAST_ID IS NOT NULL
BEGIN

    -- Get next lowest value
    SELECT @ID = MIN(id)
    FROM dbo.sysobjects
    WHERE id > @LAST_ID  AND type = 'P' AND category = 0
    
    SET @LAST_ID = @ID
END

Once you've got your loop working, you'll want to grab the details of the stored procedure and perform the GRANT. On each iteration of the loop you can build a SQL string then execute it using xp_execresultset

DECLARE @DB  sysname ; set @DB = DB_NAME()
DECLARE @U  sysname ; set @U = QUOTENAME('<username>')

DECLARE @ID           integer,
        @LAST_ID     integer,
        @NAME        varchar(1000),
        @SQL         varchar(4000)

SET @LAST_ID = 0

WHILE @LAST_ID IS NOT NULL
BEGIN
    SELECT @ID = MIN(id)
    FROM dbo.sysobjects
    WHERE id > @LAST_ID  AND type = 'P' AND category = 0
    
    SET @LAST_ID = @ID
    
    -- We have a record so go get the name
    IF @ID IS NOT NULL
    BEGIN
        SELECT @NAME = name
        FROM dbo.sysobjects
        WHERE id = @ID
    
        -- Build the DCL to do the GRANT
        SET @SQL = 'GRANT EXECUTE ON ' + @NAME + ' TO ' + @U
        
        -- Run the SQL Statement you just generated
        EXEC master.dbo.xp_execresultset @SQL, @DB

    END
    

END

And that's it. Loop round the dbo.sysobjects table, get each stored procedure in turn, build a SQL string and execute it.

Using a standard naming convention for your stored procs will allow you to extend this further by picking up specific groups of procedures in the initial query so you can GRANT functionality to the correct user or role.

kick it on DotNetKicks.com del.icio.us digg Mister Wong YahooMyWeb Reddit Furl Spurl blogmarks
Paul Marshall Skype
Author : Paul Marshall
Published : 16 June 2006

A self confessed Microsoft bigot, Paul loves all Microsoft products with a particular fondness for SQL Server. Paul is currently focusing on Web 2.0 patterns and practices and is always looking for better ways of doing things. I love the .net platform, and I find it to be the most productive toolset I have used to date.

Comments

Anonymous said:

I usually do something like:

DECLARE @User varchar(50)

SELECT @User = '<a user or role>'

SELECT

        'GRANT EXEC ON ' + name + ' TO ' + @User

FROM

        sysobjects

WHERE

        type = 'P'

        AND category = 0

and i get a script that i can reuse

July 14, 2006 - 3:14 PM

B said:

Thanks guys. Very Useful.

March 02, 2007 - 4:04 PM

Anonymous said:

This sp do the same with a cursor and automatically adds the permissions for the user if someone is interested.

set ANSI_NULLS OFF

set QUOTED_IDENTIFIER ON

GO

ALTER PROCEDURE dbo.usp_ActualizarPermisos_USP

AS

declare @consulta as varchar(250)

declare @nombreSP as varchar(100)

declare @user as varchar(50)

SET @user = '<input your user here>'

DECLARE cursorSP CURSOR FOR

select name from sysobjects where xtype='P' AND category!=2

OPEN cursorSP

FETCH NEXT FROM CursorSP

INTO @nombreSP

WHILE @@FETCH_STATUS = 0

  BEGIN
     set @consulta = 'GRANT EXECUTE ON [dbo].[' + @nombreSP + '] TO [' + @user + ']'
     exec (@consulta)


  FETCH NEXT FROM CursorSP
  INTO @nombreSP

END

close CursorSP

Deallocate CursorSP

Hope this helps,

Me

June 07, 2007 - 3:20 PM

krishna@sqlserver.in said:

Declare @sql nvarchar(1000)

Declare @dbname varchar(100)

Set @dbname = db_name()

Set @sql = 'select Grant Execute on name to [kris]

            from sysobjects where xtype in (''P'')'

Exec master.dbo.xp_execresultset sql,dbname

June 10, 2008 - 9:31 PM

Laurasaur said:

Cheers very usefull :)

October 15, 2008 - 11:34 PM

who said:

Very nice! How do I grant execute permission on all types of functions?

March 17, 2009 - 7:46 AM

Add Comment

Enter your comment below and it will be submitted for moderation.

Your Name

Add Tag

Please enter tags for this article, seperated by semi-colon ;

View Tag's by : # articles | # views