Organization API: Customer Portal: Services
The 13 Organization API operations for services.
Part of Customer Portal.
Operations
Section titled OperationsList my services
Section titled List my servicesGET /api/v1/orgs/{org_slug}/portal/services
List the signed-in customer's services, newest first, with the servers other customers shared with them.
Each row has the service's status, plan, billing_cycle, amount,
next_due_date and termination_date. termination_date is when the
service is set to end, in UTC, or null. ends_at_term_end is true
when the customer cancelled it for the end of the time paid for, which
POST .../keep can withdraw, and false for no end date or an end date
our team set. pending_plan_change is
an upgrade waiting for payment, or a switch of billing period waiting for
the next renewal (its applies_at is next_renewal). is_owner is
false for a shared server.
Parameters
Section titled Parameters| Name | In | Type | Required | Description |
|---|---|---|---|---|
org_slug |
path | string | yes | |
status_filter |
query | string | no | |
page |
query | integer | no | Default: 1. |
per_page |
query | integer | no | Default: 50. |
consistency |
query | string, one of strong, eventual |
no | strong (default): reads the primary when the request carries a Coritan-Read-After inside its window, as a client that has just written must. eventual: an idle poll that always reads a pooled replica. Either way, a page with something to heal is healed on the primary. Default: strong. |
Responses
Section titled Responses| Status | Meaning |
|---|---|
200 |
Success. |
422 |
The request is not valid. detail lists each problem. |
What the customer's servers are doing right now, in one request
Section titled What the customer's servers are doing right now, in one requestGET /api/v1/orgs/{org_slug}/portal/services/live
What the customer's servers are doing right now, in one request.
Declared above /services/{service_id} deliberately: that route parses an
int, so "live" would 422 rather than reach this one.
Parameters
Section titled Parameters| Name | In | Type | Required | Description |
|---|---|---|---|---|
org_slug |
path | string | yes | |
refresh |
query | boolean | no | Default: False. |
ids |
query | string | no | Comma-separated service ids to probe |
Responses
Section titled Responses| Status | Meaning |
|---|---|
200 |
Success. |
422 |
The request is not valid. detail lists each problem. |
Get my service
Section titled Get my serviceGET /api/v1/orgs/{org_slug}/portal/services/{service_id}
One of the customer's services, or a server shared with them, in the
shape of GET /portal/services, including its termination_date (when
it is set to end, or null) and ends_at_term_end (true for a
cancellation the customer can take back). Another customer's service
answers 404.
Parameters
Section titled Parameters| Name | In | Type | Required |
|---|---|---|---|
service_id |
path | integer | yes |
org_slug |
path | string | yes |
Responses
Section titled Responses| Status | Meaning |
|---|---|
200 |
Success. |
422 |
The request is not valid. detail lists each problem. |
Cancel one of the customer's own services, now or at the end of term
Section titled Cancel one of the customer's own services, now or at the end of termPOST /api/v1/orgs/{org_slug}/portal/services/{service_id}/cancel
Cancel one of the customer's own services, now or at the end of term.
The sequence lives in app.services.org_service_lifecycle so staff
cancelling on a customer's behalf run the very same one.
A cancellation keeps a paid container on the org's free plan when it sells
one. delete_server (with immediate) is the panel's Delete Server,
which deletes it regardless; without immediate it is a 422.
When the server falls back to the free plan, its add-ons end with it unless
their ids are in keep_addon_ids: those stay and bill on their own from
then on. A server that is deleted ends every add-on. An id that is not one
of the server's add-ons is a 422.
A cancellation for the end of the term (immediate false) can be taken
back until its termination_date with POST .../keep.
Parameters
Section titled Parameters| Name | In | Type | Required |
|---|---|---|---|
service_id |
path | integer | yes |
org_slug |
path | string | yes |
Request body
Section titled Request bodyapplication/json
| Field | Type | Required | Description |
|---|---|---|---|
immediate |
boolean | no | |
reason |
string or null | no | |
keep_ipv4 |
boolean | no | |
keep_snapshot |
boolean | no | |
delete_server |
boolean | no | |
keep_addon_ids |
array of integer | no | Server add-ons (the org_service_id values in the cancel preview's addons) that stay with the server when it falls back to the free plan. Each one bills on its own from then on. The server's other add-ons end with it. Only used when the server falls back to the free plan: a server that is deleted ends every add-on and the ids do nothing. An id that is not one of this server's add-ons answers 422. |
Responses
Section titled Responses| Status | Meaning |
|---|---|
200 |
Success. |
422 |
The request is not valid. detail lists each problem. |
Cancel my pending plan change
Section titled Cancel my pending plan changePOST /api/v1/orgs/{org_slug}/portal/services/{service_id}/cancel-plan-change
Cancel an unpaid upgrade so a different plan can be chosen, or call off
a switch of billing period that is waiting for the next renewal (the answer
then has invoice_id null and applies_at next_renewal).
Parameters
Section titled Parameters| Name | In | Type | Required |
|---|---|---|---|
service_id |
path | integer | yes |
org_slug |
path | string | yes |
Responses
Section titled Responses| Status | Meaning |
|---|---|
200 |
Success. |
422 |
The request is not valid. detail lists each problem. |
What cancelling right now would return, before committing to it
Section titled What cancelling right now would return, before committing to itGET /api/v1/orgs/{org_slug}/portal/services/{service_id}/cancel-preview
What cancelling right now would return, before committing to it.
For a server, falls_back_to_free says whether it stays on the free plan, and
addons lists its add-ons that are pending, active or suspended
(org_service_id, kind, name, quantity, amount, billing_cycle,
next_due_date). When the server falls back, send the ids you want to keep
as keep_addon_ids on the cancel.
Parameters
Section titled Parameters| Name | In | Type | Required | Description |
|---|---|---|---|---|
service_id |
path | integer | yes | |
org_slug |
path | string | yes | |
immediate |
query | boolean | no | Default: True. |
Responses
Section titled Responses| Status | Meaning |
|---|---|
200 |
Success. |
422 |
The request is not valid. detail lists each problem. |
Move one of the customer's services to another plan
Section titled Move one of the customer's services to another planPOST /api/v1/orgs/{org_slug}/portal/services/{service_id}/change-plan
Move one of the customer's services to another plan.
Send an Idempotency-Key so a retry does not ask twice. An upgrade
answers requires_payment: true with the invoice_id of the invoice
to pay, and applies once it is paid. A downgrade or a move at the same
price applies at once.
A free server may move onto a plan of any billing period, such as a
weekly one. When that period is not the free plan's own, the invoice is
one whole period of the new plan, and the period starts on the day the
invoice is paid. Every other service keeps its billing period: a plan of
another period answers 400.
A service on a Standalone product, such as a rank, can also take
another billing period of the same product (monthly to annually, or
back). That change costs nothing today and applies at the next renewal:
the answer has pending: true, scheduled: true, applies_at
next_renewal, effective_at and the new_* fields of the plan
that is waiting, and no invoice_id. The renewal invoice, the service's
amount and its billing cycle then use the new plan. Asking for another
period replaces the one waiting, and POST .../cancel-plan-change calls
it off. It answers 409 while the service is set to end or an upgrade
is waiting for payment.
A server add-on cannot be moved to another plan or billing period: it
answers 409. Cancel the add-on and order the one you want.
Parameters
Section titled Parameters| Name | In | Type | Required |
|---|---|---|---|
service_id |
path | integer | yes |
org_slug |
path | string | yes |
Idempotency-Key |
header | string or null | no |
Request body
Section titled Request bodyapplication/json (required)
| Field | Type | Required | Description |
|---|---|---|---|
org_pricing_id |
integer | yes | |
coupon_code |
string or null | no | A coupon code of the organization for an upgrade, checked as an order checks it. It comes off the upgrade invoice, and its use is counted when the invoice is paid. A code that does not apply answers 422 with errors and coupon (the reason's word, such as unknown or wrong_product). |
Responses
Section titled Responses| Status | Meaning |
|---|---|
200 |
Success. |
422 |
The request is not valid. detail lists each problem. |
Get community listing
Section titled Get community listingGET /api/v1/orgs/{org_slug}/portal/services/{service_id}/community-listing
Parameters
Section titled Parameters| Name | In | Type | Required |
|---|---|---|---|
service_id |
path | integer | yes |
org_slug |
path | string | yes |
Responses
Section titled Responses| Status | Meaning |
|---|---|
200 |
Success. |
422 |
The request is not valid. detail lists each problem. |
Upsert community listing
Section titled Upsert community listingPUT /api/v1/orgs/{org_slug}/portal/services/{service_id}/community-listing
Parameters
Section titled Parameters| Name | In | Type | Required |
|---|---|---|---|
service_id |
path | integer | yes |
org_slug |
path | string | yes |
Request body
Section titled Request bodyapplication/json (required)
| Field | Type | Required |
|---|---|---|
display_name |
string or null | no |
slug |
string or null | no |
tagline |
string or null | no |
description |
string or null | no |
category |
string or null | no |
tags |
array of string or null | no |
website_url |
string or null | no |
discord_url |
string or null | no |
icon_data_uri |
string or null | no |
banner_data_uri |
string or null | no |
gallery |
array of string or null | no |
seo_title |
string or null | no |
seo_description |
string or null | no |
show_player_count |
boolean or null | no |
published |
boolean or null | no |
Responses
Section titled Responses| Status | Meaning |
|---|---|
200 |
Success. |
422 |
The request is not valid. detail lists each problem. |
Update join-address branding (MOTD/favicon) for a service's sidecar gameproxy route
Section titled Update join-address branding (MOTD/favicon) for a service's sidecar gameproxy routePATCH /api/v1/orgs/{org_slug}/portal/services/{service_id}/gameproxy
Update join-address branding (MOTD/favicon) for a service's sidecar gameproxy route.
Parameters
Section titled Parameters| Name | In | Type | Required |
|---|---|---|---|
service_id |
path | integer | yes |
org_slug |
path | string | yes |
Request body
Section titled Request bodyapplication/json (required)
Type: Body.
Responses
Section titled Responses| Status | Meaning |
|---|---|
200 |
Success. |
422 |
The request is not valid. detail lists each problem. |
Withdraw a cancellation that is set for the end of the term, so the service keeps renewing
Section titled Withdraw a cancellation that is set for the end of the term, so the service keeps renewingPOST /api/v1/orgs/{org_slug}/portal/services/{service_id}/keep
Withdraw a cancellation that is set for the end of the term, so the service keeps renewing.
Send no body (or {}). It works on the customer's own service while it
is active and has an end date in the future: the termination_date goes
back to null, a server that would have moved to the free plan on that
date stays on its paid plan, and the organization's webhooks receive
service.cancellation_withdrawn. The answer is the service, as
GET /portal/services/{service_id} returns it.
Unpaid invoices that the cancellation cancelled stay cancelled, and so does a plan change it cleared. The next renewal is invoiced as usual, on the plan the service is on now.
It answers 409 with {"error", "message"} when it cannot keep the
service: not_cancelled when nothing is scheduled, already_ended
when the service has ended or its end date has passed, not_active for a
service that is suspended or not running, and scheduled_by_support for
an end date our team set. Another customer's service answers 404. A
support session can use it only where it can cancel.
Parameters
Section titled Parameters| Name | In | Type | Required |
|---|---|---|---|
service_id |
path | integer | yes |
org_slug |
path | string | yes |
Responses
Section titled Responses| Status | Meaning |
|---|---|
200 |
Success. |
422 |
The request is not valid. detail lists each problem. |
What a plan change costs today, before committing to it
Section titled What a plan change costs today, before committing to itGET /api/v1/orgs/{org_slug}/portal/services/{service_id}/plan-preview
What a plan change costs today, before committing to it.
Charged on the days left in the current cycle, not the full price difference: moving up on the last day of the month should cost a day.
For a service on a Standalone product, such as a rank, a plan of
another billing period (monthly to annually, or back) costs nothing today
and applies at the next renewal. The answer has the same fields, with
change_type period, applies_at next_renewal, due_today
0, effective_at (when the first renewal at the new period falls due),
renewal_invoice_open (true when the next renewal is already invoiced,
so the switch lands on the one after) and current_billing_cycle.
A free server may move onto a plan of any billing period. When the period
is not the free plan's own, the upgrade buys one whole period of the new
plan from the day it is paid: first_period is true, due_today and
charge_amount are the plan's price for that period, days_remaining
and days_in_cycle are the period's length, and next_due_date is when
it would end if paid now. Every other answer has first_period false.
Parameters
Section titled Parameters| Name | In | Type | Required | Description |
|---|---|---|---|---|
service_id |
path | integer | yes | |
org_slug |
path | string | yes | |
org_pricing_id |
query | integer | yes | |
coupon_code |
query | string or null | no | A coupon code to price an upgrade with. The answer's coupon is {code, discount} and due_today is what is left to pay. A code that does not apply answers 422 with errors and coupon, as change-plan does. Ignored for a downgrade, a move at the same price and a switch of period. |
Responses
Section titled Responses| Status | Meaning |
|---|---|
200 |
Success. |
422 |
The request is not valid. detail lists each problem. |
Sizes this service can move to
Section titled Sizes this service can move toGET /api/v1/orgs/{org_slug}/portal/services/{service_id}/plans
Sizes this service can move to.
Constrained to the same game, the same hardware tier and the same billing cycle, so the list is genuinely "the same thing, bigger or smaller". Without the game filter a Minecraft server was offered Terraria and Rust plans, and without the cycle filter the same size appeared once per billing period.
A service on a Standalone product, such as a rank, has no sizes. Its
list is the product's own pricing rows, one per billing period (monthly,
annually), so the customer can switch between them. Each row says when it
would apply in applies_at: now for the service's own billing cycle,
next_renewal for another one, which the service takes when its next
renewal is invoiced. scheduled is true on the row a switch is waiting
for.
A server add-on (extra CPU, automatic backups, Server Management) has no plans to move to, so its list is empty.
Parameters
Section titled Parameters| Name | In | Type | Required |
|---|---|---|---|
service_id |
path | integer | yes |
org_slug |
path | string | yes |
Responses
Section titled Responses| Status | Meaning |
|---|---|
200 |
Success. |
422 |
The request is not valid. detail lists each problem. |