Our production DB server supports a complex web application and the problem we currently face is a kind of a basic security issue and I was asked to resolve it in a week time. The scenario is that a few of the members from web application development team by the virtue of being developers know the user Id and password of the DB account which is intended to be used by the web application only. Some of these developers manipulate the data in the table and that is causing a serious havoc. We do have triggers created on major tables that tell us who changed and what changed etc. But as theses guys use the same userId of the web application , all we can see from the trigger is that same service account user Id only. I was asked to remove the direct table insert,update & delete permission of the web application user. This should be straight forward because the web application is interacting with the database only through a set of defined stored procedures and a few functions. The application code never touch (neither select nor change) any of the tables directly. As such the web application user doesn’t need to have the write permission to these tables. It should only have execute permission on the defined SPs. I thought I could remove it easily. But that was not the case. We have more than 1000 SPs and all of them are created in one database. The underlying tables the SPs insert,update & delete are in a different database on the same server instance. In that case SQL server expect the user have the permission on the underlying table as well. The execute permission on the SP is not enough. I tried all the methods I can think of such as creating a role and changing the SP code to use with EXECUTE AS OWNER etc. but none worked. Can someone please help?
Basically I need the following test case to work. Thanks in advance..
-- Step1. creating a server login and mapping the login to two databases with read access to all tables. (NO write access)
CREATE LOGIN testUser WITH PASSWORD=N'passowrd', DEFAULT_DATABASE=[master] GO USE Database1 GO CREATE USER [testUser] FOR LOGIN [testUser] ALTER ROLE [db_datareader] ADD MEMBER [testUser] GO USE Database2 GO CREATE USER [testUser] FOR LOGIN [testUser] ALTER ROLE [db_datareader] ADD MEMBER [testUser]
--Step 2. create one table in first database and one SP in the other. The SP inserts to table in database1.
use Database1 go create table testTable(a int, b varchar(100)) use Database2 go create proc testProc @a int, @b varchar(100) as Begin insert into Database1.dbo.testTable(a,b) values (@a,@b) end
--Step 3 .grating the user execute permission on the SP without grating modify permission on the base table
GRANT EXECUTE ON testProc TO [testUser]
--Final step. login as the test user and try to execute the SP
use Database2 execute testProc 100,'aaa'
now I get the error "The INSERT permission was denied on the object 'testTable', database 'Database1', schema 'dbo'."
How can I get it working without making the user able to directly modify the table?