Breaking DML Cascades with AsyncAfterCommit in Revenue Cloud
Revenue Cloud's pricing engine runs synchronously when a Quote Line Item is created or updated. This means any additional DML that occurs in the same transaction -- triggered by a Flow, Process Builder, or Apex trigger -- executes while the pricing engine is still mid-calculation. The result is corrupted pricing state, unpredictable field values, and errors that are difficult to trace back to their source.
How the Cascade Happens
Consider this scenario:
- A record-triggered Flow fires on QuoteLineItem creation.
- The Flow performs an Update Records element on the parent Quote (e.g., setting a status field).
- That Quote update triggers Revenue Cloud's pricing engine to recalculate.
- The pricing engine is already mid-calculation from the original QuoteLineItem insert.
- The engine encounters conflicting state -- field values it set moments ago have been overwritten or are in an intermediate state.
The root cause is that synchronous DML within the same transaction creates a re-entrant call to the pricing engine. The engine does not expect to be invoked while it is already running, and it has no built-in guard against this.
Common Symptoms
- Quote Line Items saved with incorrect
TotalPriceorUnitPricevalues "FIELD_INTEGRITY_EXCEPTION: Total Price is required"on line items that have pricing data- Pricing calculations that work in isolation but fail when Flows are active
- Intermittent errors that disappear when Flows are deactivated and reappear when reactivated
- Debug logs showing field values changing unexpectedly mid-transaction
Diagnosing the Problem
The fastest way to confirm a DML cascade issue:
- Deactivate all record-triggered Flows on QuoteLineItem and Quote.
- Perform the pricing operation manually.
- If the operation succeeds, reactivate Flows one at a time to identify the offending Flow.
In debug logs, look for these indicators:
- Multiple
DML_BEGIN/DML_ENDpairs for Quote or QuoteLineItem within a single transaction FLOW_START_INTERVIEWSentries appearing between pricing engine operations- Field values in
VARIABLE_ASSIGNMENTentries that do not match what the pricing engine should have set
The Solution: AsyncAfterCommit
Salesforce Flow provides an AsyncAfterCommit path type in record-triggered Flows. This path executes after the triggering transaction has fully committed -- meaning the pricing engine has completed its work, all field values are finalized, and the record is in a stable state.
Flow Configuration
- Open the record-triggered Flow that performs secondary DML (e.g., updating the parent Quote).
- In the Flow's Start element, change the path from Run Immediately to Run Asynchronously (AsyncAfterCommit).
- Alternatively, keep the immediate path for read-only operations (like sending notifications) and move only the DML operations to an AsyncAfterCommit path.
Structuring the Flow
Start (QuoteLineItem - After Create)
├── Run Immediately Path
│ └── Read-only operations only (Get Records, Decisions, Assignments)
│ Do NOT perform Create/Update/Delete here
│
└── Run Asynchronously (After Commit) Path
└── Update Records: Set Quote status field
└── Create Records: Log entry or notification record
└── Any other DML operations
The critical rule: no DML in the immediate path when the triggering object is managed by the Revenue Cloud pricing engine.
When AsyncAfterCommit Is Appropriate
| Operation | Path | Reason |
|---|---|---|
| Update parent Quote fields | AsyncAfterCommit | Avoids re-triggering pricing engine |
| Create a related log record | AsyncAfterCommit | DML would cascade in synchronous context |
| Read Quote data for a decision | Run Immediately | No DML, no pricing engine conflict |
| Send a platform event | Run Immediately | Platform events do not trigger DML cascades |
| Update a completely unrelated object | AsyncAfterCommit | Any DML in a pricing transaction is risky |
Important Caveats
Timing: AsyncAfterCommit operations do not run instantly. There is a brief delay (typically seconds) between the transaction commit and the async execution. If downstream processes depend on the updated values being immediately available, account for this delay.
Error isolation: If the AsyncAfterCommit path fails, it does not roll back the original transaction. The Quote Line Item is already committed. Design error handling in the async path to log failures and alert administrators rather than relying on transactional rollback.
Governor limits: The AsyncAfterCommit path runs in its own transaction with a fresh set of governor limits. This is actually an advantage -- complex operations that might approach limits in the synchronous context have a full allocation in the async path.
Key Takeaway
Revenue Cloud's pricing engine assumes exclusive control of the transaction during pricing calculations. Any Flow or trigger that introduces additional DML during that window risks corrupting the pricing state. AsyncAfterCommit is the platform-native solution: it defers secondary DML until the pricing engine has finished, breaking the cascade while preserving all automation logic.