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
sfadm sfadmsfadm sfadm 

Business Hours test code coverage

I have an apex source code where I have plenty of if/else conditions which depend on the business hours Mon - Fri 9h - 18h settings in Salesforce.
I'm creating a test method to validate my code but because of the business hours settings the apex code enters only in few if conditions.
And I cannot reach the necessary percentage to validate my code.

Is it possible in the test method to change the business hours so that I can validate my code on 100% or is there a way to validate my code despite the fact that it is depending on the business hours?
Best Answer chosen by sfadm sfadm
Alain CabonAlain Cabon
Hi,

You can change the currentHour and startHourOfDay as you want using a block that is conditioned by the boolean Test.isRunningTest(). 

But that means a change of your tested class and not only your test class. 

You build your tested class (the one used in production) with somes lines that will be executed only during the tests.
That means also a new deployment for this tested class of course in all the sandboxes and finally production.

You can use a custom setting object if you don't want to use a custom object.

https://developer.salesforce.com/docs/atlas.en-us.apexcode.meta/apexcode/apex_methods_system_custom_settings.htm​
if(Test.isRunningTest()){
     startHourOfDay = <new value1 (ie: 9h30)>;
     currentHour = <new value2 (ie: 12h30)>;
} else {
     startHourOfDay = <the current value1 in your tested class>;
     currentHour = <the current value2>;
} 

if(startHourOfDay  < currentHour) {}

Regards

All Answers

Alain CabonAlain Cabon
Hi,

You can use the boolean Test.isRunningTest()​ in your tested class:
if (Test.isRunningTest()) {
  if (aValueOfaCreatedObjectDuringTheTest = 'val1') 
   myCurrentDateTime = <datet_time1>;
  if (aValueOfaCreatedObjectDuringTheTest = 'val2') 
   myCurrentDateTime = <datet_time2>;
....
} else {
   myCurrentDateTime = Datetime.now();
}

You can also force the created date just after the creations of objects in your test class ( Test.setCreatedDate( ... ) ) .
Account a = new Account(name='myAccount');
insert a;
Test.setCreatedDate(a.Id, DateTime.newInstance(2012,12,12));
Test.startTest();
Account myAccount = [SELECT Id, Name, CreatedDate FROM Account WHERE Name ='myAccount' limit 1];
System.assertEquals(myAccount.CreatedDate, DateTime.newInstance(2012,12,12));
Test.stopTest();
But I am not sure at all that it is your problem without seeing your source code.

Best regards
Alain
sfadm sfadmsfadm sfadm
Here is an example:
if(startHourOfDay < currentHour) {}
I compare the start working hour of the day (startHourOfDay) with the currentHour. Both variables do not depend on Object I'm working on. I still need the test code to be executed in the if and in the else conditions. Please advise how this can be achieved?

Need a way to set the current hour from the test method. 

Can you advise how this can be achieved?
 
Alain CabonAlain Cabon
Hi,

You can change the currentHour and startHourOfDay as you want using a block that is conditioned by the boolean Test.isRunningTest(). 

But that means a change of your tested class and not only your test class. 

You build your tested class (the one used in production) with somes lines that will be executed only during the tests.
That means also a new deployment for this tested class of course in all the sandboxes and finally production.

You can use a custom setting object if you don't want to use a custom object.

https://developer.salesforce.com/docs/atlas.en-us.apexcode.meta/apexcode/apex_methods_system_custom_settings.htm​
if(Test.isRunningTest()){
     startHourOfDay = <new value1 (ie: 9h30)>;
     currentHour = <new value2 (ie: 12h30)>;
} else {
     startHourOfDay = <the current value1 in your tested class>;
     currentHour = <the current value2>;
} 

if(startHourOfDay  < currentHour) {}

Regards
This was selected as the best answer