I am receiving the following error when I run the below apex invocable method in my flow:
An Apex error occurred: System.CalloutException: You have uncommitted work pending. Please commit or rollback before calling out
I believe what is happening here is that As of Winter '16, the PageReference getContent() method is treated as a callout.
I am struggling to understand how I can perform this action in a future context. My idea is to set the entire invocable method in a future context, but I am not sure if that is the best solution here.
/**
* @description :
* @author : ChangeMeIn@UserSettingsUnder.SFDoc
* @group :
* @last modified on : 05-18-2022
* @last modified by : ChangeMeIn@UserSettingsUnder.SFDoc
**/
global class SendAdvancedEmail {
@InvocableMethod(label='Send Advanced Email')
global static List <Results> SendAdvancedEmail(List<Requests> requests) {
List<Results> results = new List<Results>();
List<Messaging.SingleEmailMessage> singleEmailList = new List<Messaging.SingleEmailMessage>();
for (Requests curRequest : requests)
{
Set<Id> contentDocumentIds = new Set<Id>();
Set<Id> reportIds = new Set<Id>();
Messaging.SingleEmailMessage mail = new Messaging.SingleEmailMessage();
List<Messaging.EmailFileAttachment> attachments = new List<Messaging.EmailFileAttachment>();
if (curRequest.reports != null)
{
for (Report report : curRequest.reports)
{
reportIds.add(report.Id);
}
// Add reports as attchments
attachments.addAll(addReportsAsEmailAttachment(reportIds));
}
// Create a new single email message object
// that will send out a single email to the addresses in the To, CC & BCC list.
// Assign the addresses for the To and CC lists to the mail object.
mail.setToAddresses(curRequest.toAddresses);
mail.setCcAddresses(curRequest.ccAddresses);
mail.setBccAddresses(curRequest.bccAddresses);
mail.setSenderDisplayName(curRequest.senderDisplayName);
mail.setReplyTo(curRequest.replyEmailAddress);
mail.setSubject(curRequest.subject);
mail.setReplyTo(curRequest.replyEmailAddress);
mail.setHtmlBody(curRequest.HTMLbody);
mail.setPlainTextBody(curRequest.plainTextBody);
singleEmailList.add(mail);
}
if (singleEmailList != null && singleEmailList.size() > 0)
{
Results result = new Results();
List<Messaging.SendEmailResult> emailResults = new List<Messaging.SendEmailResult>();
emailResults = Messaging.sendEmail(singleEmailList, false);
for(Messaging.SendEmailResult emailResult : emailResults)
{
if(!emailResult.IsSuccess())
{
result.isSuccess = false;
List<Messaging.SendEmailError> errors = emailResult.getErrors();
if (errors.size() > 0){
result.errors = errors[0].getMessage();
result.statusCode = String.valueOf(errors[0].getStatusCode());
result.fields = errors[0].getFields();
}
} else{
result.isSuccess = true;
}
}
}
return results;
}
global static List<Messaging.EmailFileAttachment> addReportsAsEmailAttachment(Set<Id> reportIDs)
{
List<Report> reportList = [SELECT Id,DeveloperName,Name FROM Report where Id in :reportIDs];
String reportId = (String)reportList.get(0).get('Id');
//Get Report Name
string reportName=(String)reportList.get(0).get('Name');
//get instance Url
String instanceName = URL.getSalesforceBaseUrl().toExternalForm();
string url=instanceName+'/servlet/PrintableViewDownloadServlet?isdtp=p1&reportId='+reportId;
ApexPages.PageReference objPage = new ApexPages.PageReference(url);
Messaging.SingleEmailMessage email=new Messaging.SingleEmailMessage();
Messaging.EmailFileAttachment objMsgEmailAttach = new Messaging.EmailFileAttachment();
objMsgEmailAttach.setFileName(reportName+'.csv');
if(Test.isRunningTest()) {
objMsgEmailAttach.setBody(blob.valueOf('Unit.Test'));
}else{
objMsgEmailAttach.setBody(objPage.getContent());
}
objMsgEmailAttach.setContentType('text/csv');
List<Messaging.EmailFileAttachment> attachments=new List<Messaging.EmailFileAttachment>();
attachments.add(objMsgEmailAttach);
return attachments;
}
global class Requests {
@invocableVariable(label='To Addresses' required=true)
global String[] toAddresses;
@invocableVariable(label='CC Addresses' )
global String[] ccAddresses;
@invocableVariable(label='BCC Addresses' )
global String[] bccAddresses;
@invocableVariable(label='Subject' required=true)
global String subject;
@invocableVariable(label='Email HTML Body')
global String HTMLbody;
@invocableVariable(label='Email Plain Text Body')
global String plainTextBody;
@invocableVariable(label='Sender Display Name' )
public String senderDisplayName;
@invocableVariable(label='Sender Email Address' required=true)
public String senderEmailAddress;
@invocableVariable(label='Reply Email Address')
public String replyEmailAddress;
@invocableVariable(label='List of Content Documents (NOT CURRENTLY IN USE)')
global List<ContentDocumentLink> contentDocuments;
@invocableVariable(label='List of Reports')
global List<Report> reports;
}
global class Results {
@InvocableVariable(label='Succesfully Sent')
global boolean isSuccess;
@invocableVariable(label='Error Messages')
public String errors;
@invocableVariable(label='Status Code')
public String statusCode;
@invocableVariable(label='Error Fields')
public List<String> fields;
}
}