SQL Server DDL Security Audit

Source: Internet
Author: User

Application scenarios:

As part of SQL Server Security Audit, DBAs may need a report like this: Know Which database objects (such as tables, stored procedures, views, users, functions, user permissions, etc) who modified the content and so on. You may also need a copy of the code modification history list of stored procedures, functions, and views to know that these codes have been modified for a certain period of time. The following code is exactly what you need.

This code runs well on SQL Server 2005/2008.

1. Create an audit database for storing audit records;

This step is omitted. Audit Database Name: auditdb;

 

2. Create an audit user for the permissions required for implementing the audit;

CREATE LOGIN[AuditUser]WITH PASSWORD=N'123',DEFAULT_DATABASE=[AuditDB]GOuse AuditDBGOCREATE USERAudituserFOR LOGIN Audituser;GOALTER LOGIN[AuditUser]DISABLEGO

Note: This user does not need to log on, so you can disable this user's logon.


3. Create the following audit table in the audit database auditdb:

Table 1: dba_changedobjectlog (audit master table)

Table 2: dba_changedobjecttext (audit slave table)


Note:

The Association field between the audit master table and the audit slave table is logid;

Only views, stored procedures, functions, and triggers have slave table data, because only these objects have code definitions;

 

4. Authorization for Audit User:

use mastergogrant viewserverstate to Audituseruse AuditDBgogrant insertonDBA_ChangedObjectLogtoAuditusergrant insertonDBA_ChangedObjectTexttoAudituser


5. Grant the simulated audituser permission to all users who can modify database objects:

If you do not do this, you must grant the audituser permission in Step 4 to all these users;

grant impersonateonlogin::user1toauditusergrant impersonateonlogin::auditusertouser1

If your database already has dozens or hundreds of thousands of users, you can use the following statements to generate code for batch authorization:

select 'grant impersonate on login::['+[name]+'] to audituser'fromsys.server_principalswhere type='S'andname<>'audituser'union allselect 'grant impersonate onlogin::audituser to ['+[name]+']'fromsys.server_principalswhere type='S'andname<>'audituser'

Note: To authorize each new user.

 

6. Create the trigger tr_dba_objectchangelog_insert on the audit master table.

The purpose of this trigger is to get the code definition of the currently modified database object (view, stored procedure, function, trigger) and save it to the slave table.

Use [auditdb] goset ansi_nullsongoset quoted_identifierongo -- create a trigger on the audit master table: Alter trigger [DBO]. [tr_dba_objectchangelog_insert] on [DBO]. [UNKNOWN] For insertasbegin declare @ logid uniqueidentifier, @ resolve (256), @ usernamenvarchar (256), @ resolve (256), @ objectnamenvarchar (256), @ objecttypenvarchar (256 ), -- @ original_usernvarchar (256), @ eventtypenvarchar (256), @ SQL nvarchar (256), @ isaddltriggerint execute as login = original_login () set @ isaddltrigger =-1 select @ logid = logid, @ databasename = databasename, @ schemaname = schemaname, @ objectname = objectname, @ objecttype = objecttype, @ username = username, @ eventtype = eventtype from inserted; If @ objecttype not in ('Procedure ', 'view', 'function', 'trigger') return; if @ eventtype like 'drop % 'return; Set @ SQL = n' select @ isaddltriggerout = count (*) from [' + @ databasename + ']. SYS. triggers where name = ''' + @ objectname + ''' and parent_class = 0'; execute sp_executesql @ SQL, n' @ isaddltriggerout int output', @ isaddltriggerout = @ isaddltriggeroutput; -- DDL triggers cannot use sp_helptext to obtain its text. If @ isaddltrigger> 0 return; If object_id ('tempdb .. # temp ') isnot null drop table # temp create table # temp ([Line] [int] identity (1, 1) notnull, [linetext] varchar (max )) set @ SQL = 'insert into # temp exec ['+ @ databasename +']. DBO. sp_helptext ''' + @ schemaname + '. '+ @ objectname + '''; Exec (@ SQL) execute as caller insert into DBO. dba_changedobjecttext select @ logid, @ databasename, @ schemaname, @ objectname, [Line], [linetext] From # temp drop table # temp end


7. Create the trigger tr_dba_trace_objectchangelog on the database to be audited:

Before creating a database, you need to configure the database to be audited as follows. For example, if you need to perform DDL audit on the database test, then:

alter database[TEST]set trustworthy on

Create the trigger tr_dba_trace_objectchangelog.

Use [test] goset events triggers trigger [events] on database -- withexecute as 'audituser' for ddl_table_events, ddl_view_events, ddl_index_events, events, functions, functions --, ddl_rule_events asbegin set nocount on declare @ newid uniqueidentifier, @ data XML, @ spid smallint, @ loginnamevarchar (256), @ programnamevarchar (256), @ IP varchar (15 ), @ Mac varchar (12), @ eventtypevarchar (50), @ objecttypevarchar (25), @ objectnamevarchar (256), @ isaddltriggerint, @ line smallint set @ newid = newid () set @ DATA = eventdata () set @ spid = @ data. value ('(/event_instance/spid) [1]', 'smallint') set @ eventtype = @ data. value ('(/event_instance/eventtype) [1]', 'varchar (50) ') set @ objecttype = @ data. value ('(/event_instance/objecttype) [1]', 'varchar (25) ') set @ objectname = @ data. value ('(/event_instance/objectname) [1]', 'varchar (256) ') set @ loginname = @ data. value ('(/event_instance/loginname) [1]', 'varchar (256) ') -- set @ objectname = @ data. value ('(/event_instance/objectname) [1]', 'varchar (256) ') set @ MAC = (selectnet_addressfrom master. DBO. sysprocesseswherespid = @ spid) set @ line = 0 -- filter out the rebuilt index records generated by the Maintenance Plan (so the Class records are too large) if @ loginname = 'nt Authority \ system' and @ objecttype = 'index' return; -- if the objectis a ddl trigger if (selectcount (*) from sys. triggerswherename = @ objectnameandparent_class = 0) = 0 set @ isaddltrigger = 0 else set @ isaddltrigger = 1 execute as login = 'audituser' select @ programname = [program_name] fromsys. dm_exec_sessionswheresession_id = @ spid select @ IP = client_net_addressfromsys.dm_exec_connectionswheresession_id = @ spid insert into dbadminplat. DBO. dba_changedobjectlog ([logid], [eventtype], [posttime], [spid], [servername], [host_ip_address], [host_mac_address], [programname], [loginname], [username], [databasename], [schemaname], [objectname], [objecttype], [tsqlcommand] --, [eventdate]) values (@ newid, @ eventtype, @ data. value ('(/event_instance/posttime) [1]', 'datetime'), @ spid, @ data. value ('(/event_instance/servername) [1]', 'varchar (256) '), @ IP, @ Mac, @ programname, @ loginname, -- @ data. value ('(/event_instance/loginname) [1]', 'varchar (256) '), @ data. value ('(/event_instance/username) [1]', 'varchar (256) '), @ data. value ('(/event_instance/databasename) [1]', 'varchar (256) '), @ data. value ('(/event_instance/schemaname) [1]', 'varchar (256) '), @ objectname, @ objecttype, -- for objectslike procs, views, triggers and functions, text of which will be stored inmaster. [DBO]. [tb_dba_changedobjecttext] table. case when @ objecttype in ('processed', 'view', 'function', 'trigger ') and (@ eventtype <> 'Grant _ database' or @ eventtype like 'drop % ') and @ isaddltrigger = 0 then null else @ data. value ('(/event_instance/tsqlcommand) [1]', 'varchar (max) ') End); revert; endgo set ansi_nullsoffgoset quoted_identifieroffgoenable trigger [Break] On databasego

 

 

 

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.