- SalesforceChaCha
- Posts
- π If at first you don't succeed ... πΊ
π If at first you don't succeed ... πΊ
... then implement a retry framework! π₯
Good morning, Salesforce Nerds! Do you know how healthy πͺ your batch jobs are in your org(s)? π€
Are there super-critical jobs that run overnight you rush to check the results of first thing in the morning? π
You know the drill β¦ π·ββοΈ
Setup βΆοΈ Environments βΆοΈ Jobs βΆοΈ Apex Jobs
Search feverously for overnight batch failures. π°
Nooooooooooooo! ποΈ There were a handful of failures! Time to put on that firefighting hat - there goes your morning plans. π₯π§βππ
Ugh, this sucks. Donβt get stuck in this cycle. ππ
Truth is, thereβs always going to be a reactionary element π΅βπ« to building apps for our clients. π―
One of our jobs as Technical Architects and Developers is to mitigate this as much as possible. π§
Today weβre going to check out one way to do just that when it comes to handling exceptions in Batch Apex! πͺ£

Agenda for today includes
If at first you donβt succeed β¦
Daily Principle
All the Memes
If at first you donβt succeed β¦
Today we will discuss -
π The problem πΊ
π The solution πΊ
π Show me the code πΊ
π The Problem
First, letβs level π set on what Batch Apex is β¦
β¦ Batch Apex operates over small batches of records, covering your entire record set and breaking the processing down to manageable chunks β¦
Basically - we can write code π₯οΈ thatβs only job is to run specialized business logic against huge π data sets - think hundreds of thousands or even millions of records! π₯
It does this by breaking down ποΈ the overall data set into smaller chunks (aka batches)! π¦οΈ
Hereβs a quick visual: π

do the thing on 500k records in batches of 2000 records at a time
This is a fairly standard Batch processing workflow. π€
Got it? ποΈ If you need a little more - no worries - just hit these up:
Issues arise when batches start to fail. β
Remember, Batch Apex is a form of Asynchronous Apex. Ultimately, this means the batches run independently of one another. π
But, they can also fail independently of one another too! π
Meaning, in our example above βοΈ, itβs entirely possible for some of the batches to blow up. π₯
Giving us something like this: ποΈ
Getting back to that mitigation thing β¦ π€
These kinds of errors can be amongst the trickiest πͺ to solve. Many times requiring analysis to:
Find the records that failed ποΈ
Determine why they failed βοΈ
βFixβ the reason they failed π οΈ
Re-run the business logic against the βfixedβ records βΆοΈ
How can Architects and Developers solve for this? π§©
Turns out the mothership has provided a solution! π
π The Solution
Itβs actually pretty simple! π€¦
Itβs just another interface! π₯
Youβve herd us tout the importance of these in the past. Weβve even discussed other interfaces native to the platform you can leverage.
This is no different.
From a developerβs perspective π we just need to do 3 things:
Add this code your batch class declaration
implements Database.RaisesPlatformEventsAdd an after insert trigger to the BatchApexErrorEvent Platform Event
Process the data from the Platform Event in the trigger
Thatβs really it. π€·
Of course, the obtuse part here is what does βProcess the dataβ mean to you and your org? π€
This is up to your business and should fit your needs. Typically, I see some variation of one or all of the following: ποΈ
β Log the exception in a custom object. Thereβs lots of useful data in the event record - reason for exception, the Idβs of the records being operated on in the batch, the full stack trace, and more!
β Decorate the records that failed processing with something that will notify a user it failed. Maybe add a link to the error log record or something to the Account if it failed?
β Write another batch class that will automatically retry execution on all the failed batches that your persisted in your Custom Object!
Pretty slick stuff if you ask me! π
β No need to stress π if your batches are failing!
β No need to dig through the Setup UI π to troubleshoot!
β No need to analyze π§ tons of data to figure out why batches are failing!
π€ Show me the code
Like we said up top ποΈ , devs just need to do 3 things.
Letβs see them in an example! π Taken straight from the dev guide!
First, implement the interface in your batch class. π»οΈ This tells Salesforce to fire the Platform Event if an error happens during execution of this class:
public with sharing class YourSampleBatchJob implements Database.Batchable<SObject>,
Database.RaisesPlatformEvents{
// class implementation
}Something to note βοΈ here. There are no methods to implement from this interface - itβs whatβs known as a marker interface.
Moving on β¦ π¬οΈ
Next, create an after insert trigger on the BatchApexErrorEvent Platform Event like so and fill it in with your custom logic:
trigger MarkDirtyIfFail on BatchApexErrorEvent (after insert) {
Set<Id> asyncApexJobIds = new Set<Id>();
for(BatchApexErrorEvent evt:Trigger.new){
asyncApexJobIds.add(evt.AsyncApexJobId);
}
Map<Id,AsyncApexJob> jobs = new Map<Id,AsyncApexJob>(
[SELECT id, ApexClass.Name FROM AsyncApexJob WHERE Id IN :asyncApexJobIds]
);
List<Account> records = new List<Account>();
for(BatchApexErrorEvent evt:Trigger.new){
//only handle events for the job(s) we care about
if(jobs.get(evt.AsyncApexJobId).ApexClass.Name == 'AccountUpdaterJob'){
for (String item : evt.JobScope.split(',')) {
Account a = new Account(
Id = (Id)item,
ExceptionType__c = evt.ExceptionType,
Dirty__c = true
);
records.add(a);
}
}
}
update records;
}Here weβre just pulling data off the error event and adding some details on the original record that failed. This is where you could also log the error for later processing, too.
Weβre skipping some best practices for brevity - in the real world you wouldnβt want your code inside your trigger! π―
But, you can begin to see how useful this really is. π±
This event provides all the data we need to track and take action on our Batch Apex failures! β
So, now we can provide a full end-to-end batch solution that looks something like this: π₯³ππ₯³

implement the interface, pull data off the error event in a trigger, do the needful
Do yourself and your clients a favor. π Start planning to leverage this for any Batch Apex you implement!
Your client with love β€οΈ it and youβre solution will be that much stronger! π§±
Daily Principle
"Never allow the same bug to bite you twice."
and now....Your Daily Memes



What did you think about today's newsletter? |
