This page covers the API. For the billing logic behind it, see Billing changes. For the same change in the app, see Subscriptions.
POST /v1/subscriptions/{id}/units sets a subscription’s unit count. It needs the subscriptions:write scope. Send the new total, not the difference.
Saasybill applies the same rules as the Update Units dialog in the app. You choose whether to prorate, or leave it out and let the organisation’s proration defaults decide. The plan type and the direction of the change decide the document.
Units are for a plan’s recurring fee. A plan with no recurring fee (
no_base_fee) has no units, and the request is refused. Metered usage isn’t set as units. Report it as events instead.Request fields
proration_behaviour is refused unless prorate is true. effective_date is refused when the change isn’t prorated.
units can be lower than the subscription’s minimum. See Minimum units.What happens
Saasybill classifies the new total against the units already paid for this period.Increasing units
Prorated amounts follow the proration formula: the difference in value, multiplied by the days remaining, divided by the days in the period.
Decreasing units
The subscription’sunits update straight away, but the customer has paid for the period. What happens next depends on prorate.
A credit only covers units that were paid for. Units already removed without a credit aren’t credited again.
Volume plans
On a volume plan, a unit change that crosses into another band re-prices every unit, so the total can move the opposite way to the units. An increase that crosses into a cheaper band lowers the total. Saasybill raises a prorated credit note instead of an invoice.proratecan’t befalsefor this change. It answers422 proration_required. When you leaveprorateout, Saasybill prorates the change whatever the proration defaults say.- The credit is always issued immediately, so
proration_behaviouris fixed tocharge_immediately. - The credit note is held as a credit balance on the subscription and applied to future invoices.
change.credit_noteholds its id.
prorate out.
Units already paid for
Units at or below the number already paid for this period are never charged twice. If a customer drops from 10 to 8 units and then returns to 10, nothing more is billed until renewal.When proration is fixed
proration_behaviour is fixed to charge_immediately when:
- the subscription is in its final period, because there is no renewal to charge at
- the renewal invoice has already been created, because there is no renewal invoice left to add to
Minimum units
A minimum is a billing floor, not a limit onunits. You can set units below the subscription’s minimum, including to 0. Each period bills the larger of units and minimum_units.
minimum_units on the subscription is the minimum in force: the plan’s, or the subscription’s own when that is higher. units stays what you set.
For example, a subscription has a minimum of 10 units and is paid for 15.
- Prorating a decrease to 6 credits only the 5 units between 15 and 10. The drop from 10 to 6 changes
unitsand credits nothing. - Setting 6 and later prorating an increase to 15 charges only the 5 units between 10 and 15.
- Moving from 8 to 5 changes
unitsand raises no document. The period already bills the minimum.
A change that costs nothing extra has nothing to prorate. Naming
prorate: true for it is refused with 422 proration_not_available. Send prorate: false, or leave prorate out. units_unchanged compares your total with units, not with the minimum.minimum_units at creation. See Create a subscription.
Proration defaults
When a request leavesprorate out, the organisation’s proration defaults decide whether to prorate. They are off unless an admin switches them on, so an integration that never sends prorate behaves as it always has.
An owner or admin can change them under Developer Settings, then Configuration. The setting is called Proration Behaviour. It has two parts.
The rules:
- A
proratein the request always wins. It is checked exactly as it always was, and the defaults aren’t consulted. - The outcome picks the setting, not the direction. A change that charges follows Upgrades. A credit you could decline follows Downgrades.
- A default prorates from today.
effective_datedefaults to today in the subscription’s timezone. You can still sendeffective_dateto choose another day in the current period. - A default yields instead of refusing. If the change can’t be prorated, the default doesn’t prorate and the request goes through. That is when there is nothing to prorate, when a non-prorated change has already locked proration for the period, or when the timing is fixed. A volume increase that lowers the total is credited immediately whatever the settings say.
- A change left unprorated counts as non-prorated. It locks proration in that direction until the next renewal, exactly as
prorate: falsewould. - Fields that contradict the outcome are still refused.
proration_behaviourwithoutprorate: trueis refused whatever the settings say. So iseffective_datewhen the defaults leave the change unprorated, with422 effective_date_not_applicable.
change.proration_source is organisation_default when the settings decided, and change.prorated says whether the change was prorated.
The defaults apply to API requests only. The Update Units dialog in the app always asks.
After the renewal invoice is created
Saasybill creates a renewal invoice ahead of the renewal date, set by Invoice Creation Date in Company Settings. Once that has happened, a unit change touches two periods: the current one, and the next one that’s already been invoiced. Then a document has to carry the change. You choose it per request withdocument, or once for the organisation.
Before the renewal invoice exists,
document is refused. After it exists, document is optional.
Set a default for the organisation
Amending changes a document the customer may already hold, so the default isseparate. An owner or admin can change it under Developer Settings, then Configuration. The setting is called Changes After Invoicing.
A
document in the request always wins over the setting.
If the setting is Amend and the renewal invoice can no longer be changed, for example because it has a payment or credit on it, Saasybill raises a separate invoice instead. It doesn’t refuse the request. The response says so in
change.document_fallback_reason. A request that names amend itself is refused in that case, and the error says why.amend, change.renewal_invoice is the updated renewal invoice. With separate, change.invoice is the new invoice. change.document tells you which happened.
The response
The response is the updated subscription with achange object.
- Charged now
- Charged at renewal
- Prorated by default
- No document
renewal_value in the response is what the next renewal will bill at the new units.Example
When a change is refused
A unit change is refused with422 when it breaks a rule. See the unit change codes for each.
A
409 xero_accounts_not_mapped means an admin needs to map the Xero accounts on the Integrations tab before units can change.