You need to sign in to do that
Don't have an account?
Developer.mikie.Apex.Student
Example code for an apex trigger that will set a lookup based upon a picklist field
Hi there,
I am new to apex and was wondering if someone would be able to help me out by providing some example code on how I would write an apex trigger which sets the value of a lookup field based on identical values in a picklist.
Any help would be much appreciated,
Mikie
(Apex Rookie)
Gonna use some abbreviations, your object names are really long!
Adding another picklist wouldn't matter at all. When someone picks "Picklist Value One" on your picklist from DS, you're looking to update the DP reference field so that it points to the actual DPAS record that's named "Picklist Value One", right? The thing is, that record isn't really named "Picklist Value One", that's just the field dpas__c.Name. That's why we need to query for the record ID belonging to the thing named "Picklist Value One". Then the reference field on DP needs to be set to the dpas__c.id, which is a salesforce 15 digit ID.
That's what the trigger does.
Only thing I can't tell you is what your field is called on that last line. On your DP object, what's the lookup field's name?
Unless you're going the other way or something, or I misunderstood your archetecture. Let me know the object and field names. That trigger works in my sandbox fine. When I pick from my picklist on DP, it updates the reference field on DS pointing to a DPAS record of the same name.
All Answers
E.G. If someone were creating a record and they were to select ''Advantage Program'' within the picklist. The Lookup field would be automatically set as 'Advantage Program''.
Thankyou in advance for your help.
Mikie
Had some time, gave it a go! The reference needs the object ID, it doesn't really matter that the picklist value's name matches the object name...
Trigger GrabReference on Account (before insert, before update) {
for (Account acc: trigger.new) {
if(acc.Picklist__c != null) {
List<Object__c> obj = new List<Object__c>();
obj = [Select Id from Object__c WHERE Object__c.Name = :acc.Picklist__c ORDER BY Id LIMIT 1];
if (obj.size() > 0){
acc.ObjectRef__c = obj[0].Id;
}
}
}
}
Hey Ekorz,
Thankyou so much for the quick reply. I have attempted to alter the code, except I am new to apex and was not 100% sure on where to put everything.
This is what I came up with:
Trigger GrabReference on Destiny_Products__c (before insert, before update) {
for (Destiny_Products__c: trigger.new) {
if(Product_Hidden_Picklist__c != null) {
List<Destiny_Products_and_Services__c> obj = new List<Destiny_Products_and_Services__c>();
obj = [Select Id from Destiny_Products_and_Services__c WHERE Destiny_Products_and_Services__c.Id = :Product_Hidden_Picklist__c ORDER BY Id LIMIT 1];
if (obj.size() > 0){
acc.Destiny_Product__c = obj[0].Id;
}
}
}
}
Destiny_Products__c is the custom object with the lookup and the picklist and Destiny_Products_and_services__c is the custom object which the lookup refers to.
It would not let me save because of an error, I am pretty sure that I put the information in wrong.
Mikie
thankyou again
I am not sure if I built it the way you did, but here goes.
Destiny Product has the picklist "Product Hidden Picklist" and the reference field to the other object, "Destiny Reference Field".
When you toggle the picklist to Product 1, Product 2, Product 3, you'd like the reference to be updated to the actual record for Product 1, Product 2, or Product 3 (those all have object id's like "a0eM0000005wzNR")
This trigger does the trick:
Hey Ekorz,
I entered the trigger into sandbox and had a play around. When creating the record or updating the picklist field, upon saving it clears itself and the lookup filter is clear aswell.Why do you think it would be doing that? Maybe I entered it wrong.
Thank you so much for your time and help.
Would it help, if I put another picklist field into the object that is refferrenced. If I set each record with its own unique picklist value/name, would it be easier to referrence.
Gonna use some abbreviations, your object names are really long!
Adding another picklist wouldn't matter at all. When someone picks "Picklist Value One" on your picklist from DS, you're looking to update the DP reference field so that it points to the actual DPAS record that's named "Picklist Value One", right? The thing is, that record isn't really named "Picklist Value One", that's just the field dpas__c.Name. That's why we need to query for the record ID belonging to the thing named "Picklist Value One". Then the reference field on DP needs to be set to the dpas__c.id, which is a salesforce 15 digit ID.
That's what the trigger does.
Only thing I can't tell you is what your field is called on that last line. On your DP object, what's the lookup field's name?
Unless you're going the other way or something, or I misunderstood your archetecture. Let me know the object and field names. That trigger works in my sandbox fine. When I pick from my picklist on DP, it updates the reference field on DS pointing to a DPAS record of the same name.
Hahaha, I am soooo sorry.
I had an apex trigger which did the exact reverse of it before. Basically the idea was to automatically set the picklist from the lookup, then make the picklist invisible and a dependant picklist, therefore each product would have its own stages. I needed the lookup field in order to autopopulate price, type, etc. This did not work out as there ended up being two fields with the products name on the page.
So basically, it was working fine, except upon saving the picklist would set itself to the same as the lookup and the lookup would set itself to the same as the picklist, therefore clearing them both.
I have de-activated the other trigger and it works perfectly. You are a genius my friend, thankyou soo much for the help, especially considering the amount of information I gave you.
You have really helped me out here my friend. Thankyou
no prob. you're gonna need to write a test for that trigger to get it deployed. I had these same questions like a month ago so it's nice to give back a little to these forums. This clears 100% for me.
Thank you again, I was going to ask, but did not want to be cheeky. I attempted to insert it as:
Error: Compile Error: Field is not writeable: Destiny_Products__c.Name at line 13 column 67
But got this error:
@isTest
private class TestGrabReference {
static testMethod void myGrabTest() {
//name a dpas record, insert it
Destiny_Products_and_Services__c dpas = new Destiny_Products_and_Services__c ( Name = 'TestProduct');
insert dpas;
//build a test dp record with the picklist field set to your previous record
Destiny_Products__c dp = new Destiny_Products__c ( Name = 'TestDP', Product_Hidden_Picklist__c = 'TestProduct');
insert dp;
//query for the record, now that it's been inserted and the trigger has been fired
dp = [ SELECT Destiny_Product__c FROM Destiny_Products__c WHERE Id = :dp.Id ];
//asert that the trigger's field change was made
{ System.assertEquals(dpas.Id, dp.Destiny_Reference_Field__c); }
}
}
Am I doing soemthing wrong?
I bet your Destiny_Products__c.Name field is set to be an auto-number, in which case the system wll give it a name automatically. Just delete "Name = 'TestDP'" and you'll be set. Keep in mind if you have any other required fields set for either of those objects, you should define them in the test records that way (field = value, field = value). Same goes if you have validatons, your test records need to conform or the record will fail the insert part of the test.
You would assume correctly. Can't believe I always miss things like that. Ok, that error is gone and now I have error:
Error: Compile Error: unexpected token: ';' at line 8 column 84
This is my code:
@isTest
private class TestGrabReference {
static testMethod void myGrabTest() {
//name a dpas record, insert it
Destiny_Products_and_Services__c dpas = new Destiny_Products_and_Services__c;
insert dpas;
//build a test dp record with the picklist field set to your previous record
Destiny_Products__c dp = new Destiny_Products__c ( Name = 'TestDP', Product_Name__c = 'TestProduct');
insert dp;
//query for the record, now that it's been inserted and the trigger has been fired
dp = [ SELECT Destiny_Reference_Field__c FROM Destiny_Products__c WHERE Id = :dp.Id ];
//asert that the trigger's field change was made
{ System.assertEquals(dpas.Id, dp.Destiny_Reference_Field__c); }
}
}
I changed the name of the product hidden picklist, just to product name. I feel like we are soo close. I am so sorry to trouble you one last time.
mikie
Whoops, once again I am an idiot. I deleted the wrong part. This was the code and it saved:
@isTest
private class TestProduct_GrabReference {
static testMethod void myGrabTest() {
//name a dpas record, insert it
Destiny_Products_and_Services__c dpas = new Destiny_Products_and_Services__c ( Name = 'TestProduct');
insert dpas;
//build a test dp record with the picklist field set to your previous record
Destiny_Products__c dp = new Destiny_Products__c (Product_Name__c = 'TestProduct');
insert dp;
//query for the record, now that it's been inserted and the trigger has been fired
dp = [ SELECT Destiny_Product__c FROM Destiny_Products__c WHERE Id = :dp.Id ];
//asert that the trigger's field change was made
{ System.assertEquals(dpas.Id, dp.Destiny_Product__c); }
}
}
Except when running in sandbox it failed with a cross next to it. Is this because I ran it in sandbox and not in production?
Now I am really confused. Although it said the test failed, the grab reference trigger I wrote passed with 100%....I will try and deploy it and tell you how it goes. Thank you sooo much for all your help.
Mikie
Turns out I needed to add a valid account reference. But I deployed it all, even created a similar trigger for another object and it all works perfectly. I cannot tell you how long I have waited to implement something like this. thankyou sooo much. I really appreciate it