2015-10-13 56 views
0

这是我的代码块。它编译得很好,当我关闭事件我收到电子邮件,但我然后得到这个错误 电子邮件附件错误在Adobe打开时(Acrobat无法打开'Att00002.pdf',因为它不是支持的文件类型或因为该文件已被损坏(例如,它被发送作为电子邮件的附件和wasnt正确地解码。)试图使用PdfStamper和MemoryStream将数据添加到现有的PDF然后发电子邮件

string agentName = "My Name";    
MemoryStream _output = new MemoryStream(); 
      PdfReader reader = new PdfReader("/pdf/Agent/Specialist_Certificate.pdf"); 
      using (PdfStamper stamper = new PdfStamper(reader, _output)) 
      { 
       AcroFields fields = stamper.AcroFields; 
      // set form fields 
      fields.SetField("FIELD_AGENT_NAME", agentName); 
      fields.SetField("FIELD_DATE", AvalonDate); 

      // flatten form fields and close document 
      stamper.FormFlattening = true; 
      SendEmail(_output); 
      DownloadAsPDF(_output); 
      stamper.Close(); 
     } 

private void SendEmail(MemoryStream ms) 
{ 
    Attachment attach = new Attachment(ms, new System.Net.Mime.ContentType("application/pdf")); 
    EmailHelper.SendEMail("[email protected]", "[email protected]", null, "", "Avalon Cert", "Hope this works", EmailHelper.EmailFormat.Html,attach); 
} 

EDITED ******************* ******************

 using (MemoryStream _output = new MemoryStream()) 
     { 
      using (PdfStamper stamper = new PdfStamper(reader, _output)) 
      { 
       AcroFields fields = stamper.AcroFields; 
       // set form fields 
       fields.SetField("FIELD_AGENT_NAME", agentName); 
       fields.SetField("FIELD_DATE", AvalonDate); 

       // flatten form fields and close document 
       stamper.FormFlattening = true; 
      } 
      SendEmail(_output); 
     } 
+0

尝试调用'SendEmail'之前关闭'PdfStamper'。您可能只附加了PDF字节流的一部分,因为并非所有内容都被刷新为输出。 – rhens

+0

当我将其更改为stamper.Close(); SendEmail(_output);发送电子邮件时出现此错误 System.ObjectDisposedException:无法访问已关闭的流 – user1566783

回答

2

你调用stamper.close()using (PdfStamper stamper = new PdfStamper(reader, _output))内。该using将部门自动化除了手动关闭()之外,在关闭压模后关闭压模,因此在技术上压模试图关闭两次。正因为如此,它也试图不止一次关闭MemoryStream。这是例外来自的地方。

我会用设在这里的答案技术的MemoryStreamPdfStamper(修改,摘自:Getting PdfStamper to work with MemoryStreams (c#, itextsharp)):

using (MemoryStream _output = new MemoryStream()) { 
    using (PdfStamper stamper = new PdfStamper(reader, _output)) { 
// do stuff  
    }  
} 
+2

我同意这一点,但我会更进一步,主张kuujinbo的完整模式,我也一直使用它,这就是返回一个字节数组流。如果您稍后需要流,则只需将新数组包装到字节数组中。是的,这里有一些额外的CPU周期,但实际上并不多。流经周围的问题正是UncleRico指向的问题,也就是说其他人可以通过关闭他们或设置职位或其他方式来惹恼他们。 –

+0

好的,我会在哪里放我的SendEmail(_output);大块呢?如果我把它放在使用PdfStamper之外,我会得到一个错误,说明流已经关闭。 – user1566783

+0

@ user1566783我会主张先创建加盖的pdf,然后使用上面的代码作为模板关闭它。然后作为辅助进程使用您的'SendEmail()'方法将其附加到您的电子邮件中。请记住,在一种情况下,您的MemoryStream正在用于写入信息,您的附件进程正在使用同一个MemoryStream从中读取(这不是一件好事)。 –

相关问题