You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

ASP.NET MVC C#:表单提交后用Rotativa生成PDF并附加至自动邮件

在ASP.NET MVC中用Rotativa生成PDF并附加到确认邮件,同时跳转成功页面

核心问题是一个Action只能返回一个结果,无法同时返回PDF文件和视图页面。解决思路是先在后台生成PDF字节流,将其写入临时文件作为邮件附件发送,最后返回成功视图,具体实现如下:

完整实现代码

public ActionResult ProcessOrder(int? id)
{
    if (!id.HasValue)
    {
        return RedirectToAction("Index");
    }

    // 1. 获取订单详情(根据你的业务逻辑从数据库/数据源读取)
    var orderDetail = db.OrderDetails.FirstOrDefault(o => o.OrderID == id.Value);
    if (orderDetail == null)
    {
        return HttpNotFound();
    }

    string orderPdfFileName = $"FulfillmentOrder{orderDetail.OrderID}.pdf";
    byte[] pdfContent = null;
    string tempPdfPath = string.Empty;
    string errorMessage = string.Empty;

    try
    {
        // 2. 使用Rotativa生成PDF字节流(不直接返回,而是自行处理内容)
        var pdfGenerator = new ActionAsPdf("OrderReportPDF", new { id = orderDetail.OrderID })
        {
            FileName = orderPdfFileName
        };
        pdfContent = pdfGenerator.BuildFile(ControllerContext);

        // 3. 将PDF字节流写入临时文件(WebMail.Send需要文件路径作为附件)
        tempPdfPath = Path.Combine(Path.GetTempPath(), orderPdfFileName);
        System.IO.File.WriteAllBytes(tempPdfPath, pdfContent);

        // 4. 发送带附件的确认邮件
        var emailSubject = $"Order Confirmation #{orderDetail.OrderID}";
        var recipientEmail = "john.doe@example.com"; // 替换为实际用户邮箱
        var emailBody = "Your order has been placed and is pending review. Attached is a copy of your order.";

        // 初始化SMTP配置(根据你的实际邮件服务器调整)
        WebMail.SmtpServer = "abc.net";
        WebMail.SmtpPort = 555;
        WebMail.UserName = "your-smtp-username@samplecode.com"; // 注意:这里应该是SMTP服务器的认证账号,不是收件人
        WebMail.Password = "your-smtp-password";
        WebMail.From = "orders@samplecode.com";

        // 发送邮件
        WebMail.Send(
            to: recipientEmail,
            subject: emailSubject,
            body: emailBody,
            filesToAttach: new[] { tempPdfPath }
        );
    }
    catch (Exception ex)
    {
        errorMessage = ex.Message;
        // 可选:记录错误日志,或者返回错误提示视图
    }
    finally
    {
        // 5. 清理临时PDF文件,避免磁盘空间浪费
        if (!string.IsNullOrEmpty(tempPdfPath) && System.IO.File.Exists(tempPdfPath))
        {
            try
            {
                System.IO.File.Delete(tempPdfPath);
            }
            catch { /* 忽略删除失败的情况,比如文件被临时占用 */ }
        }
    }

    // 6. 清除购物车会话并返回成功页面
    Session.Remove("strCart"); // 替换为你实际的购物车会话键
    return View("OrderSuccess");
}

关键说明

  1. 使用BuildFile方法生成字节流:
    Rotativa的ActionAsPdf提供了BuildFile方法,传入当前ControllerContext即可生成PDF的字节数组,这样就不需要返回ActionAsPdf对象,而是可以自行处理生成的内容。

  2. 临时文件处理:
    因为WebMail.Send的filesToAttach参数只能接收文件路径,所以我们把PDF字节流写入系统临时目录的文件中,邮件发送完成后在finally块中删除该文件,避免磁盘堆积。

  3. SMTP配置注意:
    你原代码中WebMail.UserName使用了收件人邮箱,这通常是错误的——这里应该填写SMTP服务器的认证账号(比如发件人邮箱的账号),请根据你的邮件服务提供商的配置调整。

  4. 权限问题:
    部署到IIS时,确保应用程序池身份有写入系统临时目录的权限,否则无法创建临时PDF文件。

内容的提问来源于stack exchange,提问作者Kip M.

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.19 09:55:23