For the complete documentation index, see llms.txt. This page is also available as Markdown.

Plan Entitlements

Commerce → Plan Entitlements (admin only)

Plan entitlements answer one question for your application: what does this customer's plan actually let them do?

Without them, the answer usually lives inside your app as a hard-coded list — "Starter means five seats, Pro means unlimited." That works until you want to change what a plan includes, at which point you need a code change and a deploy to sell something different. Moving the answer into PeakCommerce means changing a plan is a settings change.

PeakCommerce never interprets what your feature keys mean. You define your own vocabulary; PeakCommerce stores it, resolves it per customer, and only ever looks at a feature's type — which it uses to reject values that would break your app.

The two halves

Setting this up is two steps, and the page is laid out in that order.

  1. Feature vocabulary — the things your product can gate on, named once.

  2. What each plan grants — the value each product carries for each feature.

You need step 1 before step 2 will do anything.

Step 1 — Register your feature vocabulary

Give each feature a key, a display name, and a type.

The key is what your application code will ask for, so treat it as an API contract rather than a label — max_seats, not "Max Seats". It must be lower_snake_case. Once other systems are reading it, it is not editable: see Changing your mind below.

Pick the type carefully, because it decides what values are legal:

Type
Use it for
Legal values

Boolean

A capability that is simply on or off — "can export reports"

On / Off. There is no third state.

Limit

A countable ceiling — seats, projects, API calls

A whole number, or blank for unlimited

Config

Anything structured — a theme, a tier name, a list

Any JSON value

"Blank means unlimited" is the one to remember

For a Limit feature, leaving the value empty does not mean "not set" — it means unlimited, and it is delivered to your app as an explicit null.

This trips people up in a way that matters: if your application treats a missing or null limit as zero, an unlimited plan will lock your best customers out of the feature they are paying most for. Decide deliberately how your app reads null, and read the Entitlements API reference before you write that gating code.

Step 2 — Set what each plan grants

Choose a product from the picker. Your products are your plans — there is no separate plan object to maintain.

Set a value for each feature. Values save as you go. A feature you leave untouched shows "Not set — this plan grants nothing for it", which is different from a Limit set to blank/unlimited.

If you enter something the feature's type does not allow, the save is rejected with the reason. That check happens on write on purpose: a bad value that gets stored is served to your app immediately, and from inside your app it is nearly impossible to work out where a nonsense number came from.

What happens next — how your app uses this

Defining entitlements is not the end of the job; something has to read them.

Your application reads the resolved values from the Entitlements API and gates its own features on them:

Both need an API key with the read scope. The response is a flat map of your keys to their final values, along with resolvedFrom, which names the product the values came from.

Subscription webhooks carry the same resolved set, so an app reacting to subscription.created can gate immediately without a second call. See Webhooks overview.

Two behaviours worth knowing before you build against it:

  • A customer holding several subscriptions gets one resolved set per subscription, never merged. Two plans can disagree, and PeakCommerce will not silently pick a winner for you.

  • Add-on products do not contribute to a resolved set today. The values come from the subscription's base product. If a customer needs more than their plan grants, use an override.

Granting one customer more — overrides

You will eventually need to give a specific customer something their plan does not include: an apology after an outage, a promotional bump, a negotiated exception.

That is an override, and it is deliberately not on this page. Overrides are granted against a customer's subscription by staff with the Customer Entitlement Overrides permission — tenant admins, Sales, and CSR — with a reason recorded and an optional expiry. An expiring override simply stops applying when its time is up; nothing needs cleaning up.

Keeping the two apart is the point: a CSR can grant one customer an exception without being able to redefine what a plan means for everybody.

Changing your mind

  • Renaming a feature's display name is safe — it is only a label.

  • The key and type cannot be edited. Your app gates on the key, and every stored value was validated against the type; changing either would silently invalidate data already written and break a live integration with no error anywhere. To genuinely change one, delete the feature and register it again.

  • Deleting a feature also removes every plan default and every per-customer override for it, and any app gating on that key stops receiving it. The confirmation says so.

Who can see this page

Plan Entitlements is admin only. It appears under Commerce for users whose profile grants the Plan Entitlements resource; it is not available to CSR, Sales, partner, or customer profiles, and cannot be granted to them.

Last updated

Was this helpful?