+ Start a Discussion
Developer118Developer118 

Trigger to Check new Owner

Hi Everyone,
                     I have a requirement where i need to check the Owner Territory, and User Title Before Update,
The Previous owner can transfer the particualr opportuntiy to a new Owner if the Parent Territory of both (New Owner, Previous Owner) are same and the new user has title as "Special" .  A particular user can sit on  more then one territory. so only those users can be new owner which satisfy this condition.

I am new to Apex, i wrote something based on S-Control i saw on the community.
 
Code:
trigger NewOwner on Opportunity (before update, after update) 
{
//string profileid =UserInfo.getProfileId();
ID oppsid = Trigger.old[0].Id;
User[] PreviousOwner = [select id, profileid from User where id=:Trigger.old[0].OwnerId Limit 1];
//String OwnerId = user.Id[0];
if(PreviousOwner[0].ProfileId =='00eT0000000dnyE')
{
// Territory of the Owner
UserTerritory[] OwnerTerritory = [select Id, TerritoryId, IsActive from UserTerritory where UserId=:Trigger.old[0].OwnerId and IsActive = TRUE];
for(Integer i=0; i<OwnerTerritory.size(); i++)
{
// Parent Territory of the Owner
Territory[] OwnerParentTerritory = [select Id, Name, ParentTerritoryID from Territory where Id=:OwnerTerritory[i].TerritoryId];
for (Integer j=0; j<OwnerParentTerritory.size(); j++)
{
// Get the New User's Id and Title.
User[] NewOwner = [select Id, Title from User where id=:Trigger.new[0].OwnerId Limit 1];
// To get the New User's Territory
UserTerritory[] NewOwnerTerritory = [select Id, TerritoryId, IsActive from UserTerritory where UserId =:Trigger.new[0].OwnerId and IsActive = TRUE];
Territory[] NewOwnerParentTerritory = [select Id, Name, ParentTerritoryID from Territory where Id=:NewOwnerTerritory[0].TerritoryId];
for(Integer k=0; k<NewOwnerParentTerritory.size(); k++)
if(NewOwner[0].Title == 'Special' && NewOwnerParentTerritory[k].ParentTerritoryID == OwnerParentTerritory[j].ParentTerritoryID)
{
UserTerritory[] OldOwner = [select TerritoryId, UserId from UserTerritory where UserId=:Trigger.old[0].OwnerId and IsActive = TRUE];
for(Integer l=0; l<OldOwner.size(); l++)
{
for(UserTerritory OldOwnerTerritoryUsers:[select UserId from UserTerritory where TerritoryId=:OldOwner[l].TerritoryId and IsActive = TRUE])
{
OpportunityShare oppsshare = new OpportunityShare();
oppsshare.OpportunityId = oppsid ;
oppsshare.UserOrGroupId = OldOwnerTerritoryUsers.UserId;
oppsshare.OpportunityAccessLevel = 'Read';
try
{
insert oppsshare ;
}
catch (Exception e)
{
System.debug(e.getMessage());
}
}
}
}
/*else
{
Trigger.new[0].OwnerId.addError('Deal can only be assigned to User in your parent territory and with title as Special');
}
*/
}
}
}
}
}

The trigger saved and also is valid but at the time of Operation, i recieve this error message.
Error - Apex trigger: NewOwner caused an unexpected exception, contact your administrator: NewOwner: execution of BeforeUpdate caused by: System.ListException: List index out of bounds: 0: Trigger.NewOwner

Error: Apex trigger NewOwner caused an unexpected exception, contact your administrator: NewOwner: execution of AfterUpdate caused by: System.Exception: Too many SOQL queries: 21: Trigger.NewOwner: line 18, column 19

If someone can please help me with this, would be great help.
Many Thanks in Advance.
Developer118


Message Edited by Developer118 on 02-12-2008 02:16 PM

Message Edited by Developer118 on 02-12-2008 02:17 PM
mikefmikef
dev118:

Error 1 is telling you that the List is out of bounds so that means that the List or Trigger.new[0] is not passing any records into the query on line 18.
So Trigger.new[0] doesn't exist.

(for lack of a better example)
You would get this same exception if you where trying to get a substring from a String at position 4 but the String is only 2 characters in length.

Do a System.debug('this is the trigger list when I get to here ' + Trigger.new); to see what the trigger List looks like at this point in your code.

Error 2 is a common one when people are learning Apex. There is a underground phase in Apex dev land, "Did you bulkafy your code?"
What this means is do you have queries inside for loops? And in your code you have lots of queries in for loops.

Please reference this post to help you bulk up your code. post

Keep in mind you want to query only when you need to and you want to do it in mass, and store the query in a map of some kind for future referrence.
Store the results in memory then look through thoes results to do your logic.

asdfgasdfg
Hi Mikef,
              My problem is to selecta new owner, who has to be a 'Team Lead' and should belong to the same parent territory as of the old owner's Parent territory.
 
This is the only reason, i was writing queries in the for loop (Many of them :smileysad: )
 
because m users belong to multiple territories and thus multiple parent territories..
 
can u help me in getting a way out ??
 
Many Thanks in Advance..
Developer118
mikefmikef
So you need to do the queries in bulk and cache the results in instance variables.
Then look in the instance maps to get your values to update.


Wingsrul91Wingsrul91

I am trying to do something very similar:

I am trying to create a trigger to pull related record owner (user) information such as the user's office.  I have created a field on the case page layout so that everytime the case record owner is changed it displays the current owners office: 

 

 

trigger updateProfile on Case (before insert) { for (Case accs : Trigger.new) { User u = [select id, User.Office__c from User where id = :Userinfo.getUserId()]; accs.Test_Office__c = u.Office__c; } }

 

 So far, it works when the record is created but not when it is updated.  It throws the 'read only' error.

 Any ideas?

 

nguntherngunther
You missing 'before update' modf. on trigger definition, try with this code:

trigger updateProfile on Case (before insert, before update)
{
for (Case accs : Trigger.new) {
User u = [select id, User.Office__c from User where id = :Userinfo.getUserId()];
accs.Test_Office__c = u.Office__c;
}
}
Wingsrul91Wingsrul91
I am trying to create a trigger that checks to see if a check box is checked in the user (owner) profile before the record can be owned by that individual.  Basically, we have an Out Of Office checkbox in the user profile and we want to make it impossible for a case owner to have the check box checked.  Any ideas?