<?xml version="1.0" encoding="UTF-8"?><!-- generator="wordpress.com" -->
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	>

<channel>
	<title>sql-server-admin &amp;laquo; WordPress.com Tag Feed</title>
	<link>http://en.wordpress.com/tag/sql-server-admin/</link>
	<description>Feed of posts on WordPress.com tagged "sql-server-admin"</description>
	<pubDate>Thu, 23 May 2013 03:22:09 +0000</pubDate>

	<generator>http://en.wordpress.com/tags/</generator>
	<language>en</language>

<item>
<title><![CDATA[Checkpoint]]></title>
<link>http://togrady.wordpress.com/2011/08/22/checkpoint/</link>
<pubDate>Mon, 22 Aug 2011 19:06:52 +0000</pubDate>
<dc:creator>togrady</dc:creator>
<guid>http://togrady.wordpress.com/2011/08/22/checkpoint/</guid>
<description><![CDATA[Overview The checkpoint process writes dirty pages from the buffer pool area of memory to physical d]]></description>
<content:encoded><![CDATA[<div id="codeSnippetWrapper"></div>
<h2>Overview</h2>
<p>The checkpoint process writes dirty pages from the buffer pool area of memory to physical disk. It does not remove the pages from the buffer pool instead it marks them as clean again.Its purpose is to reduce the active portion of the log necessary to preform recovery so the frequency at which the checkpoint process is run determines the length of time it will take to recover the database when it is started up.  This needs to be balanced against the overhead required to run the checkpoint process. Similarly to the lazy writer process, checkpoint runs as a background task. We can query the sysprocesses system table to view its status:</p>
<p>&#160;</p>
<pre class="brush: sql; title: ; notranslate" title="">
SELECT cmd, spid, status, dbid, login_time, waittime, lastwaittype,
loginame,cpu, memusage, physical_io
FROM sysprocesses
WHERE  cmd IN ('LAZY WRITER', 'CHECKPOINT')
</pre>
<p>&#160;</p>
<div id="codeSnippetWrapper"></div>
<p>&#160;</p>
<p><a href="http://togrady.files.wordpress.com/2011/08/image2.png"><img style="background-image:none;padding-left:0;padding-right:0;display:inline;padding-top:0;border-width:0;" title="image" src="http://togrady.files.wordpress.com/2011/08/image_thumb2.png?w=592&#038;h=60" alt="image" width="592" height="60" border="0" /></a></p>
<p>&#160;</p>
<p>By default SQL Server determines the interval at which the checkpoint process runs. This is usually every 1 minute. This behaviour can be changed by setting the <strong>recovery interval</strong> which is an advanced configuration option.</p>
<p>&#160;</p>
<p>Generally I don&#8217;t change the default value of 0 which is to allow SQL Server control the checkpoint process.</p>
<p>&#160;</p>
<h2>Checkpoint and the buffer pool</h2>
<p>I want to see exactly what the checkpoint process does and how this impacts on the buffer pool. I have setup a test database called DBA (DB_ID = 7)with a table called tblTest. This is a small table with a couple of rows. I have already determined that it is using page 222. The first thing I want to do is clear the page from cache. TO do this I am going to call the checkpoint statement to clean the page and then I am going to call DBCC DROPCLEANBUFFERS  to remove all clean pages form the buffer pool.  Since I have set the recovery interval to 1000 minutes the automatic checkpoint process should not kick in. Just to be sure I am also going to turn on Trace flag  3502. This will log all checkpoint activity in the SQL Server Log.</p>
<div id="codeSnippetWrapper">
<div id="codeSnippet" style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;">
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum1" style="color:#606060;"> 1:</span> <span style="color:#0000ff;">DBCC</span> TRACEON (3502, -1);</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum2" style="color:#606060;"> 2:</span></pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum3" style="color:#606060;"> 3:</span> <span style="color:#0000ff;">GO</span></pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum4" style="color:#606060;"> 4:</span></pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum5" style="color:#606060;"> 5:</span> <span style="color:#0000ff;">CHECKPOINT</span>;</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum6" style="color:#606060;"> 6:</span></pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum7" style="color:#606060;"> 7:</span> <span style="color:#0000ff;">GO</span></pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum8" style="color:#606060;"> 8:</span></pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum9" style="color:#606060;"> 9:</span> <span style="color:#0000ff;">DBCC</span> DROPCLEANBUFFERS;</pre>
<p>&#160;</p>
</div>
</div>
<p>I can verify that the page is not in the buffer pool by using the dm_os_buffer_descriptors  dmv.</p>
<div id="codeSnippetWrapper">
<div id="codeSnippet" style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;">
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum1" style="color:#606060;"> 1:</span> <span style="color:#0000ff;">select</span> * <span style="color:#0000ff;">from</span> sys.dm_os_buffer_descriptors</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum2" style="color:#606060;"> 2:</span> <span style="color:#0000ff;">where</span> page_id = 222 <span style="color:#0000ff;">and</span> database_id = 7</pre>
<p>&#160;</p>
</div>
</div>
<p>&#160;</p>
<p><a href="http://togrady.files.wordpress.com/2011/08/image3.png"><img style="background-image:none;padding-left:0;padding-right:0;display:inline;padding-top:0;border-width:0;" title="image" src="http://togrady.files.wordpress.com/2011/08/image_thumb3.png?w=529&#038;h=56" alt="image" width="529" height="56" border="0" /></a></p>
<p>&#160;</p>
<p>Next I am going to bring the tblTest into the buffer pool and dirty it., I am going to do this by updating all the existing rows in the table.</p>
<p><a href="http://togrady.files.wordpress.com/2011/08/image5.png"><img style="background-image:none;padding-left:0;padding-right:0;display:inline;padding-top:0;border-width:0;margin:0;" title="image" src="http://togrady.files.wordpress.com/2011/08/image_thumb4.png?w=244&#038;h=125" alt="image" width="244" height="125" border="0" /></a></p>
<p>&#160;</p>
<p>I can verify that the page is now in the buffer pool and that the page has been modified (dirty). The is_modiifed column in sys.dm_os_buffer_discriptors indicates the status of the page (clean / dirty as 1/0)</p>
<div id="codeSnippetWrapper">
<div id="codeSnippet" style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;">
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum1" style="color:#606060;"> 1:</span> <span style="color:#0000ff;">select</span> * <span style="color:#0000ff;">from</span> sys.dm_os_buffer_descriptors</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum2" style="color:#606060;"> 2:</span> <span style="color:#0000ff;">where</span> page_id = 222 <span style="color:#0000ff;">and</span> database_id = 7</pre>
<p>&#160;</p>
</div>
</div>
<p>&#160;</p>
<p><a href="http://togrady.files.wordpress.com/2011/08/image6.png"><img style="background-image:none;padding-left:0;padding-right:0;display:inline;padding-top:0;border-width:0;" title="image" src="http://togrady.files.wordpress.com/2011/08/image_thumb5.png?w=529&#038;h=87" alt="image" width="529" height="87" border="0" /></a></p>
<p>&#160;</p>
<p>When we run a checkpoint again the page should remain in the buffer pool but it should now be clean</p>
<p>&#160;</p>
<div id="codeSnippetWrapper">
<div id="codeSnippet" style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;">
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum1" style="color:#606060;"> 1:</span> CHECPOINT;</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum2" style="color:#606060;"> 2:</span></pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum3" style="color:#606060;"> 3:</span> <span style="color:#0000ff;">GO</span></pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum4" style="color:#606060;"> 4:</span></pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum5" style="color:#606060;"> 5:</span> <span style="color:#0000ff;">select</span> * <span style="color:#0000ff;">from</span> sys.dm_os_buffer_descriptors</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum6" style="color:#606060;"> 6:</span> <span style="color:#0000ff;">where</span> page_id = 222 <span style="color:#0000ff;">and</span> database_id = 7</pre>
<p>&#160;</p>
</div>
</div>
<p><a href="http://togrady.files.wordpress.com/2011/08/image7.png"><img style="background-image:none;padding-left:0;padding-right:0;display:inline;padding-top:0;border-width:0;" title="image" src="http://togrady.files.wordpress.com/2011/08/image_thumb6.png?w=537&#038;h=64" alt="image" width="537" height="64" border="0" /></a></p>
<p>&#160;</p>
<p>&#160;</p>
<p>This shows that the checkpoint process cleaned the page and left it in the buffer pool</p>
<p>&#160;</p>
<h2>Checkpoint and the transaction log</h2>
<p>I am not going to get into Transaction Log management. For the purposes of the demo I setup the following</p>
<ul>
<li>The database is in the simple recovery mode</li>
<li>There were no outstanding active transactions</li>
<li>No other transaction log dependant features such as replication or DB mirroring were setup on the box.</li>
</ul>
<p>I have a database setup and I have run a number of transactions against it. The recovery interval has been set to 1000 minutes. I am going to use DBCC LOGINFO and the undocumented</p>
<div id="codeSnippetWrapper" style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:97.5%;">
<div id="codeSnippet" style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;">
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum1" style="color:#606060;"> 1:</span></pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum2" style="color:#606060;"> 2:</span></pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum3" style="color:#606060;"> 3:</span> <span style="color:#0000ff;">DBCC</span> LOGINFO;</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum4" style="color:#606060;"> 4:</span></pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum5" style="color:#606060;"> 5:</span></pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum6" style="color:#606060;"> 6:</span> <span style="color:#0000ff;">SELECT</span> [<span style="color:#0000ff;">Current</span> LSN],[previous LSN], [<span style="color:#0000ff;">Operation</span>], context,</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum7" style="color:#606060;"> 7:</span> [<span style="color:#0000ff;">Checkpoint</span> <span style="color:#0000ff;">Begin</span>], [<span style="color:#0000ff;">checkpoint</span> <span style="color:#0000ff;">end</span>], [page id], [minimum lsn],</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum8" style="color:#606060;"> 8:</span> Dirty Pages] spid, [<span style="color:#0000ff;">Begin</span> <span style="color:#0000ff;">Time</span>], [<span style="color:#0000ff;">Transaction</span> Name],</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum9" style="color:#606060;"> 9:</span> [<span style="color:#0000ff;">End</span> <span style="color:#0000ff;">Time</span>], [Lock Information],Description</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum10" style="color:#606060;"> 10:</span> <span style="color:#0000ff;">FROM</span> ::fn_dblog(<span style="color:#0000ff;">NULL</span>, <span style="color:#0000ff;">NULL</span>) ;</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum11" style="color:#606060;"> 11:</span></pre>
<p>&#160;</p>
</div>
</div>
<p>&#160;</p>
<p><a href="http://togrady.files.wordpress.com/2011/08/image8.png"><img style="background-image:none;padding-left:0;padding-right:0;display:inline;padding-top:0;border-width:0;" title="image" src="http://togrady.files.wordpress.com/2011/08/image_thumb7.png?w=600&#038;h=255" alt="image" width="600" height="255" border="0" /></a></p>
<div id="codeSnippetWrapper"></div>
<div></div>
<div>
<div id="codeSnippet" style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;">
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum1" style="color:#606060;"> 1:</span> <span style="color:#0000ff;">checkpoint</span>;</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum2" style="color:#606060;"> 2:</span></pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum3" style="color:#606060;"> 3:</span> <span style="color:#0000ff;">dbcc</span> loginfo;</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum4" style="color:#606060;"> 4:</span></pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum5" style="color:#606060;"> 5:</span> <span style="color:#0000ff;">SELECT</span> [<span style="color:#0000ff;">Current</span> LSN],[previous LSN], <span style="color:#0000ff;">Operation</span>, context,</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum6" style="color:#606060;"> 6:</span> [<span style="color:#0000ff;">Checkpoint</span> <span style="color:#0000ff;">Begin</span>], [<span style="color:#0000ff;">checkpoint</span> <span style="color:#0000ff;">end</span>], [page id], [minimum lsn],</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum7" style="color:#606060;"> 7:</span> [Dirty Pages] spid, [<span style="color:#0000ff;">Begin</span> <span style="color:#0000ff;">Time</span>], [<span style="color:#0000ff;">Transaction</span> Name], [<span style="color:#0000ff;">End</span> <span style="color:#0000ff;">Time</span>],</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:#f4f4f4;width:100%;"><span id="lnum8" style="color:#606060;"> 8:</span> [Lock Information], Description</pre>
<p>&#160;</p>
<pre style="text-align:left;line-height:12pt;background-color:white;width:100%;"><span id="lnum9" style="color:#606060;"> 9:</span> <span style="color:#0000ff;">FROM</span> ::fn_dblog(<span style="color:#0000ff;">NULL</span>, <span style="color:#0000ff;">NULL</span>)</pre>
<p>&#160;</p>
</div>
</div>
<p>&#160;</p>
<p><a href="http://togrady.files.wordpress.com/2011/08/image9.png"><img style="background-image:none;padding-left:0;padding-right:0;display:inline;padding-top:0;border-width:0;" title="image" src="http://togrady.files.wordpress.com/2011/08/image_thumb8.png?w=600&#038;h=245" alt="image" width="600" height="245" border="0" /></a></p>
<p>&#160;</p>
<h2>So when does checkpoint run</h2>
<p>When the database is shutdown a checkpoint is run against each database. The only exception to this is when shutdown is called with the no wait option or the server crashes.</p>
<p>The checkpoint process is run before each backup</p>
<p>The transaction exceeds maximum&#8217;s for the active portion</p>
]]></content:encoded>
</item>
<item>
<title><![CDATA[Using xp_fixeddrives to check free drive space]]></title>
<link>http://mrsql.wordpress.com/2011/05/06/using-xp_fixeddrives-to-check-free-drive-space/</link>
<pubDate>Fri, 06 May 2011 11:47:36 +0000</pubDate>
<dc:creator>mrsql</dc:creator>
<guid>http://mrsql.wordpress.com/2011/05/06/using-xp_fixeddrives-to-check-free-drive-space/</guid>
<description><![CDATA[The inbuilt stored procedure &#8216;xp_fixeddrives&#8217; returns the free space available (in Megab]]></description>
<content:encoded><![CDATA[<p>The inbuilt stored procedure &#8216;xp_fixeddrives&#8217; returns the free space available (in Megabytes) for all standard hard drives installed on the server that the query is run against.</p>
<pre class="brush: sql; title: ; notranslate" title="">
exec xp_fixeddrives
</pre>
]]></content:encoded>
</item>
<item>
<title><![CDATA[Failing Over Multiple Databases]]></title>
<link>http://mrsql.wordpress.com/2011/04/08/failing-over-multiple-databases/</link>
<pubDate>Fri, 08 Apr 2011 15:21:30 +0000</pubDate>
<dc:creator>mrsql</dc:creator>
<guid>http://mrsql.wordpress.com/2011/04/08/failing-over-multiple-databases/</guid>
<description><![CDATA[Many software systems use multiple databases to support an application. If the system requires all d]]></description>
<content:encoded><![CDATA[<p>Many software systems use multiple databases to support an application. If the system requires all databases to be available on the same server, then issues can arise in a mirrored setup. Problems occur when one or more databases fail over unexpectedly, but others remain as Principal. In this scenario, the required response is for any remaining principals to also failover to the secondary server. We can achieve this response by proactively monitoring the mirroring status of all databases.</p>
<p>To setup the mirroring status check, setup a WMI Alert that queries DATABASE_MIRRORING_STATE_CHANGE. </p>
<p>Add a new alert and select WMI Alert from the Type box. The namespace should automatically be populated with the correct setting. The following example should be pasted into the Query box. It checks the status of three mirrored databases. Change the database names accordingly:-</p>
<pre class="brush: sql; title: ; notranslate" title="">
SELECT *
FROM DATABASE_MIRRORING_STATE_CHANGE
WHERE ((State = 7 or State = 8) AND DatabaseName = 'Database1') OR ((State = 7 or State = 8) AND DatabaseName = 'Database2')
OR ((State = 7 or State = 8) AND DatabaseName = 'Database3')
</pre>
<p>State 7 indicates a Manual Failover whilst state 8 indicates an Automatic Failover. If any database now fails over then the alert should fire.</p>
<p>Obviously we need to setup an appropriate response for the alert. Create an Agent job containing the following SQL task:-</p>
<pre class="brush: sql; title: ; notranslate" title="">
if exists (select database_id
from sys.database_mirroring
where db_name(database_id) = 'Database1'
and mirroring_role_desc = 'principal')
ALTER DATABASE Database1 SET PARTNER FAILOVER
GO

if exists (select database_id
from sys.database_mirroring
where db_name(database_id) = 'Database2'
and mirroring_role_desc = 'principal')
ALTER DATABASE Database2 SET PARTNER FAILOVER
GO

if exists (select database_id
from sys.database_mirroring
where db_name(database_id) = 'Database3'
and mirroring_role_desc = 'principal')
ALTER DATABASE Database3 SET PARTNER FAILOVER
GO
</pre>
<p>The above code checks to see whether any mirrored databases are still set as principal and automatically fails them over. Open up the Alert in SQL Agent and select this newly created job to execute if the alert is fired. Now, if one or more of the databases fails over, the remaining databases will also do so.</p>
]]></content:encoded>
</item>
<item>
<title><![CDATA[SQl Agent Job Management with Mirrored Databases]]></title>
<link>http://mrsql.wordpress.com/2011/04/04/sql-agent-job-management-with-mirrored-databases/</link>
<pubDate>Mon, 04 Apr 2011 15:00:25 +0000</pubDate>
<dc:creator>mrsql</dc:creator>
<guid>http://mrsql.wordpress.com/2011/04/04/sql-agent-job-management-with-mirrored-databases/</guid>
<description><![CDATA[Mirroring is a high availability solution for individual databases. Implementing mirroring on a busi]]></description>
<content:encoded><![CDATA[<p>Mirroring is a high availability solution for individual databases. Implementing mirroring on a business critical database adds many benefits, but also introduces some management dilemmas. Running jobs against the mirrored version of a database generates errors due to the database being in a restoring state. Most solutions focus on enabling and disabling Agent jobs by using job categories. An example solution can be found <a href="http://sqlcat.com/msdnmirror/archive/2010/04/01/using-sql-agent-job-categories-to-automate-sql-agent-job-enabling-with-database-mirroring.aspx" target="_blank">here</a>.</p>
<p>The issue I have with the aforementioned solution is that it relies on continually calling a job to check the mirroring status of that database. Therefore, wherever possible, I add the following to each job step:-</p>
<pre class="brush: sql; title: ; notranslate" title="">
If Exists (select * from sys.database_mirroring
dm join sys.databases d on (dm.database_id=d.database_id)
where (d.name=N'Your_Mirrored_Database')and mirroring_role_desc &#60;&#62; 'Principal') PRINT 'Mirrored Version of Database. No Action Taken.'
ELSE
BEGIN
    EXEC MyBackupProc
END
</pre>
<p>The mirroring status (mirroring_role_desc) of the database is tested before calling the applicable stored procedure. If the status is found to not be &#8216;principal&#8217;, then the procedure is not called and a simple text message is printed. With the &#8216;Backup&#8217; Agent job being present on both servers, only one job will fire the procedure; the other will simply print out the message which can then be viewed within the job history. No more errors!</p>
]]></content:encoded>
</item>
<item>
<title><![CDATA[Using OUTPUT Clause to Audit Updates]]></title>
<link>http://mrsql.wordpress.com/2011/03/31/using-output-clause-to-audit-updates/</link>
<pubDate>Thu, 31 Mar 2011 10:01:24 +0000</pubDate>
<dc:creator>mrsql</dc:creator>
<guid>http://mrsql.wordpress.com/2011/03/31/using-output-clause-to-audit-updates/</guid>
<description><![CDATA[SQL Server offers an OUTPUT command to capture data that is changed, either through updating, deleti]]></description>
<content:encoded><![CDATA[<p>SQL Server offers an OUTPUT command to capture data that is changed, either through updating, deletion or insertion. The &#8216;before&#8217; and &#8216;after&#8217; images of the data are stored in system tables named DELETED and INSERTED. It is possible to query the applicable table to retrieve data that has been deleted or inserted by your sql statement. In the case of updates, the old data can be found in DELETED and the newly written data in INSERTED.</p>
<p>The following example demonstrates the process. An Audit table is created to store the results. An UPDATE is then issued against a number of columns. OUTPUT writes the old and new versions of the data (along with the id of the row changed and the date and time) to the audit table. Adding the output clause to stored procedures will allow you to audit all data changes in your database, although there will obviously be some overhead due to additional writes.</p>
<pre class="brush: sql; pad-line-numbers: false; title: ; notranslate" title="">
CREATE TABLE Audit_Table (CustomerID varchar(12),
                         OldAddress1 varchar(50),
                         OldAddress2 varchar(50),
                         OldAddress3 varchar(50),
                         OldAddress4 varchar(50),
                         OldAddress5 varchar(50),
                         OldPostCode varchar(12),
                         NewAddress1 varchar(50),
                         NewAddress2 varchar(50),
                         NewAddress3 varchar(50),
                         NewAddress4 varchar(50),
                         NewAddress5 varchar(50),
                         NewPostCode varchar(12),
                         DateChanged datetime);

UPDATE CustomerTable
SET Address1 = '99 My Road',
      Address2 = 'My Area',
      Address3 = 'My City',
      Address4 = 'My County',
      Address5 = 'My Country',
      PostCode = 'AA1 1AA'
OUTPUT INSERTED.CustomerID,
	    DELETED.Address1 AS 'OldAddress1',
	    INSERTED.Address1 AS 'NewAddress1',
	    DELETED.Address2 AS 'OldAddress2',
	    INSERTED.Address2 AS 'NewAddress2',
	    DELETED.Address3 AS 'OldAddress3',
	    INSERTED.Address3 AS 'NewAddress3',
	    DELETED.Address4 AS 'OldAddress4',
	    INSERTED.Address4 AS 'NewAddress4',
	    DELETED.Address5 AS 'OldAddress5',
	    INSERTED.Address5 AS 'NewAddress5',
	    DELETED.stu_capc AS 'OldPostCode',
	    INSERTED.stu_capc AS 'NewPostCode',
	    GETDATE() AS 'DateChanged'
INTO AuditTable
WHERE CustomerTable.CustomerID = 'AB123456';
</pre>
]]></content:encoded>
</item>
<item>
<title><![CDATA[Loading Trace File Into SQL Server]]></title>
<link>http://mrsql.wordpress.com/2011/03/15/loading-trace-file-into-sql-server/</link>
<pubDate>Tue, 15 Mar 2011 13:52:29 +0000</pubDate>
<dc:creator>mrsql</dc:creator>
<guid>http://mrsql.wordpress.com/2011/03/15/loading-trace-file-into-sql-server/</guid>
<description><![CDATA[When running a trace in SQL Server Profiler, it is bad practice to save the trace information direct]]></description>
<content:encoded><![CDATA[<p>When running a trace in SQL Server Profiler, it is bad practice to save the trace information directly into a SQL Server table. Writing trace data directly to a table uses a lot or resources  and this can greatly errode server performance. However, it is possible to load the contents of a file once a trace has been captured. </p>
<p>Find the path of any existing traces by executing the following:-</p>
<pre class="brush: sql; title: ; notranslate" title="">
select path 
from sys.traces
</pre>
<p>Once the path and file name are known, run the following SQL:-</p>
<pre class="brush: sql; title: ; notranslate" title="">
-- Load contents of trace into a SQL temporary table
-- Do not specify log numbers to load all log files for a trace
SELECT * INTO ##temp_trc
FROM fn_trace_gettable('C:\Program Files\Microsoft SQL Server\MSSQL.1\MSSQL\LOG\log.trc', default);

SELECT * FROM ##temp_trc
</pre>
<p>The above example loads all trace files like log%.trc [<em>log1.trc</em>, <em>log2.trc</em> etc] into a temporary table. You can of course load into a physically stored table by removing the hashes. If you want to load data from just one trace file from a group of rolled over trace files then specify the number on the end [e.g. C:\Program Files\Microsoft SQL Server\MSSQL.1\MSSQL\LOG\log7.trc].</p>
]]></content:encoded>
</item>
<item>
<title><![CDATA[SQL Server whoami?]]></title>
<link>http://mrsql.wordpress.com/2011/03/11/sql-server-whoami/</link>
<pubDate>Fri, 11 Mar 2011 11:52:59 +0000</pubDate>
<dc:creator>mrsql</dc:creator>
<guid>http://mrsql.wordpress.com/2011/03/11/sql-server-whoami/</guid>
<description><![CDATA[Need to identify who you are logged in as? SELECT SUSER_NAME() AS 'Login', USER_NAME() AS 'User' Or]]></description>
<content:encoded><![CDATA[<p>Need to identify who you are logged in as?</p>
<pre class="brush: sql; title: ; notranslate" title="">
SELECT SUSER_NAME() AS 'Login', USER_NAME() AS 'User'
</pre>
<p>Or try specifying an ID. ID of 1 should return SA.</p>
<pre class="brush: sql; title: ; notranslate" title="">
SELECT SUSER_NAME(1) AS 'Login'
</pre>
]]></content:encoded>
</item>
<item>
<title><![CDATA[Configuring Alerts for Fatal Errors]]></title>
<link>http://mrsql.wordpress.com/2011/03/10/configuring-alerts-for-fatal-errors/</link>
<pubDate>Thu, 10 Mar 2011 15:11:20 +0000</pubDate>
<dc:creator>mrsql</dc:creator>
<guid>http://mrsql.wordpress.com/2011/03/10/configuring-alerts-for-fatal-errors/</guid>
<description><![CDATA[SQL Server errors with a severity level of 19 or above are considered fatal errors. The following is]]></description>
<content:encoded><![CDATA[<p>SQL Server errors with a severity level of 19 or above are considered fatal errors. The following is taken from Books online:-</p>
<p><strong>Severity Level 19: SQL Server Error in Resource</strong></p>
<p>These messages indicate that some nonconfigurable internal limit has been exceeded and the current batch process is terminated. Severity level 19 errors occur rarely; however, they must be corrected by the system administrator or your primary support provider. The administrator should be informed every time a severity level 19 message occurs.</p>
<p><strong>Severity Levels 20 through 25</strong></p>
<p>Severity levels from 20 through 25 indicate system problems. These are fatal errors, which means that the process (the program code that accomplishes the task specified in your statement) is no longer running. The process freezes before it stops, records information about what occurred, and then terminates. The client connection to SQL Server closes, and depending on the problem, the client might not be able to reconnect.</p>
<p>Error messages with a severity level of 19 or higher stop the current batch. Errors messages with a severity level of 20 or higher are considered fatal errors and terminate the client connection. Errors messages in this range may affect all of the processes in the database, and may indicate that a database or object is damaged. Error messages with a severity level from 19 through 25 are written to the error log.</p>
<p><strong>Severity Level 20: SQL Server Fatal Error in Current Process</strong></p>
<p>These messages indicate that a statement has encountered a problem. Because the problem has affected only the current process, it is unlikely that the database itself has been damaged.</p>
<p><strong>Severity Level 21: SQL Server Fatal Error in Database (dbid) Processes</strong></p>
<p>These messages indicate that you have encountered a problem that affects all processes in the current database; however, it is unlikely that the database itself has been damaged.</p>
<p><strong>Severity Level 22: SQL Server Fatal Error Table Integrity Suspect</strong></p>
<p>These messages indicate that the table or index specified in the message has been damaged by a software or hardware problem.</p>
<p>Severity level 22 errors occur rarely; however, if you should encounter one, run DBCC CHECKDB to determine if other objects in the database are also damaged. It is possible that the problem is in the cache only and not on the disk itself. If so, restarting SQL Server corrects the problem. To continue working, you must reconnect to SQL Server. Otherwise, use DBCC to repair the problem. In some cases, it may be necessary to restore the database.</p>
<p>If restarting does not help, the problem is on the disk. Sometimes destroying the object specified in the error message can solve the problem. For example, if the message tells you that SQL Server has found a row with a length of 0 in a nonclustered index, delete the index and rebuild it.</p>
<p><strong>Severity Level 23: SQL Server Fatal Error: Database Integrity Suspect</strong></p>
<p>These messages indicate that the integrity of the entire database is in question because of a hardware or software problem.</p>
<p>Severity level 23 errors occur rarely; however, if you should encounter one, run DBCC CHECKDB to determine the extent of the damage. It is possible that the problem is in the cache only and not on the disk itself. If so, restarting SQL Server corrects the problem. To continue working, you must reconnect to SQL Server. Otherwise, use DBCC to repair the problem. In some cases, it may be necessary to restore the database.</p>
<p><strong>Severity Level 24: Hardware Error</strong></p>
<p>These messages indicate some type of media failure. The system administrator might have to reload the database. It might also be necessary to call your hardware vendor.</b></table>
<p><strong>Setting up Alerts</strong></p>
<p>You should set up alerts in SQL Server Agent for any errors that have a severity level of 19 or above. Use the following script to generate the alerts, ensuring you replace &#8220;Operator Name&#8221; with the appropriate name of the operator to notify by email:-</p>
<pre class="brush: sql; pad-line-numbers: false; title: ; notranslate" title="">
USE [msdb]
GO

EXEC msdb.dbo.sp_add_alert @name=N'019 - Fatal Error In Resource',
		@message_id=0,
		@severity=19,
		@enabled=1,
		@delay_between_responses=1800,
		@include_event_description_in=1,
		@category_name=N'[Uncategorized]',
		@job_id=N'00000000-0000-0000-0000-000000000000'
GO

EXEC msdb.dbo.sp_add_alert @name=N'020 - Fatal Error in Current Process',
		@message_id=0,
		@severity=20,
		@enabled=1,
		@delay_between_responses=1800,
		@include_event_description_in=1,
		@category_name=N'[Uncategorized]',
		@job_id=N'00000000-0000-0000-0000-000000000000'
GO

EXEC msdb.dbo.sp_add_alert @name=N'021 - Fatal Error in Database Processes',
		@message_id=0,
		@severity=21,
		@enabled=1,
		@delay_between_responses=1800,
		@include_event_description_in=1,
		@category_name=N'[Uncategorized]',
		@job_id=N'00000000-0000-0000-0000-000000000000'
GO

EXEC msdb.dbo.sp_add_alert @name=N'022 - Fatal Error: Table Integrity Suspect',
		@message_id=0,
		@severity=22,
		@enabled=1,
		@delay_between_responses=1800,
		@include_event_description_in=1,
		@category_name=N'[Uncategorized]',
		@job_id=N'00000000-0000-0000-0000-000000000000'
GO

EXEC msdb.dbo.sp_add_alert @name=N'023 - Fatal Error: Database Integrity Suspect',
		@message_id=0,
		@severity=23,
		@enabled=1,
		@delay_between_responses=1800,
		@include_event_description_in=1,
		@category_name=N'[Uncategorized]',
		@job_id=N'00000000-0000-0000-0000-000000000000'
GO

EXEC msdb.dbo.sp_add_alert @name=N'024 - Fatal Error: Hardware Error',
		@message_id=0,
		@severity=24,
		@enabled=1,
		@delay_between_responses=1800,
		@include_event_description_in=1,
		@category_name=N'[Uncategorized]',
		@job_id=N'00000000-0000-0000-0000-000000000000'
GO

EXEC msdb.dbo.sp_add_alert @name=N'025 - Fatal Error',
		@message_id=0,
		@severity=25,
		@enabled=1,
		@delay_between_responses=1800,
		@include_event_description_in=1,
		@category_name=N'[Uncategorized]',
		@job_id=N'00000000-0000-0000-0000-000000000000'
GO

EXEC msdb.dbo.sp_add_notification @alert_name=N'019 - Fatal Error In Resource', @operator_name=N'Operator Name', @notification_method = 1
GO

EXEC msdb.dbo.sp_add_notification @alert_name=N'020 - Fatal Error in Current Process', @operator_name=N'Operator Name', @notification_method = 1
GO

EXEC msdb.dbo.sp_add_notification @alert_name=N'021 - Fatal Error in Database Processes', @operator_name=N'Operator Name', @notification_method = 1
GO

EXEC msdb.dbo.sp_add_notification @alert_name=N'022 - Fatal Error: Table Integrity Suspect', @operator_name=N'Operator Name', @notification_method = 1
GO

EXEC msdb.dbo.sp_add_notification @alert_name=N'023 - Fatal Error: Database Integrity Suspect', @operator_name=N'Operator Name', @notification_method = 1
GO

EXEC msdb.dbo.sp_add_notification @alert_name=N'024 - Fatal Error: Hardware Error', @operator_name=N'Operator Name', @notification_method = 1
GO

EXEC msdb.dbo.sp_add_notification @alert_name=N'025 - Fatal Error', @operator_name=N'Operator Name', @notification_method = 1
GO
</pre>
]]></content:encoded>
</item>
<item>
<title><![CDATA[Querying SQL Server Default Trace Files]]></title>
<link>http://mrsql.wordpress.com/2011/01/31/querying-sql-server-default-trace-files/</link>
<pubDate>Mon, 31 Jan 2011 11:46:31 +0000</pubDate>
<dc:creator>mrsql</dc:creator>
<guid>http://mrsql.wordpress.com/2011/01/31/querying-sql-server-default-trace-files/</guid>
<description><![CDATA[SQL Server Profiler is a useful tool for troubleshooting and monitoring database and server performa]]></description>
<content:encoded><![CDATA[<p>SQL Server Profiler is a useful tool for troubleshooting and monitoring database and server performance. Usually, a DBA has to manually setup a trace to monitor a specific area of interest (e.g. Deadlocks, Login audit). However, many are unaware that a default Profiler trace is permanently running on the majority of servers. It is possible to query the trace files from within SQL Server. The default trace captures information such as file growth, mirroring status, object creation/deletion/alteration and security auditing, amongst other items. If you decide that this is not valuable information then you can switch off the default trace. </p>
<p>To check to see whether a default trace is indeed currently running, execute the following:-</p>
<pre class="brush: sql; title: ; notranslate" title="">
SELECT * 
FROM sys.configurations 
WHERE configuration_id = 1568
</pre>
<p>If the value is &#8217;1&#8242; then the trace is running. Once you have established that the trace is enabled, you need to run a query to determine the most recent trace file. Trace files automatically rollover, so you need to know which one to query. </p>
<pre class="brush: sql; title: ; notranslate" title="">
SELECT traceid, value 
FROM [fn_trace_getinfo](default) 
WHERE [property] = 2;
</pre>
<p>The full path and file name will be returned. You can then run the following query and include the correct path to the most recent file. You could of course setup a variable to automatically populate the path.</p>
<pre class="brush: sql; title: ; notranslate" title="">
SELECT *  
FROM [fn_trace_gettable]('C:\Program Files\Microsoft SQL Server\MSSQL.1\MSSQL\LOG\log_49.trc', DEFAULT) 
ORDER BY StartTime;
</pre>
<p>You can disable the trace by issuing the following commands. However, don&#8217;t expect a dramatic increase in server performance as the trace uses only minimal resources.</p>
<pre class="brush: sql; pad-line-numbers: false; title: ; notranslate" title="">
EXEC master.dbo.sp_configure 'allow updates', 1;
GO 
EXEC master.dbo.sp_configure 'show advanced options', 1;
GO 
EXEC master.dbo.sp_configure 'default trace enabled', 0;
GO
RECONFIGURE WITH OVERRIDE;
GO
EXEC master.dbo.sp_configure 'show advanced options', 0;
GO
EXEC master.dbo.sp_configure 'allow updates', 0;
GO
</pre>
]]></content:encoded>
</item>
<item>
<title><![CDATA[Defragment all Indexes in a Database]]></title>
<link>http://mrsql.wordpress.com/2011/01/17/defragment-all-indexes-in-a-database/</link>
<pubDate>Mon, 17 Jan 2011 10:10:48 +0000</pubDate>
<dc:creator>mrsql</dc:creator>
<guid>http://mrsql.wordpress.com/2011/01/17/defragment-all-indexes-in-a-database/</guid>
<description><![CDATA[The following script defragments all indexes in a database that are above a given fragmentation thre]]></description>
<content:encoded><![CDATA[<p>The following script defragments all indexes in a database that are above a given fragmentation threshold. I can&#8217;t claim to have written this &#8211; this script can be found on the <a href="http://msdn.microsoft.com/en-us/library/ms177571.aspx">MSDN Website</a>. I would suggest creating a stored procedure in your database and calling it from a scheduled SQL Agent job every evening. Be careful of running this on a database with many indexes or with large tables as it may take some time to complete. </p>
<pre class="brush: sql; pad-line-numbers: false; title: ; notranslate" title="">
/*Perform a 'USE &#60;database name&#62;' to select the database in which to run the script.*/
-- Declare variables
SET NOCOUNT ON;
DECLARE @tablename varchar(255);
DECLARE @execstr   varchar(400);
DECLARE @objectid  int;
DECLARE @indexid   int;
DECLARE @frag      decimal;
DECLARE @maxfrag   decimal;

-- Decide on the maximum fragmentation to allow for.
SELECT @maxfrag = 30.0;

-- Declare a cursor.
DECLARE tables CURSOR FOR
   SELECT TABLE_SCHEMA + '.' + TABLE_NAME
   FROM INFORMATION_SCHEMA.TABLES
   WHERE TABLE_TYPE = 'BASE TABLE';

-- Create the table.
CREATE TABLE #fraglist (
   ObjectName char(255),
   ObjectId int,
   IndexName char(255),
   IndexId int,
   Lvl int,
   CountPages int,
   CountRows int,
   MinRecSize int,
   MaxRecSize int,
   AvgRecSize int,
   ForRecCount int,
   Extents int,
   ExtentSwitches int,
   AvgFreeBytes int,
   AvgPageDensity int,
   ScanDensity decimal,
   BestCount int,
   ActualCount int,
   LogicalFrag decimal,
   ExtentFrag decimal);

-- Open the cursor.
OPEN tables;

-- Loop through all the tables in the database.
FETCH NEXT
   FROM tables
   INTO @tablename;

WHILE @@FETCH_STATUS = 0
BEGIN
-- Do the showcontig of all indexes of the table
   INSERT INTO #fraglist 
   EXEC ('DBCC SHOWCONTIG (''' + @tablename + ''') 
      WITH FAST, TABLERESULTS, ALL_INDEXES, NO_INFOMSGS');
   FETCH NEXT
      FROM tables
      INTO @tablename;
END;

-- Close and deallocate the cursor.
CLOSE tables;
DEALLOCATE tables;

-- Declare the cursor for the list of indexes to be defragged.
DECLARE indexes CURSOR FOR
   SELECT ObjectName, ObjectId, IndexId, LogicalFrag
   FROM #fraglist
   WHERE LogicalFrag &#62;= @maxfrag
      AND INDEXPROPERTY (ObjectId, IndexName, 'IndexDepth') &#62; 0;

-- Open the cursor.
OPEN indexes;

-- Loop through the indexes.
FETCH NEXT
   FROM indexes
   INTO @tablename, @objectid, @indexid, @frag;

WHILE @@FETCH_STATUS = 0
BEGIN
   PRINT 'Executing DBCC INDEXDEFRAG (0, ' + RTRIM(@tablename) + ',
      ' + RTRIM(@indexid) + ') - fragmentation currently '
       + RTRIM(CONVERT(varchar(15),@frag)) + '%';
   SELECT @execstr = 'DBCC INDEXDEFRAG (0, ' + RTRIM(@objectid) + ',
       ' + RTRIM(@indexid) + ')';
   EXEC (@execstr);

   FETCH NEXT
      FROM indexes
      INTO @tablename, @objectid, @indexid, @frag;
END;

-- Close and deallocate the cursor.
CLOSE indexes;
DEALLOCATE indexes;

-- Delete the temporary table.
DROP TABLE #fraglist;
GO
</pre>
]]></content:encoded>
</item>
<item>
<title><![CDATA[Table Creation Dates]]></title>
<link>http://mrsql.wordpress.com/2010/11/04/table-creation-dates/</link>
<pubDate>Thu, 04 Nov 2010 15:13:07 +0000</pubDate>
<dc:creator>mrsql</dc:creator>
<guid>http://mrsql.wordpress.com/2010/11/04/table-creation-dates/</guid>
<description><![CDATA[It is possible to obtain the &#8216;date of creation&#8217; of a table, as well as its last modifica]]></description>
<content:encoded><![CDATA[<p>It is possible to obtain the &#8216;date of creation&#8217; of a table, as well as its last modification date (DDL, not DML) by running the following query:- </p>
<pre class="brush: sql; title: ; notranslate" title="">SELECT [name] AS 'Table', 
[create_date] AS 'Creation Date', 
[modify_date] AS 'Modification Date' 
FROM sys.objects
WHERE type_desc = 'USER_TABLE' 
ORDER BY [modify_date] DESC</pre>
]]></content:encoded>
</item>
<item>
<title><![CDATA[Moving SQL Server user accounts]]></title>
<link>http://togrady.wordpress.com/2010/05/06/move-sql-users-between-servers/</link>
<pubDate>Thu, 06 May 2010 14:15:42 +0000</pubDate>
<dc:creator>togrady</dc:creator>
<guid>http://togrady.wordpress.com/2010/05/06/move-sql-users-between-servers/</guid>
<description><![CDATA[A number of databases currently&#160; running on SQL Server 2000 are been upgraded to a new 2005 ins]]></description>
<content:encoded><![CDATA[<p>A number of databases currently&#160; running on SQL Server 2000 are been upgraded to a new 2005 installation, this also requires moving the existing logins. Several options are available to achieve this but I found the method below to be the most straightforward.</p>
<p>Firstly make a backup of the existing database and restore it on the destination Server.</p>
<p>Next create a project in Integration Services (IS) and use the ‘transfer logins task’ to move the logins, to complete this the following properties need populating :</p>
<p><a href="http://togrady.files.wordpress.com/2010/05/image.png"><img style="display:inline;border-width:0;" title="image" border="0" alt="image" src="http://togrady.files.wordpress.com/2010/05/image_thumb.png?w=244&#038;h=133" width="244" height="133" /></a><a href="http://togrady.files.wordpress.com/2010/05/image1.png"><img style="display:inline;border-width:0;" title="image" border="0" alt="image" src="http://togrady.files.wordpress.com/2010/05/image_thumb1.png?w=244&#038;h=144" width="244" height="144" /></a> </p>
<p>&#160;</p>
<ol>
<li>Setup source connection </li>
<li>Setup destination connection </li>
<li>for LoginsToTransfer Specify <strong>SelectedLogins</strong> </li>
<li>Choose the logins to move </li>
<li>Save and Execute the task </li>
</ol>
<p>Ensure&#160; all the logins on the source server&#160; have all their attributes populated. When I initially ran the the IS package I got the error message “This property may not exist for this object, or may not be retrievable due to insufficient access rights” I traced the cause to&#160;&#160; not having a default database associated with the login, this error message appeared for all logins that were missing the attribute, even if they weren&#8217;t been moved.</p>
<p>Once the IS task completes successfully;</p>
<p>On the destination server, for each of the SQL Server logins Execute the following TSQL code. I did not have to do this for the NT logins.</p>
<p>USE <font color="#008000">&#60;Database Name&#62;</font>     <br />GO     <br />EXEC sp_change_users_login &#8216;UPDATE_ONE&#8217;, &#8216;<font color="#008000">&#60;username&#62;</font>&#8216;, &#8216;<font color="#008000">&#60;login name&#62;</font>&#8216;     <br />GO</p>
<p>&#160;</p>
<p>References</p>
<p><a title="http://sqlblog.com/blogs/eric_johnson/archive/2008/10/17/fixing-orphaned-users.aspx" href="http://sqlblog.com/blogs/eric_johnson/archive/2008/10/17/fixing-orphaned-users.aspx">http://sqlblog.com/blogs/eric_johnson/archive/2008/10/17/fixing-orphaned-users.aspx</a></p>
]]></content:encoded>
</item>

</channel>
</rss>
