<?xml version="1.0" encoding="UTF-8"?><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/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Edwin M SarmientoData Types and How They Affect HA/DR &#8211; Edwin M Sarmiento</title>
	<atom:link href="https://www.edwinmsarmiento.com/data-types-and-how-they-affect-hadr/feed/" rel="self" type="application/rss+xml" />
	<link>https://www.edwinmsarmiento.com</link>
	<description>Intentional Excellence</description>
	<lastBuildDate>Mon, 13 Apr 2026 21:00:49 +0000</lastBuildDate>
	<language>en-US</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	
<site xmlns="com-wordpress:feed-additions:1">84283043</site>		<item>
		<title>Data Types and How They Affect HA/DR</title>
		<link>https://www.edwinmsarmiento.com/data-types-and-how-they-affect-hadr/</link>
		<comments>https://www.edwinmsarmiento.com/data-types-and-how-they-affect-hadr/#comments</comments>
		<pubDate>Mon, 18 May 2015 03:37:42 +0000</pubDate>
		<dc:creator>Edwin M Sarmiento</dc:creator>
				<category><![CDATA[SQL Server]]></category>
		<category><![CDATA[data types]]></category>
		<category><![CDATA[database recovery]]></category>
		<category><![CDATA[disaster recovery]]></category>
		<category><![CDATA[HA/DR]]></category>
		<category><![CDATA[High Availability]]></category>
		<category><![CDATA[SQL Server High Availability and Disaster Recovery]]></category>
		<category><![CDATA[transaction log records]]></category>
		<guid isPermaLink="false">http://www.edwinmsarmiento.com/?p=1555</guid>

				<description><![CDATA[I previously wrote about Data Types and How They Affect Database Performance which was a way to get database developers to think about the small things that affect overall performance. As a high availability and disaster recovery (HA/DR) professional myself, I like to think of how data types affect database availability and recoverability. The fact [&#8230;]]]></description>
					<content:encoded><![CDATA[<img width="760" height="338" src="https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2-760x338.jpg" class="featured-image wp-post-image" alt="" srcset="https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2-760x338.jpg 760w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2-300x133.jpg 300w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2-1024x456.jpg 1024w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2-518x230.jpg 518w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2-82x36.jpg 82w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2-600x267.jpg 600w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2.jpg 1207w" sizes="(max-width: 760px) 100vw, 760px" /><p>I previously wrote about <a href="https://www.edwinmsarmiento.com/data-types-and-how-they-affect-performance/" target="_blank">Data Types and How They Affect Database Performance</a> which was a way to get database developers to think about the small things that affect overall performance. As a high availability and disaster recovery (HA/DR) professional myself, I like to think of how data types affect database availability and recoverability. The fact is, all SQL Server HA/DR features are affected by the amount of transaction log records generated both by user and system transactions.</p>
<p>Transaction log records are read during a database&#8217;s <strong>recovery process</strong>.  Whenever the SQL Server service is restarted, the transaction log file is read as part of the recovery phase, committed transactions are persisted to the data file (REDO phase) and uncommitted transactions are rolled back (UNDO phase) to keep the database in a transactionally consistent state. A more comprehensive discussion of the recovery phase is described in the <strong><a href="https://technet.microsoft.com/en-us/library/ms191455%28v=sql.105%29.aspx" target="_blank">Understanding How Restore and Recovery of Backups Work in SQL Server</a></strong> topic in Books Online. Every SQL Server HA/DR feature runs either just the UNDO phase or the whole recovery process.</p>
<ul>
<li><strong>Backup/restore</strong>. After the data copy phase completes as part of restoring a backup, the recovery process kicks in.</li>
<li><strong>Failover clustering</strong>. Failover is basically the process of intentionally (manual) or accidentally (automatic) stopping the SQL Server service from the current active node to any one of the nodes in a failover cluster.</li>
<li><strong>Database mirroring/Availability Group</strong>. The transaction log records are sent from the principal/primary to the mirror/secondary where the REDO phase is continuously running. When a failover is initiated, only the UNDO phase runs on the mirror/secondary to make it the new principal/primary.</li>
<li><strong>Log shipping</strong>. This is an automated backup-copy-restore process of transaction log backups. The REDO phase runs when the latest log backup is restored on the secondary and the UNDO phase runs when the databases are recovered.</li>
<li><strong>Replication</strong>. The Log Reader Agent reads the transaction log records from the Publisher that are marked for replication and converts them to their corresponding DML statements, copied to the Distributor and applied to the Subscribers.</li>
</ul>
<p>Bottom line is this: <span style="color: #0000ff;"><strong>availability and recoverability is affected by the amount of transaction log records generated in the database</strong></span>. Now, you might be asking, &#8220;<em>how do data types affect HA/DR?</em>&#8221;</p>
<p>Suppose you have a table structure similar to the one below. This was actually taken from one of the corrupted databases that I had to recover last week as part of a disaster recovery situation.</p>
<div style="background-color:#eeeeee;border:1px solid #D6D6D6;font-family:arial,helvetica,sans-serif;font-size:15px;line-height:20px;margin:8px 0 20px;padding:15px 20px;">
<code style="font-size: 14px;"><span style="color: blue;">CREATE TABLE </span><span style="color: black;">[dbo].[Users]</span><span style="color: gray;">(<br />
</span><span style="color: black;">[userID] [uniqueidentifier] </span><span style="color: gray;">NOT NULL </span><span style="color: blue;">PRIMARY KEY</span><span style="color: gray;">,<br />
</span><span style="color: black;">[FirstName] [varchar]</span><span style="color: gray;">(</span><span style="color: black;">255</span><span style="color: gray;">) NULL,<br />
</span><span style="color: black;">[LastName] [varchar]</span><span style="color: gray;">(</span><span style="color: black;">255</span><span style="color: gray;">) NULL,<br />
</span><span style="color: black;">[UserLogin] [varchar]</span><span style="color: gray;">(</span><span style="color: black;">255</span><span style="color: gray;">) NULL,<br />
</span><span style="color: black;">[IsActive] [int] </span><span style="color: gray;">NULL<br />
)<br />
</span><span style="color: black;">GO<br />
</span><span style="color: blue;">CREATE NONCLUSTERED INDEX </span><span style="color: black;">NCIX_Users<br />
</span><span style="color: blue;">ON </span><span style="color: black;">Users </span><span style="color: gray;">(</span><span style="color: black;">Lastname</span><span style="color: gray;">, </span><span style="color: black;">Firstname</span><span style="color: gray;">)<br />
</span><span style="color: black;">INCLUDE </span><span style="color: gray;">(</span><span style="color: black;">UserLogin</span><span style="color: gray;">,</span><span style="color: black;">IsActive</span><span style="color: gray;">)<br />
</span><span style="color: black;">GO<br />
</span></code></div>
<p>Let&#8217;s insert a row in this table and measure how much transaction log record gets generated in the process. Note that I will wrap the INSERT statement in an explicit transaction so I can take a look at the amount of transaction log records using the <a href="https://msdn.microsoft.com/en-us/library/ms186957.aspx" target="_blank"><em>sys.dm_tran_database_transactions</em></a> DMV.</p>
<div style="background-color:#eeeeee;border:1px solid #D6D6D6;font-family:arial,helvetica,sans-serif;font-size:15px;line-height:20px;margin:8px 0 20px;padding:15px 20px;"><code style="font-size: 14px;"><span style="color: blue;">BEGIN TRAN</span><span style="color: gray;">;<br />
</span><span style="color: blue;">INSERT INTO </span><span style="color: black;">Users </span><span style="color: blue;">VALUES </span><span style="color: gray;">(</span><span style="color: magenta;">NEWID</span><span style="color: gray;">(), </span><span style="color: red;">'James'</span><span style="color: gray;">, </span><span style="color: red;">'Dylaine'</span><span style="color: gray;">, </span><span style="color: red;">'jdylaine'</span><span style="color: gray;">, </span><span style="color: black;">1</span><span style="color: gray;">);<br />
</span><span style="color: blue;">INSERT INTO </span><span style="color: black;">Users </span><span style="color: blue;">VALUES </span><span style="color: gray;">(</span><span style="color: magenta;">NEWID</span><span style="color: gray;">(), </span><span style="color: red;">'Carol'</span><span style="color: gray;">, </span><span style="color: red;">'Smith'</span><span style="color: gray;">, </span><span style="color: red;">'csmith'</span><span style="color: gray;">, </span><span style="color: black;">1</span><span style="color: gray;">);<br />
</span><span style="color: blue;">INSERT INTO </span><span style="color: black;">Users </span><span style="color: blue;">VALUES </span><span style="color: gray;">(</span><span style="color: magenta;">NEWID</span><span style="color: gray;">(), </span><span style="color: red;">'Ryan'</span><span style="color: gray;">, </span><span style="color: red;">'Anker'</span><span style="color: gray;">, </span><span style="color: red;">'ranker'</span><span style="color: gray;">, </span><span style="color: black;">1</span><span style="color: gray;">);<br />
</span><span style="color: blue;">INSERT INTO </span><span style="color: black;">Users </span><span style="color: blue;">VALUES </span><span style="color: gray;">(</span><span style="color: magenta;">NEWID</span><span style="color: gray;">(), </span><span style="color: red;">'Bobby'</span><span style="color: gray;">, </span><span style="color: red;">'Reston'</span><span style="color: gray;">, </span><span style="color: red;">'breston'</span><span style="color: gray;">, </span><span style="color: black;">1</span><span style="color: gray;">);<br />
</span><span style="color: black;">GO</span></code></p>
<p><span style="color: blue;">SELECT </span><span style="color: black;">[database_transaction_log_bytes_used]</span><span style="color: gray;">, </span><span style="color: black;">[database_transaction_log_bytes_used_system]<br />
</span><span style="color: blue;">FROM </span><span style="color: black;">sys.dm_tran_database_transactions<br />
</span><span style="color: blue;">WHERE </span><span style="color: black;">[database_id] </span><span style="color: blue;">= </span><span style="color: magenta;">DB_ID </span><span style="color: gray;">(</span><span style="color: red;">N&#8217;testDB&#8217;</span><span style="color: gray;">);<br />
</span><span style="color: black;">GO</span></p>
<p><span style="color: blue;">COMMIT TRAN<br />
</span><span style="color: black;">GO</span><br />
</div>
<p><a href="https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated1.jpg"><img fetchpriority="high" decoding="async" class=" size-full wp-image-1572 aligncenter" src="https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated1.jpg" alt="LogGenerated" width="865" height="543" srcset="https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated1.jpg 865w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated1-300x188.jpg 300w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated1-760x477.jpg 760w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated1-518x325.jpg 518w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated1-82x51.jpg 82w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated1-600x377.jpg 600w" sizes="(max-width: 865px) 100vw, 865px" /></a></p>
<p>Inserting four (4) records in the table generated 1440 bytes. That&#8217;s about 1/8 the size of a data page. Imagine the amount of transaction log records generated if this was a highly transactional table. Now, if you look at the table and index structure, the <strong>userID</strong> column &#8211; a 16-byte column &#8211; is assigned as a PRIMARY KEY column. By default, this also becomes the clustered index key. And because the clustered index key is also included in the non-clustered indexes,  we are duplicating a 16-byte column for every non-clustered index we create.</p>
<p>What if we make certain modifications on this table based on the column data types? Let&#8217;s say that we&#8217;ll change the <strong>userID</strong> column data type from <a href="https://msdn.microsoft.com/en-us/library/ms187942.aspx" target="_blank"><em>uniqueidentifier</em></a> to a <a href="https://msdn.microsoft.com/en-CA/library/ms187745.aspx" target="_blank"><em>bigint </em></a>data type of size 8 bytes and make it an identity column. Note that I am only using this as a simple example as the data types should still meet your business requirements. Let&#8217;s also change the <strong>IsActive</strong> column from an <a href="https://msdn.microsoft.com/en-CA/library/ms187745.aspx" target="_blank"><em>int</em></a> to a <a href="https://msdn.microsoft.com/en-CA/library/ms177603.aspx" target="_blank"><em>bit</em></a> data type of size 1 byte since there are only two possible values for this column.</p>
<div style="background-color:#eeeeee;border:1px solid #D6D6D6;font-family:arial,helvetica,sans-serif;font-size:15px;line-height:20px;margin:8px 0 20px;padding:15px 20px;">
<code style="font-size: 14px;"><span style="color: blue;">CREATE TABLE </span><span style="color: black;">[dbo].[Users]</span><span style="color: gray;">(<br />
</span><span style="color: black;">[userID] [bigint] </span><span style="color: #434343;">IDENTITY </span><span style="color: gray;">(</span><span style="color: black;">1</span><span style="color: gray;">,</span><span style="color: black;">1</span><span style="color: gray;">) NOT NULL </span><span style="color: blue;">PRIMARY KEY</span><span style="color: gray;">,<br />
</span><span style="color: black;">[FirstName] [varchar]</span><span style="color: gray;">(</span><span style="color: black;">255</span><span style="color: gray;">) NULL,<br />
</span><span style="color: black;">[LastName] [varchar]</span><span style="color: gray;">(</span><span style="color: black;">255</span><span style="color: gray;">) NULL,<br />
</span><span style="color: black;">[UserLogin] [varchar]</span><span style="color: gray;">(</span><span style="color: black;">255</span><span style="color: gray;">) NULL,<br />
</span><span style="color: black;">[IsActive] [bit] </span><span style="color: gray;">NULL </span><span style="color: blue;">DEFAULT </span><span style="color: black;">0<br />
</span><span style="color: gray;">)<br />
</span><span style="color: black;">GO</span></code></p>
<p><span style="color: blue;">CREATE NONCLUSTERED INDEX </span><span style="color: black;">NCIX_Users<br />
</span><span style="color: blue;">ON </span><span style="color: black;">Users </span><span style="color: gray;">(</span><span style="color: black;">Lastname</span><span style="color: gray;">, </span><span style="color: black;">Firstname</span><span style="color: gray;">)<br />
</span><span style="color: black;">INCLUDE </span><span style="color: gray;">(</span><span style="color: black;">UserLogin</span><span style="color: gray;">,</span><span style="color: black;">IsActive</span><span style="color: gray;">)<br />
</span><span style="color: black;">GO</span><br />
</div>
<p>By doing this, we&#8217;ve reduced the row size by 11 bytes. Now, you might be thinking, &#8220;<em>11 bytes is almost negligible with today&#8217;s disk and memory capacity.</em>&#8221; Let&#8217;s see. I&#8217;ll insert the same four (4) records on the new table structure and measure the amount of transaction log records generated in the process. The corresponding INSERT statements need to be updated as well to reflect the change.</p>
<div style="background-color:#eeeeee;border:1px solid #D6D6D6;font-family:arial,helvetica,sans-serif;font-size:15px;line-height:20px;margin:8px 0 20px;padding:15px 20px;">
<code style="font-size: 14px;"><span style="color: blue;">BEGIN TRAN</span><span style="color: gray;">;<br />
</span><span style="color: blue;">INSERT INTO </span><span style="color: black;">Users </span><span style="color: gray;">(</span><span style="color: black;">Firstname</span><span style="color: gray;">, </span><span style="color: black;">Lastname</span><span style="color: gray;">, </span><span style="color: black;">UserLogin</span><span style="color: gray;">, </span><span style="color: black;">IsActive</span><span style="color: gray;">) </span><span style="color: blue;">VALUES </span><span style="color: gray;">(</span><span style="color: red;">'James'</span><span style="color: gray;">, </span><span style="color: red;">'Dylaine'</span><span style="color: gray;">, </span><span style="color: red;">'jdylaine'</span><span style="color: gray;">, </span><span style="color: black;">1</span><span style="color: gray;">);<br />
</span><span style="color: blue;">INSERT INTO </span><span style="color: black;">Users </span><span style="color: gray;">(</span><span style="color: black;">Firstname</span><span style="color: gray;">, </span><span style="color: black;">Lastname</span><span style="color: gray;">, </span><span style="color: black;">UserLogin</span><span style="color: gray;">, </span><span style="color: black;">IsActive</span><span style="color: gray;">) </span><span style="color: blue;">VALUES </span><span style="color: gray;">(</span><span style="color: red;">'Carol'</span><span style="color: gray;">, </span><span style="color: red;">'Smith'</span><span style="color: gray;">, </span><span style="color: red;">'csmith'</span><span style="color: gray;">, </span><span style="color: black;">1</span><span style="color: gray;">);<br />
</span><span style="color: blue;">INSERT INTO </span><span style="color: black;">Users </span><span style="color: gray;">(</span><span style="color: black;">Firstname</span><span style="color: gray;">, </span><span style="color: black;">Lastname</span><span style="color: gray;">, </span><span style="color: black;">UserLogin</span><span style="color: gray;">, </span><span style="color: black;">IsActive</span><span style="color: gray;">) </span><span style="color: blue;">VALUES </span><span style="color: gray;">(</span><span style="color: red;">'Ryan'</span><span style="color: gray;">, </span><span style="color: red;">'Anker'</span><span style="color: gray;">, </span><span style="color: red;">'ranker'</span><span style="color: gray;">, </span><span style="color: black;">1</span><span style="color: gray;">);<br />
</span><span style="color: blue;">INSERT INTO </span><span style="color: black;">Users </span><span style="color: gray;">(</span><span style="color: black;">Firstname</span><span style="color: gray;">, </span><span style="color: black;">Lastname</span><span style="color: gray;">, </span><span style="color: black;">UserLogin</span><span style="color: gray;">, </span><span style="color: black;">IsActive</span><span style="color: gray;">) </span><span style="color: blue;">VALUES </span><span style="color: gray;">(</span><span style="color: red;">'Bobby'</span><span style="color: gray;">, </span><span style="color: red;">'Reston'</span><span style="color: gray;">, </span><span style="color: red;">'breston'</span><span style="color: gray;">, </span><span style="color: black;">1</span><span style="color: gray;">);<br />
GO<br />
</span><span style="color: blue;">SELECT </span><span style="color: black;">[database_transaction_log_bytes_used]<br />
</span><span style="color: blue;">FROM </span><span style="color: black;">sys.dm_tran_database_transactions<br />
</span><span style="color: blue;">WHERE </span><span style="color: black;">[database_id] </span><span style="color: blue;">= </span><span style="color: magenta;">DB_ID </span><span style="color: gray;">(</span><span style="color: red;">N'testDB'</span><span style="color: gray;">);<br />
</span><span style="color: black;">GO<br />
</span><span style="color: blue;">COMMIT TRAN<br />
</span><span style="color: black;">GO</span></code><br />
</div>
<p><a href="https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2.jpg"><img decoding="async" class="alignnone size-full wp-image-1573" src="https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2.jpg" alt="LogGenerated2" width="1207" height="537" srcset="https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2.jpg 1207w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2-300x133.jpg 300w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2-1024x456.jpg 1024w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2-760x338.jpg 760w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2-518x230.jpg 518w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2-82x36.jpg 82w, https://www.edwinmsarmiento.com/wp-content/uploads/2015/05/LogGenerated2-600x267.jpg 600w" sizes="(max-width: 1207px) 100vw, 1207px" /></a></p>
<p>The difference in the amount of transaction log records generated between the two is a mere 88 bytes. You might be wondering, &#8220;<em>Didn&#8217;t we just reduce the row size by 11 bytes for a total of 44 bytes for all 4 rows? How come we&#8217;ve reduced it by 88 bytes?</em>&#8221; That&#8217;s because the size reduction not just applies to the row itself but to all of the non-clustered indexes since they include the clustered index key. If you do the math, considering a table with 10,000 rows and four (4) non-clustered indexes, you&#8217;ve basically reduced the size by 550,000 bytes (550 KB.) And this number just adds up depending on the number of tables, rows and indexes that your database has.</p>
<p>If we want to achieve higher availability by reducing downtime when SQL Server is restarted, failover process initiated or when a database backup is restored, using the smallest yet appropriate sized data type for your columns is just one of many ways to do it. Because we&#8217;re reducing the amount of transaction log records generated, the REDO and UNDO phases of the recovery process will definitely run faster (not to mention the amount of log records sent to the mirror/secondary replica will also be reduced.) What I really like about this approach is the fact that doing so also improves your <a href="https://www.edwinmsarmiento.com/data-types-and-how-they-affect-performance/" target="_blank">query performance</a>.</p>
]]></content:encoded>
			

		<wfw:commentRss>https://www.edwinmsarmiento.com/data-types-and-how-they-affect-hadr/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
				<post-id xmlns="com-wordpress:feed-additions:1">1555</post-id>	</item>
	</channel>
</rss>