0

I have a requirement inwhich I am calculating field 'Net revenue Impact' field of all Opportunity products and display it in Summary field 'Net Rev Impact on FY' on Opportunity Object.

Below is the apex code that I have written on OpportunityLineItem Trigger:

public with sharing class OpportunityLineItemServices {


    public static void getNetRevImpact(Id optId) {
        map<id,Decimal> oppidtoopplineitm =new map<id,Decimal>();
        Set<Id> opportunitiesId=new Set<Id>();
        list<Opportunity> finalOpportunity = new list<Opportunity>();
        Decimal sum=0.00;
        for(OpportunityLineItem lineItem:[Select Id,OpportunityId,Net_Rev_Impact_on_FY__c from OpportunityLineItem where OpportunityId=:optId ])
        {
            opportunitiesId.add(lineItem.OpportunityId);
            sum =(sum+lineItem.Net_Rev_Impact_on_FY__c).setScale(2);
            oppidtoopplineitm.put(lineItem.OpportunityId,sum);

        }

        Map<Id,Opportunity> idToOpportunity=new Map<Id,Opportunity>([SELECT Id,Net_Rev_Impact_on_FY__c FROM Opportunity WHERE Id =:opportunitiesId]);
        for(id oId: oppidtoopplineitm.keyset()){
            idToOpportunity.get(oId).Net_Rev_Impact_on_FY__c = oppidtoopplineitm.get(oId);
            finalOpportunity.add(idToOpportunity.get(oId)); 
        }
        update finalOpportunity;
  }

This code is working fine.When I add or Update or delete a product,it calculates accordingly and display it Summary field.

But I have a additional requirement inwhich when I change the ContractStartDate or ContractEndDate on Opportunity Object then it should calculate all the products accordingly and Update the Summary Field. For this I have written another same piece of code on Opportunity Trigger:

public static void getNetRevImpactOpp(Opportunity opt) {
    map<id,Decimal> oppidtoopplineitm =new map<id,Decimal>();
    list<Opportunity> finalOpportunity = new list<Opportunity>();
    Decimal sum=0.00;

    for(OpportunityLineItem lineItem:[Select Id,OpportunityId,Net_Rev_Impact_on_FY__c from OpportunityLineItem where OpportunityId=:opt.Id ])
    {
        sum =(sum+lineItem.Net_Rev_Impact_on_FY__c).setScale(2);
        oppidtoopplineitm.put(lineItem.OpportunityId,sum);

    }  
    for(id oId: oppidtoopplineitm.keyset()){

        opt.Net_Rev_Impact_on_FY__c = oppidtoopplineitm.get(oId);

    }

When I Change the ContractStartDate or ContractEndDate,it does not update the value in OpportunityLineItem and due this it does not show the correct value in Summary field.But when I click on refresh button,it displays the correct result which is strange. I have tested the functionality 15 days before and it was working absolutely fine.But I am not sure what has suddenly updated in salesforce that cause this weird issue.

Anybody has an idea?

What modification needs to be done in this code..

2
  • Make sure that recursion is not taking place ...for example you are updating opportunity. Also provide all code if possible...here the code seems poorly written. Also why not you are using rollup-summary field if you want to rollup?
    – Ayub
    Commented Jan 30, 2017 at 16:48
  • well rollup summery field u can use only in case of master detail relationship i believe and there is no master detail relationship between Opportunity and Opportunity Product.Thats why i had to gone with this option. The code that I have provided is the actual logic.and I am just calling these class methods in their respective handler class and triggers call their methods accordingly. summery field is updated properly when I add,modify or update the products but when i modify date field on opportunity,it does not update in first attempt.
    – SFDCDJ
    Commented Jan 30, 2017 at 16:55

2 Answers 2

0

You should share more of your code - are you triggering on before or after update? Is the field you are reading a formula field or regular currency field? That said, I did notice one thing: your second code block has no DML statements, so there's nothing there that would update the database, assuming it's an after trigger. Your first code block has this:

update finalOpportunity;

Now, like I said, there are more factors at play - for example, if your trigger is running in a before update context, you can modify the field values before the record is committed to the database and there is no need to call update on those records. However, if you are in an after update context on your opportunity trigger, and then you are updating the opportunity again in that trigger, you'll need to use a static variable to keep track of whether you have already processed the record in this execution context to prevent a recursive loop that will eventually cause your trigger to fail with a governor limit exception.

Another issue I see in your OpportunityLineItemServices is that it only takes a single opportunity ID and then performs two SOQL queries and an update on that opportunity which means that your trigger is not properly bulkified. Trigger.new can contain up to 200 records a pop, you'll get an exception after 101 SOQL statements, and your trigger will hit that limit with just 50 records in the best-case scenario.

It's good that you are using maps and what look like handler classes but you have to implement some flow control and bulkify your code or I promise it will cause you problems.

And if you want really good answers, you'll need to include information, because honestly nobody can tell you why your code isn't working based on what you've provided. We need to see the rest of the code at least.

2
  • The getNetRevImpactOpp method is being called on before update/insert on opportunity object hence it has no update DML. I am trying to recalculate the sum of a custom fields on opprtunity linen item object when a certain field is changed on the opportunity object. the fields on the opprtunity line item are formula field based on this custom field(in opportunity).
    – SFDCDJ
    Commented Jan 31, 2017 at 7:08
  • The idea here is to recalculate the sum of this formula fields on the opportunity line items whenever the custom field on the opprtunity object is changed. This is not working in my case, i am getting the old values for the formula fields in the opportunity line item. The code that I have mentioned in description is the actual logic.I am simply calling all these methods in respective handler class which automatically calls on Triggers.
    – SFDCDJ
    Commented Jan 31, 2017 at 7:08
0

How do you know that there is no master child relationship between Opportunity and OpportunityLineItem.

Did you give any try?

Look below: enter image description here

2
  • Sorry Missed that..But even if there is master detail relationship here,it does not consider formula field in rollup summary field.'Net_Rev_Impact_on_FY__c' on Opportunity Product is a formula field.
    – SFDCDJ
    Commented Feb 1, 2017 at 14:14
  • :) You are so unlucky......create a number field and populate this field from workflow and use it in rollup summary..
    – Ayub
    Commented Feb 1, 2017 at 19:18

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .