Receive real-time notifications when verification events occur in your VerifyBTC account. Webhooks allow your application to respond immediately to status changes.
Events
Available webhook events
Security
Signature verification
Best Practices
Implementation tips
Full API reference
To receive webhooks, you need to:
1. Create a webhook endpoint
Set up an HTTP POST endpoint on your server to receive webhook events
2. Register your webhook
Go to Webhooks and add your endpoint URL
3. Verify webhook signatures
Implement signature verification to ensure authenticity
Subscribe to the following events to receive notifications:
verification.createdNEWTriggered when a new verification request is created.
verification.completedSUCCESSTriggered when a signature is successfully verified.
verification.failedFAILEDTriggered when signature verification fails.
verification.expiredEXPIREDTriggered when a verification request expires without completion.
verification.cancelledCANCELLEDTriggered when a verification is manually cancelled.
All webhook events are sent as HTTP POST requests with a JSON payload:
Example Payload
{
"event": "verification.completed",
"timestamp": "2024-01-15T12:30:00Z",
"data": {
"id": "ver_1234567890",
"bitcoin_address": "1A1zP1eP5QGefi2DMPTfTL5SLmv7DivfNa",
"challenge_message": "Verify ownership: abc123...",
"amount": 100000,
"status": "verified",
"signature": "H8k7dQ...",
"broker_context": "Order #12345",
"created_at": "2024-01-15T10:30:00Z",
"verified_at": "2024-01-15T12:30:00Z",
"expires_at": "2024-01-15T22:30:00Z"
}
}Payload Fields
eventThe event type that triggered the webhook
timestampISO 8601 timestamp of when the event occurred
dataComplete verification object with all details
Security Best Practice: Always verify webhook signatures
Each webhook request includes an X-Webhook-Signature header containing an HMAC SHA-256 signature. Verify this signature to ensure the request came from VerifyBTC.
Signature Header
X-Webhook-Signature: sha256=5d41402abc4b2a76b9719d911017c592Node.js Example
const crypto = require('crypto');
function verifyWebhookSignature(payload, signature, secret) {
const expectedSignature = crypto
.createHmac('sha256', secret)
.update(JSON.stringify(payload))
.digest('hex');
const signatureHash = signature.replace('sha256=', '');
return crypto.timingSafeEqual(
Buffer.from(signatureHash),
Buffer.from(expectedSignature)
);
}
// Express.js example
app.post('/webhooks/verifybtc', express.json(), (req, res) => {
const signature = req.headers['x-webhook-signature'];
const secret = process.env.WEBHOOK_SECRET;
if (!verifyWebhookSignature(req.body, signature, secret)) {
return res.status(401).json({ error: 'Invalid signature' });
}
// Process the webhook event
const { event, data } = req.body;
// Handle the event based on type
switch (event) {
case 'verification.completed':
// Handle successful verification
break;
case 'verification.failed':
// Handle failed verification
break;
// ... handle other events
}
res.json({ received: true });
});Python Example
import hmac
import hashlib
import json
def verify_webhook_signature(payload, signature, secret):
expected_signature = hmac.new(
secret.encode('utf-8'),
json.dumps(payload).encode('utf-8'),
hashlib.sha256
).hexdigest()
signature_hash = signature.replace('sha256=', '')
return hmac.compare_digest(signature_hash, expected_signature)
# Flask example
from flask import Flask, request, jsonify
@app.route('/webhooks/verifybtc', methods=['POST'])
def webhook():
signature = request.headers.get('X-Webhook-Signature')
secret = os.environ.get('WEBHOOK_SECRET')
if not verify_webhook_signature(request.json, signature, secret):
return jsonify({'error': 'Invalid signature'}), 401
# Process the webhook event
event = request.json.get('event')
data = request.json.get('data')
print(f'Received event: {event}', data)
return jsonify({'received': True})Your webhook endpoint must meet these requirements:
HTTPS Required (Production)
Endpoints must use HTTPS in production environments. HTTP is allowed for development/testing only.
Return 2xx Status Code
Respond with a 200-299 status code within 5 seconds to acknowledge receipt
Process Asynchronously
Process webhook events asynchronously to ensure fast responses
Idempotent Processing
Handle duplicate events gracefully (webhooks may be retried)
If your endpoint doesn't respond or returns an error, VerifyBTC will retry the webhook delivery:
Immediately
5 minutes later
30 minutes later
2 hours later
12 hours later (final)
Tip: Implement idempotency to handle duplicate events. Use the verification id to track which events you've already processed.
Test your webhook endpoint to ensure it's working correctly:
1. Test Button in Dashboard
Use the "Test" button on the Webhooks page to send a test event
2. Local Development with ngrok
# Install ngrok
npm install -g ngrok
# Start your local server
node server.js
# Expose your local server
ngrok http 3000
# Use the ngrok URL as your webhook endpoint
# Example: https://abc123.ngrok.io/webhooks/verifybtcAlways verify signatures
Never trust webhook data without signature verification
Process asynchronously
Queue webhook events and process them in the background
Log all webhook events
Keep detailed logs for debugging and audit purposes
Implement idempotency
Use event IDs to prevent processing duplicate events
Monitor webhook health
Set up alerts for failed webhook deliveries
If you're experiencing issues with webhooks or have questions: