quote → cash
EN/FR Contact

Pricing·Advanced·11 min·Updated 2026-10-05

Procedure Plans: what to do when one pricing procedure is full

A pricing procedure has a ceiling. We hit it at 128 elements with another offer still to build. Here is what the ceiling actually is, why counting it is harder than it looks, and what splitting the procedure costs you.

Salesforce docs documented by SalesforceField experience observed on a real orgRecommended pattern what we recommendTo verify unverified

The ceiling is real, and you will meet it

A pricing procedure is an expression set: an ordered list of elements that turns a list price into a net price. On the org where this happened, the default procedure carried 128 elements against an observed ceiling of 130. The next commercial offer had nowhere to go.

That is not a lot of headroom for a catalog that is still growing, and it arrives faster than anyone plans for, because every conditional rule, every tier, every rounding step and every discount mechanism consumes elements in the same budget.

Counting the elements is harder than it looks

Here is the part that makes capacity planning genuinely difficult: the procedure that executes is not the procedure you edit.

Revenue Cloud compiles the procedure you maintain into a generated version — the one with the _Auto suffix — and that compiled version is what runs. On the same org, the source carried 81 standard steps while the compiled version carried 128. Open the source, count, and conclude you have half your budget left, and you are wrong by a factor of more than one and a half.

Anything you want to know about runtime pricing behaviour has to be read from the compiled procedure. This applies well beyond capacity: it is the same reason a migration verified against the source can fail completely in the target org.

Before you split: stop spending elements on nothing

Splitting is the interesting answer, but it is rarely the first one. The cheaper move is to stop consuming the budget on logic that does not need to be there.

The rule is simple and it is violated constantly: a decision table is for a condition or a tier. Nothing else. If a product has one price, that price belongs on the price book entry, where it costs zero procedure elements. Decision tables added by reflex — one per product, because that felt tidy — are the single biggest source of avoidable ceiling consumption we have seen.

Auditing a full procedure for tables that answer no question frequently recovers enough room to postpone the architectural change entirely.

Splitting: an orchestrator and one procedure per offer

When the logic genuinely is that large, the native answer is a procedure plan: a definition that evaluates criteria and selects which procedure to run, with one procedure per offer, each with its own element budget.

The structure is three objects. A definition that holds the plan, its criteria that decide which branch applies, and its options that name the procedure each branch runs. Salesforce exposes the whole thing through both metadata and a REST evaluation API, so a plan can be built, versioned and tested without the UI.

The second benefit is the one people underestimate: an offer's pricing logic becomes readable on its own, instead of interleaved with every other offer's steps inside one 128-element list. Debugging a price goes from reading a procedure to reading a procedure for that offer.

How we built it

  1. Build the per-offer procedure first, and prove it on a real quote. Reprice and read the line totals. Do not wire the orchestration until one branch demonstrably prices correctly on its own.
  2. Then wire the plan. The two org settings that enable plan orchestration are reversible, which matters more than it sounds — see below.
  3. Reactivate everything you touched. Editing a pricing procedure deactivates it. A deactivated procedure does not price at all, and the symptom — every line at list price — looks nothing like “you forgot to reactivate”.

The rollback that proved something unrelated

While the plan was being built, the same org threw an unrelated error in the product configurator. The two changes were close enough in time that the plan was the obvious suspect.

Rolling the two orchestration settings back did not clear the configurator error — which proved, cleanly and immediately, that pricing was not involved at all. The investigation moved to the catalog, where the cause actually was.

That is worth stating as a method rather than an anecdote. Change one thing, observe, then change the next. Had the plan and a catalog change gone in together, nothing could have been eliminated, and the error would have been attributed to the most recent architectural change — which is exactly how teams end up reverting work that was never the problem.

What it costs

More procedures means more artefacts to deploy and keep aligned, and a migration surface that grows with the catalog. Procedure plans are also newer than the rest of the pricing stack, so there is less written about them outside Salesforce's own documentation.

Against that: a single procedure at 128 of 130 elements is not a system you can extend, and the alternative to splitting is refusing the next offer.

Salesforce components

Select one to open its detail.

What this is based on

  • The ceiling of 130 elements, the 128 in use and the 81-versus-128 gap between source and compiled procedure were observed on one production org. Treat the exact numbers as indicative and count on your own org before planning capacity.
  • Editing a pricing procedure deactivates it. This has bitten every project we have run.
  • Procedure plan orchestration is enabled by org settings that can be switched back — which makes it a safe thing to try, and a useful elimination tool.

Salesforce resources