---
title: "Move an existing subscription to another paid tier"
method: POST
path: "/api/billing/change-plan"
tags: ["Internal"]
---

# Move an existing subscription to another paid tier

`POST /api/billing/change-plan`

## Request

- Base URL: `https://api.volanea.com`
- URL: `https://api.volanea.com/api/billing/change-plan`
- Auth: HTTP bearer

Upgrades or downgrades the project's ACTIVE subscription in place — on whichever provider backs it (Dodo Payments or Lemon Squeezy, resolved server-side). No new checkout; the provider prorates and the plan flips when its webhook confirms the change, so the response is `pending: true`. To go back to free, `PATCH /v1/billing` with `plan: "free"` instead. 409 when there is no active subscription (start a checkout), the project is already on that plan, or the tier has no product on this install.

## Request body

- object
  - `plan` 'starter' | 'growth' | 'scale', required: The tier to move to. Enterprise is contact-us only.

## Response `200`

The change was requested on the provider.

- object
  - `ok` boolean, required
  - `provider` 'dodo' | 'lemonsqueezy', required: Which provider's subscription was changed.
  - `plan` 'starter' | 'growth' | 'scale', required
  - `pending` boolean, required: Always true — the plan flips when the provider webhook lands.

## Other responses

- `401`: Missing or invalid API key.
- `404`: Not found.
- `409`: No active subscription, already on that plan, or no product configured for the tier.
- `422`: Request validation failed (code `validation_error`, 422).

---

[API](https://skmtc.dev/volanea/apis/volanea-api.md) · [All operations](https://skmtc.dev/volanea/apis/volanea-api/llms.txt) · [OpenAPI document](https://skmtc.dev/volanea/apis/volanea-api/revisions/9e187ae84fda?raw)
