[SalesForce] How to test Database.Error piece code in the Scheduled job (Apex class implements Schedulable)

I have a class which implements Schedulable interface. All it does is, query some list of records and mark them as 'COMPLETE' in the end.

Class looks like following:

global class MyScheduledClass implements Schedulable{

global void execute(SchedulableContext ctx) {

// Run a SOQL to get list of records of some criteria and mark their status as complete.

List<Database.SaveResult> lstResults = Database.update(lstResultsToUpdate, false);

logErrorsIfAny(lstResults);

}

private void logErrorsIfAny(List<Database.SaveResult> lstSaveResult){
    for(Database.SaveResult aResult: lstSaveResult){
        if(aResult.isSuccess() == false){
            for (Database.Error err : aResult.getErrors()){
                System.debug('Error while updating id: '+aResult.getId()+' Message: '+err.getMessage());
            }
        }
    }
}

In the test, I am trying to run the test method as a read-only user or an integration user which has a minimal access and does not have an access to modify any data. But, I believe the running user is just putting the job in the queue and Salesforce is running the job and due to that it is not hitting the error.

Here's how my part of test class looks like:

    Test.startTest();

    User readOnlyUser = createUser();

    System.runAs(readOnlyUser){
        try{        
            String jobId = System.schedule('ScheduledApexTest', CRON_EXP, new MyScheduledClass());
        }catch(Exception e){
            System.assert(e.getMessage().contains('Error while updating save attempt id:'));
        }
    }
    Test.stopTest();

I am not sure how to test the Database.Error piece of code in the Scheduled job.

Best Answer

Place @testvisible annotation above logerrorsifany

in test class

make a record that will fire a validation rule or throw an error

put in list

use database.upsert

pass the upsert return into your now testvisible method

basically, if you use testvisible you just have to make a record fail to upsert then you can pass it to that class. Maybe you have a simpler solution, you can throw the record against a validation rule depending what you have in your system

best of luck

Related Topic