reeeval
10/11/2016 - 12:24 PM

Apex trigger for update / insert Term of Delivery record based on Opportunity Product

Apex trigger for update / insert Term of Delivery record based on Opportunity Product

trigger updateTermOfDelivery on Opportunity (after insert, after update) {
    for (Opportunity opp : Trigger.new) {
        
        //delete old record first
        List<Term_of_Delivery__c> terms = [SELECT Id FROM Term_of_Delivery__c
            WHERE Opportunity__c = :opp.Id];
        if (terms.size() > 0) {
            delete terms;
        }
        
        //get all products from opportunity
        List<OpportunityLineitem> products = [SELECT Id, Frequency__c, Quantity, TotalPrice, ServiceDate, Name, UnitPrice
            FROM OpportunityLineitem
            WHERE OpportunityId = :opp.Id];
        List<Term_of_Delivery__c> termsToInsert = new List<Term_of_Delivery__c>();
        Integer seq = 1;
        
        //loop the term of delivery based on frequency each product
        for (OpportunityLineitem oli : products) {
            Decimal freq = 0;
            if (oli.Frequency__c != null) {
                freq = oli.Frequency__c;
            }
            
            if (freq > 0) {
                Decimal qtyTod = (oli.Quantity / freq).setScale(0);
                //Decimal amountTod = (oli.TotalPrice / freq).setScale(2);
                Date baseDate = oli.ServiceDate != null ? oli.ServiceDate : opp.CloseDate;
                Decimal tempSumQty = 0;
                
                for (Integer i=1; i<=freq; i++) {
                    if (i == 1 && seq == 1) {
                        Term_of_Delivery__c tod = new Term_of_Delivery__c();
                        tod.Sequence__c = seq;
                        tod.Opportunity__c = opp.Id;
                        tod.Date__c = baseDate;
                        tod.Product__c = oli.Name;
                        tod.Quantity__c = qtyTod;
                        tod.Amount__c = (oli.UnitPrice * qtyTod);
                        tod.Sales_Price__c = oli.UnitPrice;
                        tod.Sequence_Per_Product__c = i;
                        tod.Frequency_Per_Product__c = freq;
                        tod.Total_Qty_Per_Product__c = oli.Quantity;
                        termsToInsert.add(tod);
                    }
                    else if (i != freq) {
                        Term_of_Delivery__c tod = new Term_of_Delivery__c();
                        tod.Sequence__c = seq;
                        tod.Opportunity__c = opp.Id;
                        tod.Date__c = baseDate.addMonths(seq-1);
                        tod.Product__c = oli.Name;
                        tod.Quantity__c = qtyTod;
                        tod.Amount__c = (oli.UnitPrice * qtyTod);
                        tod.Sales_Price__c = oli.UnitPrice;
                        tod.Sequence_Per_Product__c = i;
                        tod.Frequency_Per_Product__c = freq;
                        tod.Total_Qty_Per_Product__c = oli.Quantity;
                        termsToInsert.add(tod);
                    }
                    else {
                        Term_of_Delivery__c tod = new Term_of_Delivery__c();
                        tod.Sequence__c = seq;
                        tod.Opportunity__c = opp.Id;
                        tod.Date__c = baseDate.addMonths(seq-1);
                        tod.Product__c = oli.Name;
                        tod.Quantity__c = (oli.Quantity - tempSumQty);
                        tod.Amount__c = (oli.UnitPrice * (oli.Quantity - tempSumQty));
                        tod.Last_Sequence__c = true;
                        tod.Sales_Price__c = oli.UnitPrice;
                        tod.Sequence_Per_Product__c = i;
                        tod.Frequency_Per_Product__c = freq;
                        tod.Total_Qty_Per_Product__c = oli.Quantity;
                        termsToInsert.add(tod);
                    }
                    tempSumQty += qtyTod;
                    seq++;
                }
            }
        }
        
        insert termsToInsert;
    }
}