Verify Endpoint
Server-side verification of CAPTCHA tokens.
Endpoint
POST https://gkcaptcha.gatekeeper.sa/api/v1/token/verifyRequest
cURL
curl -X POST https://gkcaptcha.gatekeeper.sa/api/v1/token/verify \
-H "Content-Type: application/json" \
-H "Authorization: Bearer YOUR_SECRET_KEY" \
-d '{
"token": "CAPTCHA_TOKEN_FROM_CLIENT"
}'Headers
| Header | Required | Description |
|---|---|---|
| Authorization | Yes | Bearer token with your secret key |
| Content-Type | Yes | Must be application/json |
Body Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
| token | string | Yes | The token from the client widget |
| remoteip | string | No | Client IP for additional validation |
Response
Success Response
json
{
"success": true,
"data": {
"verified": true,
"score": 0.15,
"hostname": "yourdomain.com",
"action": "login",
"timestamp": "2024-01-15T10:30:00Z",
"challenge_ts": "2024-01-15T10:29:55Z"
}
}Failed Verification
json
{
"success": true,
"data": {
"verified": false,
"score": 0.85,
"error_codes": ["timeout-or-duplicate", "invalid-input-response"]
}
}Response Fields
| Field | Type | Description |
|---|---|---|
| verified | boolean | Whether verification passed |
| score | float | Risk score (0.0 = safe, 1.0 = bot) |
| hostname | string | Domain where widget was solved |
| action | string | Action name if specified |
| error_codes | array | Error codes if verification failed |
Error Codes
| Code | Description |
|---|---|
| missing-input-secret | Secret key not provided |
| invalid-input-secret | Secret key is invalid |
| missing-input-response | Token not provided |
| invalid-input-response | Token is invalid or malformed |
| timeout-or-duplicate | Token expired or already used |
| bad-request | Request was malformed |
Code Examples
Node.js / Express
server.js
const verifyCaptcha = async (token) => {
const response = await fetch('https://gkcaptcha.gatekeeper.sa/api/v1/token/verify', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'Authorization': `Bearer ${process.env.GKCAPTCHA_SECRET_KEY}`
},
body: JSON.stringify({ token })
});
const result = await response.json();
if (!result.success) {
throw new Error('API request failed');
}
return result.data;
};
// Usage in Express route
app.post('/submit-form', async (req, res) => {
const { captchaToken, ...formData } = req.body;
const verification = await verifyCaptcha(captchaToken);
if (!verification.verified) {
return res.status(400).json({ error: 'CAPTCHA verification failed' });
}
// Check hostname matches your domain
if (verification.hostname !== 'yourdomain.com') {
return res.status(400).json({ error: 'Invalid origin' });
}
// Process the form...
res.json({ success: true });
});Go
main.go
package main
import (
"bytes"
"encoding/json"
"net/http"
"os"
)
type VerifyRequest struct {
Token string `json:"token"`
}
type VerifyResponse struct {
Success bool `json:"success"`
Data VerifyData `json:"data"`
}
type VerifyData struct {
Verified bool `json:"verified"`
Score float64 `json:"score"`
Hostname string `json:"hostname"`
ErrorCodes []string `json:"error_codes,omitempty"`
}
func verifyCaptcha(token string) (*VerifyData, error) {
reqBody, _ := json.Marshal(VerifyRequest{Token: token})
req, _ := http.NewRequest("POST", "https://gkcaptcha.gatekeeper.sa/api/v1/token/verify",
bytes.NewBuffer(reqBody))
req.Header.Set("Content-Type", "application/json")
req.Header.Set("Authorization", "Bearer "+os.Getenv("GKCAPTCHA_SECRET_KEY"))
client := &http.Client{}
resp, err := client.Do(req)
if err != nil {
return nil, err
}
defer resp.Body.Close()
var result VerifyResponse
json.NewDecoder(resp.Body).Decode(&result)
return &result.Data, nil
}Python / Flask
app.py
import os
import requests
def verify_captcha(token: str) -> dict:
response = requests.post(
'https://gkcaptcha.gatekeeper.sa/api/v1/token/verify',
headers={
'Content-Type': 'application/json',
'Authorization': f'Bearer {os.environ["GKCAPTCHA_SECRET_KEY"]}'
},
json={'token': token}
)
result = response.json()
if not result.get('success'):
raise Exception('API request failed')
return result['data']
# Usage in Flask
@app.route('/submit', methods=['POST'])
def submit_form():
token = request.json.get('captchaToken')
verification = verify_captcha(token)
if not verification['verified']:
return jsonify({'error': 'Verification failed'}), 400
# Process form...
return jsonify({'success': True})Best Practices
- Always verify tokens server-side, never trust client-side results
- Check the
hostnamematches your domain - Handle errors gracefully - don't block users on API failures
- Set appropriate timeouts (recommended: 10 seconds)
- Log verification failures for security monitoring