Asp.net MVC Razor模板引擎技巧分享


Razor是Asp.net MVC中新的默認模板類型, 語法簡單易用。這篇文章不涉及Razor的語法,主要介紹Razor的一些在MVC項目中的使用技巧,以及脫離MVC環境下,如何使用Razor.

閱讀目錄:

一、Razor和MVC關系

二、MVC中擴展Razor尋找模板范圍

三、MVC中使用Razor生成Html片段

四、脫離MVC, 使用Razor獨立作為模板引擎

五、其它

1. Razor和MVC關系

Razor是MVC中的默認模板引擎,MVC中還有ASPX模板引擎,在早期的MVC版本中,默認使用的是ASPX模板引擎。
當默認添加一個View文件的時候,可以看到MVC默認帶的2個模板引擎。

image

你還可以引入其它的模板引擎到MVC項目中來, MVCContrib項目是一個對MVC進行擴展的項目, 項目的地址是:http://mvccontrib.codeplex.com
這里有它提供的一份MVC中可以擴展的模板引擎列表。

template-engines

總之,這里想說的是,模板引擎是獨立的,它們甚至是獨立的項目,由不同的公司和組織來開發。你可以在MVC中使用你熟悉的模板引擎。
下面主要是關於Razor在MVC中的一些使用技巧。

2. MVC中擴展Razor尋找模板范圍

看下面這個Controller中的Action方法:

public class TestController : Controller
{
     public ActionResult Index()
     {
         return View();
     }
}

這是一個簡單的Action方法Index,  其中的return View()方法會將流程轉向View Engine來處理。如果我們沒有創建一個View\Test\Index.cshtml文件,則會出現下面的錯誤頁面:

view-not-found-error

從上面很容易看出來,MVC默認支持的view類型, aspx, ascx, cshtml和vbhtml.
以及找尋對應View的路徑規則是:

~View/{Controller}/{Action}
~View/Shared/{Action}

然而在現實開發中,使用默認的查找View路徑,就完全限定住了View的層級結構,不適合復雜項目的開發

比如在Shared共享的View文件夾中,希望再細分為Partial, Common, Email, EditorTemplate等
比如在每個Controller對應的文件夾中,你希望在添加一個文件夾為Partial,用來存放那些呈現頁面某個部分的view文件。

你只需要在Global.asax.cs文件中的Application_Start方法中,添加幾行代碼就可以了。

protected void Application_Start()
{
    ……………….
    ViewEngines.Engines.Add(
    new RazorViewEngine
        {
            PartialViewLocationFormats = new[]
                  {
                        "~/Views/{1}/Partial/{0}.cshtml",
                        "~/Views/Shared/Partial/{0}.cshtml",
                        "~/Views/Shared/Common/{0}.cshtml",
                        "~/Views/Shared/Email/{0}.cshtml",
                        "~/Views/Shared/EditorTemplate/{0}.cshtml"
                  }
      });
 }

上面中的{1}是Controller, {0}對應的是Action.

看看下面這張圖, 可以看出來,還有很多其它的擴展點,Area, FileExtensions等,大家可以試試看。

viewengine_extension

3. MVC中使用Razor生成Html字符串

項目中常常會用到Ajax局部刷新頁面的情況,如果只是刷新一個局部區域,還比較簡單,可以使用一個對應的Action來響應Ajax請求,獲取刷新的html內容,但是如果是需要刷新頁面中的多個區域的時候,怎么辦呢? 這個時候,我們希望后台返回的結果是一個類似這樣的Json格式.

return Json(new
           {
               Success = true,
               Message = "Sucess",
               HtmlPart1 = ……..
               HtmlPart2 = …….
           }, JsonRequestBehavior.AllowGet);

要解決這個問題,可以非常方便的使用下面的Controller擴展方法解決:

public static class ControllerExtension
{
      /// <summary>
      /// Renders a (partial) view to string.
      /// </summary>
      /// <param name="controller">Controller to extend</param>
      /// <param name="viewName">(Partial) view to render</param>
      /// <returns>Rendered (partial) view as string</returns>
      public static string RenderPartialViewToString(this ControllerBase controller, string viewName)
      {
          return controller.RenderPartialViewToString(viewName, null);
      }

      /// <summary>
      /// Renders a (partial) view to string.
      /// </summary>
      /// <param name="controller">Controller to extend</param>
      /// <param name="viewName">(Partial) view to render</param>
      /// <param name="model">Model</param>
      /// <returns>Rendered (partial) view as string</returns>
      public static string RenderPartialViewToString(this ControllerBase controller, string viewName, object model)
      {
          if (string.IsNullOrEmpty(viewName))
              viewName = controller.ControllerContext.RouteData.GetRequiredString("action");

          controller.ViewData.Model = model;

          using (var sw = new StringWriter())
          {
              var viewResult = ViewEngines.Engines.FindPartialView(controller.ControllerContext, viewName);
              var viewContext = new ViewContext(controller.ControllerContext, viewResult.View, controller.ViewData, controller.TempData, sw);
              viewResult.View.Render(viewContext, sw);

              return sw.GetStringBuilder().ToString();
          }
      }
}

那么上面的返回結果,就可以改成:

return Json(new
           {
               Success = true,
               Message = "Sucess",
               HtmlPart1 = this.RenderPartialViewToString("_HtmlPart1", model1),
               HtmlPart2 = this.RenderPartialViewToString("_HtmlPart2", model2),

           }, JsonRequestBehavior.AllowGet);

4. 脫離MVC, 使用Razor獨立作為模板引擎

RazorEngine是一個獨立的開源項目,項目的地址是https://github.com/Antaris/RazorEngine
它是基於微軟的Razor之上,包裝而成的一個可以獨立使用的模板引擎。也就是說,保留了Razor的模板功能,但是使得Razor脫離於Asp.net MVC,能夠在其它應用環境下使用。我現在一般這個來生成Email文本,當然也有人用來做代碼生成器。

使用也非常簡單:

string template = "Hello @Model.Name! Welcome to Razor!";
string result = Razor.Parse(template, new { Name = "World" });

上面result的結果就是 “Hello World! Welcome to Razor!”

5. 其它

這篇文章主要是在Razor實際使用過程中,一些學到到知識,拿來這里分享. 沒有涉及Razor的語法這些內容,大家可以自行搜索,網上有很多介紹的文章。

關於代碼生成器的一些個人看法,以前在看到代碼生成器的時候,覺得是個好東西,非常牛,能夠減少不少工作量。后來在深入的學習之后,發現必要性不是很大,如果程序中的代碼很多是需要生成的,那么可能大部分都是重復和相似的代碼,這些代碼應該是可以通過設計模式來重構精簡的。

避免使用代碼生成器,不止能夠精簡代碼,還能為你打開另外一道門,大家不妨試試。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM