Webhooks
Open certain actions taking place within your account, we can trigger a JSON POST callback to a URL or your choice, containing resource ID and event name. For example:
{
"event": "instance.created",
"resourceID": "84894d17-da88-45bb-8817-9b3b75cf61bf"
}
Webhook Lifecycle
Your Webhook handlers are expected to respond within 5 seconds. If they take longer than this, then the failures
count will be incremented and the webhook queued for reprocessing. Reprocessing happens at 5 minutes, 30 minutes, 1 hour, 2 hours, 6 hours - and after that the webhook will be disabled.
Payload Headers
The headers of the request from our servers will contain the following two important headers: X-Civo-Event
and X-Civo-Signature
. X-Civo-Event
is a UUID that is unique to this event. We don't track them ourside, but retries of the same event will have the same ID, so you can track it and not process it twice.
X-Civo-Signature
is an OpenSSL HMAC SHA1 digest of the entire payload using either the secret
of the webhook. The secret
is randomly generated when the webhook is created if one isn't specified. A simple example of how to calculate this in Ruby would be:
signature = OpenSSL::HMAC.hexdigest(
OpenSSL::Digest.new('sha1'),
webhook.secret,
request.body
)
The following events are available to subscribe to:
Name | Description |
---|---|
* | Any event happens |
instance.created | After an instance has been requested to be built |
instance.deleted | When the instance has been requested to be deleted |
instance.firewall.updated | When the firewall is requested to be updated for an instance |
instance.rebooted | When an instance has been requested to reboot |
instance.resized | After an instance has been resized |
instance.started | When an instance is requested to start (note: not when it's completed booting up and all daemons running) |
instance.stopped | When an instance is requested to stop(note: not when it's finished shutting down) |
instance.tags.updated | When an instance's tags have changed |
domain.created | After a domain name has been added to our DNS service |
domain.updated | After a domain name has been updated to our DNS service |
domain.deleted | After a domain has been removed from our DNS service |
domain_record.created | After a DNS record has been added for a domain in our DNS service |
domain_record.deleted | After a DNS record has been removed for a domain from our DNS service |
domain_record.updated | After a DNS record has been changed for a domain in our DNS service |
firewall.created | After a firewall is created |
firewall.updated | After a firewall is updated |
firewall.deleted | After a firewall is deleted |
firewall_rule.created | After a rule is added to a firewall |
firewall_rule.deleted | After a rule is removed from a firewall |
kubernetes_cluster.created | After a Kubernetes cluster is initially created |
kubernetes_cluster.deleted | After a Kubernetes cluster is initially created |
kubernetes_cluster.updated | After a Kubernetes cluster has been updated(Name, Version or Applications) |
kubernetes_cluster_pool.updated | After the number of nodes in a Kubernetes cluster has scaled up or down |
kubernetes_cluster_node.recycled | After the number of nodes in a Kubernetes cluster has scaled up |
network.created | After a network is added |
network.updated | After a network is updated |
network.deleted | After a network is removed |
ip.created | After a ip is created |
ip.updated | After a ip is updated |
ip.deleted | After a ip is deleted |
ssh_key.created | After an SSH key has been uploaded to our site |
ssh_key.updated | After an SSH key has been changed |
ssh_key.deleted | After an SSH key has been deleted |
volume.created | After a volume has been created |
volume.updated | After a volume has been updated |
volume.deleted | After a volume has been removed |
volume.attached | After a volume has been attached |
volume.detached | After a volume has been detached |
volume.resize | After a volume has been resized |
app.created | An app has been created |
app.deleted | An app has been deleted |
objectstore.created | After a objectstore is created |
objectstore.updated | After a objectstore is updated |
objectstore.deleted | After a objectstore is deleted |
objectstorecredential.created | After an objectstorecredential is created |
objectstorecredential.updated | After an objectstorecredential is updated |
objectstorecredential.deleted | After an objectstorecredential is deleted |
subnet.created | After a subnet is added |
subnet.deleted | After a subnet is removed |
database.created | After a database is initially created |
database.updated | After a database has been updated |
database.deleted | After a database is deleted |
database.restored | After a database is restored |
databasebackup.created | After a database backup is initially created |
databasebackup.updated | After a database backup has been updated |
databasebackup.deleted | After a database backup is deleted |
Listing webhooks
Listing the webhooks is possible by making a GET
request to the https://api.civo.com/v2/webhooks
resource.
Request
This request doesn't take any parameters.
Response
The response from the server will be a JSON array of webhooks.
[
{
"id": "20f54d3e-6de8-4074-a1a7-8715e0ad5295",
"created_at": "2021-09-08T09:01:28.000+01:00",
"events": [
"*"
],
"url": "https://example.com",
"secret": "foobar",
"disabled": false,
"failures": 0,
"last_failure_reason": ""
}
]
Example of listing webhooks
curl -H "Authorization: bearer 12345" https://api.civo.com/v2/webhooks
// At a shell prompt run:
// npm init -y
// npm i --save request
var request = require('request');
request.get(
'https://api.civo.com/v2/webhooks',
{},
function (error, response, body) {
if (!error && response.statusCode == 200) {
console.log(body)
}
}
).auth(null, null, true, '12345');
require 'net/http'
http = Net::HTTP.new('api.civo.com', 443)
http.use_ssl = true
headers = {
'Authorization' => 'bearer 12345',
'Content-Type' => 'application/x-www-form-urlencoded'
}
resp, data = get('v2/webhooks', headers)
Create a new webhook
Any user can create webhooks for their account.
New webhooks are created by sending a POST
request to https://api.civo.com/v2/webhooks
.
Request
The required parameters are listed below.
Name | Description |
---|---|
url | (required) this is the URL to send the webhook to |
events | (optional) this is a list of events that the webhook should be triggered for (default is * ) |
secret | (optional) this is if you want to specify your own secret, if not a random one will be created for you |
Response
The response is a JSON representation of the webhook, including the secret.
{
"result": "success",
"id": "a1381788-a669-4f7f-9d30-d1d83d4d7ebd"
}
Example of creating a webhook
curl -H "Authorization: bearer 12345" https://api.civo.com/v2/webhooks \
-F events='["*"]' -F url=https://api.example.com/webhook
// At a shell prompt run:
// npm init -y
// npm i --save request
var request = require('request');
request.post(
'https://api.civo.com/v2/webhooks',
{
"events": ["*"],
"url": "https://api.example.com/webhook"
},
function (error, response, body) {
if (!error && response.statusCode == 200) {
console.log(body)
}
}
).auth(null, null, true, '12345');
require 'net/http'
http = Net::HTTP.new('api.civo.com', 443)
http.use_ssl = true
headers = {
'Authorization' => 'bearer 12345',
'Content-Type' => 'application/x-www-form-urlencoded'
}
safe_url = CGI::escape("https://api.example.com/webhook")
resp, data = http.post('/v2/webhooks', 'events=["*"]&url=' + safe_url, headers)
Test a webhook
Once a webhook is created, you can test it by sending a POST
request to https://api.civo.com/v2/webhooks/:id/test
and this will call your webhook handler with a random resource ID and the first event the webhook was registered for. If the event is *
, then we will send a random event name.
Request
No parameters are required for this request.
Response
The response is a JSON object that simply confirms that the request to test the webhook was received.
{
"result": "success"
}
Example of testing a webhook
curl -H "Authorization: bearer 12345" -X POST https://api.civo.com/v2/webhooks/12345/test
// At a shell prompt run:
// npm init -y
// npm i --save request
var request = require('request');
request.post(
'https://api.civo.com/v2/webhooks/12345/test',
{},
function (error, response, body) {
if (!error && response.statusCode == 200) {
console.log(body)
}
}
).auth(null, null, true, '12345');
require 'net/http'
http = Net::HTTP.new('api.civo.com', 443)
http.use_ssl = true
headers = {
'Authorization' => 'bearer 12345',
'Content-Type' => 'application/x-www-form-urlencoded'
}
resp, data = http.post('/v2/webhooks/12345/test', '', headers)
Update a webhook
After creating a webhook, any user can update it.
Webhooks are updated by sending a PUT
request to https://api.civo.com/v2/webhooks/:id
.
Request
Name | Description |
---|---|
url | (optional) this is the URL to send the webhook to |
events | (optional) this is a list of events that the webhook should be triggered for (default is * ) |
secret | (optional) this is if you want to specify your own secret, if not a random one will be created for you |
Response
The response is a JSON representation of the updated webhook, including the secret.
{
"id": "b8de2e4e-72f4-4911-83ee-f4fc030fc4a2",
"created_at": "2021-09-08T09:09:32.000+01:00",
"events": ["*"],
"url": "https://api.example.com/webhook",
"secret": "DfeFUON8gorc5Zj0hk4GT1M9QImnRL6J",
"disabled": false,
"failures": 0,
"last_failure_reason": "",
}
Example of updating a webhook
curl -H "Authorization: bearer 12345" -X PUT https://api.civo.com/v2/webhooks/12345 \
-F events='["instance.created"]'
// At a shell prompt run:
// npm init -y
// npm i --save request
var request = require('request');
request.put(
'https://api.civo.com/v2/webhooks/12345',
{
"events": ["instance.created"]
},
function (error, response, body) {
if (!error && response.statusCode == 200) {
console.log(body)
}
}
).auth(null, null, true, '12345');
require 'net/http'
http = Net::HTTP.new('api.civo.com', 443)
http.use_ssl = true
headers = {
'Authorization' => 'bearer 12345',
'Content-Type' => 'application/x-www-form-urlencoded'
}
resp, data = http.put('/v2/webhooks/12345', 'events=["instance.created"]', headers)
Deleting a webhook
An account holder can remove one of their webhooks by sending a DELETE
request to https://api.civo.com/v2/webhooks/:id
.
Request
This request takes no parameters, only the ID of the webhook to delete is in the URL. No confirmation step is required, this step will remove the webhook immediately.
Response
The response from the server will be a JSON block. The response will include a result
field and the HTTP status will be 200 OK
.
{
"result": "success"
}
Example of deleting a webhook
curl -H "Authorization: bearer 12345" \
-X DELETE https://api.civo.com/v2/webhooks/12345
// At a shell prompt run:
// npm init -y
// npm i --save request
var request = require('request');
request.del(
'https://api.civo.com/v2/webhooks/12345',
function (error, response, body) {
if (!error && response.statusCode == 202) {
console.log(body)
}
}
).auth(null, null, true, '12345');
require 'net/http'
http = Net::HTTP.new('api.civo.com', 443)
http.use_ssl = true
headers = {
'Authorization' => 'bearer 12345',
'Content-Type' => 'application/x-www-form-urlencoded'
}
resp, data = http.delete('/v2/webhooks/12345', headers)