//Orignally from: https://github.com/NancyFx/Nancy/blob/master/src/Nancy.ViewEngines.Razor.BuildProviders/NancyCSharpRazorBuildProvider.cs
using System;
using System.CodeDom;
using System.CodeDom.Compiler;
using System.Globalization;
using System.Web.Compilation;
using System.Web.Razor;
namespace ServiceStack.Razor
{
[BuildProviderAppliesTo(BuildProviderAppliesTo.Code | BuildProviderAppliesTo.Web)]
public class CSharpRazorBuildProvider : BuildProvider
{
private readonly RazorEngineHost host;
private readonly CompilerType compilerType;
private CodeCompileUnit generatedCode;
///
/// Initializes a new instance of the class.
///
public CSharpRazorBuildProvider()
{
this.compilerType = this.GetDefaultCompilerTypeForLanguage("C#");
this.host = new RazorEngineHost(new CSharpRazorCodeLanguage()) {
DefaultBaseClass = typeof(ViewPageRef).FullName,
DefaultNamespace = "RazorOutput",
DefaultClassName = "ViewPage"
};
}
///
/// Represents the compiler type used by a build provider to generate source code for a custom file type.
///
/// A read-only representing the code generator, code compiler, and compiler settings used to build source code for the virtual path. The base class returns null.
public override CompilerType CodeCompilerType
{
get { return this.compilerType; }
}
///
/// Generates source code for the virtual path of the build provider, and adds the source code to a specified assembly builder.
///
/// The assembly builder that references the source code generated by the build provider.
public override void GenerateCode(AssemblyBuilder assemblyBuilder)
{
assemblyBuilder.AddCodeCompileUnit(this, this.GetGeneratedCode());
assemblyBuilder.GenerateTypeFactory(string.Format(CultureInfo.InvariantCulture, "{0}.{1}", new object[] { this.host.DefaultNamespace, this.host.DefaultClassName }));
}
///
/// Returns a type generated by the build provider from the virtual path.
///
/// The type that is generated by the build provider for the virtual path. The base class returns null.
/// The compilation results for the build provider's virtual path.
public override Type GetGeneratedType(CompilerResults results)
{
return results.CompiledAssembly.GetType(string.Format(CultureInfo.CurrentCulture, "{0}.{1}", new object[] { this.host.DefaultNamespace, this.host.DefaultClassName }));
}
private CodeCompileUnit GetGeneratedCode()
{
if (this.generatedCode == null)
{
var engine = new RazorTemplateEngine(this.host);
GeneratorResults results;
using (var reader = this.OpenReader())
{
results = engine.GenerateCode(reader);
}
if (!results.Success)
{
throw new InvalidOperationException(results.ToString());
}
this.generatedCode = results.GeneratedCode;
}
return this.generatedCode;
}
}
}