<?xml version="1.0" encoding="UTF-8"?>
<!-- generator="wordpress/2.3.3" -->
<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>Oleg Sych &#187; Oleg Sych</title>
	<link>http://www.olegsych.com</link>
	<description>this.Write(code);</description>
	<pubDate>Wed, 12 Nov 2008 12:01:35 +0000</pubDate>
	<generator>http://wordpress.org/?v=2.3.3</generator>
	<language>en</language>
			<item>
		<title>T4 Tutorial: Handling Errors in Code Generators</title>
		<link>http://www.olegsych.com/2008/11/t4-tutorial-handling-errors-in-code-generators/</link>
		<comments>http://www.olegsych.com/2008/11/t4-tutorial-handling-errors-in-code-generators/#comments</comments>
		<pubDate>Wed, 12 Nov 2008 11:58:17 +0000</pubDate>
		<dc:creator>Oleg Sych</dc:creator>
		
		<category><![CDATA[Articles]]></category>

		<category><![CDATA[C#]]></category>

		<category><![CDATA[Code Generation]]></category>

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

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

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

		<category><![CDATA[Visual Studio]]></category>

		<guid isPermaLink="false">http://www.olegsych.com/2008/11/t4-tutorial-handling-errors-in-code-generators/</guid>
		<description><![CDATA[This article is a part of a series that introduces code generation using C# and Text Templates (also known as T4 Templates) in Visual Studio; explains how to create reusable templates and combine them in complex code generators. In order to follow examples in this article, you need to have Visual Studio 2008 Standard Edition [...]]]></description>
			<content:encoded><![CDATA[<p>This article is a part of a series that introduces code generation using C# and <a href="http://www.olegsych.com/2007/12/text-template-transformation-toolkit/">Text Templates</a> (also known as T4 Templates) in Visual Studio; explains how to create reusable templates and combine them in complex code generators. In order to follow examples in this article, you need to have Visual Studio 2008 Standard Edition or higher, SQL Server 2005, <a href="http://www.codeplex.com/t4toolbox">T4 Toolbox</a> version and <a href="http://www.t4editor.net/">T4 Editor</a> installed on your computer. </p>
<p><em>If you already have installed T4 Toolbox previously, please make sure you have version 8.11.12.1 or later. </em></p>
<h4>Introduction</h4>
<p>Error conditions exist in code generators just like in all other kinds of software. And just like with any other type of software, it is important to handle error conditions appropriately. One one hand, a code generator should handle the <em>expected</em> error conditions and display information that will help its <em>user</em> to identify and correct them. On the other hand, the code generator should not handle the <em>unexpected </em>error conditions in a way that would make troubleshooting them more difficult for its <em>author</em>. Complete discussion of error handling strategy is outside of scope of this article. More information on this subject is available in <a href="http://blogs.msdn.com/kcwalina/archive/2007/01/30/ExceptionHierarchies.aspx">How to Design Exception Hierarchies by Krzysztof Cwalina</a> and <a href="http://martinfowler.com/ieeeSoftware/failFast.pdf">Fail Fast by Jim Shore</a>.</p>
<p>This article reviews examples of error conditions in the code generator created <a href="http://www.olegsych.com/2008/09/t4-tutorial-creating-complex-code-generators/">earlier in this series</a> and discusses how to handle them. As you remember, this <em>generator</em> (shown below) uses several <em>templates</em> that retrieve table schema information from a given SQL Server database using <a target="_blank" href="http://msdn.microsoft.com/en-us/library/ms162169.aspx">SMO</a> and generate DELETE, INSERT and UPDATE stored procedures for each table.&#160; </p>
<p><em>CrudProcedureGenerator.tt</em></p>
<pre class="code">

<span style="background: gold">&lt;#@</span><span style="color: red"> </span><span style="color: brown">assembly </span><span style="color: red">name=</span>&quot;<span style="color: blue">Microsoft.SqlServer.ConnectionInfo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">assembly </span><span style="color: red">name=</span>&quot;<span style="color: blue">Microsoft.SqlServer.Smo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">import </span><span style="color: red">namespace=</span>&quot;<span style="color: blue">Microsoft.SqlServer.Management.Smo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">DeleteProcedureTemplate.tt</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">InsertProcedureTemplate.tt</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">UpdateProcedureTemplate.tt</span>&quot; <span style="background: gold">#&gt;
&lt;#+
</span><span style="background: #f0f8ff; color: #191970">public class CrudProcedureGenerator : Generator
{
  public string DatabaseName;

  public DeleteProcedureTemplate DeleteTemplate = new DeleteProcedureTemplate();
  public InsertProcedureTemplate InsertTemplate = new InsertProcedureTemplate();
  public UpdateProcedureTemplate UpdateTemplate = new UpdateProcedureTemplate();

  protected override void RunCore()
  {
    Server server = new Server();
    Database database = new Database(server, this.DatabaseName);
    database.Refresh();</span>

<span style="background: #f0f8ff; color: #191970">    // &#8230;
  }
}
</span><span style="background: gold">#&gt;</span>
</pre>
<p><a href="http://11011.net/software/vspaste"></a></p>
<p>Below is an example of using this code generator to produce stored procedures for the <em>Northwind</em> database on the local computer. Complete source code of this example is available for download at the bottom of this article.</p>
<p><em>NorthwindStoredProcedures.tt</em></p>
<pre class="code"><span style="background: gold">&lt;#@</span><span style="color: red"> </span><span style="color: brown">template </span><span style="color: red">language=</span>&quot;<span style="color: blue">C#</span>&quot; <span style="color: red">hostspecific=</span>&quot;<span style="color: blue">True</span>&quot; <span style="color: red">debug=</span>&quot;<span style="color: blue">True</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">output </span><span style="color: red">extension=</span>&quot;<span style="color: blue">txt</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">T4Toolbox.tt</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">CrudProcedureGenerator.tt</span>&quot; <span style="background: gold">#&gt;
&lt;#
</span><span style="background: #f0f8ff; color: #191970">    CrudProcedureGenerator generator = new CrudProcedureGenerator();
    generator.DatabaseName = &quot;Northwind&quot;;
    generator.Run();
</span><span style="background: gold">#&gt;</span></pre>
<p><a href="http://11011.net/software/vspaste"></a></p>
<h4>Usage Errors</h4>
<p>A typical error in using a complex code generator is forgetting to specify a required parameter, such as <em>DatabaseName</em> in our example. We can simulate this error by commenting out the line that assigns <em>“Northwind”</em> to <em>generator.DatabaseName</em> in <em>NorthwindStoredProcedures.tt</em> and saving the file which causes Visual Studio to run the code generator and display the following error.</p>
<p><img style="display: inline" title="image" border="0" alt="image" src="http://www.olegsych.com/wp-content/uploads/2008/11/image.png" width="580" height="189" /> </p>
<p>As you can see, this error provides complete details about the exception that caused it and will help the <em>author</em> of the code generator to identify the problem quickly. Unfortunately, it does not help the <em>user</em> of the code generator, because it is too verbose and low-level. We can make it a lot more specific and helpful by adding the following code <em>to CrudProcedureGenerator.tt</em>. </p>
<pre class="code"><span style="background: gold">&lt;#@&#8230;#</span><span style="background: gold">&gt;
</span><span style="background: gold">&lt;#+
</span><span style="background: #f0f8ff; color: #191970">public class CrudProcedureGenerator : Generator
{
  public string DatabaseName;
  // &#8230;
  protected override void Validate()
  {
    if (string.IsNullOrEmpty(this.DatabaseName))
    {
      this.Error(
        &quot;DatabaseName property of CrudProcedureGenerator must be assigned&quot;);
    }
  }
}
</span><span style="background: gold">#&gt;</span></pre>
<p><a href="http://11011.net/software/vspaste"></a><a href="http://11011.net/software/vspaste"></a><a href="http://11011.net/software/vspaste"></a></p>
<p><em>Validate</em> is a protected virtual method defined in the base class - <em>Generator</em>. When overridden in a concrete descendant class, such as <em>CrudProcedureGenerator</em>, this method can use <em>Error </em>and <em>Warning </em>methods of the <em>Generator </em>class to report errors and warnings. The <em>Run </em>method, also defined in the <em>Generator </em>class, will call the <em>Validate </em>method first. If <em>Validate </em>doesn’t report any errors, <em>Run </em>will call <em>RunCore</em> which <em>CrudProcedureGenerator</em> overrides to implement the actual code generation logic. And finally, <em>Run</em> will display any errors or warnings reported during code generation in the Error List window of Visual Studio. With added error-handling code, the following error message is displayed when we try to run the code generator without specifying <em>DatabaseName</em>.&#160; </p>
<p><img style="display: inline" title="image" border="0" alt="image" src="http://www.olegsych.com/wp-content/uploads/2008/11/image1.png" width="580" height="189" /> </p>
<p><em>Template</em> class of <a target="_blank" href="http://www.olegsych.com/2008/08/t4-toolbox/">T4 Toolbox</a> follows the same pattern to support error handling. This class also defines virtual <em>Validate </em>method as well as <em>Error</em> and <em>Warning</em> methods which can be used by concrete descendants to report errors and warnings.</p>
<h4>Environment Errors</h4>
<p>Code generators typically access external resources to obtain metadata for code generation. File system and database are perhaps the most common sources of metadata. In our example, we are accessing a database running on the local computer. While <em>NorthwindStoredProcedures.tt</em> may work perfectly for the developer who originally created it, another developer on the same team, might have SQL Server configured differently, perhaps using a named instance, which can prevent the same code generator from running on her computer. We can simulate this error by stopping the SQL Server service (using the “net stop mssqlserver” in Windows command prompt) and re-running the code generator (by selecting “Run Custom Tool” from the context menu of <em>NorthwindStoredProcedures.tt</em> in Solution Explorer of Visual Studio).&#160; </p>
<p><img style="display: inline" title="image" border="0" alt="image" src="http://www.olegsych.com/wp-content/uploads/2008/11/image2.png" width="580" height="189" /> </p>
<p>Similar to the usage error we discussed earlier, this error is very verbose and low-level. We can make it more precise and useful for the <em>users </em>of the code generator by wrapping the original <em>FailedOperationException</em>, thrown by SMO in a <em>TransformationException</em> defined by the T4 Toolbox.</p>
<pre class="code"><span style="background: gold">&lt;#@&#8230;#</span><span style="background: gold">&gt;
</span><span style="background: gold">&lt;#+
</span><span style="background: #f0f8ff; color: #191970">public class CrudProcedureGenerator : Generator
{
  public string DatabaseName;
  // &#8230;
  protected override void RunCore()
  {
    try
    {
      Server server = new Server();
      Database database = new Database(server, this.DatabaseName);
      database.Refresh();
      // &#8230;
    }
    catch (FailedOperationException e)
    {
      throw new TransformationException(
        string.Format(
          &quot;Unable to access {0} database on local SQL Server instance&quot;,
          this.DatabaseName),
        e);
    }
  }
  // &#8230;
}
</span><span style="background: gold">#&gt;</span></pre>
<p><a href="http://11011.net/software/vspaste"></a></p>
<p><em>Run </em>method of the <em>Generator</em> class will catch <em>TransformationException</em> and displays its <em>Message</em> in the <em>Error List</em> of <em>Visual Studio</em>. </p>
<p><img style="display: inline" title="image" border="0" alt="image" src="http://www.olegsych.com/wp-content/uploads/2008/11/image3.png" width="580" height="189" /> </p>
<p>In other words, instances of <em>TransformationException</em> class are considered to be expected exceptions, thrown by the code generator itself. Only error message is displayed for expected exceptions. All other exception types are treated as unexpected and will be displayed with complete stack trace.</p>
<p><em>Render </em>method of the <em>Template</em> class also catches <em>TransformationException</em> instances and reports them as expected errors.</p>
<h4>Unexpected Errors</h4>
<p>Unexpected errors are, well, unexpected. The <em>author</em> of the code generator does not expect them to occur. When <em>user </em>of&#160; the code generator encounters such an error, having complete details about it will help to troubleshoot and resolve the problem quickly. Allowing unexpected exceptions to simply bubble up unhandled will display their complete stack trace in the Error List of Visual Studio. On the other hand, trying to make the code generator more “robust” and “user-friendly” by catching all exceptions hides the exception stack trace and makes it more difficult to troubleshoot. It is best to catch only those exceptions that indicate error conditions you expect and can make specific recommendations to the user on how to resolve them. </p>
<h4>Conclusion</h4>
<p>By default, Visual Studio displays complete details for unhandled exceptions that occur during code generation in the Error List window. This makes them easier to troubleshoot for <em>authors </em>of code generators. Appropriate error handling can helps to make code generators easier for the <em>users </em>to use. T4 Toolbox defines <em>TransformationException</em>, which code generators can throw with a user-readable messages to indicate expected error conditions. <em>Template </em>and <em>Generator</em> classes catch exceptions of this type and display only the exception message in the Error List of Visual Studio. Both <em>Template </em>and <em>Generator</em> classes provide virtual <em>Validate</em> methods that descendants can override to implement validation of code generation parameters. <em>Error </em>and <em>Warning </em>methods are available in both base classes to report multiple errors and warnings.</p>
<h4>Download</h4>
<ul>
<li><a href="http://www.olegsych.com/wp-content/uploads/2008/09/t4-tutorial-creating-complex-code-generators.zip">Source code, initial</a> </li>
<li><a href="http://www.olegsych.com/wp-content/uploads/2008/11/t4-tutorial-handling-errors-in-code-generators.zip">Source code, completed</a> </li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://www.olegsych.com/2008/11/t4-tutorial-handling-errors-in-code-generators/feed/</wfw:commentRss>
		</item>
		<item>
		<title>Advanced Code Generation Patterns with T4 &#38; DSL Tools</title>
		<link>http://www.olegsych.com/2008/10/advanced-code-generation-patterns-with-t4-and-dsl-tools/</link>
		<comments>http://www.olegsych.com/2008/10/advanced-code-generation-patterns-with-t4-and-dsl-tools/#comments</comments>
		<pubDate>Wed, 22 Oct 2008 11:10:55 +0000</pubDate>
		<dc:creator>Oleg Sych</dc:creator>
		
		<category><![CDATA[Uncategorized]]></category>

		<category><![CDATA[Code Generation]]></category>

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

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

		<category><![CDATA[Visual Studio]]></category>

		<guid isPermaLink="false">http://www.olegsych.com/2008/10/advanced-code-generation-patterns-with-t4-and-dsl-tools/</guid>
		<description><![CDATA[Back in September, I had a chance to co-present Advanced code generation patterns with T4 &#38; DSL Tools with Gareth Jones and Jean-Marc Prieur at the VSX Developer Conference. Here is the abstract of this session:
Code generation is an increasingly common technique in application development and forms a part of many Visual Studio extensions. With [...]]]></description>
			<content:encoded><![CDATA[<p>Back in September, I had a chance to co-present <a href="http://channel9.msdn.com/posts/AnthonyC/Advanced-code-generation-patterns-with-T4--DSL-Tools/">Advanced code generation patterns with T4 &amp; DSL Tools</a> with <a href="http://blogs.msdn.com/garethj/">Gareth Jones</a> and <a href="http://blogs.msdn.com/jmprieur">Jean-Marc Prieur</a> at the <a href="http://msdn.com/vsx/conference">VSX Developer Conference</a>. Here is the abstract of this session:</p>
<blockquote><p>Code generation is an increasingly common technique in application development and forms a part of many Visual Studio extensions. With the addition of T4 to Visual Studio 2008, every developer has a powerful code generation engine available to them. In this session we&#8217;ll look at patterns of usage of T4 and ways to structure your templates for large-scale reuse. We&#8217;ll explore a sample that aids large scale code generation from DSL models and finally look at a community library which adds facilities to make the tricky problems of incremental code generation and reverse engineering from a DSL easier.</p>
</blockquote>
<p>Gareth recently <a href="http://feeds.feedburner.com/~r/GarethjsWeblog/~3/427880572/new-dsl-screencasts-avaialble-from-vsx-conference.aspx">wrote</a> that recording of <a href="http://channel9.msdn.com/posts/AnthonyC/Advanced-code-generation-patterns-with-T4--DSL-Tools/">this</a> and <a href="http://msdn.microsoft.com/en-us/vsx/cc676517.aspx">other VSX sessions</a> is now available on <a href="http://channel9.msdn.com">Channel 9</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.olegsych.com/2008/10/advanced-code-generation-patterns-with-t4-and-dsl-tools/feed/</wfw:commentRss>
		</item>
		<item>
		<title>T4 Tutorial: Reusing code generators on multiple projects</title>
		<link>http://www.olegsych.com/2008/10/t4-tutorial-reusing-code-generators-on-multiple-projects/</link>
		<comments>http://www.olegsych.com/2008/10/t4-tutorial-reusing-code-generators-on-multiple-projects/#comments</comments>
		<pubDate>Sun, 05 Oct 2008 23:27:03 +0000</pubDate>
		<dc:creator>Oleg Sych</dc:creator>
		
		<category><![CDATA[Articles]]></category>

		<category><![CDATA[C#]]></category>

		<category><![CDATA[Code Generation]]></category>

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

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

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

		<category><![CDATA[Visual Studio]]></category>

		<guid isPermaLink="false">http://www.olegsych.com/2008/10/t4-tutorial-reusing-code-generators-on-multiple-projects/</guid>
		<description><![CDATA[This article is a part of a series that introduces code generation using C# and Text Templates (also known as T4 Templates) in Visual Studio; explains how to create reusable templates and combine them in complex code generators.]]></description>
			<content:encoded><![CDATA[<p>This article is a part of a series that introduces code generation using C# and <a href="http://www.olegsych.com/2007/12/text-template-transformation-toolkit/">Text Templates</a> (also known as T4 Templates) in Visual Studio; explains how to create reusable templates and combine them in complex code generators. In order to follow examples in this article, you need to have Visual Studio 2008 Standard Edition or higher, SQL Server 2005, <a href="http://www.codeplex.com/t4toolbox">T4 Toolbox</a> and <a href="http://www.t4editor.net/">T4 Editor</a> installed on your computer. </p>
<h4>Introduction</h4>
<p><img style="margin: 0px 0px 5px 5px; display: inline" title="Code Generation Solution" border="0" alt="Code Generation Solution" align="right" src="http://www.olegsych.com/wp-content/uploads/2008/10/image.png" width="240" height="217" /> In the <a href="http://www.olegsych.com/2008/09/t4-tutorial-creating-complex-code-generators/">previous article</a> of this series, we created <em>CrudProcedureGenerator.tt – </em>a reusable code generator that produces <a href="http://en.wikipedia.org/wiki/Create,_read,_update_and_delete">CRUD</a> stored procedures for all tables in a given SQL Server database. Each type of stored procedure is produced by a separate <a href="http://www.olegsych.com/2008/09/t4-tutorial-creating-reusable-code-generation-templates/">template</a> – <em>DeleteProcedureTemplate.tt</em>, <em>InsertProcedureTemplate.tt</em> or <em>UpdateProcedureTemplate.tt</em>. The <em>Generator and</em>&#160;<em>Templates </em>use <a target="_blank" href="http://msdn.microsoft.com/en-us/library/ms162169.aspx">SMO</a> (<a target="_blank" href="http://msdn.microsoft.com/en-us/library/ms162169.aspx">SQL Server Management Objects</a>) to retrieve table and column information from the database. We have also created a simple code generation file shown below to generate CRUD stored procedures for all tables in the <em>Northwind</em> sample database. </p>
<pre class="code"><span style="background: gold">&lt;#@</span><span style="color: red"> </span><span style="color: brown">template </span><span style="color: red">language=</span>&quot;<span style="color: blue">C#</span>&quot; <span style="color: red">hostspecific=</span>&quot;<span style="color: blue">True</span>&quot; <span style="color: red">debug=</span>&quot;<span style="color: blue">True</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">output </span><span style="color: red">extension=</span>&quot;<span style="color: blue">txt</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">T4Toolbox.tt</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">CrudProcedureGenerator.tt</span>&quot; <span style="background: gold">#&gt;
&lt;#
</span><span style="background: #f0f8ff; color: #191970">    CrudProcedureGenerator generator = new CrudProcedureGenerator();
    generator.DatabaseName = &quot;Northwind&quot;;
    generator.Run();
</span><span style="background: gold">#&gt;</span></pre>
</p>
<p>In its current form, this code generation solution will work well for producing CRUD stored procedures in a single application development project. This article will illustrate how it can be reused across multiple projects and multiple teams.</p>
<h4>Source control</h4>
<p>It is important to keep both generated source code and code generation files under <a href="http://en.wikipedia.org/wiki/Source_control">source control</a>. During initial development of the code generation solution, the code generation files are typically stored side-by-side with the generated files.</p>
<p><img style="display: inline" title="image" border="0" alt="image" src="http://www.olegsych.com/wp-content/uploads/2008/10/image1.png" width="580" height="363" /></p>
<p>However, as soon as the code generation files need to be reused outside of the original project where they were developed, they need to be stored separately and treated as a separate project. </p>
<h4>Separate code generation files from project files</h4>
<ul>
<li>Create a new folder called <em>CodeGeneration</em> and move reusable code generation files from the original project folder into the new folder. </li>
</ul>
<p><img style="display: inline" title="image" border="0" alt="image" src="http://www.olegsych.com/wp-content/uploads/2008/10/image2.png" width="580" height="363" /> </p>
<p>Note that <em>NorthwindStoredProcedures.tt</em> remained in its original location. This file relies on reusable code generation files to generate SQL scripts specific to a particular project, <em>Northwind </em>database in this example. In other words, <em>NorthwindStoredProcedures.tt</em> is project-specific and should be stored with the rest of this project’s source code. </p>
<h4>Use relative file paths</h4>
<p>It is important to rely on relative file paths in team environment to allow for differences in computer configurations of different team members. However, after moving reusable code generation files out of their original location, we will get an error trying to regenerate <em>NorthwindStoredProcedures.tt</em>.</p>
<p><img style="display: inline" title="image" border="0" alt="image" src="http://www.olegsych.com/wp-content/uploads/2008/10/image3.png" width="580" height="189" /> </p>
<p>As you can see in the source code of <em>NorthwindStoredProcedures.tt</em> at the top of this article, it uses <a target="_blank" href="http://www.olegsych.com/2008/02/t4-include-directive/">include directive</a> with a relative path to pull in the contents of <em>CrudProcedureGenerator.tt</em>. Although we can fix the immediate problem by changing the <em>NorthwindStoredProcedures.tt </em>to refer to <em>CrudProcedureGenerator.tt </em>as “..\CodeGeneration\CrudProcedureGenerator.tt”, support for relative file paths in the <em>include directive</em> is limited just one level of nesting and it will not be able to find <em>DeleteProcedureTemplate.tt</em>, <em>IncludeProcedureTemplate.tt</em> and <em>UpdateProcedureTemplate.tt </em>included by <em>CrudProcedureGenerator.tt</em>. We can work around this limitation by adding path to shared code generation files to the list of known <em>IncludeFolders</em>.</p>
<ul>
<li>Add <em>IncludeCodeGeneration</em> string value to the HKLM\Software\Microsoft\VisualStudio\9.0\TextTemplating\IncludeFolders\.tt registry key. Enter full path to the <em>CodeGeneration</em> folder as the value data. </li>
</ul>
<p><img style="display: inline" title="image" border="0" alt="image" src="http://www.olegsych.com/wp-content/uploads/2008/10/image4.png" width="580" height="188" /></p>
<p>Visual Studio will attempt to resolve relative file paths used in the include directive by combining them with the known <em>IncludeFolders</em>. As long as each developer working on the project has the path to the <em>CodeGeneration</em> folder added to the registry, they will be able to use the shared code generation files without having to modify them or using absolute paths in files themselves. </p>
<h4>Reusing code generator on another project</h4>
<p>At this point, all we need to start using <em>CrudProcedureGenerator</em> on another project is create a code generation file similar to <em>NorthwindStoredProcedures.tt</em> and specify a different database in it. </p>
<pre class="code"><span style="background: gold">&lt;#@</span><span style="color: red"> </span><span style="color: brown">template </span><span style="color: red">language=</span>&quot;<span style="color: blue">C#</span>&quot; <span style="color: red">hostspecific=</span>&quot;<span style="color: blue">True</span>&quot; <span style="color: red">debug=</span>&quot;<span style="color: blue">True</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">output </span><span style="color: red">extension=</span>&quot;<span style="color: blue">txt</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">T4Toolbox.tt</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">CrudProcedureGenerator.tt</span>&quot; <span style="background: gold">#&gt;</span><span style="color: red">
</span><span style="background: gold">&lt;#
</span><span style="background: #f0f8ff; color: #191970">    CrudProcedureGenerator generator = new CrudProcedureGenerator();
    generator.DatabaseName = &quot;pubs&quot;;
    generator.Run();
</span><span style="background: gold">#&gt;</span></pre>
<p><a href="http://11011.net/software/vspaste"></a></p>
<p><img style="margin: 0px 0px 0px 5px; display: inline" title="image" border="0" alt="image" align="right" src="http://www.olegsych.com/wp-content/uploads/2008/10/image5.png" width="254" height="320" />The resulting structure of folders and projects in your solution may look as shown on the right. Complete source code is available for download at the bottom of the article.</p>
</p>
<h4>Reusing code generator on another team</h4>
<p>In this article we assumed that both projects using the shared code generator are stored in the same source control repository. This may be the case when the same team is working on both projects. If separate teams are working on these projects, they may be using separate source control repositories. Only one repository should be used for development and maintenance of the code generation files. This repository stores the “master” copy of the code generation files. Other teams will typically store a copy of these files in their own source control repository to preserve complete source code history of their project. As improvements are made to the master copy, other teams can upgrade their copy when it’s appropriate for their project.</p>
<h4>Download</h4>
<ul>
<li><a href="http://www.olegsych.com/wp-content/uploads/2008/09/t4-tutorial-creating-complex-code-generators.zip">Source code, initial</a> </li>
<li><a href="http://www.olegsych.com/wp-content/uploads/2008/10/t4-tutorial-reusing-code-generators-on-multiple-projects.zip">Source code, completed</a> </li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://www.olegsych.com/2008/10/t4-tutorial-reusing-code-generators-on-multiple-projects/feed/</wfw:commentRss>
		</item>
		<item>
		<title>T4 Tutorial: Creating complex code generators</title>
		<link>http://www.olegsych.com/2008/09/t4-tutorial-creating-complex-code-generators/</link>
		<comments>http://www.olegsych.com/2008/09/t4-tutorial-creating-complex-code-generators/#comments</comments>
		<pubDate>Sat, 27 Sep 2008 18:36:34 +0000</pubDate>
		<dc:creator>Oleg Sych</dc:creator>
		
		<category><![CDATA[Articles]]></category>

		<category><![CDATA[C#]]></category>

		<category><![CDATA[Code Generation]]></category>

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

		<category><![CDATA[Visual Studio]]></category>

		<guid isPermaLink="false">http://www.olegsych.com/2008/09/t4-tutorial-creating-complex-code-generators/</guid>
		<description><![CDATA[This article is a part of a series that introduces code generation using C# and Text Templates (also known as T4 Templates) in Visual Studio; explains how to create reusable templates and combine them in complex code generators.]]></description>
			<content:encoded><![CDATA[<p>This article is a part of a series that introduces code generation using C# and <a href="http://www.olegsych.com/2007/12/text-template-transformation-toolkit/">Text Templates</a> (also known as T4 Templates) in Visual Studio; explains how to create reusable templates and combine them in complex code generators. In order to follow examples in this article, you need to have Visual Studio 2008 Standard Edition or higher, SQL Server 2005, <a href="http://www.codeplex.com/t4toolbox">T4 Toolbox</a> and <a href="http://www.t4editor.net/">T4 Editor</a> installed on your computer. </p>
<h4>Introduction</h4>
<p>In the <a href="http://www.olegsych.com/2008/09/t4-tutorial-creating-reusable-code-generation-templates/">previous article</a> of this series, we created a reusable code generation template called <em>DeleteProcedureTemplate</em> that generates a DELETE stored procedure for a given database table using <a target="_blank" href="http://msdn.microsoft.com/en-us/library/ms162169.aspx">SMO</a>. We have also created a simple code generation file shown below to generate a DELETE procedure for the <em>Products </em>table in the <em>Northwind </em>database.</p>
<pre class="code"><span style="background: gold">&lt;#@</span><span style="color: red"> </span><span style="color: brown">template </span><span style="color: red">language=</span>&quot;<span style="color: blue">C#</span>&quot; <span style="color: red">hostspecific=</span>&quot;<span style="color: blue">True</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">output </span><span style="color: red">extension=</span>&quot;<span style="color: blue">sql</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">T4Toolbox.tt</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">DeleteProcedureTemplate.tt</span>&quot; <span style="background: gold">#&gt;
&lt;#
</span><span style="background: #f0f8ff; color: #191970">    DeleteProcedureTemplate template = new DeleteProcedureTemplate();
    template.DatabaseName = &quot;Northwind&quot;;
    template.TableName = &quot;Products&quot;;
    template.Render();
</span><span style="background: gold">#&gt;</span></pre>
<p>In its current form, this code generator has several drawbacks. Extending this file to generate stored procedures for multiple tables will produce a single large SQL script, which becomes increasingly difficult to work with. On the other hand, creating similar files to generate additional stored procedures in separate files results in code duplication and increases the number of the code generation files themselves. Ideally, we want to generate all <a href="http://en.wikipedia.org/wiki/Create,_read,_update_and_delete">CRUD</a> stored procedures for a given set of database tables in separate SQL scripts. Let’s see how we can accomplish that using <a target="_blank" href="http://www.olegsych.com/2007/12/text-template-transformation-toolkit/"></a><a target="_blank" href="http://www.olegsych.com/2008/08/t4-toolbox/">T4 Toolbox</a>. </a></p>
<h4>Creating a new code generator</h4>
<ul>
<li>Continue using the C# project you created previously or download the initial source code below. </li>
<li>Click Project-&gt;Add New Item in the main menu and select <em>Generator </em>item from the <em>Code Generation</em> folder in the dialog. If you don&#8217;t see this folder or this item, make sure you have the latest version of <a href="http://www.olegsych.com/2008/08/t4-toolbox/">T4 Toolbox</a> installed. </li>
</ul>
<p><img style="display: inline" title="Add New Item dialog" border="0" alt="Add New Item dialog" src="http://www.olegsych.com/wp-content/uploads/2008/09/image18.png" width="580" height="330" /> </p>
</p>
<ul>
<li>Enter <em>CrudProcedureGenerator.tt</em> as the item name and click the Add button. </li>
<li>Double-click <em>CrudProcedureGenerator.tt</em> in the Solution Explorer. You will see the following text in the editor. </li>
</ul>
<p><a href="http://11011.net/software/vspaste"></a></p>
<pre class="code"><span style="background: gold">&lt;#+
</span><span style="background: #f0f8ff; color: #191970">// &lt;copyright file=&quot;CrudProcedureGenerator.tt&quot; company=&quot;Your Company&quot;&gt;
//  Copyright © Your Company. All Rights Reserved.
// &lt;/copyright&gt;

public class CrudProcedureGenerator : Generator
{
    protected override void RunCore()
    {

    }
}
</span><span style="background: gold">#&gt;</span></pre>
<p>This file contains a <a target="_blank" href="http://www.olegsych.com/2008/02/t4-class-feature-blocks/">class feature block</a> that defines a class called <em>CrudProcedureGenerator.</em> It inherits from a base class <em>Generator</em>, which is defined in <a href="http://www.olegsych.com/2008/08/t4-toolbox/">T4 Toolbox</a>. Similar to the <em>template </em>class definition we talked about in the previous article, this file is not intended to be used for code generation directly. Instead it will be reused by other code generation files, as we will see shortly. </p>
<ul>
<li>Select <em>DeleteProcedureTemplate.tt</em> in the solution explorer and change Custom Tool property from TextTemplatingFileGenerator to an empty value. This will prevent Visual Studio from trying to use this file for code generation and reporting errors in the Error List window. </li>
</ul>
<h4>Encapsulate code generation logic in the generator class</h4>
<p><em>Generator </em>base class defines an abstract method called <em>RunCore</em>. Each concrete generator must override this method and implement the code generation logic inside of it. A concrete <em>generator </em>typically uses one or more <em>templates</em> to generate one or more output files.</p>
<ul>
<li>Modify <em>CrudStoredProcedureGenerator.tt </em>to look like this: </li>
</ul>
<p><a href="http://11011.net/software/vspaste"></a></p>
<pre class="code"><span style="background: gold">&lt;#@</span><span style="color: red"> </span><span style="color: brown">assembly </span><span style="color: red">name=</span>&quot;<span style="color: blue">Microsoft.SqlServer.ConnectionInfo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">assembly </span><span style="color: red">name=</span>&quot;<span style="color: blue">Microsoft.SqlServer.Smo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">import </span><span style="color: red">namespace=</span>&quot;<span style="color: blue">Microsoft.SqlServer.Management.Smo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">DeleteProcedureTemplate.tt</span>&quot; <span style="background: gold">#&gt;
&lt;#+
</span><span style="background: #f0f8ff; color: #191970">public class CrudProcedureGenerator : Generator
{
    public string DatabaseName;
    public DeleteProcedureTemplate DeleteTemplate = new DeleteProcedureTemplate();

    protected override void RunCore()
    {
        Server server = new Server();
        Database database = new Database(server, this.DatabaseName);
        database.Refresh();
        foreach (Table table in database.Tables)
        {
            this.DeleteTemplate.DatabaseName = this.DatabaseName;
            this.DeleteTemplate.TableName = table.Name;
            this.DeleteTemplate.RenderToFile(table.Name + &quot;_Delete.sql&quot;);
        }
    }
}
</span><span style="background: gold">#&gt;</span></pre>
<p>Note that this class defines a public field, <em>DatabaseName</em>, to allow the caller to specify a database for which stored procedures need to be generated. It also defines a public field, <em>DeleteTemplate</em>, which is initialized with a <em>DeleteProcedureTemplate </em>instance. The <em>RunCore </em>method retrieve the list of all tables in a database with the specified <em>DatabaseName</em> and generates a DELETE stored procedure for each table with the help of the <em>DeleteTemplate</em>. Thanks to the <em>RenderToFile</em> method, which is defined in the <em>Template </em>base class, each stored procedure is generated in a separate SQL file.</p>
<h4>Reuse the code generator</h4>
<p>Having the logic necessary to generate DELETE stored procedures for multiple tables encapsulated in the <em>CrudProcedureGenerator </em>class, we can now start using this generator on one or more application development projects to generate stored procedures for different databases.</p>
<ul>
<li>Click Project-&gt;Add New Item in the main menu and select File item from the Code Generation folder in the dialog. </li>
<li>Name the new file NorthwindProcedures.tt and change its contents to look similar to this. </li>
</ul>
<pre class="code"><span style="background: gold">&lt;#@</span><span style="color: red"> </span><span style="color: brown">template </span><span style="color: red">language=</span>&quot;<span style="color: blue">C#</span>&quot; <span style="color: red">hostspecific=</span>&quot;<span style="color: blue">True</span>&quot; <span style="color: red">debug=</span>&quot;<span style="color: blue">True</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">output </span><span style="color: red">extension=</span>&quot;<span style="color: blue">txt</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">T4Toolbox.tt</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">CrudProcedureGenerator.tt</span>&quot; <span style="background: gold">#&gt;
&lt;#
</span><span style="background: #f0f8ff; color: #191970">    CrudProcedureGenerator generator = new CrudProcedureGenerator();
    generator.DatabaseName = &quot;Northwind&quot;;
    generator.Run();
</span><span style="background: gold">#&gt;</span></pre>
<p>This code generation file uses <a target="_blank" href="http://www.olegsych.com/2008/02/t4-include-directive/">include directive</a> to pull in the contents of <em>CrudProcedureGenerator.tt</em> and a <a target="_blank" href="http://www.olegsych.com/2008/02/t4-statement-blocks/">statement block</a> to create a new instance of the <em>CrudProcedureGenerator </em>class. It specifies value for the <em>DatabaseName</em> field of the generator and calls its <em>Run </em>method. <em>Run </em>method calls the <em>RunCore</em> method we implemented previously, with additional validation checks and error handling.</p>
<p><img style="margin: 0px 0px 0px 10px; display: inline" title="Solution Explorer window" border="0" alt="Solution Explorer window" align="right" src="http://www.olegsych.com/wp-content/uploads/2008/09/image19.png" width="313" height="449" /> </p>
<ul>
<li>Save <em>NorthwindStoredProcedures.tt -</em> Visual Studio will compile and run the code generator. Be patient, it can take a while for the code generator to retrieve metadata from a “cold” database. </li>
<li>Click the “+” sign next to the <em>NorthwindStoredProcedures.tt</em> in Solution Explorer. You will see a number of SQL files nested under it, each with a single DELETE stored procedure for a particular database table. </li>
</ul>
<p>At this point, we have a <em>generator </em>that produces stored procedures for all tables in the <em>Northwind </em>database. We can reuse this generator on another project by creating another code generation file, such as <em>AdventureWorksStoredProcedures.tt</em> that specifies a different database name to generate stored procedures for. It would be straightforward to implement additional <em>templates </em>for SELECT, INSERT and UPDATE procedures and extend our <em>generator </em>to incorporate them. We could also improve the <em>generator</em> by allowing the caller to define a subset of tables that need stored procedures using a wildcard or a regular expression. However, these enhancements are outside of the scope of this tutorial and are left for the readers to complete. </p>
<h4>Conclusion</h4>
<p>This article showed how to create a complex <em>generator</em>, which uses one or more <em>templates</em> to generate multiple output files of different types. This generator is easy to manage, as it generates all outputs for the given input. It can also be easily reused without introducing code duplication. </p>
<p>The <a href="http://www.olegsych.com/2008/10/t4-tutorial-reusing-code-generators-on-multiple-projects/">next article</a> will discuss reusing code generators on multiple projects and multiple teams. </p>
<h4>Download</h4>
<ul>
<li><a href="http://www.olegsych.com/wp-content/uploads/2008/09/t4-tutorial-creating-reusable-code-generation-templates.zip">Source code, initial</a>. </li>
<li><a href="http://www.olegsych.com/wp-content/uploads/2008/09/t4-tutorial-creating-complex-code-generators.zip">Source code, completed</a>. </li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://www.olegsych.com/2008/09/t4-tutorial-creating-complex-code-generators/feed/</wfw:commentRss>
		</item>
		<item>
		<title>T4 Tutorial: Creating reusable code generation templates</title>
		<link>http://www.olegsych.com/2008/09/t4-tutorial-creating-reusable-code-generation-templates/</link>
		<comments>http://www.olegsych.com/2008/09/t4-tutorial-creating-reusable-code-generation-templates/#comments</comments>
		<pubDate>Sat, 20 Sep 2008 13:28:14 +0000</pubDate>
		<dc:creator>Oleg Sych</dc:creator>
		
		<category><![CDATA[Articles]]></category>

		<category><![CDATA[C#]]></category>

		<category><![CDATA[Code Generation]]></category>

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

		<category><![CDATA[Visual Studio]]></category>

		<guid isPermaLink="false">http://www.olegsych.com/2008/09/t4-tutorial-creating-reusable-code-generation-templates/</guid>
		<description><![CDATA[This article is a part of a series that introduces code generation using C# and Text Templates (also known as T4 Templates) in Visual Studio; explains how to create reusable templates and combine them in complex code generators.]]></description>
			<content:encoded><![CDATA[<p>This article is a part of a series that introduces code generation using C# and <a href="http://www.olegsych.com/2007/12/text-template-transformation-toolkit/">Text Templates</a> (also known as T4 Templates) in Visual Studio; explains how to create reusable templates and combine them in complex code generators. In order to follow examples in this article, you need to have Visual Studio 2008 Standard Edition or higher, SQL Server 2005, <a href="http://www.codeplex.com/t4toolbox">T4 Toolbox</a> and <a href="http://www.t4editor.net/">T4 Editor</a> installed on your computer. </p>
<h4>Introduction</h4>
<p>In the <a href="http://www.olegsych.com/2008/09/t4-tutorial-creatating-your-first-code-generator/">first article</a> of this series, we created the following code generation file to generate a DELETE stored procedure for a given database table using <a href="http://msdn.microsoft.com/en-us/library/ms162169.aspx">SMO</a>. This stored procedure is one of the <a href="http://en.wikipedia.org/wiki/Create,_read,_update_and_delete">CRUD</a> procedures that would need to be created to encapsulate access to a particular database table. Accessing data exclusively through CRUD stored procedures helps to eliminate SQL injection vulnerabilities, prevent accidental data corruption during casual browsing and may help to improve performance of SQL queries.</p>
<pre class="code"><span style="background: gold">&lt;#@</span><span style="color: red"> </span><span style="color: brown">template </span><span style="color: red">language=</span>&quot;<span style="color: blue">C#</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">output </span><span style="color: red">extension=</span>&quot;<span style="color: blue">SQL</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">assembly </span><span style="color: red">name=</span>&quot;<span style="color: blue">Microsoft.SqlServer.ConnectionInfo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">assembly </span><span style="color: red">name=</span>&quot;<span style="color: blue">Microsoft.SqlServer.Smo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">import </span><span style="color: red">namespace=</span>&quot;<span style="color: blue">Microsoft.SqlServer.Management.Smo</span>&quot; <span style="background: gold">#&gt;</span><span style="color: red">
</span><span style="background: gold">&lt;#
</span><span style="background: #f0f8ff; color: #191970">    Server server = new Server();
    Database database = new Database(server, &quot;Northwind&quot;);
    Table table = new Table(database, &quot;Products&quot;);
    table.Refresh();
</span><span style="background: gold">#&gt;
</span><span style="color: gray">create procedure </span><span style="background: gold">&lt;#=</span><span style="background: #f0f8ff; color: #191970"> table.Name </span><span style="background: gold">#&gt;</span><span style="color: gray">_Delete
</span><span style="background: gold">&lt;#
</span><span style="background: #f0f8ff; color: #191970">    PushIndent(&quot;\t&quot;);
    foreach (Column column in table.Columns)
    {
        if (column.InPrimaryKey)
            WriteLine(&quot;@&quot; + column.Name + &quot; &quot; + column.DataType.Name);
    }
    PopIndent();
</span><span style="background: gold">#&gt;
</span><span style="color: gray">as
    delete from </span><span style="background: gold">&lt;#=</span><span style="background: #f0f8ff; color: #191970"> table.Name </span><span style="background: gold">#&gt;
</span><span style="color: red">    </span><span style="color: gray">where
</span><span style="background: gold">&lt;#
</span><span style="background: #f0f8ff; color: #191970">    PushIndent(&quot;\t</span>\<span style="background: #f0f8ff; color: #191970">t&quot;);
    foreach (Column column in table.Columns)
    {
        if (column.InPrimaryKey)
            WriteLine(column.Name + &quot; = @&quot; + column.Name);
    }
    PopIndent();
</span><span style="background: gold">#&gt;</span><span style="color: red">    </span></pre>
<p>Note that this file has code generation parameters (database name and table name) embedded in its source code. In order to reuse this code generator in its current form, we would need to create a copy of this file and modify the embedded parameters to specify another database and table names. While this approach certainly works for simple code generators that need to be used a limited number of times, it creates code duplication and makes maintaining code generators more and more difficult.</p>
<p>We also need to extend this code generator to create additional types of stored procedures to encapsulate INSERT, UPDATE and SELECT SQL statements. We could accomplish that by extending this file to generate all of these stored procedures. Again, this approach works well for a simple code generator, but as the number of procedures this template generates grows, it becomes more and more difficult to manage.</p>
<p>Let&#8217;s see how we can extend this code generator without introducing code duplication and additional complexity.</p>
<h4>Create a new code generation template</h4>
<p>Let&#8217;s define <em>code generation template </em>(or simply <em>template</em>)<em>&#160;</em>as a <em>reusable</em> code generator, which produces a <em>single </em>logical unit of code. In our example, the <em>template </em>will generate a delete stored procedure for a single database table. </p>
<ul>
<li>Create a new C# Class Library project in Visual Studio. </li>
<li>Click Project-&gt;Add New Item in the main menu and select <em>Template</em> item from the <em>Code Generation</em> folder in the dialog. If you don&#8217;t see this folder or this item, make sure you have the latest version of <a href="http://www.olegsych.com/2008/08/t4-toolbox/">T4 Toolbox</a> installed. </li>
</ul>
<p><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="image" src="http://www.olegsych.com/wp-content/uploads/2008/09/image14.png" width="580" height="343" /> </p>
<ul>
<li>Enter <em>DeleteProcedureTemplate.tt</em> as the item name and click the Add button. </li>
<li>Double-click <em>DeleteProcedureTemplate.tt</em> in the Solution Explorer. You will see the following text in the editor. </li>
</ul>
<pre class="code"><span style="background: gold">&lt;#+
</span><span style="background: #f0f8ff; color: #191970">// &lt;copyright file=&quot;DeleteProcedureTemplate.tt&quot; company=&quot;Your Company&quot;&gt;
//  Copyright © Your Company. All Rights Reserved.
// &lt;/copyright&gt;

public class DeleteProcedureTemplate : Template
{
    protected override void RenderCore()
    {

    }
}
</span><span style="background: gold">#&gt;</span></pre>
</p>
<p><a href="http://11011.net/software/vspaste"></a></p>
<p>This file contains a <a href="http://www.olegsych.com/2008/02/t4-class-feature-blocks/">class feature block</a> that defines a <em>template class </em>called <em>DeleteProcedureTemplate</em>. It inherits from a base class called <em>Template</em>, which is defined in <a href="http://www.olegsych.com/2008/08/t4-toolbox/">T4 Toolbox</a>. Although this file has a .tt extension, it is not intended to be used for code generation directly. Instead it will be reused by other code generation files, as we will see shortly. In the mean time, note that Visual Studio displays an error when trying to process this file.</p>
<p><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="image" src="http://www.olegsych.com/wp-content/uploads/2008/09/image15.png" width="580" height="208" /> </p>
<ul>
<li>Select <em>DeleteProcedureTemplate.tt</em> in the solution explorer and change Custom Tool property from TextTemplatingFileGenerator to an empty value. </li>
</ul>
<table border="0" cellspacing="0" cellpadding="2" width="580">
<tbody>
<tr>
<td valign="top" width="290"><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="image" src="http://www.olegsych.com/wp-content/uploads/2008/09/image16.png" width="280" height="271" /> </td>
<td valign="top" width="290"><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="image" src="http://www.olegsych.com/wp-content/uploads/2008/09/image17.png" width="287" height="274" /></td>
</tr>
</tbody>
</table>
<p><em>TextTemplatingFileGenerator </em>is a custom tool that invokes the code generation <em>Engine</em> to run or <em>transform</em> the code generation file. Clearing the <em>Custom Tool </em>property of the code generation file prevents Visual Studio from trying to process the file and displaying the unnecessary error.</p>
<h4>Encapsulate code generation logic in the template class</h4>
<p><em>Template base class </em>defines an abstract method called <em>RenderCore</em>. Each concrete template must override this method and implement code generation logic inside of it.</p>
<ul>
<li>Copy the contents of the original file inside of the <em>RenderCore</em> method in <em>DeleteProcedureTemplate.tt </em>and modify it to look like this: </li>
</ul>
<pre class="code"><span style="background: gold">&lt;#@</span><span style="color: red"> </span><span style="color: brown">assembly </span><span style="color: red">name=</span>&quot;<span style="color: blue">Microsoft.SqlServer.ConnectionInfo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">assembly </span><span style="color: red">name=</span>&quot;<span style="color: blue">Microsoft.SqlServer.Smo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">import </span><span style="color: red">namespace=</span>&quot;<span style="color: blue">Microsoft.SqlServer.Management.Smo</span>&quot; <span style="background: gold">#&gt;
&lt;#+
</span><span style="background: #f0f8ff; color: #191970">public class DeleteProcedureTemplate : Template
{
    public string DatabaseName;
    public string TableName;

    protected override void RenderCore()
    {
        Server server = new Server();
        Database database = new Database(server, DatabaseName);
        Table table = new Table(database, TableName);
        table.Refresh();
</span><span style="background: gold">#&gt;
</span><span style="color: gray">create procedure </span><span style="background: gold">&lt;#=</span><span style="background: #f0f8ff; color: #191970"> table.Name </span><span style="background: gold">#&gt;</span><span style="color: gray">_Delete
</span><span style="background: gold">&lt;#+
</span><span style="background: #f0f8ff; color: #191970">        PushIndent(&quot;\t&quot;);
        foreach (Column column in table.Columns)
        {
            if (column.InPrimaryKey)
                WriteLine(&quot;@&quot; + column.Name + &quot; &quot; + column.DataType.Name);
        }
        PopIndent();
</span><span style="background: gold">#&gt;
</span><span style="color: gray">as
    delete from </span><span style="background: gold">&lt;#=</span><span style="background: #f0f8ff; color: #191970"> table.Name </span><span style="background: gold">#&gt;
</span><span style="color: red">    </span><span style="color: gray">where
</span><span style="background: gold">&lt;#+
</span><span style="background: #f0f8ff; color: #191970">        PushIndent(&quot;\t</span>\<span style="background: #f0f8ff; color: #191970">t&quot;);
        foreach (Column column in table.Columns)
        {
            if (column.InPrimaryKey)
                WriteLine(column.Name + &quot; = @&quot; + column.Name);
        }
        PopIndent();
    }
}
</span><span style="background: gold">#&gt;</span></pre>
<p><a href="http://11011.net/software/vspaste"></a></p>
<p>Note that code generation parameters database name and table name are now encapsulated as public fields in the <em>DeleteProcedureTemplate</em> class. These fields are used inside of the <em>RenderCore</em> method to retrieve table metadata information and generate the stored procedure with the help of <a href="http://www.olegsych.com/2008/02/t4-text-blocks/">text blocks</a>, <a href="http://www.olegsych.com/2008/02/t4-expression-blocks/">expression blocks</a> and <a href="http://www.olegsych.com/2008/02/t4-class-feature-blocks/">class feature blocks</a>.</p>
<h4>Reuse the code generation template</h4>
<p>Having the code generation logic encapsulated in a template class, we can now reuse it in another code generation file without duplicating the code.</p>
<ul>
<li>Click Project-&gt;Add New Item in the main menu and select File item from the Code Generation folder in the dialog. </li>
<li>Name the new file Products_Delete.tt and change its contents to look similar to this. </li>
</ul>
<pre class="code"><span style="background: gold">&lt;#@</span><span style="color: red"> </span><span style="color: brown">template </span><span style="color: red">language=</span>&quot;<span style="color: blue">C#</span>&quot; <span style="color: red">hostspecific=</span>&quot;<span style="color: blue">True</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">output </span><span style="color: red">extension=</span>&quot;<span style="color: blue">sql</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">T4Toolbox.tt</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">DeleteProcedureTemplate.tt</span>&quot; <span style="background: gold">#&gt;
&lt;#
</span><span style="background: #f0f8ff; color: #191970">    DeleteProcedureTemplate template = new DeleteProcedureTemplate();
    template.DatabaseName = &quot;Northwind&quot;;
    template.TableName = &quot;Products&quot;;
    template.Render();
</span><span style="background: gold">#&gt;</span></pre>
<p>This code generation file uses <a href="http://www.olegsych.com/2008/02/t4-include-directive/">include directive</a> to pull in the contents of <em>DeleteProcedureTemplate.tt. </em>It then uses a <a href="http://www.olegsych.com/2008/02/t4-statement-blocks/">statement block</a> to create a new instance of the <em>DeleteProcedureTemplate</em> class; assigns database name and table name values and calls the <em>Render</em> method of the <em>template </em>object. <em>Render </em>method ultimately calls the <em>RenderCore</em> method with additional validation checks and exception handling.</p>
<ul>
<li>Open <em>Products_Delete.sql </em>generated by this file. </li>
</ul>
<pre class="code"><span style="color: blue">create procedure </span>Products_Delete
    @ProductID <span style="color: blue">int
as
    delete from </span>Products
    <span style="color: blue">where
        </span>ProductID = @ProductID</pre>
<p>At this point we have a delete procedure for the Products table generated by the code generation file <em>Products_Delete.tt </em>with the help of the <em>template</em> defined in <em>DeleteProcedureTemplate.tt</em>. We can continue reusing the template by creating similar code generation files to produce delete procedures for other tables - <em>Customers_Delete.tt</em>, <em>Orders_Delete.tt</em>, etc. We can also create additional <em>templates</em> - <em>InsertProcedureTemplate</em>, <em>UpdateProcedureTemplate, etc. </em>to generate remaining types of CRUD stored procedures.</p>
<h4>Conclusion</h4>
<p>We have encapsulated logic for generating a DELETE stored procedure as a reusable <em>template</em>, which we can now reuse to generate multiple stored procedures without duplicating the code generation logic. However, table-specific code generation files like <em>Products_Delete.tt </em>and <em>Customers_Delete.tt </em>still contain a lot of duplication - 9 out of 10 lines required to <em>render </em>the template in each file are the same. Another problem with the current version is having a separate code generation file for each stored procedure. Combined with insert, update and select stored procedures, the total number of code generation files becomes difficult to manage even for a simple database like Northwind. </p>
<p>We will address these problems in the <a href="http://www.olegsych.com/2008/09/t4-tutorial-creating-complex-code-generators/">next article</a>, by creating a composite code <em>generator </em>that produces multiple types of stored procedures for a given database tables or multiple tables in a given database.</p>
<h4>Download</h4>
<p><a href="http://www.olegsych.com/wp-content/uploads/2008/09/t4-tutorial-creating-reusable-code-generation-templates.zip">Source code, completed.</a></p>
]]></content:encoded>
			<wfw:commentRss>http://www.olegsych.com/2008/09/t4-tutorial-creating-reusable-code-generation-templates/feed/</wfw:commentRss>
		</item>
		<item>
		<title>T4 Tutorial: Debugging Code Generation Files</title>
		<link>http://www.olegsych.com/2008/09/t4-tutorial-debugging-code-generation-files/</link>
		<comments>http://www.olegsych.com/2008/09/t4-tutorial-debugging-code-generation-files/#comments</comments>
		<pubDate>Sat, 13 Sep 2008 10:59:35 +0000</pubDate>
		<dc:creator>Oleg Sych</dc:creator>
		
		<category><![CDATA[Articles]]></category>

		<category><![CDATA[C#]]></category>

		<category><![CDATA[Code Generation]]></category>

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

		<category><![CDATA[Visual Studio]]></category>

		<guid isPermaLink="false">http://www.olegsych.com/2008/09/t4-tutorial-debugging-code-generation-files/</guid>
		<description><![CDATA[This article is a part of a series that introduces code generation using C# and Text Templates (also known as T4 Templates) in Visual Studio; explains how to create reusable templates and combine them in complex code generators.]]></description>
			<content:encoded><![CDATA[<p>This article is a part of a series that introduces code generation using C# and <a href="http://www.olegsych.com/2007/12/text-template-transformation-toolkit/">Text Templates</a> (also known as T4 Templates) in Visual Studio; explains how to create reusable templates and combine them in complex code generators. In order to follow examples in this article, you need to have Visual Studio 2008 Standard Edition or higher, SQL Server 2005, <a href="http://www.codeplex.com/t4toolbox">T4 Toolbox</a> and <a href="http://www.t4editor.net/">T4 Editor</a> installed on your computer.</p>
<h4>Overview</h4>
<p>As you remember from the <a href="http://www.olegsych.com/2008/09/t4-tutorial-troubleshooting-code-generation-errors/">previous article</a> in this series, <em>Runtime Errors </em>are caused by exceptions thrown by code in the <em>GeneratedTextTransformation </em>class, which is compiled and executed by the code generation <a href="http://msdn.microsoft.com/it-it/library/microsoft.visualstudio.texttemplating.engine.aspx">Engine</a>.</p>
<p><img alt="Compilation and Runtime Errors" src="http://www.olegsych.com/wp-content/uploads/2008/09/image7.png" /></p>
<p>Although the <em>Engine </em>reports detailed stack dump for every exception thrown, troubleshooting non-trivial runtime errors may require using a debugger to step through the template code as it executes. Because template code is running inside of Visual Studio process itself, a second instance of Visual Studio is required to serve as a debugger for the first instance, which is running the template code.</p>
<p>Current support for debugging of code generation templates in Visual Studio is somewhat limited. It requires you to either use a manual breakpoint in the template code to trigger the just-in-time debugger or starting a debugging instance of Visual Studio in advance and attaching it to the instance that&#8217;s running the template.</p>
<h4>Setup</h4>
<p>Use Visual Studio to open CrudStoredProcedures.tt created in the <a href="http://www.olegsych.com/2008/09/t4-tutorial-creatating-your-first-code-generator/">first article</a> of this series. As you remember, it&#8217;s a code generation file that produces a DELETE stored procedure using table schema information retrieved from SQL server using <a href="http://msdn.microsoft.com/en-us/library/ms162169.aspx">SMO</a>.</p>
<pre class="code"><span style="background: gold">&lt;#@</span><span style="color: red"> </span><span style="color: brown">template </span><span style="color: red">language=</span>&quot;<span style="color: blue">C#</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">output </span><span style="color: red">extension=</span>&quot;<span style="color: blue">sql</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">assembly </span><span style="color: red">name=</span>&quot;<span style="color: blue">Microsoft.SqlServer.ConnectionInfo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">assembly </span><span style="color: red">name=</span>&quot;<span style="color: blue">Microsoft.SqlServer.Smo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">import </span><span style="color: red">namespace=</span>&quot;<span style="color: blue">Microsoft.SqlServer.Management.Smo</span>&quot; <span style="background: gold">#&gt;</span><span style="color: gray">
</span><span style="background: gold">&lt;#
</span><span style="color: gray">    </span>Server server = <span style="color: blue">new </span>Server<span style="color: gray">();
    </span>Database database = <span style="color: blue">new </span>Database<span style="color: gray">(</span>server<span style="color: gray">, </span><span style="color: #a31515">&quot;Northwind&quot;</span><span style="color: gray">);
    </span>Table table = <span style="color: blue">new </span>Table<span style="color: gray">(</span>database<span style="color: gray">, </span><span style="color: #a31515">&quot;Products&quot;</span><span style="color: gray">);
    </span>table.Refresh<span style="color: gray">();
</span><span style="background: gold">#&gt;
</span><span style="color: gray">create procedure </span><span style="background: gold">&lt;#=</span><span style="color: gray"> </span>table.Name <span style="background: gold">#&gt;</span><span style="color: gray">_Delete
</span><span style="background: gold">&lt;#
</span><span style="color: gray">    </span>PushIndent<span style="color: gray">(</span><span style="color: #a31515">&quot;\t&quot;</span><span style="color: gray">);
    </span><span style="color: blue">foreach </span><span style="color: gray">(</span>Column column <span style="color: blue">in </span>table.Columns<span style="color: gray">)
    {
        </span><span style="color: blue">if </span><span style="color: gray">(</span>column.InPrimaryKey<span style="color: gray">)
            </span>WriteLine<span style="color: gray">(</span><span style="color: #a31515">&quot;@&quot; </span>+ column.Name + <span style="color: #a31515">&quot; &quot; </span>+ column.DataType.Name<span style="color: gray">);
    }
    </span>PopIndent<span style="color: gray">();
</span><span style="background: gold">#&gt;
</span><span style="color: gray">as
    delete from </span><span style="background: gold">&lt;#=</span><span style="color: gray"> </span>table.Name <span style="background: gold">#&gt;
</span><span style="color: gray">    where
</span><span style="background: gold">&lt;#
</span><span style="color: gray">    </span>PushIndent<span style="color: gray">(</span><span style="color: #a31515">&quot;\t\t&quot;</span><span style="color: gray">);
    </span><span style="color: blue">foreach </span><span style="color: gray">(</span>Column column <span style="color: blue">in </span>table.Columns<span style="color: gray">)
    {
        </span><span style="color: blue">if </span><span style="color: gray">(</span>column.InPrimaryKey<span style="color: gray">)
            </span>WriteLine<span style="color: gray">(</span>column.Name + <span style="color: #a31515">&quot; = @&quot; </span>+ column.Name<span style="color: gray">);
    }
    </span>PopIndent<span style="color: gray">();
</span><span style="background: gold">#&gt;</span><span style="color: gray">    </span></pre>
<ul>
<li>Simulate a runtime error by assigning null to the <em>server</em> variable. This should trigger a run-time exception in the call to Database constructor. </li>
</ul>
<p><img alt="Simulate Runtime Error" src="http://www.olegsych.com/wp-content/uploads/2008/09/image4.png" /></p>
<ul>
<li>Set <em>debug</em> parameter of the <a href="http://www.olegsych.com/2008/02/t4-template-directive/">template directive</a> to “True”. </li>
</ul>
<p><img src="http://www.olegsych.com/wp-content/uploads/2008/09/image5.png" /></p>
<ul>
<li>Save the template file or select Run Custom Tool item from context menu in Solution Explorer to trigger template transformation. </li>
</ul>
<p><img src="http://www.olegsych.com/wp-content/uploads/2008/09/image26-thumb.png" /></p>
<h4>Just-In-Time Debugging</h4>
<p>The quickest way to start debugging is by placing a breakpoint in the code of the template and triggering the just-in-time debugger. Note, if you are using Windows Vista, this technique can hang Visual Studio. Please read the <em>Just In Time Debugging on Windows Vista</em> section below first.</p>
<ul>
<li>Modify the template to call <a href="http://msdn.microsoft.com/en-us/library/system.diagnostics.debugger.break.aspx">Debugger.Break</a> method in the beginning of the code block. </li>
</ul>
<p><a href="http://www.olegsych.com/wp-content/uploads/2008/09/image-thumb3.png"><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="image_thumb3" src="http://www.olegsych.com/wp-content/uploads/2008/09/image-thumb3-thumb.png" width="443" height="132" /></a></p>
<ul>
<li>Save the template file or select Run Custom Tool item from context menu in Solution Explorer to trigger template transformation. </li>
</ul>
<p><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="image" src="http://www.olegsych.com/wp-content/uploads/2008/09/image10.png" width="408" height="441" /></p>
<p><a href="http://msdn.microsoft.com/en-us/library/system.diagnostics.debugger.break.aspx">Debugger.Break</a> method attempts to launch the Just-In-Time Debugger configured on your system.You should see a Visual Studio Just-In-Time Debugger dialog (shown above).</p>
<ul>
<li>In Visual Studio Just-In-Time Debugger dialog, select New instance of Visual Studio 2008 in the list and click Yes. </li>
</ul>
<p><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="Breakpoint Hit" src="http://www.olegsych.com/wp-content/uploads/2008/09/image-thumb20.png" width="458" height="130" /></p>
<p>This will launch a new instance of Visual Studio and attach it as a debugger to the first instance which is running your template. You should see the source code of your template automatically loaded in debugger and a green line pointing where the execution point currently is.</p>
<p>While in debugger, you can use all standard features, like stepping through code, and windows, like Watch, Call Stack, Immediate, etc.</p>
<ul>
<li>Select Exceptions item from Debug menu in Visual Studio; turn on the option to break when exception is thrown and click OK. </li>
</ul>
<p><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="Exceptions Dialog" src="http://www.olegsych.com/wp-content/uploads/2008/09/image-thumb23.png" width="580" height="292" /></p>
<ul>
<li>Select Continue item from Debug menu in Visual Studio. </li>
</ul>
<p><a href="http://www.olegsych.com/wp-content/uploads/2008/09/image-thumb26.png"><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="image_thumb26" src="http://www.olegsych.com/wp-content/uploads/2008/09/image-thumb26-thumb.png" width="475" height="258" /></a></p>
<p>The template will continue to run until it encounters the exception. At that point, the Visual Studio debugger will pause it and display the dialog shown above. You can inspect the exception object by clicking View Detail link.</p>
<ul>
<li>Select Continue item from Debug menu. </li>
<li>Close the debugging instance of Visual Studio. </li>
<li>Back in the original instance of Visual Studio, remove the call to <a target="_blank" href="http://msdn.microsoft.com/en-us/library/system.diagnostics.debugger.break.aspx">Debugger.Break</a> method from the template code. </li>
</ul>
<h4>Just-In-Time Debugging on Windows Vista</h4>
<p>By default on Windows Vista, the just-in-time debugger is configured to display a user-friendly dialog shown below. Although you can click the <em>Debug the program</em> button and start the debugger successfully, your original Visual Studio instance will hang in the end of the debugging session.</p>
<p><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="User-defined breakpoint dialog on Windows Vista" src="http://www.olegsych.com/wp-content/uploads/2008/09/image-thumb171.png" width="345" height="195" /></p>
<p>In order to avoid having to constantly kill the Visual Studio process after debugging, you will want to change Just-In-Time debugger configuration to work the same way it does on Windows XP and Windows Server 2003. This configuration is stored in registry as <em>DbgJITDebugLaunchSetting</em> value in HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\.NETFramework key. It&#8217;s default value on Windows Vista is 0&#215;10. Change it to 0&#215;2, which is the default value on Windows XP. After making this change, you should no longer see the User-Defined Breakpoint dialog and will be able to continue using Visual Studio after debugging.</p>
<h4>Attaching Debugger Manually</h4>
<p>Just-in-time debugging, described above, is the fastest and most precise way to set a breakpoint in template code and hit it in the debugger. However, it may not be appropriate if the code generation file you want to debug is read-only (such as when it is stored in source control repository or received from a third-party). In this situation, you can attach the debugger manually, which takes longer but doesn&#8217;t require you to modify the template code.</p>
<ul>
<li>Start a second instance of Visual Studio and open the code generation file you need to debug - <em>CrudStoredProcedures.tt</em> in this example. </li>
<li>Select Attach to Process from the Debug menu in Visual Studio. </li>
</ul>
<p><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="Attach to Process dialog" src="http://www.olegsych.com/wp-content/uploads/2008/09/image11.png" width="580" height="396" /></p>
<ul>
<li>In the list of Available Processes, select devenv.exe and click the Attach button. This will attach the current instance of Visual Studio as a debugger for the first instance of Visual Studio running the template. Let&#8217;s call the first instance as simply <em>Visual Studio</em> and the second instance as <em>Debugger</em>. </li>
<li>Back in text editor of the <em>Debugger</em>, where you have the CrudStoredProcedures.tt file open, click on the left side of line 8 to sent a breakpoint. </li>
</ul>
<p><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="Set a Breakpoint" src="http://www.olegsych.com/wp-content/uploads/2008/09/image12.png" width="518" height="195" /></p>
<p>Normally, the red breakpoint icon would appear next to the line you clicked. However, due to limitations in the current support for template debugging, Visual Studio displays the breakpoint icon in line 2 instead.</p>
<ul>
<li>In the original <em>Visual Studio </em>instance, trigger template transformation by either saving the template or selecting Run Custom Tool from the context menu in Solution Explorer. This will trigger the breakpoint and you will see something like this in the <em>Debugger</em>. </li>
</ul>
<p><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="Stepping through template code in debugger" src="http://www.olegsych.com/wp-content/uploads/2008/09/image13.png" width="514" height="196" /></p>
<p>You can use all debugging features as you would expect in regular .NET code with the exception of breakpoints. I have not found a way to place breakpoints in the template code precisely using the debugger and have to resort to manual breakpoints using <a target="_blank" href="http://msdn.microsoft.com/en-us/library/system.diagnostics.debugger.break.aspx">Debugger.Break</a> as described above.</p>
<ul>
<li>Select Continue item from Debug menu. </li>
<li>Close the debugging instance of Visual Studio. </li>
<li>Back in the original instance of Visual Studio, restore the original initialization code for <em>server </em>variable shown in the source code at the beginning of this article. </li>
</ul>
<h4>Conclusion</h4>
<p>Debugging is the most powerful technique in troubleshooting runtime errors that occur during code generation. Although current support for debugging of template code in Visual Studio is somewhat limited, you can debug templates effectively by either triggering Just-In-Time debugger with <a target="_blank" href="http://msdn.microsoft.com/en-us/library/system.diagnostics.debugger.break.aspx">Debugger.Break</a> from template code or by attaching a separate instance of Visual Studio as a debugger in advance.</p>
<p>In the <a href="http://www.olegsych.com/2008/09/t4-tutorial-creating-reusable-code-generation-templates/">next article</a> of this series, we will talk about creating reusable code generation templates.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.olegsych.com/2008/09/t4-tutorial-debugging-code-generation-files/feed/</wfw:commentRss>
		</item>
		<item>
		<title>September meeting of Tampa Bay IASA chapter</title>
		<link>http://www.olegsych.com/2008/09/september-2008-meeting-of-tampa-bay-iasa-chapter/</link>
		<comments>http://www.olegsych.com/2008/09/september-2008-meeting-of-tampa-bay-iasa-chapter/#comments</comments>
		<pubDate>Thu, 11 Sep 2008 16:45:20 +0000</pubDate>
		<dc:creator>Oleg Sych</dc:creator>
		
		<category><![CDATA[Events]]></category>

		<guid isPermaLink="false">http://www.olegsych.com/2008/09/september-2008-meeting-of-tampa-bay-iasa-chapter/</guid>
		<description><![CDATA[SharePoint Architectural Perspectives
While SharePoint does have the one-button install option, it isn&#8217;t a monolithic application that just gets dropped on a server. SharePoint has a number of moving pieces that should be understood by both infrastructure and application architects. In this session, we&#8217;ll review the architectural makeup of SharePoint&#8217;s infrastructure, as well as the components [...]]]></description>
			<content:encoded><![CDATA[<h4>SharePoint Architectural Perspectives</h4>
<p>While SharePoint does have the one-button install option, it isn&#8217;t a monolithic application that just gets dropped on a server. SharePoint has a number of moving pieces that should be understood by both infrastructure and application architects. In this session, we&#8217;ll review the architectural makeup of SharePoint&#8217;s infrastructure, as well as the components of a custom SharePoint solution. A thoughtfully-designed SharePoint architecture can be the difference between smashing success and humiliating failure.<br />
<h5>Speaker</h5>
<p>David McNamee, SharePoint Technical Specialist, Microsoft Corp.<br />
<h5>When</h5>
<p>Thursday, September 25, 2008 <br />6:30 PM - 8:30 PM <br />Pizza: 6:00 PM - 6:30 PM<br />
<h5>Location</h5>
<p>Kforce, 1001 East Palm Avenue, Tampa, FL 33605 <br /><a href="http://maps.live.com/default.aspx?v=2&amp;FORM=LMLTCP&amp;cp=27.9623~-82.449779&amp;style=h&amp;lvl=16&amp;tilt=-90&amp;dir=0&amp;alt=-1000&amp;scene=9552102&amp;phx=0&amp;phy=0&amp;phscl=1&amp;ss=yp.KForce~pg.1~sst.0&amp;encType=1">Map</a>, <a href="http://maps.live.com/OneClickDirections.aspx?rtp=%7epos.nntbbg83w7zx_1001+E+Palm+Ave%2c+Tampa%2c+FL_Kforce+Professional+Staffing_(813)+552-5000_a_&amp;mkt=en-us&amp;FORM=LLMP">Directions</a><br />
<h5>Registration</h5>
<p>Click <a href="http://www.eventbrite.com/event/120521483">here</a> to register.<br />
<h5>About IASA</h5>
<p>Established in 2002, IASA (<a href="http://www.iasahome.org/">International Association of Software Architects</a>) is an international non-profit business association dedicated to the advancement and sharing of issues related to software architecture in the enterprise, product, education and government sectors. The association is committed to improving the quality of the IT architecture industry by developing and delivering standards, education programs and developing accreditation programs and services that optimize the development of architecture profession. </p>
]]></content:encoded>
			<wfw:commentRss>http://www.olegsych.com/2008/09/september-2008-meeting-of-tampa-bay-iasa-chapter/feed/</wfw:commentRss>
		</item>
		<item>
		<title>T4 Tutorial: Troubleshooting Code Generation Errors</title>
		<link>http://www.olegsych.com/2008/09/t4-tutorial-troubleshooting-code-generation-errors/</link>
		<comments>http://www.olegsych.com/2008/09/t4-tutorial-troubleshooting-code-generation-errors/#comments</comments>
		<pubDate>Sat, 06 Sep 2008 15:35:34 +0000</pubDate>
		<dc:creator>Oleg Sych</dc:creator>
		
		<category><![CDATA[Articles]]></category>

		<category><![CDATA[C#]]></category>

		<category><![CDATA[Code Generation]]></category>

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

		<category><![CDATA[Visual Studio]]></category>

		<guid isPermaLink="false">http://www.olegsych.com/2008/09/t4-tutorial-troubleshooting-code-generation-errors/</guid>
		<description><![CDATA[This article is a part of a series that introduces code generation using C# and Text Templates (also known as T4 Templates) in Visual Studio; explains how to create reusable templates and combine them in complex code generators.]]></description>
			<content:encoded><![CDATA[<p>This article is a part of a series that introduces code generation using C# and <a href="http://www.olegsych.com/2007/12/text-template-transformation-toolkit/">Text Templates</a> (also known as T4 Templates) in Visual Studio; explains how to create reusable templates and combine them in complex code generators. In order to follow examples in this article, you need to have Visual Studio 2008 Standard Edition or higher, SQL Server 2005, <a href="http://www.codeplex.com/t4toolbox">T4 Toolbox</a> and <a href="http://www.t4editor.net/">T4 Editor</a> installed on your computer.</p>
<h4>Overview</h4>
<p>There are two distinct stages in the process of generating output from a template or <em>template transformation</em>. </p>
<p><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="Compilation and Runtime Errors" src="http://www.olegsych.com/wp-content/uploads/2008/09/image7.png" width="580" height="319" /></p>
<p>During the first stage, the code generation <a href="http://msdn.microsoft.com/it-it/library/microsoft.visualstudio.texttemplating.engine.aspx">Engine</a> parses the template, uses <a href="http://www.olegsych.com/2008/02/t4-text-blocks/">text blocks</a>, <a href="http://www.olegsych.com/2008/02/t4-statement-blocks/">code blocks</a> and <a href="http://www.olegsych.com/2008/02/t4-template-directive/">directives</a> to create a special class called <em>GeneratedTextTransformation</em> and compiles it in a temporary .NET assembly. <em>Compilation Errors </em>that occur during this stage include errors detected by the code generation <em>engine</em> in the template syntax and errors detected by the <em>compiler</em> when compiling <em>GeneratedTextTransformation</em>.</p>
<p>During the second stage, the <em>Engine</em> creates an instance of the <em>GeneratedTextTransformation</em> class, calls its <a href="http://msdn2.microsoft.com/en-us/library/microsoft.visualstudio.texttemplating.texttransformation.transformtext.aspx">TransformText</a> method and saves the string it returns to the output file. <em>Runtime errors</em> that occur during this stage are exceptions thrown by code in <em>GeneratedTextTransformation</em> when it is running.</p>
<h4>Setup</h4>
<p>Use Visual Studio to open CrudStoredProcedures.tt created in the <a href="http://www.olegsych.com/2008/09/t4-tutorial-creatating-your-first-code-generator/">previous article</a> of this series. As you remember, it&#8217;s a code generation file that produces a DELETE stored procedure using table schema information retrieved from SQL server using <a href="http://msdn.microsoft.com/en-us/library/ms162169.aspx">SMO</a>.</p>
<pre class="code"><span style="background: gold">&lt;#@</span><span style="color: red"> </span><span style="color: brown">template </span><span style="color: red">language=</span>&quot;<span style="color: blue">C#</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">output </span><span style="color: red">extension=</span>&quot;<span style="color: blue">sql</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">assembly </span><span style="color: red">name=</span>&quot;<span style="color: blue">Microsoft.SqlServer.ConnectionInfo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">assembly </span><span style="color: red">name=</span>&quot;<span style="color: blue">Microsoft.SqlServer.Smo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">import </span><span style="color: red">namespace=</span>&quot;<span style="color: blue">Microsoft.SqlServer.Management.Smo</span>&quot; <span style="background: gold">#&gt;</span><span style="color: gray">
</span><span style="background: gold">&lt;#
</span><span style="color: gray">    </span>Server server = <span style="color: blue">new </span>Server<span style="color: gray">();
    </span>Database database = <span style="color: blue">new </span>Database<span style="color: gray">(</span>server<span style="color: gray">, </span><span style="color: #a31515">&quot;Northwind&quot;</span><span style="color: gray">);
    </span>Table table = <span style="color: blue">new </span>Table<span style="color: gray">(</span>database<span style="color: gray">, </span><span style="color: #a31515">&quot;Products&quot;</span><span style="color: gray">);
    </span>table.Refresh<span style="color: gray">();
</span><span style="background: gold">#&gt;
</span><span style="color: gray">create procedure </span><span style="background: gold">&lt;#=</span><span style="color: gray"> </span>table.Name <span style="background: gold">#&gt;</span><span style="color: gray">_Delete
</span><span style="background: gold">&lt;#
</span><span style="color: gray">    </span>PushIndent<span style="color: gray">(</span><span style="color: #a31515">&quot;\t&quot;</span><span style="color: gray">);
    </span><span style="color: blue">foreach </span><span style="color: gray">(</span>Column column <span style="color: blue">in </span>table.Columns<span style="color: gray">)
    {
        </span><span style="color: blue">if </span><span style="color: gray">(</span>column.InPrimaryKey<span style="color: gray">)
            </span>WriteLine<span style="color: gray">(</span><span style="color: #a31515">&quot;@&quot; </span>+ column.Name + <span style="color: #a31515">&quot; &quot; </span>+ column.DataType.Name<span style="color: gray">);
    }
    </span>PopIndent<span style="color: gray">();
</span><span style="background: gold">#&gt;
</span><span style="color: gray">as
    delete from </span><span style="background: gold">&lt;#=</span><span style="color: gray"> </span>table.Name <span style="background: gold">#&gt;
</span><span style="color: gray">    where
</span><span style="background: gold">&lt;#
</span><span style="color: gray">    </span>PushIndent<span style="color: gray">(</span><span style="color: #a31515">&quot;\t\t&quot;</span><span style="color: gray">);
    </span><span style="color: blue">foreach </span><span style="color: gray">(</span>Column column <span style="color: blue">in </span>table.Columns<span style="color: gray">)
    {
        </span><span style="color: blue">if </span><span style="color: gray">(</span>column.InPrimaryKey<span style="color: gray">)
            </span>WriteLine<span style="color: gray">(</span>column.Name + <span style="color: #a31515">&quot; = @&quot; </span>+ column.Name<span style="color: gray">);
    }
    </span>PopIndent<span style="color: gray">();
</span><span style="background: gold">#&gt;</span><span style="color: gray">    </span></pre>
<h4>Troubleshooting Compilation Errors</h4>
<ul>
<li>Simulate a parsing error by misspelling one of the <a href="http://www.olegsych.com/2008/02/t4-assembly-directive/">assembly directives</a> as <em>assembl</em>.&#160; </li>
</ul>
<p><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="Compilation Error, Source Code" src="http://www.olegsych.com/wp-content/uploads/2008/09/image2.png" width="514" height="131" /> </p>
<ul>
<li>Save the template file or select Run Custom Tool item from context menu in Solution Explorer to trigger template transformation.</li>
</ul>
<p><a target="_blank" href="http://www.olegsych.com/wp-content/uploads/2008/09/image3.png"><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="Compilation Error, Error List" src="http://www.olegsych.com/wp-content/uploads/2008/09/image-thumb.png" width="580" height="179" /></a> </p>
<p>Code generation <a href="http://msdn.microsoft.com/it-it/library/microsoft.visualstudio.texttemplating.engine.aspx">Engine</a> reports errors in the Error List of Visual Studio. Compilation errors, like this one, include information about file and line where it occurred. You can double-click the error in the Error List to quickly jump to the location where it occurred in the template source code.</p>
<ul>
<li>Correct spelling of the <a href="http://www.olegsych.com/2008/02/t4-assembly-directive/">assembly directive</a>, save the template file and verify compilation error is removed from the list.</li>
</ul>
<h4>Troubleshooting Runtime Errors</h4>
<ul>
<li>Simulate a runtime error by assigning null to the <em>server</em> variable. This should trigger a run-time exception in the call to Database constructor.</li>
</ul>
<p><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="Runtime Error, Source Code" src="http://www.olegsych.com/wp-content/uploads/2008/09/image4.png" width="495" height="148" /> </p>
<ul>
<li>Save the template file or select Run Custom Tool item from context menu in Solution Explorer to trigger template transformation.</li>
</ul>
<p><a target="_blank" href="http://www.olegsych.com/wp-content/uploads/2008/09/image51.png"><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="Runtime Error, Error List" src="http://www.olegsych.com/wp-content/uploads/2008/09/image51-thumb.png" width="580" height="143" /></a> </p>
<p>Runtime errors are reported as exception stack dumps. Note that Line number for this error doesn&#8217;t point to the actual location of this error. Although the File column shows correct file name in this case, it will not be correct for runtime errors that occur in a template file referenced using <a href="http://www.olegsych.com/2008/02/t4-include-directive/">include directive</a>.</p>
<p>In order to troubleshoot runtime errors, we need to compile the template file with debugging information.</p>
<ul>
<li>Set <em>debug</em> parameter of the <a href="http://www.olegsych.com/2008/02/t4-template-directive/">template directive</a> to &quot;True&quot;.</li>
</ul>
<p><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="Debug parameter of the template directive" src="http://www.olegsych.com/wp-content/uploads/2008/09/image5.png" width="503" height="148" /> </p>
<ul>
<li>Save the template file or select Run Custom Tool item from context menu in Solution Explorer to trigger template transformation.</li>
</ul>
<p><a target="_blank" href="http://www.olegsych.com/wp-content/uploads/2008/09/image26.png"><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="Runtime Error with debugging information" src="http://www.olegsych.com/wp-content/uploads/2008/09/image26-thumb.png" width="580" height="155" /></a> </p>
<p>Note that exception stack dump now includes file name and line number (<em>CrudStoredProcedures.tt:line 8</em>)pointing to the exact location where the error occurred. This will help you to find and fix simpler runtime errors. In more difficult cases, when the cause of the error is not as obvious, you may need to debug the template while it is running, which is the topic of my next post.</p>
<h4>Troubleshooting Obscure Compilation Errors</h4>
<p>Compiling the template file with debug information can also help in troubleshooting of obscure template compilation errors. </p>
<ul>
<li>Simulate a compilation error by adding an empty <a href="http://www.olegsych.com/2008/02/t4-class-feature-blocks/">class feature block</a> followed by a couple of trailing spaces on the last line of the template file. </li>
</ul>
<p><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="Obscure Compilation Error, Source Code" src="http://www.olegsych.com/wp-content/uploads/2008/09/image6.png" width="211" height="107" /> </p>
<ul>
<li>Save the template file or select Run Custom Tool item from context menu in Solution Explorer to trigger template transformation.</li>
</ul>
<h5><a target="_blank" href="http://www.olegsych.com/wp-content/uploads/2008/09/image8.png"><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="Obscure Compilation Error, Error List" src="http://www.olegsych.com/wp-content/uploads/2008/09/image-thumb1.png" width="580" height="179" /></a></h5>
<p>As you can see, the three compilation errors simply don&#8217;t make sense if you are looking at the template code. Fortunately, when compiling a template with debug information, code generation <em>Engine</em> saves the source code of <em>GeneratedTextTransformation</em> to a temporary file. Looking at this source code can help us understand the cause of an obscure compilation error like this.</p>
<ul>
<li>Open the most recently modified .cs file from %TEMP% directory on your computer. You can find the exact location of this directory by executing &quot;set %TEMP%&quot; in command prompt window.</li>
</ul>
<p><a target="_blank" href="http://www.olegsych.com/wp-content/uploads/2008/09/image9.png"><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="GeneratedTextTransformation source code" src="http://www.olegsych.com/wp-content/uploads/2008/09/image-thumb2.png" width="580" height="298" /></a></p>
<p>As you can see, the couple of trailing white spaces we placed on the last line, was incorrectly interpreted as a <a href="http://www.olegsych.com/2008/02/t4-text-blocks/">text block</a> and converted to a <a href="http://msdn.microsoft.com/en-us/library/microsoft.visualstudio.texttemplating.texttransformation.write.aspx">Write</a> method call at the class level in <em>GeneratedTextTransformation</em>. This is a bug in the code generation <em>Engine</em>, but knowing what triggers it allows us to easily work around it.</p>
<ul>
<li>Correct the problem by removing the offending trailing spaces from the template source code and saving the file.</li>
</ul>
<h4>Conclusion</h4>
<p>Visual Studio makes it relatively easy to troubleshoot compilation errors that occur during code generation. Although in most cases, the error information it displays brings you directly to the source of problem, on rare occasions, you may need to look at the generated transformation code to determine what caused it. You can also use exception stack trace information Visual Studio displays to troubleshoot simple runtime errors. However, in more difficult cases, you will need to debug the code generation files, which we will talk about in the <a href="http://www.olegsych.com/2008/09/t4-tutorial-debugging-code-generation-files/">next article</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.olegsych.com/2008/09/t4-tutorial-troubleshooting-code-generation-errors/feed/</wfw:commentRss>
		</item>
		<item>
		<title>T4 Tutorial: Creating your first code generator</title>
		<link>http://www.olegsych.com/2008/09/t4-tutorial-creatating-your-first-code-generator/</link>
		<comments>http://www.olegsych.com/2008/09/t4-tutorial-creatating-your-first-code-generator/#comments</comments>
		<pubDate>Tue, 02 Sep 2008 10:57:54 +0000</pubDate>
		<dc:creator>Oleg Sych</dc:creator>
		
		<category><![CDATA[Articles]]></category>

		<category><![CDATA[C#]]></category>

		<category><![CDATA[Code Generation]]></category>

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

		<guid isPermaLink="false">http://www.olegsych.com/2008/09/code-generation-with-csharp-and-visual-studio-text-templates-part-1/</guid>
		<description><![CDATA[This is the first article in a series that introduces code generation using C# and Text Templates (also known as T4 Templates) in Visual Studio; explains how to create reusable templates and combine them in complex code generators.]]></description>
			<content:encoded><![CDATA[<p>This is the first post in a series that introduces code generation using C# and <a href="http://msdn.microsoft.com/en-us/library/bb126445.aspx">Text Templates</a> (a.k.a. T4 Templates) in Visual Studio; explains how to create reusable templates and combine them in complex code generators. In order to follow examples in this article, you need to have Visual Studio 2008 Standard Edition or higher, SQL Server 2005, <a href="http://www.codeplex.com/t4toolbox">T4 Toolbox</a> and <a href="http://www.t4editor.net/">T4 Editor</a> installed on your computer. </p>
<p>In this series of articles, we will create a code generator produces <a href="http://en.wikipedia.org/wiki/Create,_read,_update_and_delete">CRUD</a> stored procedures for tables in a SQL Server database. In the examples, we will be using the <a href="http://www.microsoft.com/downloads/details.aspx?FamilyID=06616212-0356-46A0-8DA2-EEBC53A68034&amp;displaylang=en">Northwind</a> sample database.</p>
<h4>Creating a Code Generation File</h4>
<ul>
<li>Create a new C# Class Library project in Visual Studio. </li>
<li>Click Project-&gt;Add New Item in the main menu and select Code Generation-&gt;File template in the dialog. </li>
</ul>
<p> <img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="Add New Item Dialog" src="http://www.olegsych.com/wp-content/uploads/2008/09/image.png" width="580" height="343" />
<ul>
<li>Enter CrudStoredProcedures.tt as the item name and click the Add button. </li>
<li>Double-click the new file in the Solution Explorer. You will see the following text in the text editor. </li>
</ul>
<pre class="code"><span style="background: gold">&lt;#@</span><span style="color: red"> </span><span style="color: brown">template </span><span style="color: red">language=</span>&quot;<span style="color: blue">C#</span>&quot; <span style="color: red">hostspecific=</span>&quot;<span style="color: blue">True</span>&quot; <span style="color: red">debug=</span>&quot;<span style="color: blue">True</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">output </span><span style="color: red">extension=</span>&quot;<span style="color: blue">txt</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">include </span><span style="color: red">file=</span>&quot;<span style="color: blue">T4Toolbox.tt</span>&quot; <span style="background: gold">#&gt;
&lt;#
</span><span style="background: #f0f8ff; color: #191970">// &lt;copyright file=&quot;CrudStoredProcedures.tt&quot; company=&quot;Your Company&quot;&gt;
//  Copyright © Your Company. All Rights Reserved.
// &lt;/copyright&gt;

</span><span style="background: gold">#&gt;</span></pre>
<p>This file is a <em>Text Template</em>, also known as a <em><a href="http://www.olegsych.com/2007/12/text-template-transformation-toolkit/">T4</a> Template</em>. Text Templates are code generators that can be used to generate any text files, including C#, Visual Basic, SQL and XML. Text Templates use ASP.NET-like syntax and consist of <a href="http://www.olegsych.com/2008/02/t4-text-blocks/">text blocks</a>, <a href="http://www.olegsych.com/2008/02/t4-statement-blocks/">code blocks</a> and directives. <em>Text blocks </em>are blocks of text in the template that are copied to the output file as is. <em>Directives </em>provide instructions to the text templating <a href="http://www.olegsych.com/2008/05/t4-architecture/">Engine</a> on how to process the template. In the example above, <a href="http://www.olegsych.com/2008/02/t4-template-directive/">template directive</a> tells the <em>Engine </em>that this template uses C# in code blocks. <em>Code blocks</em> contain C# or Visual Basic code that runs during template transformation and allow making generated output dynamic. </p>
<h4>Generating Static Output</h4>
<p>We will start implementing our code generator by hard-coding DELETE stored procedure for the Products table of Northwind database.</p>
<ul>
<li>Change CrudStoredProcedures.tt to look like so.</li>
</ul>
<pre class="code"><span style="background: gold">&lt;#@</span><span style="color: red"> </span><span style="color: brown">output </span><span style="color: red">extension=</span>&quot;<span style="color: blue">SQL</span>&quot; <span style="background: gold">#&gt;
</span><span style="color: gray">create procedure Products_Delete
    @ProductID int
as
    delete from Products
    where ProductID = @ProductID</span></pre>
<p><img style="border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" border="0" alt="Solution Explorer" align="right" src="http://www.olegsych.com/wp-content/uploads/2008/09/image1.png" width="240" height="182" /> When you save CrudStoredProcedures.tt, the text templating <em>Engine</em> transforms it to generate the output file. In the Solution Explorer, the output file appears nested under the the file. You can also transform the file by right-clicking it in the Solution Explorer and selecting &quot;Run Custom Tool&quot; from the context menu. If you have multiple text templates in your project, you can transform them all by clicking &quot;Transform All Templates&quot; button in the toolbar.</p>
<p>In the template above, the text block is shown in gray. If you double-click the generated file, its contents will be identical to the contents of the text block and will look like so.</p>
<pre class="code"><span style="color: blue">create procedure </span>Products_Delete
    @ProductID <span style="color: blue">int
as
    delete from </span>Products
    <span style="color: blue">where </span>ProductID = @ProductID</pre>
<p>At this point, the generated output is static, which is not any better than coding this stored procedure by hand. Instead, we can generate it dynamically, using database schema information provided by SQL Server. </p>
<h4>Adding .NET code to text template</h4>
<ul>
<li>Change CrudStoredProcedures.tt to look like so</li>
</ul>
<pre class="code"><span style="background: gold">&lt;#@</span><span style="color: red"> </span><span style="color: brown">template </span><span style="color: red">language=</span>&quot;<span style="color: blue">C#</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">output </span><span style="color: red">extension=</span>&quot;<span style="color: blue">SQL</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">assembly </span><span style="color: red">name=</span>&quot;<span style="color: blue">Microsoft.SqlServer.ConnectionInfo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">assembly </span><span style="color: red">name=</span>&quot;<span style="color: blue">Microsoft.SqlServer.Smo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">import </span><span style="color: red">namespace=</span>&quot;<span style="color: blue">Microsoft.SqlServer.Management.Smo</span>&quot; <span style="background: gold">#&gt;</span><span style="color: red">
</span><span style="background: gold">&lt;#
</span><span style="background: #f0f8ff; color: #191970">    Server server = new Server();
    Database database = new Database(server, &quot;Northwind&quot;);
    Table table = new Table(database, &quot;Products&quot;);
    table.Refresh();
</span><span style="background: gold">#&gt;
</span><span style="color: gray">create procedure Products_Delete
    @ProductID int
as
    delete from Products
    where ProductID = @ProductID</span></pre>
<p><a href="http://11011.net/software/vspaste"></a>This code uses <a href="http://www.olegsych.com/2008/02/t4-template-directive/">template directive</a> to specify that this template uses C# in its <a href="http://www.olegsych.com/2008/02/t4-statement-blocks/">code blocks</a>.&#160; This template contains a <a href="http://www.olegsych.com/2008/02/t4-statement-blocks/">statement block</a> which is defined using special markers - &lt;# and #&gt;. This block uses <a href="http://msdn.microsoft.com/en-us/library/ms162169.aspx">SQL Server Management Objects</a> (SMO) to retrieve metadata information about Products table from the Northwind database running on the local SQL server instance. This API (SMO) is defined in a .NET assembly, Microsoft.SqlServer.Smo which is installed in the Global Assembly Cache by SQL Server setup program. In order to use this API, this template uses an <a href="http://www.olegsych.com/2008/02/t4-assembly-directive/">assembly directive</a> to reference the assembly where it is defined and an <a href="http://www.olegsych.com/2008/02/t4-import-directive/">import directive</a> to specify the namespace where <a href="http://msdn.microsoft.com/en-us/library/microsoft.sqlserver.management.smo.server.aspx">Server</a>, <a href="http://msdn.microsoft.com/en-us/library/microsoft.sqlserver.management.smo.database.aspx">Database</a> and <a href="http://msdn.microsoft.com/ru-ru/library/microsoft.sqlserver.management.smo.table.aspx">Table</a> types are defined without having to use fully-qualified type names.</p>
<h4>Making Code Generation Dynamic</h4>
<p>Having metadata information about the target table, we can now generate the DELETE stored procedure dynamically.</p>
<ul>
<li>Change CrudStoredProcedures.tt to look like so.</li>
</ul>
<pre class="code"><span style="background: gold">&lt;#@</span><span style="color: red"> </span><span style="color: brown">template </span><span style="color: red">language=</span>&quot;<span style="color: blue">C#</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">output </span><span style="color: red">extension=</span>&quot;<span style="color: blue">SQL</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">assembly </span><span style="color: red">name=</span>&quot;<span style="color: blue">Microsoft.SqlServer.ConnectionInfo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">assembly </span><span style="color: red">name=</span>&quot;<span style="color: blue">Microsoft.SqlServer.Smo</span>&quot; <span style="background: gold">#&gt;
&lt;#@</span><span style="color: red"> </span><span style="color: brown">import </span><span style="color: red">namespace=</span>&quot;<span style="color: blue">Microsoft.SqlServer.Management.Smo</span>&quot; <span style="background: gold">#&gt;</span><span style="color: red">
</span><span style="background: gold">&lt;#
</span><span style="background: #f0f8ff; color: #191970">    Server server = new Server();
    Database database = new Database(server, &quot;Northwind&quot;);
    Table table = new Table(database, &quot;Products&quot;);
    table.Refresh();
</span><span style="background: gold">#&gt;
</span><span style="color: gray">create procedure </span><span style="background: gold">&lt;#=</span><span style="background: #f0f8ff; color: #191970"> table.Name </span><span style="background: gold">#&gt;</span><span style="color: gray">_Delete
</span><span style="background: gold">&lt;#
</span><span style="background: #f0f8ff; color: #191970">    PushIndent(&quot;\t&quot;);
    foreach (Column column in table.Columns)
    {
        if (column.InPrimaryKey)
            WriteLine(&quot;@&quot; + column.Name + &quot; &quot; + column.DataType.Name);
    }
    PopIndent();
</span><span style="background: gold">#&gt;
</span><span style="color: gray">as
    delete from </span><span style="background: gold">&lt;#=</span><span style="background: #f0f8ff; color: #191970"> table.Name </span><span style="background: gold">#&gt;
</span><span style="color: red">    </span><span style="color: gray">where
</span><span style="background: gold">&lt;#
</span><span style="background: #f0f8ff; color: #191970">    PushIndent(&quot;\t</span>\<span style="background: #f0f8ff; color: #191970">t&quot;);
    foreach (Column column in table.Columns)
    {
        if (column.InPrimaryKey)
            WriteLine(column.Name + &quot; = @&quot; + column.Name);
    }
    PopIndent();
</span><span style="background: gold">#&gt;</span><span style="color: red">    </span></pre>
<p>This template uses <a href="http://www.olegsych.com/2008/02/t4-expression-blocks/">expression blocks</a> to dynamically generate name of the target table in the output file. Expression blocks are defined using special markers - &lt;#= and #&gt; and can contain any valid programming expression, which will be converted to string and written to the output file. This template also uses additional <a href="http://www.olegsych.com/2008/02/t4-statement-blocks/">statement blocks</a> to iterate through the list of <a href="http://msdn.microsoft.com/en-us/library/microsoft.sqlserver.management.smo.tableviewtabletypebase.columns.aspx">Columns</a> and calls <a href="http://msdn.microsoft.com/en-us/library/microsoft.visualstudio.texttemplating.texttransformation.writeline.aspx">WriteLine</a> method to generate stored procedure parameter declarations and WHERE clause for the DELETE statement based on the primary key of the table. <a href="http://msdn.microsoft.com/en-us/library/microsoft.visualstudio.texttemplating.texttransformation.pushindent.aspx">PushIndent</a> and <a href="http://msdn.microsoft.com/en-us/library/microsoft.visualstudio.texttemplating.texttransformation.popindent.aspx">PopIndent</a> methods are used to format parameter declarations and the where clause.</p>
<h4>Conclusion</h4>
<p>The text template shown in this article generates a single DELETE stored procedure based on table schema information retrieved from SQL Server using SMO. In the next article, we will talk about <a href="http://www.olegsych.com/2008/09/t4-tutorial-troubleshooting-code-generation-errors/">troubleshooting code generation errors</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.olegsych.com/2008/09/t4-tutorial-creatating-your-first-code-generator/feed/</wfw:commentRss>
		</item>
		<item>
		<title>Killing three birds with one stone</title>
		<link>http://www.olegsych.com/2008/09/killing-three-birds-with-one-stone/</link>
		<comments>http://www.olegsych.com/2008/09/killing-three-birds-with-one-stone/#comments</comments>
		<pubDate>Mon, 01 Sep 2008 22:10:22 +0000</pubDate>
		<dc:creator>Oleg Sych</dc:creator>
		
		<category><![CDATA[Uncategorized]]></category>

		<category><![CDATA[Code Generation]]></category>

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

		<category><![CDATA[Visual Studio]]></category>

		<guid isPermaLink="false">http://www.olegsych.com/2008/09/killing-three-birds-with-one-stone/</guid>
		<description><![CDATA[I&#8217;ve had a difficult time trying to start a series of posts explaining design of T4 Toolbox. For instance, it includes a class called Template. When I sat down to write about it, the question I asked myself and tried to answer was &#8220;What is a Template?&#8221; Well, it&#8217;s a template. I&#8217;ve been thinking about [...]]]></description>
			<content:encoded><![CDATA[<p>I&#8217;ve had a difficult time trying to start a series of posts explaining design of <a href="http://www.olegsych.com/2008/08/t4-toolbox/">T4 Toolbox</a>. For instance, it includes a class called Template. When I sat down to write about it, the question I asked myself and tried to answer was &#8220;What is a Template?&#8221; Well, it&#8217;s a template. I&#8217;ve been thinking about it so long that it became self explanatory and I couldn&#8217;t describe it effectively. After spending a couple of hours on failed drafts, I realized this approach was not working.</p>
<p>At the same time, I also had a thought in my mind that my blog doesn&#8217;t offer much help to people who are only getting started with T4 and code generation. I cover this information in my <a href="http://www.olegsych.com/presentations">talks</a>, but most of my readers are located outside of Florida and don&#8217;t have the opportunity to hear them. </p>
<p>Finally, some of the articles I wrote early on are becoming outdated and many of them are more complicated than necessary. OK, some of them are a lot more complicated than a template developer needs..</p>
<p>To address these issues, I am starting a short series of posts about code generation with text templates in Visual Studio. This series will cover a range of topics, starting with basics and ending with advanced topics, such as design of templates and code generators. It will be based on T4 Toolbox to take advantage of the framework it provides for generating multiple output files and integration with Visual Studio. As this series is targeted at a template developer, it will not cover the finer points of <a href="http://www.olegsych.com/2008/05/t4-architecture/">T4 Architecture</a>.&nbsp; It will cover some of the topics discussed by the <a href="http://www.olegsych.com/2008/04/t4-template-design/">T4 Template Design</a> mini-series. However, instead of describing all of the various ways you could design your templates, it will focus on the approach I believe to be the best and have chosen for <a href="http://www.olegsych.com/2008/08/t4-toolbox/">T4 Toolbox</a>.</p>
<p>I hope you find this series useful. As always, I would like to hear from you.&nbsp; Please post a comment or <a href="http://www.olegsych.com/about/">send me an email</a> if you find this information useful, if you have a specific question or suggestion. A simple <a href="http://en.wiktionary.org/wiki/attaboy">attaboy</a> is always appreciated.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.olegsych.com/2008/09/killing-three-birds-with-one-stone/feed/</wfw:commentRss>
		</item>
	</channel>
</rss>
