You need to sign in to do that
Don't have an account?
Help with trigger
Hi Guys,
Iam trying to update parent campaign based on record type it's working fine when i create a new one but when iam trying to change the record type for existing campaign the parent campaign doesn't gets updated, iam kinda new to this coding, any help is appreciated, here is my trigger
trigger ParentCampaign on Campaign (after insert) {
String CampaignID =Trigger.new[0].Id;
Campaign Cmp=[select id, RecordTypeID,ParentID from Campaign where id =:CampaignID];
If (Cmp.RecordTypeID =='012400000004v8d'){
Cmp.ParentID='701Q0000000Cxq2';
}
else if
(Cmp.RecordTypeID =='012300000004svr'){
Cmp.ParentID='701Q0000000CxqM';
}
else if
(Cmp.RecordTypeID =='012300000004svw'){
Cmp.ParentID='701Q0000000CxqR';
}
else if
(Cmp.RecordTypeID =='012300000004sw1'){
Cmp.ParentID='701Q0000000CxqW';
}
else if
(Cmp.RecordTypeID =='01240000000M32w'){
Cmp.ParentID='701Q0000000Cxqb';
}
else if
(Cmp.RecordTypeID =='012400000004umS'){
Cmp.ParentID='701Q0000000Cxqg';
}
Update cmp;
}
trigger ParentCampaign on Campaign (before insert, before update) {
For(Campaign Cmp : trigger.new)
{
If (Cmp.RecordTypeID =='012400000004v8d')
Cmp.ParentID='701Q0000000Cxq2';
else if (Cmp.RecordTypeID =='012300000004svr')
Cmp.ParentID='701Q0000000CxqM';
else if (Cmp.RecordTypeID =='012300000004svw')
Cmp.ParentID='701Q0000000CxqR';
else if
(Cmp.RecordTypeID =='012300000004sw1')
Cmp.ParentID='701Q0000000CxqW';
else if (Cmp.RecordTypeID =='01240000000M32w')
Cmp.ParentID='701Q0000000Cxqb';
else if (Cmp.RecordTypeID =='012400000004umS')
Cmp.ParentID='701Q0000000Cxqg';
}
}
All Answers
Hi Sam,
Welcome to the world of SF triggers. Your trigger is only fired on insert. If you want it to fire on update as well then you need to change the first line to
Secondly, there is not a need to query for the campaign object. It is already available in the Trigger.new list.
Thirdly, your trigger is only going to update the first campaign record, even if more than one campaign record is being edited at once. You need to "bulkify" your trigger.
And finally, it is never a good idea to hard-code IDs into any Salesforce code. I see you are doing that for RecordTypes and for Campaigns. The reason this is a problem is that the same record can have different IDs in different environments.
To access the RecordTypeID for a record type by name you can use code like this:
To get the IDs for your parent campaigns, I would recommend querying them by name and/or by RecordTypeID, whatever unique combination will give you the right campaign. For example:
Mark,
i tried using after update but iam getting exception error and to be honest i didn't understand your code , you are right that i cannot use the Id's in trigger but i was trying to organize your code but couldn't do that :(
Ritesh: Before insert doesn't works for me , iam trying to update when i create a new one and even when i edit the record
thx for your suggestion guys
So your trigger can be
Trigger CampaignBefore on Campaign (before insert, before update)
This will fire for inserts and updates
Thx again,this is what i got when i used before insert and before update
Apex trigger ParentCampaign caused an unexpected exception, contact your administrator: ParentCampaign: execution of BeforeInsert caused by: System.QueryException: List has no rows for assignment to SObject: Trigger.ParentCampaign: line 3, column 14
trigger ParentCampaign on Campaign (before insert, before update) {
For(Campaign Cmp : trigger.new)
{
If (Cmp.RecordTypeID =='012400000004v8d')
Cmp.ParentID='701Q0000000Cxq2';
else if (Cmp.RecordTypeID =='012300000004svr')
Cmp.ParentID='701Q0000000CxqM';
else if (Cmp.RecordTypeID =='012300000004svw')
Cmp.ParentID='701Q0000000CxqR';
else if
(Cmp.RecordTypeID =='012300000004sw1')
Cmp.ParentID='701Q0000000CxqW';
else if (Cmp.RecordTypeID =='01240000000M32w')
Cmp.ParentID='701Q0000000Cxqb';
else if (Cmp.RecordTypeID =='012400000004umS')
Cmp.ParentID='701Q0000000Cxqg';
}
}
Thx Ritesh, it worked but mark was saying that we cannot use the hard code values in the trigger, but since iam new to this trigger world i just don't knw how to store the id's in variable or just like he showed , since even the code which i have ryte now works fine but is it good to deploy this to production.
You could google salesforce custom settings and red up on how to use them. Jeff Douglas has written a very good blog entry describing their use,
http://blog.jeffdouglas.com/2010/01/07/using-list-custom-settings-in-salesforce-com/
Ritesh,
Finally the trigger has been modified to avoid the Id's and iam in process of writing test class but it just gave me 60%, but not sure how to get it to 75%, here is thr trigger and class the red ones are not being covered
Trigger:
trigger ParentCampaign on Campaign (before insert, before update)
{
MAP<String,Id> ParentMap = new MAP<String,Id>();
Map<Id,RecordType> recordTypeMap = new Map<Id,Recordtype>([Select Name,Id from Recordtype where SobjectType='Campaign']);
Set<String> parentName = new Set<String>();
for(ParentCompaign__c c : ParentCompaign__c.getall().values())
{
parentName.add(c.Name);
}
for(Campaign c : [Select Id,Name from Campaign where name in : parentName])
{
ParentMap.put(c.Name,C.Id);
}
For(Campaign Cmp : trigger.new)
{
If (recordTypeMap.get(Cmp.RecordTypeID).Name == 'Campaign (AU)')
Cmp.ParentID=ParentMap.get('International AU4');
else If (recordTypeMap.get(Cmp.RecordTypeID).Name == 'Campaign (DE)')
Cmp.ParentID=ParentMap.get('International DE4');
else If (recordTypeMap.get(Cmp.RecordTypeID).Name == 'Campaign (ES)')
Cmp.ParentID=ParentMap.get('International ES4');
else If (recordTypeMap.get(Cmp.RecordTypeID).Name == 'Campaign (FR)')
Cmp.ParentID=ParentMap.get('International FR4');
else If (recordTypeMap.get(Cmp.RecordTypeID).Name == 'Campaign (JP)')
Cmp.ParentID=ParentMap.get('International JP4');
else If (recordTypeMap.get(Cmp.RecordTypeID).Name == 'Campaign (UK)')
Cmp.ParentID=ParentMap.get('International UK4');
}
}
Class:
@isTest
private class ParentCampaignTest {
static testMethod void myUnitTest() {
// TO DO: implement unit test
MAP<String,Id> ParentMap = new MAP<String,Id>();
Map<Id,RecordType> recordTypeMap = new Map<Id,Recordtype>([Select Name,Id from Recordtype where SobjectType='Campaign']);
//Set<String> parentName = new Set<String>();
Account acc = new Account(Name = 'test', phone = '1234567890');
insert acc;
Case c = new Case(Type = 'Transformation', Status = 'Closed', Description = 'Text', AccountId = acc.Id);
insert c;
Campaign_Request__c cr = new Campaign_Request__c(Name = 'Testing', Program_Type__c = 'Other', CostMin__c = 90, Target_Date__c = Date.newInstance(2008,03,01),
Sectors__c = 'Anesthesia', Sector_Contact__c = 'Baldwin');
insert cr;
Campaign cmp = new Campaign(Name = 'International AU4', Campaign_Objective__c = 'Market Development', StartDate = Date.newInstance(2009,02,01),
EndDate = Date.newInstance(2010,02,01));
insert cmp;
Campaign cm = new Campaign( Name = 'Test',ParentId = cmp.Id, Campaign_Objective__c = 'Market Development', StartDate = Date.newInstance(2009,03,01),
EndDate = Date.newInstance(2010,03,01));
insert cm;
}
}
Since you have several if blocka, To increase test coverage you will need to create campaigns of the various record types in your test class.
Inserting campaigns of the different record types which your if statements are looking for, will send the execution path through the if statements.
So just create campaigns of different record types, insert them and you should be sorted
Thx Ritesh, i modified the class infact i just copied the same code from trigger, but ryte now my test class fails, i get this msg, iam not sure how to correct it
System.NullPointerException: Attempt to de-reference a null object
Class.ParentCampaignTest.myUnitTest: line 46, column 49 External entry point
private class ParentCampaignTest {
static testMethod void myUnitTest() {
// TO DO: implement unit test
MAP<String,Id> ParentMap = new MAP<String,Id>();
Map<Id,RecordType> recordTypeMap = new Map<Id,Recordtype>([Select Name,Id from Recordtype where SobjectType='Campaign']);
//Set<String> parentName = new Set<String>();
Account acc = new Account(Name = 'test', phone = '1234567890');
insert acc;
Case c = new Case(Type = 'Transformation', Status = 'Closed', Description = 'Text', AccountId = acc.Id);
insert c;
Campaign_Request__c cr = new Campaign_Request__c(Name = 'Testing', Program_Type__c = 'Other', CostMin__c = 90, Target_Date__c = Date.newInstance(2008,03,01),
Sectors__c = 'Anesthesia', Sector_Contact__c = 'Baldwin');
insert cr;
Campaign Cmp = new Campaign(Name = 'Testing', Campaign_Objective__c = 'Market Development', StartDate = Date.newInstance(2009,02,01),
EndDate = Date.newInstance(2010,02,01));
insert Cmp;
If (recordTypeMap.get(Cmp.RecordTypeID).Name == 'Campaign (AU)')
Cmp.ParentID=ParentMap.get('International AU4');
else If (recordTypeMap.get(Cmp.RecordTypeID).Name == 'Campaign (DE)')
Cmp.ParentID=ParentMap.get('International DE4');
else If (recordTypeMap.get(Cmp.RecordTypeID).Name == 'Campaign (ES)')
Cmp.ParentID=ParentMap.get('International ES4');
else If (recordTypeMap.get(Cmp.RecordTypeID).Name == 'Campaign (FR)')
Cmp.ParentID=ParentMap.get('International FR4');
else If (recordTypeMap.get(Cmp.RecordTypeID).Name == 'Campaign (JP)')
Cmp.ParentID=ParentMap.get('International JP4');
else If (recordTypeMap.get(Cmp.RecordTypeID).Name == 'Campaign (UK)')
Cmp.ParentID=ParentMap.get('International UK4');
}
}
not quite, you want to be inserting campaigns of the various record types
Map<String, Id> nameRTIDMap = new Map<String, Id>{};
for(RecordType rt : recordTypemap.values)
nameRTIDMap.put(rt.name, rt.id);
......
.....
Campaign c1 = new Campaign(........, RecordTypeId = nameRTIDMap.get('Campaign (AU)')....);
insert c1;
Campaign c2 = new Campaign (.......RecordTypeId = nameRTIDMap.get('Campaign (DE)').....);
insert c2;
and so on....