Skip to main content

Overview

SO1 APIs use Bearer token authentication with API keys. All requests must include a valid API key in the Authorization header.
API keys provide full access to your account. Treat them like passwords and never commit them to version control.

Authentication Methods

Include your API key in the Authorization header with the Bearer scheme:
Authorization: Bearer YOUR_API_KEY
Example Request:
curl https://control-plane.so1.io/api/v1/workflows \
  -H "Authorization: Bearer cp_live_sk_1234567890abcdef"
For testing only, you can include the API key as a query parameter:
https://control-plane.so1.io/api/v1/workflows?api_key=YOUR_API_KEY
Query parameter authentication is not recommended for production use as API keys may be logged in server logs, browser history, and proxy logs.

API Key Types

SO1 provides different API key types for different use cases:

Control Plane API Keys

Format: cp_live_sk_... (production) or cp_test_sk_... (test mode) Permissions:
  • Agent execution
  • Workflow orchestration
  • FORGE gate validation
  • System metrics access
Generate in: Console → Settings → API Keys

Veritas API Keys

Format: ver_live_... (production) or ver_test_... (test mode) Permissions:
  • Prompt retrieval
  • Chain execution
  • Fragment management
  • A/B testing
Generate in: Veritas Dashboard → Settings

n8n API Keys

Format: n8n_... Permissions:
  • Workflow creation/modification
  • Workflow execution
  • Webhook management
  • Credential access
Generate in: n8n Settings → API

Generating API Keys

Via SO1 Console

1

Navigate to API Keys

2

Create New Key

Click “Create API Key” and select the key type
3

Configure Permissions

Select specific permissions (optional):
  • Read-only access
  • Agent execution only
  • Workflow management
  • Full access (default)
4

Save Key Securely

Copy the key immediately - it will only be shown once
export CONTROL_PLANE_API_KEY="cp_live_sk_..."

Via API

You can also generate API keys programmatically:
curl -X POST https://control-plane.so1.io/api/v1/auth/api-keys \
  -H "Authorization: Bearer ${CONTROL_PLANE_API_KEY}" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "CI/CD Pipeline Key",
    "permissions": ["agent:execute", "workflow:read"],
    "expires_at": "2027-03-10T00:00:00Z"
  }'
Response:
{
  "api_key_id": "key_abc123",
  "api_key": "cp_live_sk_1234567890abcdef",
  "name": "CI/CD Pipeline Key",
  "permissions": ["agent:execute", "workflow:read"],
  "created_at": "2026-03-10T15:30:00Z",
  "expires_at": "2027-03-10T00:00:00Z"
}
Store the api_key value securely. It cannot be retrieved again after creation.

Environment-Specific Keys

Use different API keys for each environment:
export CONTROL_PLANE_API_KEY="cp_test_sk_dev123..."
export VERITAS_API_KEY="ver_test_dev123..."
export N8N_API_KEY="n8n_dev123..."

Authentication Errors

401 Unauthorized

Cause: Missing, invalid, or expired API key
{
  "error": {
    "code": "unauthorized",
    "message": "Invalid API key",
    "details": {
      "reason": "The provided API key is not valid"
    }
  }
}
Solutions:
  • Verify the API key is correct
  • Check the key hasn’t been revoked
  • Ensure the key hasn’t expired
  • Verify you’re using the correct environment key

403 Forbidden

Cause: API key doesn’t have required permissions
{
  "error": {
    "code": "forbidden",
    "message": "Insufficient permissions",
    "details": {
      "required_permission": "agent:execute",
      "key_permissions": ["workflow:read"]
    }
  }
}
Solutions:
  • Use an API key with appropriate permissions
  • Request permission upgrade from account admin
  • Generate a new key with required permissions

Security Best Practices

1. Use Environment Variables

Never hardcode API keys in your application code:
// ✅ Good: Use environment variables
const apiKey = process.env.CONTROL_PLANE_API_KEY;

// ❌ Bad: Hardcoded API key
const apiKey = "cp_live_sk_1234567890abcdef";

2. Rotate Keys Regularly

Rotate API keys every 90 days:
# List existing keys
curl https://control-plane.so1.io/api/v1/auth/api-keys \
  -H "Authorization: Bearer ${CONTROL_PLANE_API_KEY}"

# Create new key
curl -X POST https://control-plane.so1.io/api/v1/auth/api-keys \
  -H "Authorization: Bearer ${CONTROL_PLANE_API_KEY}" \
  -d '{"name": "Production Key - Q2 2026"}'

# Update application with new key
# ...

# Revoke old key
curl -X DELETE https://control-plane.so1.io/api/v1/auth/api-keys/key_old123 \
  -H "Authorization: Bearer ${CONTROL_PLANE_API_KEY}"

3. Use Least Privilege

Create keys with minimum required permissions:
# Read-only key for monitoring
curl -X POST https://control-plane.so1.io/api/v1/auth/api-keys \
  -H "Authorization: Bearer ${CONTROL_PLANE_API_KEY}" \
  -d '{
    "name": "Monitoring Dashboard",
    "permissions": ["metrics:read", "workflow:read"]
  }'

# Agent execution only (no workflow modification)
curl -X POST https://control-plane.so1.io/api/v1/auth/api-keys \
  -H "Authorization: Bearer ${CONTROL_PLANE_API_KEY}" \
  -d '{
    "name": "CI/CD Agent Runner",
    "permissions": ["agent:execute"]
  }'

4. Set Expiration Dates

Always set expiration dates on API keys:
curl -X POST https://control-plane.so1.io/api/v1/auth/api-keys \
  -H "Authorization: Bearer ${CONTROL_PLANE_API_KEY}" \
  -d '{
    "name": "Temporary Integration Test Key",
    "expires_at": "2026-06-10T00:00:00Z"
  }'

5. Monitor Key Usage

Track API key usage and set up alerts:
# Get key usage statistics
curl https://control-plane.so1.io/api/v1/auth/api-keys/key_abc123/usage \
  -H "Authorization: Bearer ${CONTROL_PLANE_API_KEY}"
Response:
{
  "key_id": "key_abc123",
  "usage": {
    "requests_today": 1247,
    "requests_this_month": 38492,
    "last_used_at": "2026-03-10T15:25:00Z",
    "last_used_ip": "203.0.113.45"
  }
}

6. Revoke Compromised Keys

If a key is compromised, revoke it immediately:
# Revoke key
curl -X DELETE https://control-plane.so1.io/api/v1/auth/api-keys/key_abc123 \
  -H "Authorization: Bearer ${CONTROL_PLANE_API_KEY}"

# Verify revocation
curl https://control-plane.so1.io/api/v1/workflows \
  -H "Authorization: Bearer cp_live_sk_revoked_key"
# Should return 401 Unauthorized

Managing API Keys

List All API Keys

curl https://control-plane.so1.io/api/v1/auth/api-keys \
  -H "Authorization: Bearer ${CONTROL_PLANE_API_KEY}"
Response:
{
  "api_keys": [
    {
      "id": "key_abc123",
      "name": "Production API Key",
      "permissions": ["*"],
      "created_at": "2026-01-15T10:00:00Z",
      "expires_at": "2027-01-15T00:00:00Z",
      "last_used_at": "2026-03-10T15:25:00Z"
    },
    {
      "id": "key_def456",
      "name": "CI/CD Pipeline",
      "permissions": ["agent:execute", "workflow:read"],
      "created_at": "2026-02-01T14:30:00Z",
      "expires_at": "2026-08-01T00:00:00Z",
      "last_used_at": "2026-03-10T14:50:00Z"
    }
  ]
}

Update API Key

curl -X PATCH https://control-plane.so1.io/api/v1/auth/api-keys/key_abc123 \
  -H "Authorization: Bearer ${CONTROL_PLANE_API_KEY}" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "Production API Key - Updated",
    "expires_at": "2027-03-10T00:00:00Z"
  }'

Delete API Key

curl -X DELETE https://control-plane.so1.io/api/v1/auth/api-keys/key_abc123 \
  -H "Authorization: Bearer ${CONTROL_PLANE_API_KEY}"

Webhook Authentication

For webhook endpoints, SO1 uses HMAC signature verification:

Verifying Webhook Signatures

import { createHmac } from 'crypto';

function verifyWebhookSignature(
  payload: string,
  signature: string,
  secret: string
): boolean {
  const hmac = createHmac('sha256', secret);
  hmac.update(payload);
  const expectedSignature = `sha256=${hmac.digest('hex')}`;
  
  return signature === expectedSignature;
}

// Express.js example
app.post('/webhooks/so1', (req, res) => {
  const signature = req.headers['x-so1-signature'];
  const payload = JSON.stringify(req.body);
  const secret = process.env.WEBHOOK_SECRET;
  
  if (!verifyWebhookSignature(payload, signature, secret)) {
    return res.status(401).json({ error: 'Invalid signature' });
  }
  
  // Process webhook
  res.json({ status: 'received' });
});

OAuth 2.0 (Coming Soon)

OAuth 2.0 support for third-party integrations will be available soon:
  • Authorization Code Flow: For web applications
  • Client Credentials Flow: For server-to-server
  • Scoped Permissions: Fine-grained access control

Join OAuth Beta

Contact us to participate in the OAuth 2.0 beta program