function readOnly(count){ }
Starting November 20, the site will be set to read-only. On December 4, 2023,
forum discussions will move to the Trailblazer Community.
+ Start a Discussion
Timothy SmithTimothy Smith 

Batch Class, AsyncApex, Send CSV file as attachment

Been working on this one for a while.  Trying to cycle through the AsyncApex and send a list of errors as a csv to an email address:  I don't believe I am attaching the file correctly (or even creating it correctly).  My code is as follows:

global class AriaBatchErrors implements Database.Batchable<sOBject>, Database.Stateful{
   
    global string excelHeader = 'ApexClassId, CompletedDate , ExtendedStatus, JobItemsProcessed, JobType, MethodName, NumberOfErrors, Status, TotalJobItems \n';
    global string finalstr = '';
   
    //constructor
    global AriaBatchErrors(){
        finalstr = excelHeader;
    }
    //start method
    global Database.QueryLocator start(Database.BatchableContext BC){
        return Database.getQueryLocator('SELECT ApexClassId, CompletedDate, ExtendedStatus, JobItemsProcessed, JobType, MethodName, NumberOfErrors, Status, TotalJobItems FROM AsyncApexJob WHERE NumberOfErrors > 0');
    }
 
    //execute
    global void execute(Database.BatchableContext BC, List<sOBject> scope){
        string recordString;
        for(sOBject a: scope){
            // Type Cast sOBject to AsyncApexJob
            AsyncApexJob asyncApexJobRecord = (AsyncApexJob) a;
           
            recordString = asyncApexJobRecord.ApexClassID +',' + asyncApexJobRecord.CompletedDate +','+ asyncApexJobRecord.ExtendedStatus+',' + asyncApexJobRecord.JobItemsProcessed + ',' + asyncApexJobRecord.JobType +  ',' + asyncApexJobRecord.MethodName + ',' + asyncApexJobRecord.NumberOfErrors + ',' + asyncApexJobRecord.TotalJobItems + ','+ asyncApexJobRecord.CreatedBy.Email + '\n';
            finalstr =+ finalstr + recordString;
         //   asyncApexJobRecord.JobItemsProcessed + ',' +asyncApexJobRecord.JobType + ',' + asyncApexJobRecord.TotalJobItems+','+ asyncApexJobRecord.CreatedBy.Email + '\n';
        }
    }
    
    //finish
    global void finish (Database.BatchableContext BC){
       
        system.debug('**** Final String *** ' + finalstr);
        //TODO: pass this string to create CSV in your CSV Method.
            String csvContent = finalstr;
                Attachment attachment = new Attachment();
                attachment.Body = Blob.valueOf(csvContent);
                attachment.Name = 'csvFile.csv';
              
                insert attachment;
       
            //TODO: Create an generic method to send emails & pass this attachment.
            
        Messaging.Singleemailmessage mail = new Messaging.Singleemailmessage();
            mail.setToAddresses((new String[] {'test@test.com'}));
            //mail.setReplyTo('noreply@privatebudget.com');
            mail.setSenderDisplayName('Batch Class Errors');
            mail.setSubject('Batch Class Errors');
            mail.setBccSender(false);
            mail.setUseSignature(false);
            mail.setPlainTextBody('This is a test');
            system.debug('@@@@ sendEmail - mail : ' + mail);
            Messaging.sendEmail(new Messaging.SingleEmailMessage[] { mail });
 
    }
}
 

I do receive an email a few minutes later, here are the contents.

Sandbox: Developer script exception from EchoSign, Inc. : 'AriaBatchErrors' for job id '7071800000gP8l4' : Insert failed. First exception on row 0; first error: REQUIRED_FIELD_MISSING, Required fields are missing: [ParentId]: [ParentId]


Sandbox

Apex script unhandled exception by user/organization: 00518000001WfNj/00D180000008oBS
Source organization: 00D300000006IaD (null)
Failed to process batch for class 'AriaBatchErrors' for job id '7071800000gP8l4'

caused by: System.DmlException: Insert failed. First exception on row 0; first error: REQUIRED_FIELD_MISSING, Required fields are missing: [ParentId]: [ParentId]

Class.AriaBatchErrors.finish: line 39, column 1

Debug Log:
40.0 APEX_CODE,DEBUG;APEX_PROFILING,FINEST;CALLOUT,FINEST;DB,FINEST;SYSTEM,FINE;VALIDATION,INFO;VISUALFORCE,FINER;WAVE,FINEST;WORKFLOW,FINER
15:54:08.0 (257958)|USER_INFO|[EXTERNAL]|00518000001WfNj|all60388@adobe.com.signstage|Pacific Standard Time|GMT-07:00
15:54:08.0 (287766)|EXECUTION_STARTED
15:54:08.0 (290789)|CODE_UNIT_STARTED|[EXTERNAL]|01p1800000062WP|AriaBatchErrors
15:54:08.0 (12257171)|SYSTEM_METHOD_ENTRY|[32]|System.debug(ANY)
15:54:08.0 (12286463)|USER_DEBUG|[32]|DEBUG|**** Final String *** ApexClassId, CompletedDate , ExtendedStatus, JobItemsProcessed, JobType, MethodName, NumberOfErrors, Status, TotalJobItems 

15:54:08.0 (12295041)|SYSTEM_METHOD_EXIT|[32]|System.debug(ANY)
15:54:08.0 (12482382)|SYSTEM_METHOD_ENTRY|[36]|Blob.valueOf(String)
15:54:08.0 (12528807)|SYSTEM_METHOD_EXIT|[36]|Blob.valueOf(String)
15:54:08.0 (12699903)|DML_BEGIN|[39]|Op:Insert|Type:Attachment|Rows:1
15:54:08.0 (12712483)|LIMIT_USAGE|[39]|DML|1|150
15:54:08.0 (12722414)|LIMIT_USAGE|[39]|DML_ROWS|1|10000
15:54:08.0 (83455960)|CODE_UNIT_STARTED|[EXTERNAL]|01q40000000Td0s|AttachmentTrigger on Attachment trigger event BeforeInsert for [new]
15:54:08.0 (83670879)|SYSTEM_METHOD_ENTRY|[13]|Limit.getLimitQueries()
15:54:08.0 (83707497)|SYSTEM_METHOD_EXIT|[13]|Limit.getLimitQueries()
15:54:08.0 (83717576)|SYSTEM_METHOD_ENTRY|[13]|Limit.getQueries()
15:54:08.0 (83724294)|SYSTEM_METHOD_EXIT|[13]|Limit.getQueries()
15:54:08.0 (83730393)|SYSTEM_METHOD_ENTRY|[13]|Limit.getLimitDmlRows()
15:54:08.0 (83735294)|SYSTEM_METHOD_EXIT|[13]|Limit.getLimitDmlRows()
15:54:08.0 (83740959)|SYSTEM_METHOD_ENTRY|[13]|Limit.getDmlRows()
15:54:08.0 (83746131)|SYSTEM_METHOD_EXIT|[13]|Limit.getDmlRows()
15:54:08.88 (88592579)|CUMULATIVE_LIMIT_USAGE
15:54:08.88 (88592579)|LIMIT_USAGE_FOR_NS|(default)|
  Number of SOQL queries: 0 out of 200
  Number of query rows: 0 out of 50000
  Number of SOSL queries: 0 out of 20
  Number of DML statements: 1 out of 150
  Number of DML rows: 1 out of 10000
  Maximum CPU time: 0 out of 60000
  Maximum heap size: 0 out of 12000000
  Number of callouts: 0 out of 0
  Number of Email Invocations: 0 out of 10
  Number of future calls: 0 out of 0
  Number of queueable jobs added to the queue: 0 out of 1
  Number of Mobile Apex push calls: 0 out of 10

15:54:08.88 (88592579)|TOTAL_EMAIL_RECIPIENTS_QUEUED|0
15:54:08.88 (88592579)|STATIC_VARIABLE_LIST|
  char[]:DigitTens:0
  long:serialVersionUID:0
  long:serialVersionUID:0
  String:_sfdcAdditionalCodeLocations:0
  double:MAX_VALUE:0
  Boolean:FALSE:0
  long:serialVersionUID:0
  double:MIN_VALUE:0
  int:SIZE:0
  double:NEGATIVE_INFINITY:0
  int:MAX_VALUE:0
  String:_sfdcAdditionalCodeLocations:0
  char[]:digits:0
  double:NaN:0
  Boolean:TRUE:0
  String:_sfdcAdditionalCodeLocations:0
  String:_sfdcSuppressedCodeLocations:0
  int:MIN_VALUE:0
  char[]:DigitOnes:0
  int:BYTES:0
  int:MIN_EXPONENT:0
  int[]:sizeTable:0
  int:MAX_EXPONENT:0
  String:_sfdcAdditionalCodeLocations:0
  String:__sfdcParameterizedTypes:0
  int:SIZE:0
  double:POSITIVE_INFINITY:0
  double:MIN_NORMAL:0
  int:BYTES:0

15:54:08.88 (88592579)|CUMULATIVE_LIMIT_USAGE_END

15:54:08.0 (89922641)|CODE_UNIT_FINISHED|AttachmentTrigger on Attachment trigger event BeforeInsert for [new]
15:54:08.0 (93268983)|DML_END|[39]
15:54:08.0 (93369881)|EXCEPTION_THROWN|[39]|System.DmlException: Insert failed. First exception on row 0; first error: REQUIRED_FIELD_MISSING, Required fields are missing: [ParentId]: [ParentId]
15:54:08.0 (93774368)|FATAL_ERROR|System.DmlException: Insert failed. First exception on row 0; first error: REQUIRED_FIELD_MISSING, Required fields are missing: [ParentId]: [ParentId]

Class.AriaBatchErrors.finish: line 39, column 1
15:54:08.113 (113740269)|CUMULATIVE_PROFILING_BEGIN
15:54:08.113 (113740269)|CUMULATIVE_PROFILING|No profiling information for SOQL operations
15:54:08.113 (113740269)|CUMULATIVE_PROFILING|No profiling information for SOSL operations
15:54:08.113 (113740269)|CUMULATIVE_PROFILING|DML operations|
Class.AriaBatchErrors.finish: line 39, column 1: Insert: Attachment: executed 1 time in 81 ms

15:54:08.113 (113740269)|CUMULATIVE_PROFILING|method invocations|
External entry point: global void finish(Database.BatchableContext): executed 1 time in 82 ms
External entry point: public void invoke(): executed 1 time in 5 ms
Class.AttachmentTriggerHandler.executeOperations: line 19, column 1: private static void onBeforeInsert(List<Attachment>): executed 1 time in 0 ms
Trigger.AttachmentTrigger: line 13, column 1: global public static Integer getLimitQueries(): executed 4 times in 0 ms
Trigger.AttachmentTrigger: line 14, column 1: public static void executeOperations(List<Attachment>, List<Attachment>, Map<Id,Attachment>, Map<Id,Attachment>, Boolean, Boolean, Boolean, Boolean, Boolean, Boolean, Boolean): executed 1 time in 0 ms
Class.AriaBatchErrors.finish: line 32, column 1: global public static void debug(ANY): executed 1 time in 0 ms
Class.AriaBatchErrors.finish: line 36, column 1: public static Blob valueOf(String): executed 1 time in 0 ms

15:54:08.113 (113740269)|CUMULATIVE_PROFILING_END



(I am just lost, thank you for any help/guidance)

 
Ajay Ghuge 6Ajay Ghuge 6
You are supposed to provide the value for the parentId field in the attachment. Usually, it is the sobject.