We have multi-currency enabled and custom pricebooks. I have a before insert class that automatically sets the pricebook when an Opportunity is created that works well. When a user changes the currency on the Opportunity the pricebook is removed by Salesforce API per the standard functionality.
So I wrote a before update class to check if the currency changes and then set the pricebook back. The problem is Salesforce still removes the pricebook after the the record is saved and reloads in the UI. Checking debug logs, before the process, during the process, after the process, the pricebook2id is set all through my filters and setting the pricebook.
If you save/edit the record after changing the currency the pricebook gets sets so I'm pretty sure my logic is right.
My question is do you know when Salesforce actually removes the Pricebook2Id when the currency is changed on an Opportunity? If the before update doesn't work I suppose I have to move it to after update but then I'd have to do another update on the record to update it after instead of setting it before. That feels like a wrong way to do it.
Example:
public static void filterupdate(Map<Id, Opportunity> oldMap, Map<Id, Opportunity> newMap)
{
List<Opportunity> oppsToUpdate = new List<Opportunity>();
// Check if the fields changed
for(Opportunity oppy : newMap.values())
{
if(
oppy.Pricebook2Id != oldMap.get(oppy.Id).Pricebook2Id ||
oppy.CurrencyISOCode != oldMap.get(oppy.Id).CurrencyISOCode ||
oppy.Pricebook2id == null
)
{
oppsToUpdate.add(oppy);
}
}
setPricebook(oppsToUpdate);
}
public static void setPricebook(List<Opportunity> newList)
{
Id pb = [
SELECT Id
FROM Pricebook2
WHERE Name = 'NPD Price Book'
ORDER BY Id DESC
LIMIT 1].Id;
if(pb != null)
{
for(Opportunity oppy : newList)
{
oppy.Pricebook2id = pb;
}
}
}