RazorEngineCore 2023.11.1

There is a newer version of this package available.
See the version list below for details.
dotnet add package RazorEngineCore --version 2023.11.1
NuGet\Install-Package RazorEngineCore -Version 2023.11.1
This command is intended to be used within the Package Manager Console in Visual Studio, as it uses the NuGet module's version of Install-Package.
<PackageReference Include="RazorEngineCore" Version="2023.11.1" />
For projects that support PackageReference, copy this XML node into the project file to reference the package.
paket add RazorEngineCore --version 2023.11.1
#r "nuget: RazorEngineCore, 2023.11.1"
#r directive can be used in F# Interactive and Polyglot Notebooks. Copy this into the interactive tool or source code of the script to reference the package.
// Install RazorEngineCore as a Cake Addin
#addin nuget:?package=RazorEngineCore&version=2023.11.1

// Install RazorEngineCore as a Cake Tool
#tool nuget:?package=RazorEngineCore&version=2023.11.1

RazorEngineCore

.NET6 Razor Template Engine. No legacy code. No breaking changes.

  • .NET 6.0
  • .NET 5.0
  • .NET Standard 2.0
  • .NET Framework 4.7.2
  • Windows / Linux
  • Publish as single file supported
  • Thread safe

NuGet NuGet Gitter

Every single star makes maintainer happy! ⭐

NuGet

Install-Package RazorEngineCore

Feature requests

✅ Feel free to create new issues and vote for existing ones!

Articles

Wiki

Extensions

  • wdcossey/RazorEngineCore.Extensions
    • HTML values encoded by default (See issue #65 and @Raw)
    • Template precompiling
    • Direct model usage without RazorEngineTemplateBase
      template.Run(object model = null)
      template.RunAsync(object model = null)
      template.Run<TModel>(TModel model = null)
      template.RunAsync<TModel>(TModel model = null)
    

💥 HTML Safety

RazorEngineCore is not HTML safe by default.
It can be easily turned on: see #65 and @Raw

Examples

Basic usage
IRazorEngine razorEngine = new RazorEngine();
IRazorEngineCompiledTemplate template = razorEngine.Compile("Hello @Model.Name");

string result = template.Run(new
{
    Name = "Alexander"
});

Console.WriteLine(result);
Strongly typed model
IRazorEngine razorEngine = new RazorEngine();
string templateText = "Hello @Model.Name";

// yeah, heavy definition
IRazorEngineCompiledTemplate<RazorEngineTemplateBase<TestModel>> template = razorEngine.Compile<RazorEngineTemplateBase<TestModel>>(templateText);

string result = template.Run(instance =>
{
    instance.Model = new TestModel()
    {
        Name = "Hello",
        Items = new[] {3, 1, 2}
    };
});

Console.WriteLine(result);
Save / Load compiled templates

Most expensive task is to compile template, you should not compile template every time you need to run it

IRazorEngine razorEngine = new RazorEngine();
IRazorEngineCompiledTemplate template = razorEngine.Compile("Hello @Model.Name");

// save to file
template.SaveToFile("myTemplate.dll");

//save to stream
MemoryStream memoryStream = new MemoryStream();
template.SaveToStream(memoryStream);
IRazorEngineCompiledTemplate template1 = RazorEngineCompiledTemplate.LoadFromFile("myTemplate.dll");
IRazorEngineCompiledTemplate template2 = RazorEngineCompiledTemplate.LoadFromStream(myStream);
IRazorEngineCompiledTemplate<MyBase> template1 = RazorEngineCompiledTemplate<MyBase>.LoadFromFile<MyBase>("myTemplate.dll");
IRazorEngineCompiledTemplate<MyBase> template2 = RazorEngineCompiledTemplate<MyBase>.LoadFromStream<MyBase>(myStream);
Caching

RazorEngineCore is not responsible for caching. Each team and project has their own caching frameworks and conventions therefore making it impossible to have builtin solution for all possible needs.

If you dont have one, use following static ConcurrentDictionary example as a simplest thread safe solution.

private static ConcurrentDictionary<int, IRazorEngineCompiledTemplate> TemplateCache = new ConcurrentDictionary<int, IRazorEngineCompiledTemplate>();
private string RenderTemplate(string template, object model)
{
    int hashCode = template.GetHashCode();

    IRazorEngineCompiledTemplate compiledTemplate = TemplateCache.GetOrAdd(hashCode, i =>
    {
        RazorEngine razorEngine = new RazorEngine();
        return razorEngine.Compile(Content);
    });

    return compiledTemplate.Run(model);
}
Template functions

ASP.NET Core way of defining template functions:

<area>
    @{ RecursionTest(3); }
</area>

@{
  void RecursionTest(int level)
  {
	if (level <= 0)
	{
		return;
	}

	<div>LEVEL: @level</div>
	@{ RecursionTest(level - 1); }
  }
}

output:

<div>LEVEL: 3</div>
<div>LEVEL: 2</div>
<div>LEVEL: 1</div>
Helpers and custom members
string content = @"Hello @A, @B, @Decorator(123)";

IRazorEngine razorEngine = new RazorEngine();
IRazorEngineCompiledTemplate<CustomTemplate> template = razorEngine.Compile<CustomTemplate>(content);

string result = template.Run(instance =>
{
    instance.A = 10;
    instance.B = "Alex";
});

Console.WriteLine(result);
public class CustomTemplate : RazorEngineTemplateBase
{
    public int A { get; set; }
    public string B { get; set; }

    public string Decorator(object value)
    {
        return "-=" + value + "=-";
    }
}
Referencing assemblies

Keep your templates as simple as possible, if you need to inject "unusual" assemblies most likely you are doing it wrong. Writing @using System.IO in template will not reference System.IO assembly, use builder to manually reference it.

IRazorEngine razorEngine = new RazorEngine();
IRazorEngineCompiledTemplate compiledTemplate = razorEngine.Compile(templateText, builder =>
{
    builder.AddAssemblyReferenceByName("System.Security"); // by name
    builder.AddAssemblyReference(typeof(System.IO.File)); // by type
    builder.AddAssemblyReference(Assembly.Load("source")); // by reference
});

string result = compiledTemplate.Run(new { name = "Hello" });
Debugging templates

In the builder options, set GeneratePdbStream to true, and set the TemplateFilename.

razorEngine.Compile(templateSource, builder =>
{
    builder.Options.GeneratePdbStream = true;
    builder.Options.TemplateFilename = "TemplateFilename.cshtml"
});

Your debugger will popup a window asking you to find the source file, after which you can step through as normal.

To set a breakpoint add this line in a code block in the template.

System.Diagnostics.Debugger.Break();
Credits

This package is inspired by Simon Mourier SO post

Changelog
  • 2022.8.1
    • Proper namespace handling for nested types and types without namespace #113 (thanks @Kirmiir)
  • 2022.7.6
    • Added the option to genereate pdb alongside the assembly which allows debugging the templates.
  • 2022.1.2
    • #94 publish as single file fix
  • 2022.1.1
    • Make private methods in RazorEngine protected and virtual #PR88 (thanks @wdcossey)
    • Dictionary bug in anonymous model #91 (thanks @jddj007-hydra)
    • Template name fix #PR84 (thanks @Yazwh0)
    • CI for GitHub Actions #PR69 (thanks @304NotModified)
    • Added Source Link #PR67 (thanks @304NotModified)
    • Microsoft.AspNetCore.Razor.Language 3.1.8 → 6.0.1
    • Microsoft.CodeAnalysis.CSharp 3.7.0 → 4.0.1
  • 2021.7.1
  • 2021.3.1
    • fixed NET5 publish as single file (thanks @jddj007-hydra)
    • AnonymousTypeWrapper array handling fix
    • System.Collections referenced by default
    • Microsoft.AspNetCore.Razor.Language 3.1.8 → 5.0.3
    • Microsoft.CodeAnalysis.CSharp 3.7.0 → 3.8.0
  • 2020.10.1
    • Linux fix for #34
    • Microsoft.AspNetCore.Razor.Language 3.1.5 → 3.1.8
    • Microsoft.CodeAnalysis.CSharp 3.6.0 → 3.7.0
  • 2020.9.1
    • .NET 4.7.2 support (thanks @krmr)
  • 2020.6.1
    • Reference assemblies by Metadata (thanks @Merlin04)
    • Expose GeneratedCode in RazorEngineCompilationException
    • Microsoft.AspNetCore.Razor.Language 3.1.4 → 3.1.5
  • 2020.5.2
    • IRazorEngineTemplate interface
    • RazorEngineTemplateBase methods go virtual
  • 2020.5.1
    • Async methods (thanks @wdcossey)
    • Microsoft.AspNetCore.Razor.Language 3.1.1 → 3.1.4
    • Microsoft.CodeAnalysis.CSharp 3.4.0 → 3.6.0
  • 2020.3.3
    • Model with generic type arguments compiling fix
  • 2020.3.2
    • External assembly referencing
    • Linq included by default
  • 2020.3.1
    • In attribute rendering fix #4
  • 2020.2.4
    • Null values in model correct handling
    • Null model fix
    • Netstandard2 insted of netcore3.1
  • 2020.2.3
    • Html attribute rendering fix
    • Html attribute rendering tests

Supported by

<img src="https://resources.jetbrains.com/storage/products/company/brand/logos/jb_square.svg" />

Product Compatible and additional computed target framework versions.
.NET net5.0 is compatible.  net5.0-windows was computed.  net6.0 is compatible.  net6.0-android was computed.  net6.0-ios was computed.  net6.0-maccatalyst was computed.  net6.0-macos was computed.  net6.0-tvos was computed.  net6.0-windows was computed.  net7.0 was computed.  net7.0-android was computed.  net7.0-ios was computed.  net7.0-maccatalyst was computed.  net7.0-macos was computed.  net7.0-tvos was computed.  net7.0-windows was computed.  net8.0 was computed.  net8.0-android was computed.  net8.0-browser was computed.  net8.0-ios was computed.  net8.0-maccatalyst was computed.  net8.0-macos was computed.  net8.0-tvos was computed.  net8.0-windows was computed. 
.NET Core netcoreapp2.0 was computed.  netcoreapp2.1 was computed.  netcoreapp2.2 was computed.  netcoreapp3.0 was computed.  netcoreapp3.1 was computed. 
.NET Standard netstandard2.0 is compatible.  netstandard2.1 was computed. 
.NET Framework net461 was computed.  net462 was computed.  net463 was computed.  net47 was computed.  net471 was computed.  net472 was computed.  net48 was computed.  net481 was computed. 
MonoAndroid monoandroid was computed. 
MonoMac monomac was computed. 
MonoTouch monotouch was computed. 
Tizen tizen40 was computed.  tizen60 was computed. 
Xamarin.iOS xamarinios was computed. 
Xamarin.Mac xamarinmac was computed. 
Xamarin.TVOS xamarintvos was computed. 
Xamarin.WatchOS xamarinwatchos was computed. 
Compatible target framework(s)
Included target framework(s) (in package)
Learn more about Target Frameworks and .NET Standard.

NuGet packages (22)

Showing the top 5 NuGet packages that depend on RazorEngineCore:

Package Downloads
RazorEngineCore.Extensions

RazorEngineCore.Extensions w/ MSBuild tasks for pre-compiling and embedding Templates.

com.etsoo.Web

ETSOO Shared Web Components 亿速思维共享 Web 组件

GenHTTP.Modules.Razor

Provides renderers based on the Razor templating engine that can be used to render websites in projects running on the GenHTTP webserver.

MsM.SmartFactory.Common

Package Description

Linn.Common.Pdf

Package Description

GitHub repositories (4)

Showing the top 4 popular GitHub repositories that depend on RazorEngineCore:

Repository Stars
XINCGer/Unity3DTraining
【Unity杂货铺】unity大杂烩~
fullstackhero/dotnet-webapi-starter-kit
production grade .net 8 webapi starter kit with multitenancy support and clean code. 🔥
dotnetcore/WebApiClient
An open source project based on the HttpClient. You only need to define the c# interface and modify the related features to invoke the client library of the remote http interface asynchronously.
Kaliumhexacyanoferrat/GenHTTP
Lightweight web server written in pure C# with few dependencies to 3rd-party libraries.
Version Downloads Last updated
2024.4.1 3,764 4/16/2024
2023.11.2 173,744 11/18/2023
2023.11.1 1,741 11/17/2023
2022.8.1 1,479,224 8/7/2022
2022.1.2 427,286 1/21/2022
2022.1.1 6,534 1/17/2022
2021.7.1 571,782 7/16/2021
2021.3.1 218,483 3/1/2021
2020.10.1 93,506 10/12/2020
2020.9.1 3,813 9/29/2020
2020.6.1 28,030 6/24/2020
2020.5.2 26,565 5/28/2020
2020.5.1 2,187 5/25/2020
2020.3.3 42,320 3/4/2020
2020.3.2 940 3/4/2020
2020.3.1 1,050 3/2/2020
2020.2.4 1,020 2/25/2020
2020.2.3 1,037 2/10/2020
2020.2.2 1,000 2/8/2020
2020.2.1 2,030 2/8/2020