Quick summary of current DSL Tools text templating syntax

Having mentioned it last time and had someone ask in the newsgroup I thought it would be a good idea to post a quick summary of the syntax available with text templating in the March release of the DSL tools.

 

To set the scene, templates consist of some directives followed by a mixture of literal blocks and control blocks.  Literal blocks are just plain text in the template that you want to pass straight through to the output.  Control blocks are things with some kind of <% %> marker around them.

The content of these blocks in your template contributes to a static class which the templating system generates. This class has at least one static method, which when executed writes out the desired output of the transformation of the template.  In the parlance of the current March release we'd call this the generated code, but we're moving the naming over to be 'Text Templating' and "Transformation" as it's not just code you can generate, rather it is any text-based artefact.  If you do nothing else in your template, the static method will write out all of the text in literal blocks by simply writing out the raw text using a simple WriteLine() type statement.

I'm sure that all this is very familiar to users of ASP/ASP.Net, but not everyone has a web development background, so I'll persevere.

 

Control blocks

You can add three types of control block in this release:

 

<% %> - Regular control block

Embeds some control code in the static method.

Regular control blocks affect the literal blocks that they surround by means of the flow of control within them. This happens because the regular blocks' code is written verbatim into the static method. So if you have a regular block that begins a for loop that loops five times, then have a static block, then have another regular block that closes the for loop, you'll get the contents of the static block written into the final output text five times. You'd typically use some expression blocks inside this loop to do something interesting with the loop variable. You can put anything in a regular block that you can put in the body of a static method.

 

<%# %> - Expression control block

Embeds the value of a C# expression.

The expression will automatically have .ToString() appended to it with no culture specified.

 

<%! %> - Class features control block

Embeds control code at the static class scope.

This block allows you to add new static methods, static fields, static properties etc to the static class. You can then use these from regular and expression control blocks.

Trying to write all of your control code inside one static function can be tiresome if you have a big model to traverse - especially if the model has a recursive structure like a tree in it. Class features blocks allow you to add further static methods to the static class to make this sort of thing easier and to structure your control code well. You can also add static fields and properties to support those methods if you wish.

I touched on this in more depth in my last post.

 

Limitations

There can only be one class feature block and it must come immediately after the directives.

Code in control blocks has to be C#. We'll add VB.Net support in our next release.

 

Directives

Directives provide instructions to the templating engine. Their syntax is:

<%@ directiveName parameter="Value" %>

 

The current set for any template file is:

<%@ generatedFile extension=".cs" %>
Specify the extension of the file that gets generated.

<%@ assembly name="System.Drawing.dll" %>
Reference the assembly in compilation of control blocks.

<%@ import namespace="System.Collections" %>
Import the namespace in compilation of control blocks. (i.e. a C# using statement)

For .mdfomt templates:

<%@ modelFile path="UtilitiesModel.dmd" %>
Load the given domain model and provide a reference to it in the property Model on the context object.

For .mdfddt templates:

<%@ modelFile path="..\\SimpleArchitectureChart.dd" %>
Load the given designer definition and provide a reference to it in the property Definition on the context object.

Phew - OK, so maybe that wasn't quite such a quick post!