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
Marc GauthierMarc Gauthier 

Test class stuck at 72% for a simple duplicate prevention trigger

Hello,

 

I wrote a trigger which prevents duplicates. The trigger is on Lead object and check if the email (Email) entered is already in use in Contact's email (Applicant_Email__c). The code is perfectly working , the problem is with test class, My test class is stuck at 72%. The code covereage is not happening  after the for loop. I tried multiple ways by inserting debug statements. The records are inserted by not modified by code. In the below code lines  highlighted in organge color is not being covered by test class.

Can anyone help me pass this test case. 

 

Trigger:

 

public without sharing class Lead_EmailDuplicatepreventer extends LeadTrigger {
public Lead_EmailDuplicatepreventer(Lead[] leadOldList, Lead[] leadNewList) {
super(leadOldList, leadNewList);
}

public override void execute() {

for(Lead LeadNew : LeadNewList){

lead leadOld = leadOld(leadNew.Id);

if ((Trigger.isInsert == true && leadNew.Email == null) || (Trigger.isUpdate == true && leadNew.Email == null) ){
return;
}


for ( Contact contacts : [select Applicant_Email__c FROM Contact where email = :LeadNew.Email]){

if (Trigger.isInsert == true && leadNew.Email == contacts.Applicant_Email__c){
System.debug ('::Lead_EmailDuplicatepreventer::==>1');
LeadNew.Email.addError('Email already in use');
}
else if (Trigger.isUpdate == true && ((leadNew.Email != leadOld.Email && leadNew.Email == contacts.Applicant_Email__c) || (leadOld.Email == null && leadNew.Email == contacts.Applicant_Email__c))){
System.debug ('::Lead_EmailDuplicatepreventer::==>2');
LeadNew.Email.addError('Email already in use');
}

}
}
}

}

 

Test Class:


@IsTest
private class Lead_EmailDuplicatePreventerTest {
public static final Country__c country = [select Id, Name from Country__c limit 1];

@IsTest
public static void test() {

Contact contacts = new Contact();
contacts.LastName = 'TestContact';
contacts.Applicant_Email__c = 'TestContact@test.com';
insert contacts;
System.debug('::Lead_EmailDuplicatePreventerTest::contact==>'+contacts.Applicant_Email__c);

Lead lead = new Lead();
lead.FirstName = 'FirstName1';
lead.LastName = 'LastName1';
lead.Company = 'Company1';
lead.Email = 'LeadContact@test.com';
lead.LeadSource = 'Alumni';
lead.Status = 'Contacted';
lead.Country_Of_Citizenship__c = country.id;
lead.Country_Of_Residence__c = country.id;
insert lead;
System.debug('::Lead_EmailDuplicatePreventerTest::contact==>'+lead.Applicant_Email__c);

lead.Email = 'TestContact@test.com';
update lead;

lead.Email = '';
update lead;

lead.Email = 'lead1@test.com';
update lead;

lead.Email = 'TestContact@test.com';
update lead;


}
}

I also tried using assertions which are failing.

 

 

 

error

 

Best Answer chosen by Admin (Salesforce Developers) 
Marc GauthierMarc Gauthier

Hi Navatar,

 

With a slight change in requirement , I had to include Contact. Email and check for duplicates against it too.

Finally i got the test case working too..

  try {
        	lead1.Email = 'TestContact@test.com';
            update lead1;
          } catch (System.dmlException e) {
        	System.debug ('Updating with duplicate email will fail as expected');
        }

 So, i had to use try and catch to update the record instead of updating directly as done previously.

 Thanks everyone !!!

All Answers

Navatar_DbSupNavatar_DbSup

Hi,


Try below code as reference of test method:


@IsTest
private class Lead_EmailDuplicatePreventerTest {
public static final Country__c country = [select Id, Name from Country__c limit 1];
@IsTest
public static void test() {

Contact contacts = new Contact();
contacts.LastName = 'TestContact';
contacts.Applicant_Email__c = 'TestContact@test.com';
insert contacts;
System.debug('::Lead_EmailDuplicatePreventerTest::contact==>'+contacts.Applicant_Email__c);

Lead lead = new Lead();
lead.FirstName = 'FirstName1';
lead.LastName = 'LastName1';
lead.Company = 'Company1';
lead.Email = 'TestContact@test.com';
lead.LeadSource = 'Alumni';
lead.Status = 'Contacted';
lead.Country_Of_Citizenship__c = country.id;
lead.Country_Of_Residence__c = country.id;
insert lead;
System.debug('::Lead_EmailDuplicatePreventerTest::contact==>'+lead.Applicant_Email__c);
Lead lead1 = new Lead();
lead1.FirstName = 'FirstName1';
lead1.LastName = 'LastName1';
lead1.Company = 'Company1';
lead1.Email = 'TestContact2@test.com';
lead1.LeadSource = 'Alumni';
lead1.Status = 'Contacted';
lead1.Country_Of_Citizenship__c = country.id;
lead1.Country_Of_Residence__c = country.id;
insert lead1;
lead1.Email = 'TestContact@test.com';
update lead1;
}
}

 

Did this answer your question? If not, let me know what didn't work, or if so, please mark it solved. 

Marc GauthierMarc Gauthier

Hi Navatar_DbSup, 

 

Thanks for the code, but it's not helping me. Can u plz tell what else I may try. Do i need to create an instance of the actual class in the test class , if so how do i do it ?

Starz26Starz26

You are missing the part where there actually is a duplicate.

 

In addition to what you have already done:

 

1. Created a second lead with the:

lead.Email = 'TestContact@test.com'

 

2. Insert that lead. It will allow the record to enter the if (Trigger.isInsert == true && leadNew.Email == contacts.Applicant_Email__c) section

Marc GauthierMarc Gauthier
@IsTest
private class Lead_EmailDuplicatePreventerTest {
public static final Country__c country = [select Id, Name from Country__c limit 1];
@IsTest
public static void test() {

Contact contacts = new Contact();
contacts.LastName = 'TestContact';
contacts.Applicant_Email__c = 'TestContact@test.com';
insert contacts;
System.debug('::Lead_EmailDuplicatePreventerTest::contact==>'+contacts.Applicant_Email__c);

Lead lead = new Lead();
lead.FirstName = 'FirstName1';
lead.LastName = 'LastName1';
lead.Company = 'Company1';
lead.Email = 'LeadContact@test.com';
lead.LeadSource = 'Alumni';
lead.Status = 'Contacted';
lead.Country_Of_Citizenship__c = country.id;
lead.Country_Of_Residence__c = country.id;
insert lead;
System.debug('::Lead_EmailDuplicatePreventerTest::contact==>'+lead.Applicant_Email__c);

Lead lead1 = new Lead();
lead1.FirstName = 'FirstName1';
lead1.LastName = 'LastName1';
lead1.Company = 'Company1';
lead1.Email = 'TestContact@test.com';
lead1.LeadSource = 'Alumni';
lead1.Status = 'Contacted';
lead1.Country_Of_Citizenship__c = country.id;
lead1.Country_Of_Residence__c = country.id;
insert lead1;
System.debug('::Lead_EmailDuplicatePreventerTest::contact==>'+lead1.Applicant_Email__c);

lead.Email = 'TestContact@test.com';
update lead;

lead.Email = '';
update lead;

lead.Email = 'lead1@test.com';
update lead;

lead.Email = 'TestContact@test.com';
update lead;

} 

 I tried inserting another lead with the same id as contact's email , it's not working. Can anyone plz tell, where am i going wrong.

Starz26Starz26

Will be watching this thread. I have never extended a trigger from an Apex class. Curious as to your need for doing so vs just instantiating the class from the trigger....

 

You issue lies with returning no results for the line:

 

for ( Contact contacts : [select Applicant_Email__c FROM Contact where email = :LeadNew.Email]){

 

Thus you do not enter the for.

 

If you system.debug the SOQL in the for statement, do you get results?

Marc GauthierMarc Gauthier

HI Startz26,

 

I inserted debug after the for statement as shown below , i am able to see the value of existing email in contact. i.e in SOQL

 

for ( Contact contacts : [select Applicant_Email__c FROM Contact where email = :LeadNew.Email]){
System.debug('::Check Contact==>::'+contacts.Applicant_Email__c);.

if (Trigger.isInsert == true && leadNew.Email == contacts.Applicant_Email__c){
System.debug ('::Lead_EmailDuplicatepreventer::==>1');
LeadNew.Email.addError('Email already in use');
}
else if (Trigger.isUpdate == true && ((leadNew.Email != leadOld.Email && leadNew.Email == contacts.Applicant_Email__c) || (leadOld.Email == null && leadNew.Email == contacts.Applicant_Email__c))){
System.debug ('::Lead_EmailDuplicatepreventer::==>2');
LeadNew.Email.addError('Email already in use');
}

Starz26Starz26

 

 

 

If you are getting to the debug, I have no Idea why you are showing that the If(trigger.isInsert line is not being covered. Even if it evaluates to false it will show as covered and the subsequent lines will show in red.

 

Can you post a screenshot of your code coverage results from the UI?

Marc GauthierMarc Gauthier

I am unable to upload the snapshot . Can i send it to your emai id please. 

Navatar_DbSupNavatar_DbSup

Hi,

Sorry forget to mention the email field value inside the contact.Try below code as reference of test method:

@IsTest
private class Lead_EmailDuplicatePreventerTest {
public static final Country__c country = [select Id, Name from Country__c limit 1];
@IsTest
public static void test() {
Contact contacts = new Contact();
contacts.LastName = 'TestContact';
contacts.Applicant_Email__c = 'TestContact@test.com';
contacts.email='TestContact@test.com';
insert contacts;
System.debug('::Lead_EmailDuplicatePreventerTest::contact==>'+contacts.Applicant_Email__c);
Lead lead = new Lead();
lead.FirstName = 'FirstName1';
lead.LastName = 'LastName1';
lead.Company = 'Company1';
lead.Email = 'TestContact@test.com';
lead.LeadSource = 'Alumni';
lead.Status = 'Contacted';
lead.Country_Of_Citizenship__c = country.id;
lead.Country_Of_Residence__c = country.id;
insert lead;
System.debug('::Lead_EmailDuplicatePreventerTest::contact==>'+lead.Applicant_Email__c);
Lead lead1 = new Lead();
lead1.FirstName = 'FirstName1';
lead1.LastName = 'LastName1';
lead1.Company = 'Company1';
lead1.Email = 'TestContact2@test.com';
lead1.LeadSource = 'Alumni';
lead1.Status = 'Contacted';
lead1.Country_Of_Citizenship__c = country.id;
lead1.Country_Of_Residence__c = country.id;
insert lead1;
lead1.Email = 'TestContact@test.com';
update lead1;
}
}

Marc GauthierMarc Gauthier

HI Navatar,

 

Thanks for ur response, the field Email does not exists on Contact. 

I also tried inserting positive and negative scenrios in different methods in the same class , but the methods which needs to enter the for loop are failing. Can anyone please help me.

Navatar_DbSupNavatar_DbSup

Hi,


We have standard filed on contact with name Email So use that field while creating creating the test record for contact. To enter inside the for loop you must have to insert a contact with email value.For more details about Contact fields please so through the link below:
https://login.salesforce.com/help/doc/en/contacts_fields.htm

Marc GauthierMarc Gauthier

Hi Navatar,

 

With a slight change in requirement , I had to include Contact. Email and check for duplicates against it too.

Finally i got the test case working too..

  try {
        	lead1.Email = 'TestContact@test.com';
            update lead1;
          } catch (System.dmlException e) {
        	System.debug ('Updating with duplicate email will fail as expected');
        }

 So, i had to use try and catch to update the record instead of updating directly as done previously.

 Thanks everyone !!!

This was selected as the best answer