IONOS API Server Management Playbook
IMPORTANT — Two separate IONOS API products
| Product | Portal | API base | Credentials | What it can do |
|---|---|---|---|---|
| IONOS Hosting API | developer.hosting.ionos.de | https://api.hosting.ionos.com/dns/v1 | X-API-Key: PREFIX.ENCRYPTION | DNS zones, email forwards, hosting config |
| IONOS Cloud API | cloud.ionos.com | https://api.ionos.com/cloudapi/v6 | Authorization: Bearer PREFIX.ENCRYPTION | VPS/server reboot, NIC, firewall, snapshots |
Current status (2026-06-25):
IONOS_API_TOKEN_PREFIX / IONOS_API_TOKEN_ENCRYPTION in secrets/monitoring.env.sops are Hosting API credentials. They work for DNS management but cannot reboot or manage vps-i1.
For server management, check if vps-i1 is managed under cloud.ionos.com and create a Cloud API token there. If vps-i1 is a classic IONOS VPS (not Cloud), there is no public API for server restart — use the web Control Panel.
cost-exporter collector (collect_ionos_servers) is implemented and wired into
collect_all(): it calls the Cloud API GET /datacenters?depth=5 with
Authorization: Bearer PREFIX.ENCRYPTION and emits ionos_server_status,
ionos_server_cores, and ionos_server_ram_bytes per server. Until Cloud API
credentials replace the current Hosting-only token, the call returns 401/403 and the
collector degrades gracefully — it increments
cost_collector_errors_total{collector="ionos_servers"} and never crashes the loop.
Swap in Cloud API credentials (same env var names) to light up the server metrics.
When to use this playbook
- Managing IONOS Hosting DNS zones
- (Future) vps-i1 unreachable via SSH when Cloud API credentials are set up
- (Future) Need to reboot vps-i1 without SSH access via Cloud API
Credentials
IONOS_API_TOKEN_PREFIXandIONOS_API_TOKEN_ENCRYPTIONfromsecrets/monitoring.env.sops- Combined token:
TOKEN="${IONOS_API_TOKEN_PREFIX}.${IONOS_API_TOKEN_ENCRYPTION}" - Hosting API auth header:
X-API-Key: $TOKEN - Cloud API auth header (if Cloud credentials added):
Authorization: Bearer $TOKEN
Section: Confirm Hosting API works
# On Linux (vps-i1, bms-4) — decrypt SOPS and export IONOS vars
export SOPS_AGE_KEY_FILE="$HOME/.age/p24-infra-keys.txt"
eval $(sops --decrypt --input-type dotenv --output-type dotenv /opt/p24-infra/secrets/monitoring.env.sops | grep ^IONOS)
TOKEN="${IONOS_API_TOKEN_PREFIX}.${IONOS_API_TOKEN_ENCRYPTION}"
# Verify the Hosting API token works
curl -s -H "X-API-Key: $TOKEN" \
"https://api.ionos.com/cloudapi/v6/datacenters" | python3 -m json.tool | head -30Section: Find vps-i1 server ID
# List all datacenters — note the ID for the datacenter containing vps-i1
curl -s -H "Authorization: Bearer $TOKEN" \
"https://api.ionos.com/cloudapi/v6/datacenters?depth=1" | python3 -m json.tool
# List servers in a specific datacenter (replace {DC_ID} with the ID found above)
curl -s -H "Authorization: Bearer $TOKEN" \
"https://api.ionos.com/cloudapi/v6/datacenters/{DC_ID}/servers?depth=1" | python3 -m json.tool
# Note the vps-i1 server ID (properties.name == "vps-i1") for use in subsequent commandsSection: Get server status
curl -s -H "Authorization: Bearer $TOKEN" \
"https://api.ionos.com/cloudapi/v6/datacenters/{DC_ID}/servers/{SERVER_ID}" \
| python3 -c "import sys,json; d=json.load(sys.stdin); print(d['properties']['vmState'])"Expected output: RUNNING (healthy) or SHUTOFF / PAUSED (action needed).
Section: Reboot server (graceful)
curl -s -X POST -H "Authorization: Bearer $TOKEN" \
"https://api.ionos.com/cloudapi/v6/datacenters/{DC_ID}/servers/{SERVER_ID}/reboot"
# Returns 202 Accepted — poll GET status until vmState=RUNNING (see polling section below)Section: Hard reset (force restart)
Use when the server is unresponsive and graceful reboot does not recover it.
# Step 1: Stop the server
curl -s -X POST -H "Authorization: Bearer $TOKEN" \
"https://api.ionos.com/cloudapi/v6/datacenters/{DC_ID}/servers/{SERVER_ID}/stop"
# Wait ~10 seconds for the shutdown to propagate
sleep 10
# Step 2: Start the server
curl -s -X POST -H "Authorization: Bearer $TOKEN" \
"https://api.ionos.com/cloudapi/v6/datacenters/{DC_ID}/servers/{SERVER_ID}/start"
# Then poll until RUNNING (see below)Section: Poll until RUNNING
until [ "$(curl -s -H "Authorization: Bearer $TOKEN" \
"https://api.ionos.com/cloudapi/v6/datacenters/{DC_ID}/servers/{SERVER_ID}" \
| python3 -c "import sys,json; print(json.load(sys.stdin)['properties']['vmState'])")" = "RUNNING" ]; do
echo "Waiting..."; sleep 10
done
echo "Server is RUNNING"Section: Network / NIC management
# List NICs for a server
curl -s -H "Authorization: Bearer $TOKEN" \
"https://api.ionos.com/cloudapi/v6/datacenters/{DC_ID}/servers/{SERVER_ID}/nics" \
| python3 -m json.tool
# List firewall rules on a NIC (replace {NIC_ID} with the NIC ID from above)
curl -s -H "Authorization: Bearer $TOKEN" \
"https://api.ionos.com/cloudapi/v6/datacenters/{DC_ID}/servers/{SERVER_ID}/nics/{NIC_ID}/firewallrules" \
| python3 -m json.toolSection: What this replaces (human-action issues)
| Previous human-action issue | API alternative |
|---|---|
| ”SSH in and reboot vps-i1” when SSH is down | POST /datacenters/{DC_ID}/servers/{SERVER_ID}/reboot |
| ”Check if vps-i1 is up before re-auth attempt” | GET /datacenters/{DC_ID}/servers/{SERVER_ID} → vmState |
| ”Hard-reset vps-i1 kernel panic / unresponsive” | POST stop then POST start |
| ”Adjust IONOS-level firewall for vps-i1” | NIC firewallrules API |
Section: PowerShell equivalent (Windows workstation)
$env:SOPS_AGE_KEY_FILE = "C:\Users\konar\.age\p24-infra-keys.txt"
$env:IONOS_API_TOKEN_PREFIX = (sops --decrypt --input-type dotenv --output-type dotenv "d:\code_2026\p24-infra\secrets\monitoring.env.sops" | Select-String "^IONOS_API_TOKEN_PREFIX=") -replace "IONOS_API_TOKEN_PREFIX=", ""
$env:IONOS_API_TOKEN_ENCRYPTION = (sops --decrypt --input-type dotenv --output-type dotenv "d:\code_2026\p24-infra\secrets\monitoring.env.sops" | Select-String "^IONOS_API_TOKEN_ENCRYPTION=") -replace "IONOS_API_TOKEN_ENCRYPTION=", ""
$TOKEN = "$($env:IONOS_API_TOKEN_PREFIX).$($env:IONOS_API_TOKEN_ENCRYPTION)"
$HEADERS = @{ "Authorization" = "Bearer $TOKEN" }
# List datacenters
Invoke-RestMethod -Uri "https://api.ionos.com/cloudapi/v6/datacenters" -Headers $HEADERS | ConvertTo-Json -Depth 5
# List servers in a datacenter
Invoke-RestMethod -Uri "https://api.ionos.com/cloudapi/v6/datacenters/{DC_ID}/servers" -Headers $HEADERS | ConvertTo-Json -Depth 5
# Get server status
(Invoke-RestMethod -Uri "https://api.ionos.com/cloudapi/v6/datacenters/{DC_ID}/servers/{SERVER_ID}" -Headers $HEADERS).properties.vmState
# Reboot server
Invoke-RestMethod -Method Post -Uri "https://api.ionos.com/cloudapi/v6/datacenters/{DC_ID}/servers/{SERVER_ID}/reboot" -Headers $HEADERSSection: Escalation
| Symptom | Action |
|---|---|
| API returns 401 or 403 | Rotate credentials at https://developer.hosting.ionos.de/keys, update secrets/monitoring.env.sops |
| API returns 422 or 500 | Check IONOS status page (https://www.ionos.de/service/statusseite), open support ticket |
| Reboot does not recover SSH within 5 min | Escalate to IONOS support; request console (KVM) access |
vmState stuck in BUSY for > 10 min | Open IONOS support ticket referencing the server ID and DC ID |
Prevention / Monitoring
- The
cost-exporterscrapesionos_server_statusevery 24 h (or onPOST /refresh). - Add a Prometheus alert:
ionos_server_status{label="vps-i1"} == 0→ fire P1. - The metric uses labels
server_id(IONOS UUID) andlabel(server name from API). - Sample alert rule:
- alert: IonosVpsI1Down
expr: ionos_server_status{label="vps-i1"} == 0
for: 5m
labels:
severity: critical
annotations:
summary: "vps-i1 is not RUNNING according to IONOS API"
description: "IONOS Cloud API reports vps-i1 vmState != RUNNING. Use the IONOS API playbook to investigate."