Webhooks
When your app needs information about specific events that have occurred, it can subscribe to NVSEP webhook topics as a mechanism for receiving near-real-time data about these events.
Webhooks are useful for keeping your app in sync with NVSEP data, or as a trigger to perform an additional action after that event has occurred. They are also a performant alternative to continuously polling for changes.
Webhooks can be configured through the NVSEP Portal. The following webhook subscription topics are available:
Webhook Topics
Webhook Topic | API Name | Trigger |
---|---|---|
Self-Exclusion Created | cfs_exclusions.created | Called when a new self-exclusion has been created. |
Sample Payloads
Event: cfs_exclusions.created
{
"id": "20c6d434-9f90-48e4-a246-993ffab00477",
"type": "cfs_exclusions.created",
"createdAt": "2023-01-01T12:00:01Z",
"version": "1.0",
"data": {
"createdAt": "2023-01-01T12:00:00Z",
"createdByOrg": {
"id": "473bd688-ad6b-42dc-bbe8-8342537483cc",
"name": "IdPair, Inc."
},
"endDate": "2023-12-31",
"id": "44cd42ee-1982-423a-9b76-e629f952df88",
"player": {
"hashes": [
{
"createdAt": "2024-01-01T10:00:00Z",
"hash1": "hash_value_1",
"hash2": "hash_value_2",
"hash3": "hash_value_3"
}
]
},
"startDate": "2023-01-01"
}
}
Verifying Authenticity
You are strongly encouraged to validate the incoming webhook payload through an HMAC signature verification process. This can provide assurance that the request comes from NVSEP.
- Extract the
x-nvsep-hmac-sha256
header from the incoming request. - Use your Webhook Signing Key to compute an HMAC digest of the request body.
- Compare the computed HMAC digest to the
x-nvsep-hmac-256
header securely.
Sample pseudocode:
defmodule NVSEPWebhook do
@moduledoc """
Validates NVSEP webhook HMAC signature.
"""
@doc """
Validates the NVSEP HMAC signature.
## Parameters
- headers: Map of HTTP headers from the webhook request.
- body: Raw body of the webhook request.
## Returns
- `:ok` if the HMAC is valid.
- `:error` if the HMAC is invalid.
"""
def validate_hmac(headers, body) do
with signing_key <- System.get_env("NVSEP_WEBHOOK_SIGNING_KEY"),
{:ok, hmac_header} <- get_hmac_header(headers),
computed_hmac <- compute_hmac(body, signing_key),
true <- secure_compare(hmac_header, computed_hmac) do
:ok
else
_ -> :error
end
end
defp get_hmac_header(headers) do
case Map.get(headers, "x-nvsep-hmac-sha256") do
nil -> {:error, :missing_hmac_header}
hmac -> {:ok, hmac}
end
end
defp compute_hmac(body, signing_key) do
:crypto.mac(:hmac, :sha256, signing_key, body)
|> Base.encode64()
end
defp secure_compare(a, b) when is_binary(a) and is_binary(b) do
Plug.Crypto.secure_compare(a, b)
end
defp secure_compare(_, _), do: false
end
Troubleshooting
You should monitor for and respond to failed webhook delivery notifications. A webhook will be retried up to 8 times, after multiple failures in a 24 hour period the webhook subscription will be removed.