API Integration
Guide for automating deployments and integrating CI/CD pipelines with the DeployAlly REST API.
Overview
The API lets you:
- List and inspect the template catalog
- Create definitions (template + inputs + instance metadata)
- Trigger deployments and track status
- Run actions on running instances
- Receive events via webhooks
Environments
| Environment | Base URL | Use |
|---|---|---|
| Production | https://sys.deployally.com/api/v1 |
Production systems |
| Test | https://dev.sys.deployally.com/api/v1 |
Development |
Initial Setup
1. Get an API Key
- Log in at
https://app.deployally.com - Settings → API Keys → Create New
- Set the minimum required permissions
- Copy the key (it won't be shown again)
2. Configure Environment
export DEPLOYALLY_API_URL="https://sys.deployally.com/api/v1"
export DEPLOYALLY_API_KEY="da_xxx"3. Test
curl -X GET "${DEPLOYALLY_API_URL}/health"
curl -X GET "${DEPLOYALLY_API_URL}/templates" \
-H "Authorization: Bearer ${DEPLOYALLY_API_KEY}"Automated Deploy Flow
1. List templates → GET /templates
2. Inspect template → GET /templates/<species>
3. Register server → POST /servers/register (once)
4. Create definition → POST /definitions
5. Execute deploy → POST /deployments/execute
6. Track status → GET /deployments/<id>
7. List instances → GET /instancesFull Example
#!/bin/bash
set -euo pipefail
API="${DEPLOYALLY_API_URL}"
KEY="${DEPLOYALLY_API_KEY}"
# 1. Fetch the memos template
TEMPLATE=$(curl -s "${API}/templates/memos" \
-H "Authorization: Bearer ${KEY}" | jq -r '.data.id')
# 2. Create a definition
DEFINITION=$(curl -s -X POST "${API}/definitions" \
-H "Authorization: Bearer ${KEY}" \
-H "Content-Type: application/json" \
-d "{
\"species\": \"memos\",
\"instance_uid\": \"memos-001\",
\"server_id\": \"srv_123\",
\"inputs\": {
\"WEB_HOSTNAME\": \"memos.example.com\"
},
\"profile\": \"production\"
}" | jq -r '.data.id')
# 3. Execute the deploy
DEPLOY=$(curl -s -X POST "${API}/deployments/execute" \
-H "Authorization: Bearer ${KEY}" \
-H "Content-Type: application/json" \
-d "{\"definition_id\": \"${DEFINITION}\"}" | jq -r '.data.id')
# 4. Wait for completion
while true; do
STATUS=$(curl -s "${API}/deployments/${DEPLOY}" \
-H "Authorization: Bearer ${KEY}" | jq -r '.data.status')
case "$STATUS" in
success)
echo "Deploy completed"
break
;;
failed)
echo "Deploy failed"
exit 1
;;
*)
sleep 5
;;
esac
doneWorking with Actions
Templates declare post-deploy operations (backups, restart, etc.). The API lets you trigger those operations remotely.
List Available Actions
curl -X GET "${API}/instances/inst_abc/actions" \
-H "Authorization: Bearer ${KEY}"Run an Action
EXEC=$(curl -s -X POST "${API}/instances/inst_abc/actions/dump-database/execute" \
-H "Authorization: Bearer ${KEY}" \
-H "Content-Type: application/json" \
-d '{}' | jq -r '.execution.id')
# Track it
while true; do
STATUS=$(curl -s "${API}/actions/${EXEC}" \
-H "Authorization: Bearer ${KEY}" | jq -r '.execution.status')
[ "$STATUS" = "completed" ] && break
[ "$STATUS" = "failed" ] && exit 1
sleep 2
doneCI/CD Integration
GitHub Actions
name: Deploy to DeployAlly
on:
push:
branches: [main]
jobs:
deploy:
runs-on: ubuntu-latest
steps:
- name: Trigger Deployment
env:
DEPLOYALLY_API_KEY: ${{ secrets.DEPLOYALLY_API_KEY }}
run: |
curl -X POST "https://sys.deployally.com/api/v1/deployments/execute" \
-H "Authorization: Bearer ${DEPLOYALLY_API_KEY}" \
-H "Content-Type: application/json" \
-d '{"definition_id": "def_app_main"}'GitLab CI
deploy:
stage: deploy
script:
- |
curl -X POST "https://sys.deployally.com/api/v1/deployments/execute" \
-H "Authorization: Bearer ${DEPLOYALLY_API_KEY}" \
-H "Content-Type: application/json" \
-d '{"definition_id": "def_app_main"}'
only:
- mainWebhooks
Configure webhooks to receive notifications in real time.
Register an Endpoint
curl -X POST "${API}/webhooks/endpoints" \
-H "Authorization: Bearer ${KEY}" \
-H "Content-Type: application/json" \
-d '{
"url": "https://my-system.com/webhook/deployally",
"events": [
"deployment.success",
"deployment.failed",
"instance.unhealthy",
"action.completed"
],
"secret": "my_webhook_secret"
}'Receive a Webhook (Python/Flask)
from flask import Flask, request
import hmac
import hashlib
app = Flask(__name__)
WEBHOOK_SECRET = "my_webhook_secret"
@app.route('/webhook/deployally', methods=['POST'])
def handle_webhook():
signature = request.headers.get('X-DeployAlly-Signature')
payload = request.get_data()
expected = hmac.new(
WEBHOOK_SECRET.encode(),
payload,
hashlib.sha256
).hexdigest()
if not hmac.compare_digest(signature, expected):
return 'Invalid signature', 403
event = request.json
event_type = event['type']
if event_type == 'deployment.success':
# Notify the team
pass
elif event_type == 'instance.unhealthy':
# Alert / attempt restart
pass
return 'OK', 200Error Handling
Retry with Backoff
import requests
import time
def api_request(method, endpoint, **kwargs):
url = f"{DEPLOYALLY_API_URL}{endpoint}"
headers = {
"Authorization": f"Bearer {DEPLOYALLY_API_KEY}",
"Content-Type": "application/json"
}
for attempt in range(3):
try:
response = requests.request(
method, url, headers=headers, **kwargs
)
if response.status_code == 429:
retry_after = int(response.headers.get('Retry-After', 60))
time.sleep(retry_after)
continue
response.raise_for_status()
return response.json()
except requests.exceptions.RequestException:
if attempt == 2:
raise
time.sleep(2 ** attempt)
raise Exception("Max retries exceeded")Common Error Codes
| Code | Cause | Action |
|---|---|---|
| 401 | Invalid key | Check the API Key |
| 403 | No permission | Check the key's permissions |
| 404 | Resource not found | Check the IDs |
| 422 | Invalid data | Check the payload |
| 429 | Rate limit | Wait and retry |
| 500 | Internal error | Retry with backoff |
Best Practices
Security
- Never expose API Keys in logs, code, or repositories
- Use environment variables or secrets managers (HashiCorp Vault, AWS Secrets Manager)
- Rotate keys periodically (
POST /servers/{id}/rotate-key) - Use the minimum required permissions
- Set up an IP allowlist when possible
Performance
- Cache templates locally (they change rarely;
Cache-Control: max-age=60on the API) - Use webhooks instead of polling
- Group related operations
Resilience
- Implement retry with exponential backoff
- Handle
429 Rate Limitedproperly - Validate responses before using them (
success: true/false) - Use structured logs to audit automated actions
Next Steps
- API Reference — overview
- Authentication — key management
- Endpoints — full documentation
- CLI Reference — use via CLI
By Borlot.com.br on 05/06/2026