Move the company onto another plan
Chooses the authenticated company’s plan from the 1st of next UTC month, sized to its usage, and how it is paid for. This month keeps its plan, or its lack of one, and its usage. A company with no plan chooses its first one here; a choice for a company with no plan must name a plan_key or a monthly_price_cents. The plan is charged from the month a root admin sets as its plan billing start. The answer shows the choice as next_plan. Choosing the plan in force, or sending keep_current_plan, cancels a waiting choice. Only a company platform billing invoices has a plan to change.
curl --request PATCH \
--url https://api.fluid.app/api/settings/billing/credits \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--data '
{
"plan_key": "growth",
"billing_interval": "annual"
}
'import requests
url = "https://api.fluid.app/api/settings/billing/credits"
payload = {
"plan_key": "growth",
"billing_interval": "annual"
}
headers = {
"Authorization": "Bearer <token>",
"Content-Type": "application/json"
}
response = requests.patch(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'PATCH',
headers: {Authorization: 'Bearer <token>', 'Content-Type': 'application/json'},
body: JSON.stringify({plan_key: 'growth', billing_interval: 'annual'})
};
fetch('https://api.fluid.app/api/settings/billing/credits', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api.fluid.app/api/settings/billing/credits",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "PATCH",
CURLOPT_POSTFIELDS => json_encode([
'plan_key' => 'growth',
'billing_interval' => 'annual'
]),
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>",
"Content-Type: application/json"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://api.fluid.app/api/settings/billing/credits"
payload := strings.NewReader("{\n \"plan_key\": \"growth\",\n \"billing_interval\": \"annual\"\n}")
req, _ := http.NewRequest("PATCH", url, payload)
req.Header.Add("Authorization", "Bearer <token>")
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.patch("https://api.fluid.app/api/settings/billing/credits")
.header("Authorization", "Bearer <token>")
.header("Content-Type", "application/json")
.body("{\n \"plan_key\": \"growth\",\n \"billing_interval\": \"annual\"\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api.fluid.app/api/settings/billing/credits")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Patch.new(url)
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"plan_key\": \"growth\",\n \"billing_interval\": \"annual\"\n}"
response = http.request(request)
puts response.read_body{
"credits": {
"card_surcharge": {
"rate_basis_points": 290,
"applies": false,
"auto_reload_applies": false
},
"balance_cents": 184250,
"spendable_cents": 184250,
"expired_cents": 0,
"held_cents": 0,
"pending": {
"card": {
"count": 0,
"amount_cents": 0,
"total_cents": 0,
"credit_cents": 0
},
"us_bank_account": {
"count": 0,
"amount_cents": 0,
"total_cents": 0,
"credit_cents": 0
}
},
"drawn_cents": 0,
"pace": null,
"month_statement": {
"opening_cents": 74250,
"plan_cents": 0,
"purchased_cents": 110000,
"granted_cents": 0,
"used_cents": 0,
"expired_cents": 0,
"revoked_cents": 0,
"closing_cents": 184250
},
"expiries": [
{
"at": "2027-09-12T16:20:05Z",
"cents": 110000
}
],
"next_expiry": {
"at": "2027-09-12T16:20:05Z",
"cents": 110000
},
"low_balance_cents": 2000,
"funded_categories": [
"ai",
"hosting"
],
"credit_billing": null,
"plan": {
"key": "launch",
"name": "Launch",
"monthly_price_cents": 250000,
"bonus_percent": 0,
"included_credits": 2500,
"billing_interval": "monthly",
"monthly_charge_cents": 250000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 250000,
"monthly_price_surcharge_cents": 0,
"monthly_price_total_cents": 250000
},
"next_plan": {
"key": "growth",
"name": "Growth",
"monthly_price_cents": 1500000,
"bonus_percent": 10,
"included_credits": 16500,
"billing_interval": "annual",
"monthly_charge_cents": 1350000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 1350000,
"monthly_price_surcharge_cents": 0,
"monthly_price_total_cents": 1500000,
"starts_on": "2026-10-01"
},
"plans": [
{
"monthly_price_cents": 250000,
"bonus_percent": 0,
"included_credits": 2500,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 250000
},
{
"monthly_price_cents": 1000000,
"bonus_percent": 10,
"included_credits": 11000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 1000000
},
{
"monthly_price_cents": 2500000,
"bonus_percent": 20,
"included_credits": 30000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 2500000
},
{
"monthly_price_cents": 5000000,
"bonus_percent": 30,
"included_credits": 65000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 5000000
}
],
"catalog_plans": [
{
"key": "launch",
"name": "Launch",
"monthly_price_cents": 250000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 250000
},
{
"key": "growth",
"name": "Growth",
"monthly_price_cents": 1500000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 1500000
},
{
"key": "scale",
"name": "Scale",
"monthly_price_cents": 5000000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 5000000
},
{
"key": "enterprise",
"name": "Enterprise",
"monthly_price_cents": 15000000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 15000000
}
],
"credit_bonus_mode": "always",
"usage": {
"period_start": "2026-09-01T00:00:00Z",
"orders": 70012,
"ai": 18400,
"hosting": 0,
"media": null,
"studios": null
},
"orders_percent": "1.45",
"rollover_months": 3,
"annual_discount_percent": 10,
"top_up_cents": 100,
"min_purchase_cents": 10000,
"max_purchase_cents": 1000000,
"discounts": [
{
"min_cents": 10000,
"percent_off": 0
},
{
"min_cents": 50000,
"percent_off": 5
},
{
"min_cents": 100000,
"percent_off": 10
},
{
"min_cents": 250000,
"percent_off": 15
},
{
"min_cents": 500000,
"percent_off": 20
},
{
"min_cents": 1000000,
"percent_off": 30
}
],
"purchasable": true,
"purchase_terms": {
"version": "2026-10-06",
"text": "Usage credits are prepaid. One credit pays for one US dollar of Fluid usage. Credits you buy, and any bonus credits on them, expire one year after the purchase date. Credits are not refundable and cannot move between companies, except where Fluid refunds unused purchased credits to the payment method that paid for them. If a payment is refunded, returned, or disputed, the credits it paid for, and their bonus share, are taken back, even when that makes the balance negative. A purchase paid with a credit card or a bank account can carry a processing fee that Fluid sets for your account: a percentage of the amount, which can have a cap. The fee is shown before you pay and charged with it. Debit cards and prepaid cards carry no fee. A refund returns the fee in proportion to the amount refunded."
}
},
"status": 200,
"meta": {
"request_id": "f3b8c2d1-6a4e-4f7b-9c1d-2e5a8b7c4d90",
"timestamp": "2026-09-30T14:05:11Z"
}
}{
"message": "<string>",
"error": "<string>",
"error_message": "<string>",
"errors": "<string>",
"meta": {
"request_id": "<string>",
"timestamp": "2023-11-07T05:31:56Z"
}
}{
"message": "<string>",
"error": "<string>",
"error_message": "<string>",
"errors": "<string>",
"meta": {
"request_id": "<string>",
"timestamp": "2023-11-07T05:31:56Z"
}
}{
"message": "<string>",
"error": "<string>",
"error_message": "<string>",
"errors": "<string>",
"meta": {
"request_id": "<string>",
"timestamp": "2023-11-07T05:31:56Z"
}
}{
"message": "<string>",
"error": "<string>",
"error_message": "<string>",
"errors": "<string>",
"meta": {
"request_id": "<string>",
"timestamp": "2023-11-07T05:31:56Z"
}
}{
"message": "<string>",
"error": "<string>",
"error_message": "<string>",
"errors": "<string>",
"meta": {
"request_id": "<string>",
"timestamp": "2023-11-07T05:31:56Z"
}
}Body
The monthly charge, after any annual discount and before the credit card fee, the merchant was shown. When the choice, laid over the plan waiting or in force now, would charge anything else, nothing is saved and the answer is 409 plan_charge_changed with the charge it would be in details.monthly_charge_cents.
x >= 0The monthly total, the credit card fee on the saved payment method included, the merchant was shown. When the choice would now total anything else, as after a switch to a card, nothing is saved and the answer is 409 plan_charge_changed with the total it would be in details.monthly_total_cents.
x >= 0curl --request PATCH \
--url https://api.fluid.app/api/settings/billing/credits \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--data '
{
"plan_key": "growth",
"billing_interval": "annual"
}
'import requests
url = "https://api.fluid.app/api/settings/billing/credits"
payload = {
"plan_key": "growth",
"billing_interval": "annual"
}
headers = {
"Authorization": "Bearer <token>",
"Content-Type": "application/json"
}
response = requests.patch(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'PATCH',
headers: {Authorization: 'Bearer <token>', 'Content-Type': 'application/json'},
body: JSON.stringify({plan_key: 'growth', billing_interval: 'annual'})
};
fetch('https://api.fluid.app/api/settings/billing/credits', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api.fluid.app/api/settings/billing/credits",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "PATCH",
CURLOPT_POSTFIELDS => json_encode([
'plan_key' => 'growth',
'billing_interval' => 'annual'
]),
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>",
"Content-Type: application/json"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://api.fluid.app/api/settings/billing/credits"
payload := strings.NewReader("{\n \"plan_key\": \"growth\",\n \"billing_interval\": \"annual\"\n}")
req, _ := http.NewRequest("PATCH", url, payload)
req.Header.Add("Authorization", "Bearer <token>")
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.patch("https://api.fluid.app/api/settings/billing/credits")
.header("Authorization", "Bearer <token>")
.header("Content-Type", "application/json")
.body("{\n \"plan_key\": \"growth\",\n \"billing_interval\": \"annual\"\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api.fluid.app/api/settings/billing/credits")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Patch.new(url)
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"plan_key\": \"growth\",\n \"billing_interval\": \"annual\"\n}"
response = http.request(request)
puts response.read_body{
"credits": {
"card_surcharge": {
"rate_basis_points": 290,
"applies": false,
"auto_reload_applies": false
},
"balance_cents": 184250,
"spendable_cents": 184250,
"expired_cents": 0,
"held_cents": 0,
"pending": {
"card": {
"count": 0,
"amount_cents": 0,
"total_cents": 0,
"credit_cents": 0
},
"us_bank_account": {
"count": 0,
"amount_cents": 0,
"total_cents": 0,
"credit_cents": 0
}
},
"drawn_cents": 0,
"pace": null,
"month_statement": {
"opening_cents": 74250,
"plan_cents": 0,
"purchased_cents": 110000,
"granted_cents": 0,
"used_cents": 0,
"expired_cents": 0,
"revoked_cents": 0,
"closing_cents": 184250
},
"expiries": [
{
"at": "2027-09-12T16:20:05Z",
"cents": 110000
}
],
"next_expiry": {
"at": "2027-09-12T16:20:05Z",
"cents": 110000
},
"low_balance_cents": 2000,
"funded_categories": [
"ai",
"hosting"
],
"credit_billing": null,
"plan": {
"key": "launch",
"name": "Launch",
"monthly_price_cents": 250000,
"bonus_percent": 0,
"included_credits": 2500,
"billing_interval": "monthly",
"monthly_charge_cents": 250000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 250000,
"monthly_price_surcharge_cents": 0,
"monthly_price_total_cents": 250000
},
"next_plan": {
"key": "growth",
"name": "Growth",
"monthly_price_cents": 1500000,
"bonus_percent": 10,
"included_credits": 16500,
"billing_interval": "annual",
"monthly_charge_cents": 1350000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 1350000,
"monthly_price_surcharge_cents": 0,
"monthly_price_total_cents": 1500000,
"starts_on": "2026-10-01"
},
"plans": [
{
"monthly_price_cents": 250000,
"bonus_percent": 0,
"included_credits": 2500,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 250000
},
{
"monthly_price_cents": 1000000,
"bonus_percent": 10,
"included_credits": 11000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 1000000
},
{
"monthly_price_cents": 2500000,
"bonus_percent": 20,
"included_credits": 30000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 2500000
},
{
"monthly_price_cents": 5000000,
"bonus_percent": 30,
"included_credits": 65000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 5000000
}
],
"catalog_plans": [
{
"key": "launch",
"name": "Launch",
"monthly_price_cents": 250000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 250000
},
{
"key": "growth",
"name": "Growth",
"monthly_price_cents": 1500000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 1500000
},
{
"key": "scale",
"name": "Scale",
"monthly_price_cents": 5000000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 5000000
},
{
"key": "enterprise",
"name": "Enterprise",
"monthly_price_cents": 15000000,
"monthly_surcharge_cents": 0,
"monthly_total_cents": 15000000
}
],
"credit_bonus_mode": "always",
"usage": {
"period_start": "2026-09-01T00:00:00Z",
"orders": 70012,
"ai": 18400,
"hosting": 0,
"media": null,
"studios": null
},
"orders_percent": "1.45",
"rollover_months": 3,
"annual_discount_percent": 10,
"top_up_cents": 100,
"min_purchase_cents": 10000,
"max_purchase_cents": 1000000,
"discounts": [
{
"min_cents": 10000,
"percent_off": 0
},
{
"min_cents": 50000,
"percent_off": 5
},
{
"min_cents": 100000,
"percent_off": 10
},
{
"min_cents": 250000,
"percent_off": 15
},
{
"min_cents": 500000,
"percent_off": 20
},
{
"min_cents": 1000000,
"percent_off": 30
}
],
"purchasable": true,
"purchase_terms": {
"version": "2026-10-06",
"text": "Usage credits are prepaid. One credit pays for one US dollar of Fluid usage. Credits you buy, and any bonus credits on them, expire one year after the purchase date. Credits are not refundable and cannot move between companies, except where Fluid refunds unused purchased credits to the payment method that paid for them. If a payment is refunded, returned, or disputed, the credits it paid for, and their bonus share, are taken back, even when that makes the balance negative. A purchase paid with a credit card or a bank account can carry a processing fee that Fluid sets for your account: a percentage of the amount, which can have a cap. The fee is shown before you pay and charged with it. Debit cards and prepaid cards carry no fee. A refund returns the fee in proportion to the amount refunded."
}
},
"status": 200,
"meta": {
"request_id": "f3b8c2d1-6a4e-4f7b-9c1d-2e5a8b7c4d90",
"timestamp": "2026-09-30T14:05:11Z"
}
}{
"message": "<string>",
"error": "<string>",
"error_message": "<string>",
"errors": "<string>",
"meta": {
"request_id": "<string>",
"timestamp": "2023-11-07T05:31:56Z"
}
}{
"message": "<string>",
"error": "<string>",
"error_message": "<string>",
"errors": "<string>",
"meta": {
"request_id": "<string>",
"timestamp": "2023-11-07T05:31:56Z"
}
}{
"message": "<string>",
"error": "<string>",
"error_message": "<string>",
"errors": "<string>",
"meta": {
"request_id": "<string>",
"timestamp": "2023-11-07T05:31:56Z"
}
}{
"message": "<string>",
"error": "<string>",
"error_message": "<string>",
"errors": "<string>",
"meta": {
"request_id": "<string>",
"timestamp": "2023-11-07T05:31:56Z"
}
}{
"message": "<string>",
"error": "<string>",
"error_message": "<string>",
"errors": "<string>",
"meta": {
"request_id": "<string>",
"timestamp": "2023-11-07T05:31:56Z"
}
}