Email a Document with Salesforce.com

July 22nd, 2010

After my last post, Create and Email a PDF with Salesforce.com, I received a few comments whether it was possible to do the same with Document stored in Salesforce.com. Could you choose a Document and then send it via email as an attachment? The short answer is yes! However, I tried to do it from a Force.com Sites page but was not able to get it to work. The document is not marked for internal use and it is marked as an externally available image. I also made sure that the public settings for my Site included read access to documents but still the query for the document returns no results. No time to look at it in depth right now so if anyone has an idea, please send it my way.

DocumentEmailer Visualforce Page

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
<apex:page controller="DocumentEmailController">
  <apex:sectionHeader title="Document Example" subtitle="Email a Document" 
    description="Example of how to email a Document."/>
 
  <apex:form >
    <apex:pageMessages />
    <apex:pageBlock title="Document Input">
 
      <apex:pageBlockButtons >
        <apex:commandButton action="{!sendDoc}" value="Send Document"/>
      </apex:pageBlockButtons>
 
      <apex:pageBlockSection >
 
        <apex:pageBlockSectionItem >
            <apex:outputLabel value="Email to send to" for="email"/>
          <apex:inputText value="{!email}" id="email"/>
        </apex:pageBlockSectionItem>
 
        <apex:pageBlockSectionItem >
            <apex:outputLabel value="Document" for="document"/>
            <apex:selectList value="{!documentId}" id="document" size="1">
                 <apex:selectOptions value="{!documents}"/>
            </apex:selectList>
        </apex:pageBlockSectionItem>
 
      </apex:pageBlockSection>
 
    </apex:pageBlock>
  </apex:form>
 
</apex:page>

DocumentEmailController

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
public with sharing class DocumentEmailController {
 
  public ID documentId {get;set;}
  public String email {get;set;}
 
  public List<SelectOption> documents {
    get {
      if (documents == null) {
        documents = new List<SelectOption>();
        documents.add(new SelectOption('01570000001NZDn','Cup of Coffee? - DOC'));
        documents.add(new SelectOption('01570000001NZDi','Workflow Cheatsheet -  PDF'));
      }
      return documents;
    }
    set;
  }
 
  public PageReference sendDoc() {
 
    Document doc = [select id, name, body, contenttype, developername, type 
      from Document where id = :documentId];
 
    Messaging.EmailFileAttachment attach = new Messaging.EmailFileAttachment();
    attach.setContentType(doc.contentType);
    attach.setFileName(doc.developerName+'.'+doc.type);
    attach.setInline(false);
    attach.Body = doc.Body;
 
    Messaging.SingleEmailMessage mail = new Messaging.SingleEmailMessage();
    mail.setUseSignature(false);
    mail.setToAddresses(new String[] { email });
    mail.setSubject('Document Email Demo');
    mail.setHtmlBody('Here is the email you requested: '+doc.name);
    mail.setFileAttachments(new Messaging.EmailFileAttachment[] { attach }); 
 
    // Send the email
    Messaging.sendEmail(new Messaging.SingleEmailMessage[] { mail });
 
    ApexPages.addMessage(new ApexPages.Message(ApexPages.Severity.INFO, 'Email with Document sent to '+email));
 
    return null;
 
  }
 
}

Test Class

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
@isTest
private class Test_DocumentEmailer {
 
  static Document document;
 
  static {
 
    document = new Document();
    document.Body = Blob.valueOf('Some Text');
    document.ContentType = 'application/pdf';
    document.DeveloperName = 'my_document';
    document.IsPublic = true;
    document.Name = 'My Document';
    document.FolderId = [select id from folder where name = 'My Test Docs'].id;
    insert document;
 
  }
 
  static testMethod void testDocumentEmailer() {
 
    PageReference pref = Page.DocumentEmailer;        
    DocumentEmailController con = new DocumentEmailController();    
 
    Test.startTest();
 
    System.assertEquals(2,con.documents.size());
 
    // populate the field with values
    con.documentId = document.id;
    con.email = 'test@noemail.com';
    // submit the request
    pref = con.sendDoc();
 
    Test.stopTest(); 
 
  }
}


Categories: Apex, Code Sample, Salesforce, Visualforce

Leave a comment

Comments Feed15 Comments

  1. Mohammad Swaleh

    yay!!! Thanks a lot Jeff..This is exactly what I was looking for…
    Hope to see more great posts like this. :)

  2. Jeff Douglas

    You are welcome! Free of charge.

  3. steve

    how do i call html controls from controller?

  4. Jeff Douglas

    @Steve, can you give me an example of what you are trying to do?

  5. Ravi

    Thanks a lot Jeff.
    I am beginner of sfdc any beginner tutorial.

  6. anand

    Thanks a lot Jeff.
    am new to apex
    This code works fine for me in trail edition.
    But i tried this code in my production/developer edition it shows error in following test class line

    System.assertEquals(2,con.documents.size());
    variable does not exist:documents

  7. Sathish

    Hi Douglas
    I have used your Testclass in Salesforce developer edition. Its working fine. But the same is not working in Enterprise edition. Its showing error msg in line System.assertEquals(2,con.documents.size());
    Msg content is – Variable does not exists : documents.
    As im new to APEX, your response will be of great help for me.

  8. Jeff Douglas

    Anand, “documents” is the name of the relationship to the documents attached to the record. The name of your relationship field may be named different.

  9. Ali

    Hi,

    I have issue with sending an outbound email to more than one toaddress. Basically what I need to do is to get cCAddress from an emailMessage created linked to a case (Email to case) and send a an email out to all Cc’d people. The issue I am facing is that when there is more than one cc’d email, my code doesn’t work.

    EmailMessage[] emailMsg = [select TextBody,CcAddress,Subject from EmailMessage where parentId = :newCaseId];
    for (EmailMessage em: emailMsg){
    String Ccaddrs = em.CcAddress ;
    String[] toAddresses = Ccaddrs.split(‘;’);
    if (emailMsg.size() > 0) {
    Messaging.Singleemailmessage outboundEmail = new Messaging.Singleemailmessage();
    outboundEmail.setToAddresses(toAddresses)
    ……
    Messaging.sendEmail(new Messaging.Singleemailmessage[] {outboundEmail} );
    }

    }

    Any help much appreciated.
    Ali

  10. Lakhan

    Hi Jeff,
    I have a requirement to unzip a zip file of (more than 3 MB) in salesforce and need to store extracted files in amazon s3 storage, do you have any idea about it?

  11. Alok

    Hi Jeff,

    I need to encrypt attachements in salesforce. I got to understand that it can be achived by encryption class. But dont know how to proceed with that.

    Can you help please.

    Thansk

  12. Mayank Joshi

    Hi Jeff,

    Is it possible to call external Image Web URL through HTTP Request ?

    I am able to capture the image from URL ,saved as attachment then passed it to particular email address using APEX .

    * BUT , Attachment is corrupt file . Also, same file is not opening through Salesforce UI . I am not receiving any error .

    I have tested this behavior with PDF url with similar outcome . Like , page is opening without any content .

    Is there any limitation with Apex ?

    Also, I am a great fan of your BLOGS .

  13. Raghvendra

    Hello,
    I have to create a test class for the following class.
    pls help

    public class attachPdf{
    public Attachment att;
    public String oid{get;set;}
    Blob body;
    public attachPdf(){
    oid=apexpages.currentpage().getparameters().get(‘id’);
    att=new Attachment();
    }
    public pagereference attach(){
    pagereference pg=new pagereference(‘/’+oid);
    PageReference pdf = Page.showOpportunity;
    pdf.getParameters().put(‘id’,oid);
    try{
    body=pdf.getContent();
    }
    catch (VisualforceException e){
    System.debug(‘########## Exception Raised: ‘+e);
    }

    att.parentid=oid;
    att.name=’oppAttachment’;
    att.body = body;
    upsert att;
    return pg;
    }
    }

  14. Mani

    Hi Jeff,
    I have an requirement where I need to develop a VF wherein I need to receive an excel sheet as input from the user. Once the excel is provided, the details should be converted into records within salesforce. To be simple we need to provide the Dataloader functionality within salesforce.

    It would be helpful if u could help me out in achieving this.

  15. Jeff Douglas

    @Mani, check out developer.force.com/cookbook. I think there’s a recipe there for doing this with either Excel or CSV.

Leave a comment

Feed

http://blog.jeffdouglas.com / Email a Document with Salesforce.com

WordPress Appliance - Powered by TurnKey Linux