控制器范围之外的ControllerContext和ViewData-MVC3 C#

本文关键字:ViewData-MVC3 ControllerContext 范围 控制器 | 更新日期: 2023-09-27 18:22:24

我用下面的方法渲染PartialViews/Models,以便对发送的电子邮件进行模板化。

我正在使用下面的代码将部分和模型转换为一个html字符串,我可以将其传递给我的电子邮件发送代码。

public class BaseController : Controller
{
    public string RenderPartialViewToString(string viewName, object model)
    {
        if (string.IsNullOrEmpty(viewName))
            throw new ArgumentException("No View Path Provided.");
        ViewData.Model = model;
        using (StringWriter sw = new StringWriter())
        {
            ViewEngineResult viewResult = ViewEngines.Engines.FindPartialView(ControllerContext, viewName);
            ViewContext viewContext = new ViewContext(ControllerContext, viewResult.View, ViewData, TempData, sw);
            viewResult.View.Render(viewContext, sw);
            return sw.GetStringBuilder().ToString();
        }
    }
}

目前,它住在BaseController中,我想把它移到一个helper方法中,这样我就可以把我的电子邮件模型构建/发送也移到控制器中。

问题是我无法访问ViewData/TempData/ControllerContext

我可以新建ControllerContext,但我不知道如何处理ViewData/TempData。

这就是我将如何使用我目前在控制器中的东西:

//Do Stuff in Controller
var html = RenderPartialViewToString("~/Views/Mail/_ForgotPassword.cshtml", new MailModel { Username = "Skrillex", SomethingElse = "foo" });
//Send the Email

控制器范围之外的ControllerContext和ViewData-MVC3 C#

我认为你走在了正确的轨道上,但问题是你渴望完成分离,这太渴望了。

您正在使用Razor视图引擎来呈现富文本HTML电子邮件。一种非常高尚的方法。然而,这意味着你将非常接近你的表示层,在我看来,从控制器之外运行它没有多大意义。

我相信你需要制作(如果还没有制作的话):

  • 您的电子邮件Razor视图为强类型
  • 让渲染像往常一样在控制器中调用
  • 渲染就像将模型传递给Render方法一样简单
  • 把你的电子邮件模型的构建发给你想要的帮助者。这将不需要任何表示层逻辑,并且因此而忽略了它

所以重点是,渲染的调用不需要离开控制器,电子邮件模型的构建应该这样

现在,如果你正在做所有这些,那就意味着我还没有理解你的问题,需要更多的解释。

您可以在helper类中创建BaseController的实例或静态属性,如下所示,

public sealed class Helper {
///Gets or sets BaseController
public BaseController { get; set; }
#region "Constructors"
/// <summary>
/// Initialises a new instance of the <see cref="Helper" /> class.
/// </summary>
public Helper() : base() {
}
/// <summary>
/// Initialises a new instance of the <see cref="Helper" /> class.
/// </summary>
public Helper(BaseController baseController) : this() {
   this.BaseController = baseController;
}
#endregion
public void SendEmail(){
   // Here you can call your RenderPartialViewToString from the BaseController
 var m_RenderPartialViewToString = this.BaseController.RenderPartialViewToString( .......);
}}

谨致问候。希望这能有所帮助。

我使用了两种方法来呈现需要从控制器发出的电子邮件。。。首先,我将ControllerContext传递给我的服务层,它按预期工作,但并不理想。。。。我的服务通常被命令行应用程序使用,或者被编译到没有ControllerContext可用的Windows服务中。。。在我的第二次尝试中,我使用了Razor渲染引擎:http://razorengine.codeplex.com/或https://github.com/Antaris/RazorEngine