<?xml version="1.0" encoding="UTF-8"?>
<!-- generator="wordpress/2.3.1" -->
<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>Kirtan's Blog</title>
	<link>http://mibuso.com/blogs/kirtangor</link>
	<description>Something about Microsoft Dynamics NAV</description>
	<pubDate>Tue, 23 Mar 2010 06:46:06 +0000</pubDate>
	<generator>http://wordpress.org/?v=2.3.1</generator>
	<language>en</language>
			<item>
		<title>Implementing Encryption in Microsoft Dynamics NAV</title>
		<link>http://mibuso.com/blogs/kirtangor/2010/03/23/implementing-encryption-in-microsoft-dynamics-nav/</link>
		<comments>http://mibuso.com/blogs/kirtangor/2010/03/23/implementing-encryption-in-microsoft-dynamics-nav/#comments</comments>
		<pubDate>Tue, 23 Mar 2010 03:31:46 +0000</pubDate>
		<dc:creator>kirtangor</dc:creator>
		
		<category><![CDATA[Microsoft Dynamics NAV 2009]]></category>

		<category><![CDATA[COM]]></category>

		<category><![CDATA[Encryption]]></category>

		<category><![CDATA[Microsoft Dynamics NAV 2009 SP1]]></category>

		<category><![CDATA[Triple DES]]></category>

		<guid isPermaLink="false">http://mibuso.com/blogs/kirtangor/2010/03/23/implementing-encryption-in-microsoft-dynamics-nav/</guid>
		<description><![CDATA[There are many ways to do things. Take encryption, for example. Before a few days, I read an article titled Encrypting Data in NAV using SQL with ADO, by Rashed Amini. This article described a way of encrypting data in NAV using the encryption features provided by SQL Server.
In this article, I&#8217;ll describe a way [...]]]></description>
			<content:encoded><![CDATA[<p>There are many ways to do things. Take encryption, for example. Before a few days, I read an article titled <a href="http://mibuso.com/blogs/ara3n/2009/05/20/encrypting-data-in-nav-using-sql-with-ado/" title="Encrypting Data in NAV using SQL with ADO">Encrypting Data in NAV using SQL with ADO</a>, by Rashed Amini. This article described a way of encrypting data in NAV using the encryption features provided by SQL Server.</p>
<p>In this article, I&#8217;ll describe a way of doing this using a .NET generated COM dll.</p>
<p><u><strong>Scenario:</strong></u></p>
<p>I have a fictional customer who wants to implement credit card charging via NAV. For implementing this functionality, a field called &#8220;Credit Card No.&#8221; is to be added to the Customer table.</p>
<p>The value of the &#8220;Credit Card No.&#8221; field will be entered using the &#8220;Customer Card&#8221; window. Before saving the value of that field to the table, it must be encrypted.</p>
<p>When the &#8220;Customer Card&#8221; window is opened to view an existing customer, the credit card number field must be decrypted and display a masked value of the format &#8220;xxxx-xxxx-xxxx-1234&#8243;.</p>
<p><strong><u>Tools Used:</u></strong></p>
<p>I am using Microsoft Dynamics NAV 2009 SP1 for performing the customization, and Visual Studio 2008 for writing the .NET COM component.</p>
<p><u><strong>Implementing the COM dll:</strong></u></p>
<p>I searched <a href="http://www.codeproject.com/" title="The Code Project">CodeProject.com</a> and found an article about <a href="http://www.codeproject.com/KB/vb/VB_NET_TripleDES.aspx" title="Making TripleDES Simple in Visual Basic .NET">implementing Triple DES algorithm using .NET</a>. I picked the C# code mentioned in the article, made a few changes to it, and added it to a class library project. I made the output of the class library &#8220;COM-visible&#8221;. You can do this by right-clicking the project, and going to &#8220;Properties&#8221; &gt; &#8220;Application&#8221; tab &gt; clicking &#8220;Assembly Information&#8221; &gt; check &#8220;Make assembly COM-visible&#8221;. Also check the &#8220;Register for COM interop&#8221; checkbox in the Build tab. This will register the COM assembly in the registry.</p>
<p>As I mentioned before a few sentences, I have made a few changes to the code. One of the change that I made was creating an interface containing 2 methods &#8220;EncryptString&#8221; &amp; &#8220;DecryptString&#8221;. I have implemented this interface in a class which contains the encryption/decryption method definition. For more details, you can take a look at the <a href="http://mibuso.com/blogs/kirtangor/files/2010/03/tripledes.zip">source code</a>, its self explanatory.</p>
<p><u><strong>Implementing the EncryptString/DecryptString Methods in NAV:</strong></u></p>
<p>I have chosen Codeunit 1 to implement the EncryptString &amp; DecryptString methods. These methods will accept a string parameter, and return the encrypted &amp; decrypted string respectively.</p>
<p>The code for EncryptString &amp; DecryptString methods is given below:</p>
<p><strong><em>PROCEDURE EncryptString@1100495001(StringData@1100495001 : Text[1024]) EncryptedString : Text[1024];<br />
VAR<br />
TripleDES@1100495000 : Automation &#8220;{09B97DBF-A155-40B1-95DD-633D8672A9D3} 1.0:{8B3A39BA-5039-4248-A1FF-5455555400F8}:&#8217;TripleDES&#8217;.TripleDES&#8221;;<br />
BEGIN<br />
IF NOT ISCLEAR(TripleDES) THEN<br />
CLEAR(TripleDES);</em></strong></p>
<p><strong><em>CREATE(TripleDES);<br />
EncryptedString := TripleDES.Encrypt(StringData);<br />
CLEAR(TripleDES);<br />
END;</em></strong></p>
<p><strong><em>PROCEDURE DecryptString@1100495002(StringData@1100495000 : Text[1024]) DecryptedStringString : Text[1024];<br />
VAR<br />
TripleDES@1100495001 : Automation &#8220;{09B97DBF-A155-40B1-95DD-633D8672A9D3} 1.0:{8B3A39BA-5039-4248-A1FF-5455555400F8}:&#8217;TripleDES&#8217;.TripleDES&#8221;;<br />
BEGIN<br />
IF NOT ISCLEAR(TripleDES) THEN<br />
CLEAR(TripleDES);</em></strong></p>
<p><strong><em>CREATE(TripleDES);<br />
DecryptedStringString := TripleDES.Decrypt(StringData);<br />
CLEAR(TripleDES);<br />
END;</em></strong></p>
<p><u><strong>The actual customization:</strong></u></p>
<p>So, the base for the customization has been set up. Now, its time for the actual customization.</p>
<p>I have added a field [&#8221;Credit Card No.&#8221; Code 50] to the Customer table.</p>
<p>I have also added a global variable [&#8221;CreditCardNo&#8221; Code 50] to the &#8220;Customer Card&#8221; page. After adding the global variable, I have added a field in the &#8220;Invoicing&#8221; tab, with the source expression set to the global variable just declared.</p>
<p>The global variable is the placeholder for the decrypted credit card values, as the actual value in the field will be encrypted.</p>
<p>I have written few lines of code in the <strong><em>OnValidate</em></strong> event of the &#8220;Credit Card No.&#8221; field in the Customer table. Here it is:</p>
<p><em><strong>OnValidate=VAR<br />
EncDecUtil@1100495000 : Codeunit 1;<br />
BEGIN<br />
IF xRec.&#8221;Credit Card No.&#8221; &lt;&gt; Rec.&#8221;Credit Card No.&#8221; THEN<br />
&#8220;Credit Card No.&#8221; := EncDecUtil.EncryptString(&#8221;Credit Card No.&#8221;);<br />
END;</strong></em></p>
<p>Here, <em><strong>EncDecUtil</strong></em> is the instance of Codeunit 1, and whenever the value in the &#8220;Credit Card No.&#8221; field changes, I am updating the field with the encrypted value. This code handles the encryption logic; it will be called from the Customer Card.</p>
<p>I have also added a function to this table. This function contains the decryption and masking logic. It returns the masked string to the caller:</p>
<p><em><strong>PROCEDURE GetMaskedCreditCardNo<br />
IF &#8220;Credit Card No.&#8221; &lt;&gt; &#8221; THEN<br />
BEGIN<br />
CreditCardNo := EncDecUtil.DecryptString(&#8221;Credit Card No.&#8221;);<br />
StringLength := STRLEN(CreditCardNo);</strong></em></p>
<p><em><strong>IF StringLength &gt; 4 THEN<br />
BEGIN<br />
CreditCardNo := &#8216;XXXX-XXXX-XXXX-&#8217; + COPYSTR(CreditCardNo, StringLength - 3, 4);<br />
END;<br />
END<br />
ELSE<br />
BEGIN<br />
CreditCardNo := &#8221;;<br />
END;</strong></em></p>
<p>Here, <em><strong>CreditCardNo</strong></em> is the return variable.</p>
<p>I have added this code in the <em><strong>OnValidate</strong></em> event of the CreditCardNo field in the Customer Card:</p>
<p><em><strong>VALIDATE(&#8221;Credit Card No.&#8221;, CreditCardNo);</strong></em></p>
<p>This code will call the <em><strong>OnValidate</strong></em> event of the &#8220;Credit Card No.&#8221; field in the table, and that event, in turn, will update the table field with the encrypted value.</p>
<p>Now, after I get each record, I want to decrypt the &#8220;Credit Card No.&#8221; field, mask it, and show it on the card. I have written this code in the <em><strong>OnAfterGetRecord</strong></em> event of the Customer Card:</p>
<p><em><strong>CreditCardNo := Rec.GetMaskedCreditCardNo();</strong></em></p>
<p>Every time a record is fetched, the <em><strong>GetMaskedCreditCardNo</strong></em> method will return the decrypted and masked credit card number.</p>
<p>So, that&#8217;s it!!</p>
<p><u><strong>Downloads:</strong></u></p>
<ul>
<li><a href="http://mibuso.com/blogs/kirtangor/files/2010/03/tripledes.zip">COM dll source code</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://mibuso.com/blogs/kirtangor/2010/03/23/implementing-encryption-in-microsoft-dynamics-nav/feed/</wfw:commentRss>
		</item>
	</channel>
</rss>
