理解模板引擎Razor 的原理
2013-07-25 09:27
423 查看
Razor是ASP.NET MVC 3中新加入的技术,以作为ASPX引擎的一个新的替代项。简洁的语法与.NET Framework 结合,广泛应用于ASP.NET MVC 项目。Razor Pad是一个编辑Razor脚本的工具,脱离于ASP.NET 和Visual Studio。
微软已经有一套模板引擎T4,在设计ASP.NET MVC 3时又设计一套模板引擎Razor,对开发者而言是多一种选择,但同时也增加学习成本,至今我都没有时间和精力将Code Smith的模板转化为T4的模板。
以cshtml为后缀名的为Razor模板,可以混合脚本语言和Html代码,以呈现为ASP.NET Page页面。
来看下面的Razor脚本片段,它以div的格式输出Posts对象的标题:
.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }
Razor引擎分析上面的脚本,产生如下所示的Xml文本片段
.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }
以空格或是@作为区域(block)的分割符,将Razor解析成一个表达式树。@在Razor模板中的用法相当灵活,可以用于表达式的求值,或是定义代码块。
然后产生.NET代码,上面的脚本,会产生如下的.NET代码类型
最后,应用CodeDom API编译上面的代码,调用Execute方法输出结果。
System.Web.Razor.Parser.RazorParser
RazorParser用于解析脚本,但是它对Html,CS,VB脚本一无所知。MarkupParser用于解析Html标记,CSharpCodeParser用于解析包含C#代码的标记,相应的VBCodeParser则用于解析包含VB脚本的标记,
System.Web.Razor.Generator.RazorCodeGenerator
根据传入的Markup Parser,产生代码。与Parser相似,它也有二个与标记语言相关的类型,CSharpRazorCodeGenerator 和VBRazorCodeGenerator,用于处理标记包含的脚本。
System.Web.Razor.RazorEngineHost
System.Web.Razor.RazorTemplateEngine
引擎宿主,用于接受标记脚本,产生.NET 类型的代码。
把上面的内容综合起来,写一个例子程序,来看这些API的用法。
创建脚本宿主
添加Razor脚本引擎,读取标记(Markup)文件
.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }
编译标记文件生成的类型,生成Code Dom 脚本
执行生成的程序集类型,获取结果
.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }
Razor Pad程序的功能,也是用的这个基本思路来展来的。
Razor Pad是一个开放源码的程序,你可以从网址http://razorpad.codeplex.com中获取它的源代码。
.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }
.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }
.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }
微软已经有一套模板引擎T4,在设计ASP.NET MVC 3时又设计一套模板引擎Razor,对开发者而言是多一种选择,但同时也增加学习成本,至今我都没有时间和精力将Code Smith的模板转化为T4的模板。
Razor 从模板到.NET 代码
以cshtml为后缀名的为Razor模板,可以混合脚本语言和Html代码,以呈现为ASP.NET Page页面。
来看下面的Razor脚本片段,它以div的格式输出Posts对象的标题:
<div> @foreach(var post in Posts) { <div>@post.Title</div> } </div>
.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }
Razor引擎分析上面的脚本,产生如下所示的Xml文本片段
<Document> <Markup><div>\r\n\t</Markup> <Statement> <Transition>@</Transition> <Code>foreach(var post in posts) { </Code> <Markup> <Markup><div></Markup> <Expression> <Transition>@</Transition> <ImplicitExpression>post.Title</ImplicitExpression> </Expression> <Markup></div></Markup> </Markup> <Code> } </Code> <Markup></div></Markup> </Statement> <Markup>\r\n</div></Markup> </Document>
.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }
以空格或是@作为区域(block)的分割符,将Razor解析成一个表达式树。@在Razor模板中的用法相当灵活,可以用于表达式的求值,或是定义代码块。
然后产生.NET代码,上面的脚本,会产生如下的.NET代码类型
namespace Razor { public class __CompiledTemplate { public __CompiledTemplate() { } public override void Execute() { WriteLiteral("<div>\r\n\t"); @foreach(var post in posts) { WriteLiteral("<div>"); Write(post.Title); WriteLiteral("</div>"); } WriteLiteral("\r\n</div>"); } } }
最后,应用CodeDom API编译上面的代码,调用Execute方法输出结果。
Razor API
一开始接触这项技术时,以为是ASP.NET MVC的一个开源项目,接触之后才知道它是.NET Framework API中的类型,几年没有做Web开发,ASP.NET技术发展的确实很快。System.Web.Razor.Parser.RazorParser
RazorParser用于解析脚本,但是它对Html,CS,VB脚本一无所知。MarkupParser用于解析Html标记,CSharpCodeParser用于解析包含C#代码的标记,相应的VBCodeParser则用于解析包含VB脚本的标记,
System.Web.Razor.Generator.RazorCodeGenerator
根据传入的Markup Parser,产生代码。与Parser相似,它也有二个与标记语言相关的类型,CSharpRazorCodeGenerator 和VBRazorCodeGenerator,用于处理标记包含的脚本。
System.Web.Razor.RazorEngineHost
System.Web.Razor.RazorTemplateEngine
引擎宿主,用于接受标记脚本,产生.NET 类型的代码。
把上面的内容综合起来,写一个例子程序,来看这些API的用法。
创建脚本宿主
var language = new CSharpRazorCodeLanguage(); var host = new RazorEngineHost(language) { DefaultBaseClass = "CustomTemplateBase", DefaultClassName = "DemoTemplate", DefaultNamespace = "ProgrammingRazor", };
添加Razor脚本引擎,读取标记(Markup)文件
RazorTemplateEngine engine = new RazorTemplateEngine(host); GeneratorResults razorResult = engine.GenerateCode("C:\\Script.txt");
.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }
编译标记文件生成的类型,生成Code Dom 脚本
CompilerResults compilerResults = new CSharpCodeProvider() .CompileAssemblyFromDom( new CompilerParameters(/*...*/), razorResult.GeneratedCode );
执行生成的程序集类型,获取结果
var template = (CustomTemplateBase)Activator.CreateInstance(“ProgrammingRazor.DemoTemplate”); template.Execute();
.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }
Razor Pad程序的功能,也是用的这个基本思路来展来的。
Razor Pad是一个开放源码的程序,你可以从网址http://razorpad.codeplex.com中获取它的源代码。
.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }
.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }
.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, "Courier New", courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }
相关文章推荐
- 理解模板引擎Razor 的原理(转载)
- 理解模板引擎Razor 的原理
- 理解模板引擎Razor 的原理
- 理解模板引擎Razor 的原理
- ASP.NET Razor模板引擎中输出Html的两种方式
- 高性能JavaScript模板引擎原理解析
- Razor 也可说是一个asp.net模板引擎,用不着学习 T4 了
- JavaScript模板引擎原理,几行代码的事儿
- 高性能JavaScript模板引擎原理解析
- 高性能JavaScript模板引擎原理解析
- 高性能JavaScript模板引擎实现原理详解
- EF5+MVC4系列(9) Razor视图引擎的核心原理;@符号的使用;输出html的转义
- MVC3 Razor模板引擎 @RenderBody、@RenderPage、@RenderSection及Html.RenderPartial、Html.RenderAction
- MVC3 Razor模板引擎 @RenderBody、@RenderPage、@RenderSection
- 高性能JavaScript模板引擎原理解析
- ASP.NET MVC的Razor引擎:View编译原理
- JavaScript模板引擎原理,几行代码的事
- ASP.NET MVC的Razor引擎:View编译原理
- WebApi中利用Razor模板引擎来生成html
- MVC Razor模板引擎 @RenderBody、@RenderPage、@RenderSection及Html.RenderPartial、Html.RenderAction