Ultimately, our SSIS package Populate_DBA_Repository will read the data from this temp table and then store it in our central repository DBA_Rep.. SQL Agent jobs Finally, it is critical
Trang 1Security
For security reporting, we essentially want to know who has access to which databases, and with which permissions A sample query of the kind of information that can be gathered is in shown in Listing 2.5
IF EXISTS SELECT *
FROM tempdb dbo sysobjects
WHERE id =
OBJECT_ID( '[tempdb].[dbo].[SQL_DB_REP]' ) )
DROP TABLE [tempdb] [dbo] [SQL_DB_REP] ;
GO
CREATE TABLE [tempdb] [dbo] [SQL_DB_REP]
(
[Server] [varchar] ( 100 ) NOT NULL,
[DB_Name] [varchar] ( 70 ) NOT NULL,
[User_Name] [nvarchar] ( 90 ) NULL,
[Group_Name] [varchar] ( 100 ) NULL,
[Account_Type] [varchar] ( 22 ) NULL,
[Login_Name] [varchar] ( 80 ) NULL,
[Def_DB] [varchar] ( 100 ) NULL
)
ON [PRIMARY]
INSERT INTO [tempdb] [dbo] [SQL_DB_REP]
Exec sp_MSForEachDB 'SELECT
CONVERT(varchar(100), SERVERPROPERTY(''Servername''))
AS Server,
''?'' AS DB_Name,usu.name u_name,
CASE WHEN (usg.uid is null) THEN ''public''
ELSE usg.name
END as Group_Name,
CASE WHEN usu.isntuser=1 THEN ''Windows Domain Account''
WHEN usu.isntgroup = 1 THEN ''Windows Group'' WHEN usu.issqluser = 1 THEN''SQL Account'' WHEN usu.issqlrole = 1 THEN ''SQL Role''
END as Account_Type,
lo.loginname,
lo.dbname AS Def_DB
FROM
[?] sysusers usu LEFT OUTER JOIN
([?] sysmembers mem INNER JOIN
[?] sysusers usg ON mem.groupuid = usg.uid)
ON usu.uid = mem.memberuid LEFT OUTER JOIN
master.dbo.syslogins lo ON usu.sid = lo.sid
Trang 2( usu.islogin = 1 AND
usu.isaliased = 0 AND
usu.hasdbaccess = 1) AND
(usg.issqlrole = 1 OR
usg.uid is null)'
Listing 2.5: Query to return security information about database access
As for the database management query, a temp table is populated again using
sp_msforeachdb Ultimately, our SSIS package (Populate_DBA_Repository) will read the data from this temp table and then store it in our central repository (DBA_Rep)
A simple Select * from [tempdb].[dbo].[SQL_DB_REP], the output of which is shown in Figure 2.4, delivers a lot of information about security, some of which may be surprising You might be interested to know, for example, that
"MyDomain\BadUser" has DBO access to several user databases
Figure 2.4: Database user access levels
Over time, policies about who can access production SQL instances inevitably change You can use this data to formulate a new policy, or bolster your existing policy, to guarantee that only users that you are aware of have access to your database
Trang 3SQL Agent jobs
Finally, it is critical that a DBA monitors closely the status of any SQL Agent jobs running on their servers so that they are aware of any failed jobs, unscheduled jobs, disabled jobs, notifications and so on In most large shops, failed jobs will notify the on-call DBA and they will be expected to respond immediately, especially in the case of failed backup jobs
When using SQL Agent to schedule your jobs, it is very important that you know how the jobs are performing Over time, jobs are added and modified and these changes need to be known to the DBA team in case any issues arise Also, some jobs, such as business processes scheduled to move data, will not be owned by the DBA Any delay or failure of these jobs would be unsettling for business users waiting to make decisions on the loaded data
For these reasons, I make sure to collect almost every piece of information about SQL Agent jobs, for storage in the repository Listing 2.6 shows the query I use As you can see, it returns many fields from the system database, MSDB Unfortunately, the MSDB schema changed from version 2000 to 2005, primarily for the job schedule information, so you'll need two different versions of the query depending on whether you're using SQL 2000 or 2005/2008 Listing 2.6 shows the SQL Server 2005/2008 version The SQL 2000 version will be available in the script download file for the book (see http://www.simple‐ talk.com/RedGateBooks/RodneyLandrum/SQL_Server_Tacklebox_Code.zip)
SELECT CONVERT( nvarchar ( 128 ), SERVERPROPERTY( 'Servername' )) AS Server ,
msdb dbo sysjobs job_id ,
msdb dbo sysjobs name ,
msdb dbo sysjobs enabled AS Job_Enabled ,
msdb dbo sysjobs description ,
msdb dbo sysjobs notify_level_eventlog ,
msdb dbo sysjobs notify_level_email ,
msdb dbo sysjobs notify_level_netsend ,
msdb dbo sysjobs notify_level_page ,
msdb dbo sysjobs notify_email_operator_id ,
msdb dbo sysjobs date_created ,
msdb dbo syscategories name AS Category_Name ,
msdb dbo sysjobschedules next_run_date ,
msdb dbo sysjobschedules next_run_time ,
msdb dbo sysjobservers last_run_outcome ,
msdb dbo sysjobservers last_outcome_message ,
msdb dbo sysjobservers last_run_date ,
msdb dbo sysjobservers last_run_time ,
Trang 4msdb dbo sysjobs date_modified ,
GETDATE() AS Package_run_date ,
msdb dbo sysschedules name AS Schedule_Name , msdb dbo sysschedules enabled ,
msdb dbo sysschedules freq_type ,
msdb dbo sysschedules freq_interval ,
msdb dbo sysschedules freq_subday_interval , msdb dbo sysschedules freq_subday_type ,
msdb dbo sysschedules freq_relative_interval , msdb dbo sysschedules freq_recurrence_factor , msdb dbo sysschedules active_start_date ,
msdb dbo sysschedules active_end_date ,
msdb dbo sysschedules active_start_time ,
msdb dbo sysschedules active_end_time ,
msdb dbo sysschedules date_created AS
Date_Sched_Created ,
msdb dbo sysschedules date_modified AS
Date_Sched_Modified ,
msdb dbo sysschedules version_number ,
msdb dbo sysjobs version_number AS Job_Version FROM msdb dbo sysjobs
INNER JOIN msdb dbo syscategories ON
msdb dbo sysjobs category_id =
msdb dbo syscategories category_id
LEFT OUTER JOIN msdb dbo sysoperators ON
msdb dbo sysjobs notify_page_operator_id =
msdb dbo sysoperators id
LEFT OUTER JOIN msdb dbo sysjobservers ON
msdb dbo sysjobs job_id = msdb dbo sysjobservers job_id LEFT OUTER JOIN msdb dbo sysjobschedules ON
msdb dbo sysjobschedules job_id = msdb dbo sysjobs job_id LEFT OUTER JOIN msdb dbo sysschedules ON
msdb dbo sysjobschedules schedule_id =
msdb dbo sysschedules schedule_id
Listing 2.6: SQL Agent Job Information query
Figure 2.5 shows the output of the SQL Agent Job Information query
Trang 5Figure 2.5: SQL Agent Job Information query output
Automating information retrieval
The information provided by these scripts, regarding database backups, SQL Agent jobs, data file management, security and so on, is moderately useful when examined on a server-by-server basis However, the real power comes when you can automate the collection of this data, from multiple servers, and store the output centrally, for reporting It really does make finding potential issues orders
of magnitude faster
There are several options for building a "repository of DBA information" All of them would require you to create a central database to store all the data, but there any several different ways in which you can automate the collection of this data across all your servers The following list shows some of the tools or techniques I have reviewed that provide solutions to the problem of gathering and centrally storing SQL Server administrative data
• SQL Server Health and History Tool – though quite dated now, this is
one of the first free tools I found that would collect information from numerous databases and store it in a central database for reporting It also