アクション内でビューの生成されたhtmlを取得する方法を知っている人はいますか?
次のようなものですか:
public ActionResult Do()
{
var html = RenderView("hello", model);
...
}
Utilities.Common
というクラスで静的メソッドを使用します。ビューをクライアントにJSONオブジェクトのプロパティとして常に渡しているため、ビューを文字列にレンダリングする必要がありました。ここに行く:
public static string RenderPartialViewToString(Controller controller, string viewName, object model)
{
controller.ViewData.Model = model;
using (StringWriter sw = new StringWriter())
{
ViewEngineResult viewResult = ViewEngines.Engines.FindPartialView(controller.ControllerContext, viewName);
ViewContext viewContext = new ViewContext(controller.ControllerContext, viewResult.View, controller.ViewData, controller.TempData, sw);
viewResult.View.Render(viewContext, sw);
return sw.ToString();
}
}
これは、部分ビューだけでなく完全ビューでも機能します。ViewEngines.Engines.FindPartialView
をViewEngines.Engines.FindView
に変更するだけです。
上記の@Chevによる受け入れられた答えは良いですが、特定のviewではなく、特定のactionの結果をレンダリングしたかったのです。
また、モデルの注入に依存するのではなく、そのアクションにパラメーターを渡すことができる必要がありました。
そこで、私は自分のメソッドを思いつき、それをコントローラーの基本クラスに入れました(すべてのコントローラーが使用できるようにします)。
protected string RenderViewResultAsString(ViewResult viewResult)
{
using (var stringWriter = new StringWriter())
{
this.RenderViewResult(viewResult, stringWriter);
return stringWriter.ToString();
}
}
protected void RenderViewResult(ViewResult viewResult, TextWriter textWriter)
{
var viewEngineResult = this.ViewEngineCollection.FindView(
this.ControllerContext,
viewResult.ViewName,
viewResult.MasterName);
var view = viewEngineResult.View;
try
{
var viewContext = new ViewContext(
this.ControllerContext,
view,
this.ViewData,
this.TempData,
textWriter);
view.Render(viewContext, textWriter);
}
finally
{
viewEngineResult.ViewEngine.ReleaseView(this.ControllerContext, view);
}
}
モデルオブジェクトと他のパラメーターを使用するFoo
というアクションがあり、これらが一緒に使用されるビューに影響するとします。
public ViewResult Foo(MyModel model, int bar)
{
if (bar == 1)
return this.View("Bar1");
else
return this.View("Bar2", model);
}
ここで、アクションFoo
を呼び出した結果を取得したい場合、ViewResult
メソッドを呼び出してFoo
を取得し、RenderViewResultAsString
を呼び出すだけで済みます。 HTMLテキストを取得するには:
var viewResult = this.Foo(model, bar);
var html = this.RenderViewResultAsString(viewResult);