You are currently reviewing an older revision of this page.
or: How I Learned to Stop Worrying and Just Write HTML Templates or: HTML Templates: The Missing Manual or: The HTML Templates documentation they don't want you to know about!
or: How I Learned to Stop Worrying and Just Write HTML Templates
or: HTML Templates: The Missing Manual
or: The HTML Templates documentation they don't want you to know about!
This article aims to explain the differences between the Razor template syntax used in Tessitura HTML Templates and the syntax that you might see used in training courses for Razor Pages in ASP.NET Core/MVC web applications. At present, the Tessitura documentation only scratches the surface of what is available syntactically, and doesn't really attempt to explain how HTML Templates are implemented.
HTML Templates are rendered using an Apache-licensed, open-source project called RazorEngine, which is available on GitHub. To summarize the RazorEngine documentation, RazorEngine is a framework which consumes the Razor parser -- as is ASP.NET MVC. There is a difference between Razor's syntax and special features provided by these frameworks. RazorEngine only shares its syntax with other implementations like ASP.NET MVC. This is why convenience methods like @Html.Raw() (often seen in web results about Razor Pages) do not work in HTML templates -- the @Html helper is a class specifically implemented by the ASP.NET MVC framework. (RazorEngine instead has @Raw() built-in to provide the same functionality.) Reading the RazorEngine documentation can be informative. Tessitura appears to implement version 3.10 of RazorEngine.
@Html.Raw()
@Html
@Raw()
The fundamentals of how Razor operates still apply. The Razor syntax parser converts a .cshtml template into a C# Execute() method on a generated class, which, when invoked, has access to the provided model and returns a string.
The version of C# available in Tessitura HTML Templates in Tessitura V15.1 is C# 5.0. In Tessitura V16 there is support for interpolated strings, which indicates that the language has been updated to at least C# 6.0.
The version of Razor available in Tessitura HTML Templates in V15.1 is "Razor 3", which is versioned as such because it shipped with ASP.NET MVC 3. This means technically, the syntax documentation linked in the Tessitura docs is WAY too new for what is actually in use. This explains why "templating methods" described in these docs are not functional in Tessitura HTML Templates.
Razor supports the use of a @functions directive, which gives you a space to define additional members (methods and properties) to be added to the generated class.
@functions
The version of Razor used in RazorEngine 3.10 (Razor 3, shipped in ASP.NET MVC 3) also supports the @helper directive, which allows you to define a kind of function that contains markup, just like the rest of the template. This allows for easy reuse of template code. Helpers were removed in Razor 4, reappear in ASP.NET MVC 5, were removed again in ASP.NET Core, and finally code blocks were enhanced to allow for inline markup in functions, without the need for the @helper directive. Helpers can be used as "templating methods" which are otherwise unavailable as described above.
@helper
A regular function can be made to behave like a templating method by defining it with a void type and then calling the imperative WriteLiteral() and Write() functions, which is basically what a Razor template compiles to in the first place. Then this function can be called inside a code block (@{}) to inject its output at that location.
@{}
Helpers can be nested by calling .ToString() on the result of the inner helper before passing to the outer. Note that if the inner helper outputs HTML, then you will need to @Raw() it in the outer helper.
.ToString()