可重复使用的地方放置电子邮件视图渲染逻辑?

时间:2011-08-10 05:01:49

标签: asp.net-mvc asp.net-mvc-3 email dry separation-of-concerns

我有一个名为 EmailController 的控制器,它(你猜对了)负责发送电子邮件。

这方面的一个例子是我的网站的用户可以“喜欢”的东西,如果其他一些用户在其中一个“东西”上做某事,那么我需要向所有“喜欢”它的用户发送电子邮件。有点像电子邮件提醒。

问题是,我不确定如何从其他操作方法(当用户执行操作时的HTTP POST)调用我的EmailController的操作方法。

通常情况下,我会将此类操作(通过电子邮件发送)发送到服务中,并且服务中的实际电子邮件逻辑(SMTP) ,但 EmailController 负责用于设置电子邮件的内容(例如HTML),需要将View呈现为字符串(因此,它需要控制器上下文而不能进入服务)。

我怎样才能实现这个目标?

我不能只使用静态辅助方法,因为我如何渲染视图?我需要将控制器上下文传递给方法或其他东西。

示例流程:

  1. 用户A转到某个页面并提交表单。
  2. HTTP POST ControllerAActionMethodA调用,数据提交给DB。
  3. 卡住。
  4. 所以在第3步,我需要:

    1. 从POST'ed
    2. 的数据中提取一些信息
    3. 创建一个viewmodel
    4. 将强类型视图渲染为字符串
    5. 调用我创建的服务方法以发送SMTP电子邮件
    6. 目前,我在EmailController中有2/3/4以上,所以我希望能够使用它。

      作为旁注,我希望通过电子邮件发送异步(因为刚创建一些数据的用户并不关心其他用户是否需要通过电子邮件发送)。

      任何人都可以就如何组织这些单独关注(提交数据,将HTML视图创建为字符串,发送电子邮件)给我一些建议。

      基本控制器中的HTML帮助器或受保护的方法可能是比控制器更好的选择吗?

      仅供参考,这是我的“查看字符串”方法(我从另一个堆栈问题中提取,并且效果很好):

      protected string RenderViewToString(string viewName, object model)
      {
          if (string.IsNullOrEmpty(viewName))
              viewName = ControllerContext.RouteData.GetRequiredString("action");
      
          ViewData.Model = model;
      
          using (var sw = new StringWriter())
          {
              var viewResult = ViewEngines.Engines.FindView(ControllerContext, viewName, null);
              var viewContext = new ViewContext(ControllerContext, viewResult.View, ViewData, TempData, sw);
              viewResult.View.Render(viewContext, sw);
      
              return sw.GetStringBuilder().ToString();
          }
      }
      

1 个答案:

答案 0 :(得分:0)

您可以查看nuGet的ActionMailer包。那你就不需要一个单独的控制器了。