Is there a way to get the content of the PartialView HTML in the controller?
I have a partial view with a controller with outputCache as I need to cache this item.
Then I need to display this PartialView on every page, but first I need to do some string replacement.
So my question is, howdo I get the Partial View in the controller so that I can manipulate the content and do some string replacement before returning it to the View?
thank
source to share
No, don't do this. Your controller doesn't have to render your view, which is a templating engine setting.
Pass in "replacement" values as the model for your PartialView.
public ActionResult SomeAction()
{
SomeModelmodel = new SomeModel(); // your model
return PartialView(model); // partial view with your model
}
And a partial view:
@model SomeModel
<div>Replace your values with @Model.Value instead of String.Replace().</div>
source to share
I am using these methods in my user base Controller
.
public string RenderPartialToString(string partialViewName, object model)
{
InvalidateControllerContext();
IView view = ViewEngines.Engines.FindPartialView(ControllerContext, partialViewName).View;
string result = RenderViewToString(view, model);
return result;
}
public string RenderViewToString(string viewName, object model)
{
InvalidateControllerContext();
IView view = ViewEngines.Engines.FindView(ControllerContext, viewName, null).View;
string result = RenderViewToString(view, model);
return result;
}
public string RenderViewToString(IView view, object model)
{
InvalidateControllerContext();
string result = null;
if (view != null)
{
StringBuilder sb = new StringBuilder();
using (StringWriter writer = new StringWriter(sb))
{
ViewContext viewContext = new ViewContext(ControllerContext, view, new ViewDataDictionary(model), new TempDataDictionary(), writer);
view.Render(viewContext, writer);
writer.Flush();
}
result = sb.ToString();
}
return result;
}
private void InvalidateControllerContext()
{
if (ControllerContext == null)
{
ControllerContext context = new ControllerContext(System.Web.HttpContext.Current.Request.RequestContext, this);
ControllerContext = context;
}
}
The method is InvalidateControllerContext
intended for a scenario where a Controller
manual instance is required to render partial or views outside of the controller context.
source to share
Just wanted to share a modification with @ Nico's solution if you want to use the ViewBag data from your controller action, then change RenderViewToString
like this: I'm using controller.TempData instead new TempDataDictionary()
.
public string RenderViewToString( IView view, object model)
{
InvalidateControllerContext();
string result = null;
if (view != null)
{
StringBuilder sb = new StringBuilder();
using (StringWriter writer = new StringWriter(sb))
{
// use TempData from controller
ViewContext viewContext = new ViewContext(ControllerContext, view,
new ViewDataDictionary(model), this.TempData, writer);
view.Render(viewContext, writer);
writer.Flush();
}
result = sb.ToString();
}
return result;
}
source to share