Finding T4 text template class code - visual-studio

T4 text templates can be used to generate not only code but also any kind of text with visual studio.
I've read blogs and tutorials about T4 and as far as I can understand, visual studio dynamically builds a class in the background, compiles and runs the code in that class to build the text output.
Is it possible to see the source code of that class?

Yes, the easiest way is to change the Custom Tool in the properties window when the template file is selected in Solution Explorer.
By default, it will be 'TextTemplatingFileGenerator'.
If you change the custom tool to 'TextTemplatingFilePreprocessor' you'll get the underlying template class instead of the template output generated into your project.
To be precise, this code won't be exactly the same as that which is run under the covers, but it will be very close.
If you need the absolute exact code, you should leave the custom tool alone, but set the debug="true" flag on your <## template #> directive. This will then leave the generated code sitting around in a random named '.cs' or 'vb' file in your %TEMP% directory. Just sort the directory by time and it should be up at the top.

Related

visual studio 2010 inserts using directives inside namespace

I have exactly opposite problem to one described here. In my case Visual Studio inserts using directives inside namespace and I want to prevent this. I did try to uncheck Resharper option:
Languages -> C# -> Formatting Style -> Namespace Imports -> Add using directive to the deepest scope
And it didn't help. Also I tried to temporary disable the Resharper. Still same issue.
Btw, I have StyleCop and StyleCop+ installed as well. Maybe it is causing the issue.
So right now when I go and Add New Item -> Class - it will create new code file with using directives inside namespace. How to change this?
Have you replace your class template file with one that has one or more using directives inside the namespace declaration? If so, you're probably seeing the result of an interesting bit of C# plugin behavior: a newly added using directive is placed after the last recognized using directly already in the file, regardless of where that is.

How do I disconnect code generated by a T4 template from that template?

When I 'run' a T4 template, the class files it generates for me all appear under the template. I cannot remove the template from the project without the files going away too. I also can't copy the files out from 'under' the template into the project root because the are already in the project root. How can I emancipate these files from the template that created them?
Get creative:
Right click and open containing folder.
Drag-and-drop the generated file to another location in the solution.
Delete the original template and file from Visual Studio.
Presto.
If you want to do one-time code-generation with T4 then I would suggest using T4 scaffolding. This tool was originally created to support the generation of views, controllers etc. in MVC3 but you can use it on pretty much anything.

How to automatically run custom tool for T4 file when another file is saved

Is there a way to automatically run the T4 transform when another file is saved?
The AutoRunCustomTool Visual Studio extension was created to address this exact scenario.
It seems like T4 Toolbox is not available for VS2012. However there is now a feature in tangible T4 Editor that allows you to simply add a auto-transformed template to any exisitng file in your solution so that when the parent file is saved the dependend t4 file is transformed. See here:
http://t4-editor.tangible-engineering.com/blog/dependent-t4-templates.html
You can do that with T4 Toolbox. Select the file in Solution Explorer and set the Custom Tool Template in the Properties window.
I get this answer form How can set the custom tool property of an xml file to a T4 file?

Is it possible to generate XML from a EDMX model?

I'm generating my POCO's from edmx model, and would like to know if its possible to make use of the neat codegen features of Entity Framework to create my an xml document along with the POCO (which is needed for my project).
You can generate an XML document in Visual Studio using T4 templates.
In Visual Studio, a T4 text template is a mixture of text blocks and control logic that can generate a text file. The control logic is written as fragments of program code in Visual C# or Visual Basic. The generated file can be text of any kind, such as a Web page, or a resource file, or program source code in any language.
But you should note that the EDMX file itself is an XML document.
Right click on your Model.edmx file
'Open With...'
Choose 'XML (Text) Editor'
There are three main sections to the file
StorageModels - describes that database
ConceptualModels - describes your code and objects
Mappings - describes how the two models relate
Look at whether the standard EDMX file contains the type of information you want. If not, parse and shred it using T4 to extract the information you're looking for.
No need to parse the EDMX file, use TiraggoEdmx, you can install it via NuGet. See http://brewdawg.github.io/Tiraggo.Edmx/ it serves up all of the metadata from your EDMX files that Microsoft hides from you, very simple, works great. I wrote it but it's 100% free, even comes with a sample POCO template.

Best way to deploy and reference an XSLT file

In a visual studio project I have three layers, Data Layer, Business Layer and Presentation Layer.
In the Data Layer I have a few XSLT's that transform some objects into an email, all works fine but I have discovered that the XSLTs do not get built/copied when building.
I have currently, created a folder in the deploy location and placed the XSLT's there but I am concerned about relying on a manual process to update these.
Has anyone encountered a similar issue and if so how did they get around it.
It smacks of changing the MSBuild script to copy the build artifacts to the required location, does anyone have examples of this?
Thaks
If you are using Visual Studio 2005/2008, the easiest way to do this is by including your XSLT files as project resources.
Open the Properties for your project.
Select the Resources tab. You will probably see a link that says "This project does not contain a default resources file. Click here to create one." Go ahead and click on that.
Click the Add Resource drop-down near the top and select Add Existing File.
Browse to your XSLT files and select them.
After you have done this, you can easily access the resources in the following manner:
// To get the contents of the resource as a string:
string xslt = global::MyNamespace.Properties.Resources.MyXsltFile;
// To get a Stream containing the resource:
Stream xsltStream = global::MyNamespace.Properties.Resources.ResourceManager.GetStream("MyXsltFile");
If you are using Visual Studio 2003, your best bet is to include those XSLT files as embedded resources for the DLL. In Visual Studio, select the file(s) in Solution Explorer, open the Properties pane, and change the Build Type to "Embedded Resource". You can then use the GetManifestResourceStream method to get a Stream containing the XSLT(s). The name to pass will be based on the default namespace of your assembly, the folder containing the file, and the name of the file.
For example, say your data layer assembly has a default namespace of My.DataLayer. Within your data layer project you have a folder named Templates which contains a file called Transform.xslt. The code to get your XSLT would look like this:
// There are numerous ways to get a reference to the Assembly ... this way works
// when called from a class that is in your data layer. Have a look also at the
// static methods available on the Assembly class.
System.Reflection.Assembly assembly = (GetType()).Assembly;
System.IO.Stream xsltStream = assembly.GetManifestResourceStream("My.DataLayer.Templates.Transform.xslt");
For more information check out this article on CodeProject.
Obvious question maybe, but still has to be asked, did you include the folder containing the XSLT's in the project itself? Is this a web or forms app?
In VS, it is easy to set the properties of the XSLT files in the project to copy on build, by default they do not.
I may have explained myself poorly.
THe Data layer is a class library that a the presentation layer references.
On building the DataLayer I can get the XSLTs to output to the Bin directory of the DataLayer. However when I build and publish the presentation layer, it correctly grabs the DLL but not the XSLTs

Resources