• SubC4i-dev1
  • NEWBIE
  • 0 Points
  • Member since 2013

  • Chatter
    Feed
  • 0
    Best Answers
  • 0
    Likes Received
  • 0
    Likes Given
  • 5
    Questions
  • 12
    Replies

I've created a checkbox for the User page layout to send out a custom new user email.  The goal is to send out the email when the checkbox is true, deploy the email, and then uncheck the box.  I've got everything working in before update, but I cannot get it working for insert.  I need to use After Insert to deploy the email because the email template I created in the apex class needs to be passed user field info (pass the User Id, name, email, etc).  If I uncheck the box in the before insert, then the criteria to fire the after insert will no longer exist.  I even tried making the method that unchecks the box @future, but that didn't work.  I would prefer to create another component like a workflow that would fire after the triggers due to SFDC order of execution.  Want a clean all apex solution for this.

 

This seems like a simple process, but I'm stuck at the moment.  Any help would be greatly appreciated.

I have a trigger with recursive control that performs both Before Insert and Before Update, but I cannot figure out how to test the Before Update in my test class.  When I insert the test data in my unit test, the recursive variable is set to true and will block my update from setting off the trigger.  This is only desirable for when it runs in production, but not when I need to insert data in order to test situations where existing data is being updated.  I even tried inserting the test data above the test.startTest() line.  But this does not matter since every action in the test method occurs in the same context.

 

How do I write my test class to cover this?

 

 

Trigger code: 

 

trigger PriceModifierTrigger on OpportunityLineItem (before insert, before update) {

	if(!PriceModifierClass.hasAlreadyRunMethod()){
		if(trigger.isBefore && trigger.isInsert){
			PriceModifierClass.sortOppProducts(trigger.new, trigger.oldMap, 'Insert');
		}
		if(trigger.isBefore && trigger.isUpdate){
			PriceModifierClass.sortOppProducts(trigger.new, trigger.oldMap, 'Update');
		}
		PriceModifierClass.setAlreadyRunMethod();	
	}
}

 

 

Excerpt from class:

public static boolean hasAlreadyRun = false;
	
	public static boolean hasAlreadyRunMethod(){
		return hasAlreadyRun;
	}
	
	public static void setAlreadyRunMethod(){
		hasAlreadyRun = true;
	}

 

Having trouble understanding why my code is giving me the error below.  I have a feeling it's obvious, but I'm baffled nonetheless.  Trying to use getsobjectype in my if statement to verify that the lead owner is a user (i.e. to exclude queues).


Save error: Comparison arguments must be compatible types: SOBJECT:Lead, Id

 

Trouble line of code:

 

if(l.Lead_Stage__c.contains('Engaged') && l.Status.contains('Team Contribution') && userMap.get(l.OwnerId).Profile.Name.contains('LDR')
&& l.OwnerId.getSobjectType()==user.sObjectType && oldMap.get(l.OwnerId) == LDRmanagerQueue.Id)

 

Rest of that section of code:

 

public static void updateLDRlead(List<Lead> newList, Map<Id,Lead> oldMap){
		
		List<Lead> leadsToBeProcess = new List<Lead>();
		
		for(Lead l: newList){
			
			Lead oldL = oldMap.get(l.Id);
			leadOwnerIds.add(l.ownerId);
			leadOwnerIds.add(oldL.ownerId);
			
			if(l.Meets_LDR_Process_Criteria__c == true && l.Remove_from_LDR_Program__c == false){
				//Add to list of leads currently in the LDR Program
				leadsToBeProcess.add(l);
				
				//Set Record Type
				l.RecordTypeId = LDRrecord.Id;
				
				//Set Status to Nurture when entering the program
				if(oldL.Meets_LDR_Process_Criteria__c == false && l.Meets_LDR_Process_Criteria__c == true){
					l.Status = 'Nurture';
				}
				
				//Default Inquiry/Nuture to Lead Development Queue
				if(l.Lead_Stage__c == 'Inquiry' && l.Status == 'Nurture'){
					l.OwnerId = LDRmanagerQueue.Id;
				}
				
				//Stage is Engaged, Status is Team Contribution, and Owner changes LDR Manager Queue --> LDR
				if(l.Lead_Stage__c.contains('Engaged') && l.Status.contains('Team Contribution') && userMap.get(l.OwnerId).Profile.Name.contains('LDR') 
				&& l.OwnerId.getSobjectType()==user.sObjectType && oldMap.get(l.OwnerId) == LDRmanagerQueue.Id){
				}
				
			}
		}
	}

 

Thanks in advance for any assistance!

I have written the below for a trigger that I'm working on and both seem to produce the desired result.  Based on what I've learned they are two best pracitce ways to use SOQL queries.  But can someone please help me understand why I wouldn't want to just use the version with the SOQL For Loop almost all the time? (since it can help can avoid governor limits)

 

Version 1: SOQL List

 

List<OpportunityLineItem> OppProducts = new List<OpportunityLineItem>([SELECT Id, OpportunityId, PricebookEntryId, Post_Sale_Project__c FROM OpportunityLineItem WHERE OpportunityId IN: OppIds]);
		system.debug('OppProducts list size : ' + String.valueof(OppProducts.size()));
		
		for(OpportunityLineItem oli: OppProducts){
			if(psp.Opportunity__c == oli.OpportunityId){
				ResetOppProducts.put(oli.Id, new OpportunityLineItem(Id=oli.Id, OpportunityId = psp.Opportunity__c, Post_Sale_Project__c = null));
				UpdateOppProducts.put(oli.Id, new OpportunityLineItem(Id=oli.Id, OpportunityId = psp.Opportunity__c, Post_Sale_Project__c = psp.Id));
				system.debug('Post Sale Project Opportunity__c : ' + psp.Opportunity__c);
				system.debug('OpportunityLineItem OpportunityId : ' + oli.OpportunityId);
				system.debug('OpportunityLineItem Id : ' + oli.Id);
				system.debug('OpportunityLineItem ProductId : ' + oli.PricebookEntryId);
				system.debug('OpportunityLineItem Post Sales Project : ' + oli.Post_Sale_Project__c);
			}
		}

 

Version 2: SOQL List in For Loop

 

for(List<OpportunityLineItem> OppProducts: [SELECT Id, OpportunityId, PricebookEntryId, Post_Sale_Project__c FROM OpportunityLineItem WHERE OpportunityId IN: OppIds]){
			for(OpportunityLineItem oli: OppProducts){
				if(psp.Opportunity__c == oli.OpportunityId){
					ResetOppProducts.put(oli.Id, new OpportunityLineItem(Id=oli.Id, OpportunityId = psp.Opportunity__c, Post_Sale_Project__c = null));
					UpdateOppProducts.put(oli.Id, new OpportunityLineItem(Id=oli.Id, OpportunityId = psp.Opportunity__c, Post_Sale_Project__c = psp.Id));
				}
			}
		}

 

Thanks in advance for your help!

 

I'm new to writing apex triggers and I need some help cleaning up the SOQL queries in my collections.  Not sure what is wrong, but it just looks like too much.  Also, I'm sure it's part of what is giving me issues when I try to write a test class.

 

Thanks in advance!

 

- Matt

 

Apex Trigger:

 

trigger LDRCreatedTask on Task (after insert, after update, before delete) {

//Insert or Update command
if(trigger.isInsert || trigger.isUpdate){

	List<Task> TargetTask = [SELECT Id, WhoId, CreatedById 
							 FROM Task 
							 WHERE Id IN: Trigger.newMap.keySet()];
	
	Task TargetTaskDetails = [SELECT Id, WhoId, CreatedById 
							  FROM Task 
							  WHERE Id IN: TargetTask];
	
	Map<Id,User> UserMap = new Map<Id,User>([SELECT Id, Name, Profile.Name 
											 FROM User 
											 WHERE Id = :TargetTaskDetails.CreatedById AND isActive = true]);

	Lead ParentLead = [SELECT Id, First_LDR_Task_User__c, First_LDR_Task_Date__c 
					   FROM Lead 
					   WHERE Id = :TargetTaskDetails.WhoId];


	List<Task>LDRRelatedTasks = [SELECT Id, WhoId, CreatedBy.Profile.Name 
								 FROM Task 
								 WHERE WhoId = :ParentLead.Id AND CreatedBy.Profile.Name LIKE'%LDR%'];
							 
	List<Task> FirstTask = [SELECT Id, CreatedBy.Name, CreatedDate
							FROM Task
							WHERE Id IN: LDRRelatedTasks
							ORDER BY LastModifiedDate ASC LIMIT 1];

		Task FirstTaskDetails = [SELECT Id, CreatedBy.Name, CreatedDate
							 	FROM Task
							 	WHERE Id IN: FirstTask];	

	Map<Id,Lead> LeadstoUpdate = new Map<Id,Lead>();

for (Task t: TargetTask){

	//Update 'Most Recent' fields after each insert and everytime an existing task is modified
	if(UserMap.get(t.CreatedById).ProfileId != null 
		&& UserMap.get(t.CreatedById).Profile.Name.contains('LDR') 
		&& t.WhoId != null 
		&& (((String)t.WhoId).startswith('00Q'))){
			Lead l = new Lead(Id = t.WhoId, Most_Recent_LDR_Task_User__c = UserMap.get(t.CreatedById).Name, Most_Recent_LDR_Task_Date__c = System.now() ); 
			LeadstoUpdate.put(l.Id, l);		
			
			//Run if 1 or more LDR tasks
			if(FirstTask.size() > 0){
				if(ParentLead.First_LDR_Task_User__c == null && ParentLead.First_LDR_Task_Date__c == null){
					l.First_LDR_Task_User__c = FirstTaskDetails.CreatedBy.Name;
					l.First_LDR_Task_Date__c = FirstTaskDetails.CreatedDate;
					LeadstoUpdate.put(l.Id, l);
				}
			}
			
			//Run if 0 LDR tasks
			if(FirstTask.size() == 0){
				if(ParentLead.First_LDR_Task_User__c == null && ParentLead.First_LDR_Task_Date__c == null){
					l.First_LDR_Task_User__c = UserMap.get(t.CreatedById).Name;
					l.First_LDR_Task_Date__c = System.now();
					LeadstoUpdate.put(l.Id, l);
				}
			}
	}
	
}

update LeadstoUpdate.values();

}


if(trigger.isBefore && trigger.isDelete){

	List<Task> TargetTask = [SELECT Id, WhoId, CreatedById 
							 FROM Task 
							 WHERE Id IN: Trigger.oldMap.keySet()];
	
	Task TargetTaskDetails = [SELECT Id, WhoId, CreatedById 
							  FROM Task 
							  WHERE Id IN: TargetTask];
	
	Map<Id,User> UserMap = new Map<Id,User>([SELECT Id, Name, Profile.Name 
											 FROM User 
											 WHERE Id = :TargetTaskDetails.CreatedById AND isActive = true]);

	Lead ParentLead = [SELECT Id, First_LDR_Task_User__c, First_LDR_Task_Date__c 
					   FROM Lead 
					   WHERE Id = :TargetTaskDetails.WhoId];


	List<Task>LDRRelatedTasks = [SELECT Id, WhoId, CreatedBy.Profile.Name 
								 FROM Task 
								 WHERE WhoId = :ParentLead.Id AND CreatedBy.Profile.Name LIKE'%LDR%'];
							 
	List<Task> FirstTask = [SELECT Id, CreatedBy.Name, CreatedDate
							FROM Task
							WHERE Id IN: LDRRelatedTasks AND Id NOT IN: TargetTask
							ORDER BY LastModifiedDate ASC LIMIT 1];

	List<Task> MostRecentTask = [SELECT Id, CreatedBy.Name 
									 FROM Task 
									 WHERE Id IN: LDRRelatedTasks AND Id NOT IN: TargetTask
									 ORDER BY LastModifiedDate DESC LIMIT 1];

	Map<Id,Lead> LeadstoUpdateFirst = new Map<Id,Lead>();
	Map<Id,Lead> LeadstoUpdateMostRecent = new Map<Id,Lead>();	

for(Task t: TargetTask){
		
	//Run when all LDR tasks have been deleted
	if(LDRRelatedTasks.size() < 2){
		if(UserMap.get(t.CreatedById).ProfileId != null 
		&& UserMap.get(t.CreatedById).Profile.Name.contains('LDR') 
		&& t.WhoId != null
		&& (((String)t.WhoId).startswith('00Q'))){
			//Reset 'Most Recent' fields on lead
			Lead l = new Lead (Id = t.WhoId, Most_Recent_LDR_Task_User__c = null, Most_Recent_LDR_Task_Date__c = null);
			LeadstoUpdateMostRecent.put(l.Id, l);
		}
	}
	

	//Run when there are 1 or more LDR tasks
	if(LDRRelatedTasks.size() > 1) {
		Task MostRecentTaskDetails = [SELECT Id, CreatedBy.Name, LastModifiedDate
									  FROM Task 
									  WHERE Id IN: MostRecentTask];
		if(UserMap.get(t.CreatedById).Profile.Name.contains('LDR') && (((String)t.WhoId).startswith('00Q'))){
			//Update 'Most Recent' fields on lead			
			Lead l = new Lead (Id = t.WhoId, Most_Recent_LDR_Task_User__c = MostRecentTaskDetails.CreatedBy.Name, Most_Recent_LDR_Task_Date__c = MostRecentTaskDetails.LastModifiedDate);
			LeadstoUpdateMostRecent.put(l.Id, l);
		}	
	}
		
	//Run when there is no first LDR task - no LDR tasks on the lead record (all deleted)
	if(FirstTask.size() < 2){ 
			//Reset 'First' fields on lead			
			Lead l = new Lead(Id = t.WhoId, First_LDR_Task_User__c = null, First_LDR_Task_Date__c = null);
			LeadstoUpdateFirst.put(l.Id, l);
	}
	
	//Run when there is a first(oldest) LDR task on the lead record
	if(FirstTask.size() > 0){
		Task FirstTaskDetails = [SELECT Id, CreatedBy.Name, CreatedDate
								 FROM Task
							 	 WHERE Id IN: FirstTask];			
			//Update 'First' fields on lead		
			Lead l = new Lead(Id = t.WhoId, First_LDR_Task_User__c = FirstTaskDetails.CreatedBy.Name, First_LDR_Task_Date__c = FirstTaskDetails.CreatedDate);
			LeadstoUpdateFirst.put(l.Id, l);
	}
}

update LeadstoUpdateFirst.values();
update LeadstoUpdateMostRecent.values();

}

}

 

I've created a checkbox for the User page layout to send out a custom new user email.  The goal is to send out the email when the checkbox is true, deploy the email, and then uncheck the box.  I've got everything working in before update, but I cannot get it working for insert.  I need to use After Insert to deploy the email because the email template I created in the apex class needs to be passed user field info (pass the User Id, name, email, etc).  If I uncheck the box in the before insert, then the criteria to fire the after insert will no longer exist.  I even tried making the method that unchecks the box @future, but that didn't work.  I would prefer to create another component like a workflow that would fire after the triggers due to SFDC order of execution.  Want a clean all apex solution for this.

 

This seems like a simple process, but I'm stuck at the moment.  Any help would be greatly appreciated.

Dear Gurus,

 

I have a trigger that I am doing some summary counts on some lookup records(non master detail). My trigger processes fine with the trigger.new records. I am having trouble properly running the same process against a value in the trigger.old context. Since the trigger does not persist to the database prior to the entire trigger completion, I think my aggregate results are the same for both calls to the trigger utility class. How can I process the trigger.old request(second line in the trigger) against the records after they have updated. I am trying to update/refresh the old record count on the Trailer object with the correct count value after the new records are updated. Any help is appreciated....current code is below:

 

trigger ManifestUpdateTrailerContainerInfo on Manifest__c (after delete, after undelete, after update) {

    ManifestContainerInfoTriggerUtil.updateContainerCounts(Trigger.New);
     ManifestContainerInfoTriggerUtil.updateContainerCounts(Trigger.Old);

}

 

 

public with sharing class ManifestContainerInfoTriggerUtil {
    
    public static void updateContainerCounts(List<Manifest__c> lstManifest)    {
        
        Integer containerCount = 0;
        id trailerToUpdate;
        List<Trailer__c> lstTrailersToUpdate = new List<Trailer__c>();
    
        //new trailer collection
        Set<Id> ids = new Set<Id>();
    
          for (Manifest__c mf : lstManifest) {
              ids.add(mf.id);
          }
          
        //new counts
        AggregateResult[] counts = [SELECT Manifest__c ,count(id)containers FROM Container__c WHERE Manifest__c IN :ids GROUP BY Manifest__c];
        
        for(AggregateResult ar : counts){
            for(Manifest__c m: lstManifest){
                if(ar.get('Manifest__c') == m.Id && m.Trailer__c != null) {
                     trailerToUpdate = m.Trailer__c;
                    containerCount = integer.valueof(ar.get('containers'));
                    lstTrailersToUpdate.add(new Trailer__c(Id=trailerToUpdate, Container_Count__c = containerCount));
                }
            }
        }
        update lstTrailersToUpdate;
    }
        
}

 

  • November 07, 2013
  • Like
  • 0

I have a trigger with recursive control that performs both Before Insert and Before Update, but I cannot figure out how to test the Before Update in my test class.  When I insert the test data in my unit test, the recursive variable is set to true and will block my update from setting off the trigger.  This is only desirable for when it runs in production, but not when I need to insert data in order to test situations where existing data is being updated.  I even tried inserting the test data above the test.startTest() line.  But this does not matter since every action in the test method occurs in the same context.

 

How do I write my test class to cover this?

 

 

Trigger code: 

 

trigger PriceModifierTrigger on OpportunityLineItem (before insert, before update) {

	if(!PriceModifierClass.hasAlreadyRunMethod()){
		if(trigger.isBefore && trigger.isInsert){
			PriceModifierClass.sortOppProducts(trigger.new, trigger.oldMap, 'Insert');
		}
		if(trigger.isBefore && trigger.isUpdate){
			PriceModifierClass.sortOppProducts(trigger.new, trigger.oldMap, 'Update');
		}
		PriceModifierClass.setAlreadyRunMethod();	
	}
}

 

 

Excerpt from class:

public static boolean hasAlreadyRun = false;
	
	public static boolean hasAlreadyRunMethod(){
		return hasAlreadyRun;
	}
	
	public static void setAlreadyRunMethod(){
		hasAlreadyRun = true;
	}

 

Having trouble understanding why my code is giving me the error below.  I have a feeling it's obvious, but I'm baffled nonetheless.  Trying to use getsobjectype in my if statement to verify that the lead owner is a user (i.e. to exclude queues).


Save error: Comparison arguments must be compatible types: SOBJECT:Lead, Id

 

Trouble line of code:

 

if(l.Lead_Stage__c.contains('Engaged') && l.Status.contains('Team Contribution') && userMap.get(l.OwnerId).Profile.Name.contains('LDR')
&& l.OwnerId.getSobjectType()==user.sObjectType && oldMap.get(l.OwnerId) == LDRmanagerQueue.Id)

 

Rest of that section of code:

 

public static void updateLDRlead(List<Lead> newList, Map<Id,Lead> oldMap){
		
		List<Lead> leadsToBeProcess = new List<Lead>();
		
		for(Lead l: newList){
			
			Lead oldL = oldMap.get(l.Id);
			leadOwnerIds.add(l.ownerId);
			leadOwnerIds.add(oldL.ownerId);
			
			if(l.Meets_LDR_Process_Criteria__c == true && l.Remove_from_LDR_Program__c == false){
				//Add to list of leads currently in the LDR Program
				leadsToBeProcess.add(l);
				
				//Set Record Type
				l.RecordTypeId = LDRrecord.Id;
				
				//Set Status to Nurture when entering the program
				if(oldL.Meets_LDR_Process_Criteria__c == false && l.Meets_LDR_Process_Criteria__c == true){
					l.Status = 'Nurture';
				}
				
				//Default Inquiry/Nuture to Lead Development Queue
				if(l.Lead_Stage__c == 'Inquiry' && l.Status == 'Nurture'){
					l.OwnerId = LDRmanagerQueue.Id;
				}
				
				//Stage is Engaged, Status is Team Contribution, and Owner changes LDR Manager Queue --> LDR
				if(l.Lead_Stage__c.contains('Engaged') && l.Status.contains('Team Contribution') && userMap.get(l.OwnerId).Profile.Name.contains('LDR') 
				&& l.OwnerId.getSobjectType()==user.sObjectType && oldMap.get(l.OwnerId) == LDRmanagerQueue.Id){
				}
				
			}
		}
	}

 

Thanks in advance for any assistance!

I have written the below for a trigger that I'm working on and both seem to produce the desired result.  Based on what I've learned they are two best pracitce ways to use SOQL queries.  But can someone please help me understand why I wouldn't want to just use the version with the SOQL For Loop almost all the time? (since it can help can avoid governor limits)

 

Version 1: SOQL List

 

List<OpportunityLineItem> OppProducts = new List<OpportunityLineItem>([SELECT Id, OpportunityId, PricebookEntryId, Post_Sale_Project__c FROM OpportunityLineItem WHERE OpportunityId IN: OppIds]);
		system.debug('OppProducts list size : ' + String.valueof(OppProducts.size()));
		
		for(OpportunityLineItem oli: OppProducts){
			if(psp.Opportunity__c == oli.OpportunityId){
				ResetOppProducts.put(oli.Id, new OpportunityLineItem(Id=oli.Id, OpportunityId = psp.Opportunity__c, Post_Sale_Project__c = null));
				UpdateOppProducts.put(oli.Id, new OpportunityLineItem(Id=oli.Id, OpportunityId = psp.Opportunity__c, Post_Sale_Project__c = psp.Id));
				system.debug('Post Sale Project Opportunity__c : ' + psp.Opportunity__c);
				system.debug('OpportunityLineItem OpportunityId : ' + oli.OpportunityId);
				system.debug('OpportunityLineItem Id : ' + oli.Id);
				system.debug('OpportunityLineItem ProductId : ' + oli.PricebookEntryId);
				system.debug('OpportunityLineItem Post Sales Project : ' + oli.Post_Sale_Project__c);
			}
		}

 

Version 2: SOQL List in For Loop

 

for(List<OpportunityLineItem> OppProducts: [SELECT Id, OpportunityId, PricebookEntryId, Post_Sale_Project__c FROM OpportunityLineItem WHERE OpportunityId IN: OppIds]){
			for(OpportunityLineItem oli: OppProducts){
				if(psp.Opportunity__c == oli.OpportunityId){
					ResetOppProducts.put(oli.Id, new OpportunityLineItem(Id=oli.Id, OpportunityId = psp.Opportunity__c, Post_Sale_Project__c = null));
					UpdateOppProducts.put(oli.Id, new OpportunityLineItem(Id=oli.Id, OpportunityId = psp.Opportunity__c, Post_Sale_Project__c = psp.Id));
				}
			}
		}

 

Thanks in advance for your help!

 

I'm new to writing apex triggers and I need some help cleaning up the SOQL queries in my collections.  Not sure what is wrong, but it just looks like too much.  Also, I'm sure it's part of what is giving me issues when I try to write a test class.

 

Thanks in advance!

 

- Matt

 

Apex Trigger:

 

trigger LDRCreatedTask on Task (after insert, after update, before delete) {

//Insert or Update command
if(trigger.isInsert || trigger.isUpdate){

	List<Task> TargetTask = [SELECT Id, WhoId, CreatedById 
							 FROM Task 
							 WHERE Id IN: Trigger.newMap.keySet()];
	
	Task TargetTaskDetails = [SELECT Id, WhoId, CreatedById 
							  FROM Task 
							  WHERE Id IN: TargetTask];
	
	Map<Id,User> UserMap = new Map<Id,User>([SELECT Id, Name, Profile.Name 
											 FROM User 
											 WHERE Id = :TargetTaskDetails.CreatedById AND isActive = true]);

	Lead ParentLead = [SELECT Id, First_LDR_Task_User__c, First_LDR_Task_Date__c 
					   FROM Lead 
					   WHERE Id = :TargetTaskDetails.WhoId];


	List<Task>LDRRelatedTasks = [SELECT Id, WhoId, CreatedBy.Profile.Name 
								 FROM Task 
								 WHERE WhoId = :ParentLead.Id AND CreatedBy.Profile.Name LIKE'%LDR%'];
							 
	List<Task> FirstTask = [SELECT Id, CreatedBy.Name, CreatedDate
							FROM Task
							WHERE Id IN: LDRRelatedTasks
							ORDER BY LastModifiedDate ASC LIMIT 1];

		Task FirstTaskDetails = [SELECT Id, CreatedBy.Name, CreatedDate
							 	FROM Task
							 	WHERE Id IN: FirstTask];	

	Map<Id,Lead> LeadstoUpdate = new Map<Id,Lead>();

for (Task t: TargetTask){

	//Update 'Most Recent' fields after each insert and everytime an existing task is modified
	if(UserMap.get(t.CreatedById).ProfileId != null 
		&& UserMap.get(t.CreatedById).Profile.Name.contains('LDR') 
		&& t.WhoId != null 
		&& (((String)t.WhoId).startswith('00Q'))){
			Lead l = new Lead(Id = t.WhoId, Most_Recent_LDR_Task_User__c = UserMap.get(t.CreatedById).Name, Most_Recent_LDR_Task_Date__c = System.now() ); 
			LeadstoUpdate.put(l.Id, l);		
			
			//Run if 1 or more LDR tasks
			if(FirstTask.size() > 0){
				if(ParentLead.First_LDR_Task_User__c == null && ParentLead.First_LDR_Task_Date__c == null){
					l.First_LDR_Task_User__c = FirstTaskDetails.CreatedBy.Name;
					l.First_LDR_Task_Date__c = FirstTaskDetails.CreatedDate;
					LeadstoUpdate.put(l.Id, l);
				}
			}
			
			//Run if 0 LDR tasks
			if(FirstTask.size() == 0){
				if(ParentLead.First_LDR_Task_User__c == null && ParentLead.First_LDR_Task_Date__c == null){
					l.First_LDR_Task_User__c = UserMap.get(t.CreatedById).Name;
					l.First_LDR_Task_Date__c = System.now();
					LeadstoUpdate.put(l.Id, l);
				}
			}
	}
	
}

update LeadstoUpdate.values();

}


if(trigger.isBefore && trigger.isDelete){

	List<Task> TargetTask = [SELECT Id, WhoId, CreatedById 
							 FROM Task 
							 WHERE Id IN: Trigger.oldMap.keySet()];
	
	Task TargetTaskDetails = [SELECT Id, WhoId, CreatedById 
							  FROM Task 
							  WHERE Id IN: TargetTask];
	
	Map<Id,User> UserMap = new Map<Id,User>([SELECT Id, Name, Profile.Name 
											 FROM User 
											 WHERE Id = :TargetTaskDetails.CreatedById AND isActive = true]);

	Lead ParentLead = [SELECT Id, First_LDR_Task_User__c, First_LDR_Task_Date__c 
					   FROM Lead 
					   WHERE Id = :TargetTaskDetails.WhoId];


	List<Task>LDRRelatedTasks = [SELECT Id, WhoId, CreatedBy.Profile.Name 
								 FROM Task 
								 WHERE WhoId = :ParentLead.Id AND CreatedBy.Profile.Name LIKE'%LDR%'];
							 
	List<Task> FirstTask = [SELECT Id, CreatedBy.Name, CreatedDate
							FROM Task
							WHERE Id IN: LDRRelatedTasks AND Id NOT IN: TargetTask
							ORDER BY LastModifiedDate ASC LIMIT 1];

	List<Task> MostRecentTask = [SELECT Id, CreatedBy.Name 
									 FROM Task 
									 WHERE Id IN: LDRRelatedTasks AND Id NOT IN: TargetTask
									 ORDER BY LastModifiedDate DESC LIMIT 1];

	Map<Id,Lead> LeadstoUpdateFirst = new Map<Id,Lead>();
	Map<Id,Lead> LeadstoUpdateMostRecent = new Map<Id,Lead>();	

for(Task t: TargetTask){
		
	//Run when all LDR tasks have been deleted
	if(LDRRelatedTasks.size() < 2){
		if(UserMap.get(t.CreatedById).ProfileId != null 
		&& UserMap.get(t.CreatedById).Profile.Name.contains('LDR') 
		&& t.WhoId != null
		&& (((String)t.WhoId).startswith('00Q'))){
			//Reset 'Most Recent' fields on lead
			Lead l = new Lead (Id = t.WhoId, Most_Recent_LDR_Task_User__c = null, Most_Recent_LDR_Task_Date__c = null);
			LeadstoUpdateMostRecent.put(l.Id, l);
		}
	}
	

	//Run when there are 1 or more LDR tasks
	if(LDRRelatedTasks.size() > 1) {
		Task MostRecentTaskDetails = [SELECT Id, CreatedBy.Name, LastModifiedDate
									  FROM Task 
									  WHERE Id IN: MostRecentTask];
		if(UserMap.get(t.CreatedById).Profile.Name.contains('LDR') && (((String)t.WhoId).startswith('00Q'))){
			//Update 'Most Recent' fields on lead			
			Lead l = new Lead (Id = t.WhoId, Most_Recent_LDR_Task_User__c = MostRecentTaskDetails.CreatedBy.Name, Most_Recent_LDR_Task_Date__c = MostRecentTaskDetails.LastModifiedDate);
			LeadstoUpdateMostRecent.put(l.Id, l);
		}	
	}
		
	//Run when there is no first LDR task - no LDR tasks on the lead record (all deleted)
	if(FirstTask.size() < 2){ 
			//Reset 'First' fields on lead			
			Lead l = new Lead(Id = t.WhoId, First_LDR_Task_User__c = null, First_LDR_Task_Date__c = null);
			LeadstoUpdateFirst.put(l.Id, l);
	}
	
	//Run when there is a first(oldest) LDR task on the lead record
	if(FirstTask.size() > 0){
		Task FirstTaskDetails = [SELECT Id, CreatedBy.Name, CreatedDate
								 FROM Task
							 	 WHERE Id IN: FirstTask];			
			//Update 'First' fields on lead		
			Lead l = new Lead(Id = t.WhoId, First_LDR_Task_User__c = FirstTaskDetails.CreatedBy.Name, First_LDR_Task_Date__c = FirstTaskDetails.CreatedDate);
			LeadstoUpdateFirst.put(l.Id, l);
	}
}

update LeadstoUpdateFirst.values();
update LeadstoUpdateMostRecent.values();

}

}