API Keys
API keys let you automate cert-ctrl without interactive sessions. They are scoped to a user, carry explicit permissions, and authenticate via Authorization: Bearer. Once the server accepts a key, the request inherits the key owner's permissions.
Important: API keys are bearer secrets. Treat them like passwords. Store them securely, rotate them regularly, and delete keys you no longer need.
1. Create a key
Most users create keys in the web console. You can also create keys via the REST API.
Request
POST /apiv1/me/apikeys
{
"name": "ci-bot",
"expires_in_seconds": 86400,
"permissions": [
{"obtype": "certificates", "obid": "123", "actions": ["read", "issue"]},
{"obtype": "devices", "obid": "*", "actions": ["read"]}
]
}
Notes
expires_in_secondsis required.- The response includes a
tokenfield only once. Save it immediately. - Permission scopes are listed at
GET /apiv1/permissions/catalog. - ACME account scope name is
acme_accounts(underscore).
2. Permissions model
Each permission entry contains:
obtype: scope name (e.g.,certificates,devices,acme_accounts)obid:*or a concrete object idactions: allowed actions (e.g.,read,write,issue)
For install-config automation, the scope is ForInstallConfigUpdate with action update.
3. Certificate-focused permission recipes
This document intentionally focuses on certificate issuance and distribution. Below are practical permission sets to use when creating an API key.
A) Issue/renew + download/export one certificate
Use a concrete certificate id (recommended):
{
"name": "cert-issuer",
"expires_in_seconds": 86400,
"permissions": [
{"obtype": "certificates", "obid": "123", "actions": ["read", "issue"]}
]
}
What it enables:
GET /apiv1/me/certificates/123POST /apiv1/me/certificates/123/issuesGET /apiv1/me/certificates/123/issues/historyGET /apiv1/me/certificates/123/export
B) Assign one certificate to devices
POST /apiv1/me/certificate-assign derives the certificate id from the API key’s permissions. For this endpoint you must provide a concrete certificate id (not *).
{
"name": "cert-assigner",
"expires_in_seconds": 86400,
"permissions": [
{"obtype": "certificates", "obid": "123", "actions": ["read"]}
]
}
C) List devices (optional)
If your automation needs to discover devices via API:
{
"name": "device-reader",
"expires_in_seconds": 86400,
"permissions": [
{"obtype": "devices", "obid": "*", "actions": ["read"]}
]
}
D) Update install-config (optional)
If your automation uses POST /apiv1/me/install-config-update/:device_public_id, add:
{"obtype": "ForInstallConfigUpdate", "obid": "*", "actions": ["update"]}
4. Authenticating requests
REST / JSON clients
curl -H "Authorization: Bearer ak_yourtoken" \
https://cjj365.cc/apiv1/me/certificates
5. Common automation flows
Assign a certificate to a device (API key only)
POST /apiv1/me/certificate-assign uses the certificate id from the API key permission (certificates + read). The payload includes only the device public id.
curl -X POST https://cjj365.cc/apiv1/me/certificate-assign \
-H "Authorization: Bearer ak_yourtoken" \
-H "Content-Type: application/json" \
-d '{"device_public_id":"dev_abc123"}'
Update a device install-config (API key only)
POST /apiv1/me/install-config-update/:device_public_id requires ForInstallConfigUpdate permission.
curl -X POST https://cjj365.cc/apiv1/me/install-config-update/dev_abc123 \
-H "Authorization: Bearer ak_yourtoken" \
-H "Content-Type: application/json" \
-d '{"patches":[{"ob_type":"cert","ob_id":10,"enabled":true}]}'
Best practices
- Least privilege: create separate keys per integration with tailored scopes.
- Short-lived keys: keep lifetimes tight and rotate automatically.
- Monitoring: audit usage and revoke keys you no longer need.
Troubleshooting
Common error codes when using API keys:
| Code | Meaning | Fix |
|---|---|---|
5003 | Not found | Verify the resource exists and belongs to the API key owner. |
5022 | Forbidden | The API key lacks required permission(s) for this action. |
5018 | Unauthorized | Missing/invalid token, or API key expired/revoked. |
5000 | Invalid argument | Check request JSON fields and types. |
If authentication fails you may see api key lacks required permissions or invalid token in the error message.