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
$$ 

Batch CPU Time limit exceeded in finish method

Hello Folks, 


I have a batch class that generates a report add it to excel as attachemnt and then sends email. 
I have checked the apex jobs and all the batches gets processed in chunks in the execute method. Like for example there are 20,000 records. I am processing in 200 and all the batches gets processed which i see in apex jobs. Now when it consolidates all the chunks into one excel spreadsheet, it is running out of CPU time limit because its taking too much time in the finish method. 

My code is below:

global class SendEmailBatcher implements Database.Batchable<sObject>, Database.Stateful{

   global List<Task__c> lstTil;
  
   global SendEmailBatcher(){
   lstTil = new List<Task__c> ();
   }

   global Database.QueryLocator start(Database.BatchableContext BC){
      return Database.getQueryLocator([select id,Item__c,  Goods__c ,Goods__r.Name, Name , Stage__c , At_Ease__c , TEO_Available__c ,Map_Stage__c ,R_Verify__c 
                    from Task__c where Stage__c !='AC-00 Tape Loaded, not in Sample' AND Stage__c !='Low' AND 
                    Item__c !='K1' and Item__c != 'Test']);
   }
   
   global void execute(Database.BatchableContext BC, List<sObject> scope){
   
   List<Task__c> Tils = (List<Task__c>)scope;
   
   for (Task__c ol: Tils) {
   lstTil.add(ol);
   }
   
   }

global void finish(Database.BatchableContext BC){
   
   try {
      
      if(!lstTil.IsEmpty()){
      String generatedCSV = ''; 
      String FileRow = '';
      
       
         FileRow = '';
         FileRow = FileRow +','+'Item';
         FileRow = FileRow +','+'TISCO';
         FileRow = FileRow +','+'TEO Number';
         FileRow = FileRow +','+'At Ease';
         FileRow = FileRow +','+'TEO Available?';
         FileRow = FileRow +','+'Map Stage';
         FileRow = FileRow +','+'Records Verify';
         FileRow = FileRow +','+'Stage';
         FileRow = FileRow.replaceFirst(',','');
         generatedCSV = generatedCSV+FileRow +'\n';
         
         for(Task__c ol: lstTil){
             
             FileRow = '';
             FileRow = FileRow +','+ol.Item__c;
             FileRow = FileRow +','+ol.Goods__r.Name;
             FileRow = FileRow +','+ol.Name;
             FileRow = FileRow +','+ol.At_Ease__c ;
             FileRow = FileRow +','+ol.TEO_Available__c ;
             FileRow = FileRow +','+ol.Map_Stage__c;
             FileRow = FileRow +','+ol.R_Verify__c ;
             FileRow = FileRow +','+ol.Stage__c ;
             FileRow = FileRow.replaceFirst(',','');
             generatedCSV = generatedCSV+FileRow +'\n';
         }
         
        Messaging.SingleEmailMessage email = new Messaging.SingleEmailMessage();
        Messaging.EmailFileAttachment efa = new Messaging.EmailFileAttachment();
           efa.setFileName('TEO Data Report.csv');
           Blob b = blob.Valueof(generatedCSV);
        efa.setBody(b);
        String[] EmailIds = Label.TEOReport.split(',');

        String[] ccAddresses=EmailIds;
        email.setFileAttachments(new Messaging.EmailFileAttachment[] {efa});
        email.setSubject('TEO Data Report');
        email.setHtmlBody('All,<br/><br/> Please find the Attached Report.<br/><br/>');
        email.setToAddresses(ccAddresses);
        if(!test.IsrunningTest()){
        Messaging.sendEmail(New Messaging.SingleEmailMessage[]{email});
        }
   }
   }
   catch (Exception Ex) {
   system.debug(Ex);
       
       Messaging.SingleEmailMessage email = new Messaging.SingleEmailMessage();
        List<string> EmailIds = new List<string>();
        EmailIds.add(userInfo.getuseremail());

        String[] ccAddresses=EmailIds;
        email.setSubject('Error In TEO Data Report');
        email.setHtmlBody('All,<br/><br/> Please find the Error.<br/><br/>'+ex.getmessage());
        email.setToAddresses(ccAddresses);
        if(!test.IsrunningTest()){
        Messaging.sendEmail(New Messaging.SingleEmailMessage[]{email});
        }
   }
   
   }
}



Something is stopping in the consolidation of different batches into one excel report. Because I see that all batches are processed in execute method.  But finish method is causing the issue.
Raj VakatiRaj Vakati
Modify it below and test it

 
global class SendEmailBatcher implements Database.Batchable<sObject>, Database.Stateful{

   global List<Task__c> lstTil;
  
  
  
   global String generatedCSV = ''; 
    global  String FileRow = '';
      
       
         FileRow = '';
         FileRow = FileRow +','+'Item';
         FileRow = FileRow +','+'TISCO';
         FileRow = FileRow +','+'TEO Number';
         FileRow = FileRow +','+'At Ease';
         FileRow = FileRow +','+'TEO Available?';
         FileRow = FileRow +','+'Map Stage';
         FileRow = FileRow +','+'Records Verify';
         FileRow = FileRow +','+'Stage';
         FileRow = FileRow.replaceFirst(',','');
         generatedCSV = generatedCSV+FileRow +'\n';
		 
		 
		 
  
  
   global SendEmailBatcher(){
   lstTil = new List<Task__c> ();
   }

   global Database.QueryLocator start(Database.BatchableContext BC){
      return Database.getQueryLocator([select id,Item__c,  Goods__c ,Goods__r.Name, Name , Stage__c , At_Ease__c , TEO_Available__c ,Map_Stage__c ,R_Verify__c 
                    from Task__c where Stage__c !='AC-00 Tape Loaded, not in Sample' AND Stage__c !='Low' AND 
                    Item__c !='K1' and Item__c != 'Test']);
   }
   
   global void execute(Database.BatchableContext BC, List<sObject> scope){
   
   List<Task__c> Tils = (List<Task__c>)scope;
   
   for (Task__c ol: Tils) {
   FileRow = '';
             FileRow = FileRow +','+ol.Item__c;
             FileRow = FileRow +','+ol.Goods__r.Name;
             FileRow = FileRow +','+ol.Name;
             FileRow = FileRow +','+ol.At_Ease__c ;
             FileRow = FileRow +','+ol.TEO_Available__c ;
             FileRow = FileRow +','+ol.Map_Stage__c;
             FileRow = FileRow +','+ol.R_Verify__c ;
             FileRow = FileRow +','+ol.Stage__c ;
             FileRow = FileRow.replaceFirst(',','');
             generatedCSV = generatedCSV+FileRow +'\n';
   }
   
   }

global void finish(Database.BatchableContext BC){
   
   try {
      
      if(!lstTil.IsEmpty()){
    
         
 
         
        Messaging.SingleEmailMessage email = new Messaging.SingleEmailMessage();
        Messaging.EmailFileAttachment efa = new Messaging.EmailFileAttachment();
           efa.setFileName('TEO Data Report.csv');
           Blob b = blob.Valueof(generatedCSV);
        efa.setBody(b);
        String[] EmailIds = Label.TEOReport.split(',');

        String[] ccAddresses=EmailIds;
        email.setFileAttachments(new Messaging.EmailFileAttachment[] {efa});
        email.setSubject('TEO Data Report');
        email.setHtmlBody('All,<br/><br/> Please find the Attached Report.<br/><br/>');
        email.setToAddresses(ccAddresses);
        if(!test.IsrunningTest()){
        Messaging.sendEmail(New Messaging.SingleEmailMessage[]{email});
        }
   }
   }
   catch (Exception Ex) {
   system.debug(Ex);
       
       Messaging.SingleEmailMessage email = new Messaging.SingleEmailMessage();
        List<string> EmailIds = new List<string>();
        EmailIds.add(userInfo.getuseremail());

        String[] ccAddresses=EmailIds;
        email.setSubject('Error In TEO Data Report');
        email.setHtmlBody('All,<br/><br/> Please find the Error.<br/><br/>'+ex.getmessage());
        email.setToAddresses(ccAddresses);
        if(!test.IsrunningTest()){
        Messaging.sendEmail(New Messaging.SingleEmailMessage[]{email});
        }
   }
   
   }
}