For AI agents: markdown of this page — /docs-content-en/applications/available-servers.md documentation index — /llms.txt
Servers for moving an application
GET /v1/applications/:id/available-servers
Shows where the owner can move the application: which of their own servers fit, and whether a new server can be created. Call it before you show the replace-server screen. The response tells you whether the replace button is needed and, if the replacement is unavailable, gives the reason as a code. The replacement itself is done by POST /v1/applications/:id/replace-server.
Only the card owner can call this method. A Bitrix24 account administrator who does not own the application gets 403 FORBIDDEN, just as with the replacement itself. This way a button that would end in a refusal is never shown.
Authorization: X-Api-Key with the vibe:infra scope.
Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
Parameterid (path) |
Typestring | Requiredyes | DescriptionApplication ID. List: GET /v1/applications |
Examples
curl — personal key
curl -H "X-Api-Key: YOUR_API_KEY" \
https://vibecode.bitrix24.com/v1/applications/cmsw806qi0000tdskiw2aegii/available-servers
curl — OAuth application
curl -H "X-Api-Key: YOUR_APP_KEY" \
-H "Authorization: Bearer USER_SESSION_TOKEN" \
https://vibecode.bitrix24.com/v1/applications/cmsw806qi0000tdskiw2aegii/available-servers
JavaScript — personal key
const id = 'cmsw806qi0000tdskiw2aegii'
const res = await fetch(`https://vibecode.bitrix24.com/v1/applications/${id}/available-servers`, {
headers: { 'X-Api-Key': 'YOUR_API_KEY' },
})
const { data } = await res.json()
console.log('Own servers:', data.servers.map((s) => s.name))
if (!data.canCreateNew) {
console.log('A new server is not available:', data.createNewBlocked.code)
}
JavaScript — OAuth application
const id = 'cmsw806qi0000tdskiw2aegii'
const res = await fetch(`https://vibecode.bitrix24.com/v1/applications/${id}/available-servers`, {
headers: {
'X-Api-Key': 'YOUR_APP_KEY',
'Authorization': 'Bearer USER_SESSION_TOKEN',
},
})
const { data } = await res.json()
Response fields
| Field | Type | Description |
|---|---|---|
Fieldsuccess |
Typeboolean | DescriptionAlways true on success |
Fielddata |
Typeobject | DescriptionWhere the application can be moved |
Fielddata.servers |
Typearray | DescriptionThe owner's servers the application can be moved to. At most 50, newest first. May be empty |
Fielddata.servers[].id |
Typestring | DescriptionServer ID. Pass it as serverId to POST /v1/applications/:id/replace-server |
Fielddata.servers[].name |
Typestring | DescriptionServer name |
Fielddata.servers[].displayName |
Typestring | null | DescriptionDisplay name, if set |
Fielddata.servers[].status |
Typestring | DescriptionServer state in lowercase, as in GET /v1/infra/servers |
Fielddata.servers[].providerId |
Typestring | DescriptionServer provider |
Fielddata.servers[].plan |
Typestring | DescriptionServer plan |
Fielddata.servers[].region |
Typestring | DescriptionServer region |
Fielddata.servers[].kind |
Typestring | DescriptionSTANDALONE — a separate machine, GALAXY_APP — an application container in a galaxy |
Fielddata.servers[].blackholeStatus |
Typestring | null | DescriptionTunnel state of the server |
Fielddata.servers[].createdAt |
Typestring | DescriptionServer creation time, ISO 8601 |
Fielddata.canCreateNew |
Typeboolean | DescriptionWhether the server can be replaced with a newly created one right now |
Fielddata.createNewBlocked |
Typeobject | DescriptionPresent only when canCreateNew is false, and names the reason |
Fielddata.createNewBlocked.code |
Typestring | DescriptionACCOUNT_FROZEN, INFRA_NOT_PERMITTED, SERVER_CREATION_DISABLED or SERVER_CREATION_ADMINS_ONLY |
Fielddata.createNewBlocked.message |
Typestring | DescriptionText for logs, in English |
Fielddata.createNewBlocked.userMessage |
Typestring | DescriptionHuman-readable text in the key owner's language |
Fielddata.createNewBlocked.alternatives |
Typearray | DescriptionWhat can be done instead of creating a server. The shape matches the 402 response of POST /v1/applications/:id/replace-server |
Response example
{
"success": true,
"data": {
"servers": [
{
"id": "srv_new",
"name": "my-server",
"displayName": null,
"status": "running",
"providerId": "bitrix-cloud",
"plan": "bc-small",
"region": "bc-eu-central",
"kind": "STANDALONE",
"blackholeStatus": null,
"createdAt": "2026-10-01T09:00:00.000Z"
}
],
"canCreateNew": true
}
}
Error response example
403 — the application belongs to someone else, and a Bitrix24 account administrator replaces the server in their Vibecode account:
{
"success": false,
"error": {
"code": "FORBIDDEN",
"message": "Forbidden"
}
}
Errors
| HTTP | Code | Description |
|---|---|---|
| HTTP401 | CodeNO_PORTAL |
DescriptionThe key is not bound to a portal |
| HTTP401 | CodeMISSING_API_KEY, INVALID_API_KEY |
DescriptionNo valid key |
| HTTP402 | CodeACCOUNT_FROZEN |
DescriptionThe portal balance is frozen and the whole /v1 surface is closed. The body carries message and topupUrl. If only paid calls are closed, the method returns 200 with canCreateNew: false |
| HTTP403 | CodeINFRA_SCOPE_REQUIRED |
DescriptionThe key lacks the vibe:infra scope |
| HTTP403 | CodeINFRA_FORBIDDEN_FOR_COWORK_KEY |
DescriptionA key with the vibe:cowork scope works with data only; this method is closed to it, reads included |
| HTTP403 | CodeFORBIDDEN |
DescriptionThe application does not belong to the key owner |
| HTTP403 | CodeWRITE_BLOCKED_READONLY_KEY |
DescriptionThe key is read-only |
| HTTP403 | CodeMANAGEMENT_KEY_NO_ENTITY_ACCESS |
DescriptionManagement key: use a personal key or an authorization key |
| HTTP403 | CodePORTAL_KEY_REQUIRED |
DescriptionThe key record is corrupted and has no owner. An ordinary key without a portal gets 401 NO_PORTAL above |
| HTTP404 | CodeAPPLICATION_NOT_FOUND |
DescriptionNo such application on the portal the key is bound to. An application on another portal gets the same response |
| HTTP429 | CodeRATE_LIMITED |
Description60 requests per minute for the card owner, whichever key they use |
The error.message text is in English and meant for logs: build interface texts from error.code. The full list of common API errors is in Errors.
Known specifics
- Not all of the owner's servers are listed. A server must belong to the card owner, exist, not be the application's current server, not be linked to another application, not be an agent or bot server and not be a galaxy host. The replacement does not accept a server that is not listed here:
POST /v1/applications/:id/replace-serverreturns404 SERVER_NOT_FOUNDor409 SERVER_ALREADY_LINKEDfor it. - An empty
serversarray does not block the replacement. The server can also be replaced by creating a new one, ifcanCreateNewistrue. Hide the replace button when the list is empty andcanCreateNewisfalse, and take the reason fromcreateNewBlocked. - A frozen balance closes creation only. With
ACCOUNT_FROZENincreateNewBlocked, moving to your own existing server stays available, andserversis filled by the same rules. - Creation depends on the account policy. The codes
INFRA_NOT_PERMITTED,SERVER_CREATION_DISABLEDandSERVER_CREATION_ADMINS_ONLYmean the account policy does not let this person create servers. The replacement in thenewform returns the same codes. - The response is a snapshot at the time of the call. A server may be taken or deleted between this method and the replacement. The replacement rechecks everything itself and returns the matching code.
- The method neither changes nor creates anything. Call it as often as the screen needs.