1

I am working on a requirement where i have to read 2 summary reports and combine them based on some logic. I am able to get the response and written that response in a map, where key is the Summary report grouping and value is a List of DTO(which have specific field values from report).

My next task involves for each key and its associated value i want to populate a VF page that will be used as an attachment to a email. So for say if i have 14 keys in the map, i have to create 14 attachment for each and 1 email for each.

I am using below code to get VF page as attachment :-

public void createAttachmentForEachGrouping(){

    ReadReportsData runReport = new ReadReportsData();

    groupingBasedMap = runReport.readReportData();

    List<Messaging.SingleEmailMessage> mails = new List<Messaging.SingleEmailMessage>();

    for(String groupingVal : groupingBasedMap.keySet()){
        mails.add(send(groupingVal ,groupingBasedMap.get(groupingVal)));

    }
    Messaging.sendEmail(mails);
}

public Messaging.SingleEmailMessage send(String grpNbr,List<FieldsToPopulateDTO> dataToPopulateOnDoc) {
    // Define the email
    Messaging.SingleEmailMessage email = new Messaging.SingleEmailMessage(); 

    // Reference the attachment page 
    PageReference wordDoc =  Page.VFPageAsAttachment;
    wordDoc.getParameters().put('grpNo',grpNbr);
    wordDoc.getParameters().put('dataToPopulateOnDoc',JSON.serialize(dataToPopulateOnDoc));

    wordDoc.setRedirect(true);
    //system.debug('PageReference+++++'+wordDoc);
    // Take the PDF content
    Blob b = wordDoc.getContent();

    // Create the email attachment
    Messaging.EmailFileAttachment efa = new Messaging.EmailFileAttachment();
    efa.setFileName('Sample.doc');
    efa.setBody(b);
    List<String> toAddresses = new List<String>{'test123@test.com'};

    // Sets the paramaters of the email
    email.setSubject( 'Subject ' );
    email.setToAddresses(toAddresses );
    email.setHtmlBody(body);

    email.setFileAttachments(new Messaging.EmailFileAttachment[] {efa});

    // Sends the email
    //Messaging.SendEmailResult [] r = Messaging.sendEmail(new Messaging.SingleEmailMessage[] {email});   

    return email;
}

The reason i am sending the 'dataToPopulateOnDoc' parameter to the VF page as a JSON string is because i didn't find any other way to pass custom list as parameter.

But I am getting below exception when the dataToPopulateOnDoc list size gets large :-

"System.VisualforceException: URL starting with 'https://XXXX--XXXX--c.cs10.visual.force.com/apex/dataasattachment?dataToPopulateOnDoc=%5B%7B'... is longer than the maximum allowed length of 4,096."

Is there any other way i can achieve the desired result? I have tried making the list as static and trying to access in the VF but it didn't worked.

Considering HTTP POST to resolve the error. But the only thing before that i want to consider is it what will be the most optimized way to implement the solution as a whole approach towards it.

Is there a better way available to implement the requirement to first read two reports, combine them and then send out emails with attachment(VF as Doc).

1

The normal solution to the limitation on the URL using a HTTP GET is to use a HTTP POST instead.

You can do this for your case via Apex's Http classes where you authenticate by passing the session ID using setHeader('Authorization', 'OAuth ' + UserInfo.getSessionId());. You will also need to allow the Visualforce domain in the remote site settings.

  • Thanks for your help Keith. I was also thinking to implement HTTP POST. But the only thing before that i want to consider is it what will be the most optimized way to implement the solution as a whole approach towards it. Is it a better way available to implement the requirement to first read two reports, combine them and then send out emails with attachment(VF as Doc). – NaveenRaw Jul 13 '15 at 12:52
0

Finally got a workaround for this. Now i am first inserting the grouping value and the List of DTO associated in a table. The table stores the map's(that I get from reading those two reports) key and associated List as a JSON.

Once i am done with the insert for these values, in my class I pass the Key as parameter to the VF page. Then in my VF page controller constructor, i do a SOQL based on that key to get the JSON and deserialize it to the List of DTO.

Thanks Keith C for your help in this.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.