Configure Webhook
Get current config​
GET /api/v2/webhooks/config
Returns 404 if nothing is configured.
Response:
{
"url": "https://yourapp.com/webhooks/4pay",
"secret_set": true,
"event_types": ["card_transaction", "card_state"],
"is_active": true
}
secret_set: true means a signing secret is stored (the value itself is never returned).
Set or update config​
PUT /api/v2/webhooks/config
Content-Type: application/json
Request body​
| Field | Type | Required | Description |
|---|---|---|---|
url | string (URI) | Yes | Your HTTPS endpoint |
secret | string | No | Used to compute api-notification-sign (SHA-512). If omitted, the signature header is still sent using the provider's own key. |
event_types | string[] | No | Subset to receive. null or omit → all events. |
is_active | boolean | No | Default true |
Available event types: card_transaction, account_transaction, account_topup, card_state.
curl -s -X PUT "https://api.4pay.cc/api/v2/webhooks/config" \
-H "X-API-Token: YOUR_API_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"url": "https://yourapp.com/webhooks/incoming",
"secret": "your-secret-string",
"event_types": ["card_transaction", "account_transaction", "account_topup", "card_state"],
"is_active": true
}'
Response (200): same shape as GET config.
Delete config​
DELETE /api/v2/webhooks/config
204 — forwarding stops immediately.
Verifying the signature​
Each POST request we send to your endpoint includes:
X-Webhook-Signature: <hex-encoded HMAC-SHA256>
To verify in Python:
import hmac, hashlib
def verify(secret: str, body: bytes, header_value: str) -> bool:
digest = hmac.new(secret.encode(), body, hashlib.sha256).hexdigest()
return hmac.compare_digest(digest, header_value)
To verify in Node.js:
const crypto = require('crypto');
function verify(secret, body, headerValue) {
const digest = crypto
.createHmac('sha256', secret)
.update(body)
.digest('hex');
return crypto.timingSafeEqual(Buffer.from(digest), Buffer.from(headerValue));
}
caution
Always use a constant-time comparison (hmac.compare_digest, crypto.timingSafeEqual, etc.) to prevent timing attacks. Reject requests where the signature does not match.