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

Help!! - Bring custom info from Opportunity into Quote

I have created three custom fields for my product line items - 'StartDate', 'Duration' and 'EndDate'. I have then created the same fields in my Quote line items as I need them to appear on my quotes. I am brand new to apex and its taking a lot of reading and patience to figure out where to start. I need to get this sorted my next week or I'll be in trouble with my boss. 


What my custom fields do: The start date is self explanatory, the duration is the number of months in one of our Support contracts, the duration is entered after the start date, which then calculates the end date. For example;

Start date 01/01/2014 - Duration 12 (hit save) End Date calculates: 01/01/2015
When I hit new quote, and the information from my product line items is copied into my Quote Line Items, I need my custom information to do the same. Does anyone know how I can go about this. Below is what I have started think I am totally way off. Help! 
trigger AutopopulateStartDate on QuoteLineItems (after insert, after update) {
//. Create a container for the products that need start dates inserted to them
Set updatedStartDate = new
//If this is an insert, I want the date to be inserted to the correct product
if (trigger.isInsert) {
for (StartDate s : {

It sounds like you created three custom fields on the Product object (Product2), and also three similar fields on the QuoteLineItem object.  I'm not sure I fully understand what you are trying to do.


For example, lets say you have a product "WidgetA".  The start date is 8-1-2013, duration is 12 months, and end date is 8-1-2014.  This is on the product object, and the product info is shared across all quotes, so the dates will be the same for every quote.  For example, if I create a new quote today, the start date is already in the past.   Why would I want to use that start date as the value?


I think what you may be trying to acheive is for your users (creating the quote) to set their own start date each time they make a quote, and only the end date automatically fills in.  To put it another way, forget the start and end date on the product.  All you need on the product is to know how long the duration should be, because the support contract could begin at any time. 


If I were in your place, this is what I would do.  On the QuoteLineItem object, I'd create a custom date field StartDate__c. (This you already have).  The user can enter whatever date they want, but I would set the default value to be TODAY(), or something appropriate.  That way, the start date will "auto-populate" but only based on whatever the current date is, or the date that the quote is being created.  It has nothing to do with the product.


Next, on the QuoteLineItem object, I would create a custom FORMULA field for the EndDate.  The formula should be "date" format, and in the formula creation field I will set it equal to something like this:


DATE(YEAR(DATEVALUE(StartDate__c))+(Product2.Duration__c + MONTH(DATEVALUE(StartDate__c)))/12,
MOD((Product2.Duration__c + MONTH(DATEVALUE(StartDate__c))),12),


The formula takes the StartDate from the Quote, and the Duration from the Product and adds them together to find the EndDate.  Because it's a formula, it will never be editable, it is totally dependend on whatever the current "Duration" is for that given product.  The math might be easier if your "Duration" on the Product was in # of days instead of months, because then you can just add them to the Date variable.  (StartDate__c + DurationDays)


So, your QuoteLineItem now has StartDate, EndDate, but no duration.  If you want the duration itself to be visible on the quote, you can create a 3rd custom field on the QuoteLineItem.  Again, I would make it a formula.  It can be a straight copy of the product duration (Product2.Duration__c).  My user will now have no control over the contract duration or end date, but he can move the start date forward or backward to whatever date he wants, and the duration and end date will move to match it.  On the Quote PDF template (if that's what your using for your final displayed quote), you can add these formual fields so they show up the same as any other field.


I'm not sure if this is what your goal is or not.  Yes, you can do the same thing with an apex trigger, but if this is all you are trying to accomplish, a trigger is not required.  The method above is a little simpler than creating an apex trigger, especially if you have a tight deadline and not a lot of experience with apex.


** Edit ** if you want your user to choose their own duration every time, then you would have:

QuoteLineItem.StartDate__c (set by user, default today)

QuoteLineItem.Duration__c (set by user, maybe a drop-down list)

QuoteLineItem.EndDate__c (formula, similar to the previous one I showed). 

If you do it this way, then the user has full control to give a support contract for whatever duration they want.  This means the 3 fields you created on the Product2 object would be unused.


Hi Michael, 


Thanks for your suggestion. I am however completely confused. 


I'll try to explain what we do, we sell software, more specifically licences, support contracts and training. The dates only affect the Support contracts, they commonly run for 12 months at a time, and are more often renewals. Our biggest problem is when one of our customers comes to renew their support contracts but want to buy training or additional licences, we are having to create a new opportunity. 


You are right I have created 3 custom fields in the Product Object and the Quote Line Item object that do exactly the same thing.


An example of how I would need this to work( this is a complicated scenario that keeps coming up)


Joe Bloggs has a support contract coming up for a renewal of 15 licences, they are 12 month contracts starting at different dates. He wants to buy 6 more licences, but at the moment the probability of this is low, so I don't want to add it my opportunity just yet. I know the Support contract will come through so that is all I show on my opp. 


On my Support product, I add the relevant start dates, (they are all different as the licences were all bought at different times) the duration of my Support Contract product automatically fills in the duration as 12 months whenever that product is selected (I should have mentioned this before but didnt realise). It is editable if I need to change the duration. Then the end date is populated. 


So I've created my opportunity for the renewal of the contracts and added my products, but need to create a quote that has the Support and the additional licences. 



I create a new quote, but none of the custom fields are populated, which is all the dates I just spent a lot time filling in with different durations, start dates, etc. I also need to add 6 new licences. 


When I hit the 'New Quote' button, I need the information to be brought into the quote line items exactly the same, so all the dates/duration for the current support contracts up for renewal need to be  filled into my custom fields in my Quote Line Items. 


I need my users to be able to edit everything and our customers change their minds day to day, from you're suggestion that didn't quite sound possible. When I have explained this scenario to people I have always been told to create an apex trigger as no formula field would allow for everything I need it to do. 


Does that make any sense? 






It is true that no formula field will do everything you want, but I would still recommend using a formula to do some of it.  I didn't realize that you were also trying to put all that information on the Opportunity as well.  You only mentioned the Quote and Product in the original post.  The way I see it you have 3 separate things to accomplish.

1) DEFAULT VALUES: You want the Duration on the OpportunityLineItem and QuoteLineItem to default to a certain value but also be changeable by the user, whenever the user enters a new opportunity line.


2) AUTOMATICALLY CALCULATE THE END DATE:  (This is not the same as a "default" value because the end date is only calculated after the user has chosen a start date and duration).  You want the End Date on the OpportunityLineItem and QuoteLineItem to be a fixed formula, based on StartDate + Duration.  In my opinion, it should not be necessary for users to change the EndDate.  You just want them to edit the start date and duration.  It should be possible for you to create a formula on the OpportunityLineItem and QuoteLineItem that will accomplish this.  (Something similar to the formula in my previous post).


3) SYNC THE CUSTOM FIELDS between OpportunityLine and QuoteLine:  You want the custom fields on OpportunityLineItem and QuoteLineItem to always be synchronized.  There is a free app provided by available for this     The app contains its own triggers for transferring all the OpportunityLineItem information to the QuoteLineItem, so you don't need to recreate those yourself.  There are several steps you will need to do to install the app and set up your field mappings, but you should do this LAST, after #1 and #2 are finished.


Regarding 1).  Suppose you set the default duration to always be 12 months, no matter what the product is.  You can set this default in the custom field itself (no trigger, no code).  Then the user can adjust it however they want.  If that is sufficient for your business requirements, then it will be easy and you don't need to do any additional work. 


However, from your original post I assumed you wanted the default duration to be different depending on the product.  For example, WidgetA has a default 12 month support contract, but WidgetB has a default 18 month support contract.  The only way for the system to give those different default values each time will be to use Apex code.  If you try to do this with an Apex trigger, the trigger will do its work after the user hits "Save".  So whatever your "default" value is, the user will not see it until after they have finished, which I don't think is what you want.  Also, if you're not careful, then the trigger could override whatever the user puts, constantly setting the duration back to the default. 


In a situation like this, most customers want the value to show up in the very beginning, when a user is entering a brand new line, before he saves it.  This we can do with a custom Visualforce Page and Apex controller extension.  That is different from an Apex trigger.


What I am talking about doing is replacing the standard "New Product" page (on Opportunity) with a custom VF page.  I think that is the only way to have the "New" page display different defaults for different products.  For more information, there are examples in the Apex/VF Developers guide.  Look for "overriding a standard page" and "overriding a standard button."



If you try this method, you will create an Apex controller extension that performs a SOQL query to find the Product2 object that is being used.  That will find what the default Duration should be, so it can display it for the user.  The controller does this work when the page is loading and being rendered, not after the user clicks save, which is what a trigger does.  If you are not familiar with Apex or Visualforce, then #1 is the hardest of the 3 goals for you to do by yourself.  But it is possible, if you have a few days to read through all the examples in the developers guide and work it out in your sandbox piece by piece. 



Michael thanks taking the time to explain all of that for me. It's a great help. You're spot on with what I'm looking for. I'll put it into practice tonight and see how far I get with it. 

Zoe SmithZoe Smith
I am 9 years behind you facing the same problem!! Thank you, Emillar for asking this question and thank you Michael for explaining all of this. You saved me SO much time and a tremendous amount of frustration! :)
jhon drakejhon drake
Navigating Apex can be challenging at first, especially when dealing with custom fields. Your approach to auto-populate start dates for quotes is a good start. You may want to review and fine-tune your trigger code to ensure it correctly handles both inserts and updates. Don't hesitate to seek guidance from the Salesforce community or colleagues. Persistence and learning will pay off. Best of luck in resolving this before your deadline for more vist :