Troubleshooting Guide
Solutions to common problems and error messages
Solutions to common issues you might encounter.
Authentication Issues
Error: 401 Unauthorized
Symptoms:
{
"error": {
"code": "authentication_required",
"message": "Authentication credentials were not provided"
}
}Common Causes:
- Missing Authorization header
- Expired access token
- Invalid token format
- Token for wrong environment (dev vs prod)
Solutions:
# ✅ Correct format
curl https://api.example.com/v1/resources \
-H "Authorization: Bearer YOUR_TOKEN"
# ❌ Wrong format
curl https://api.example.com/v1/resources \
-H "Authorization: YOUR_TOKEN"Still not working?
- Verify token hasn’t expired
- Check if you’re using the correct base URL
- Ensure token has proper scopes
Error: 403 Forbidden
Symptoms:
{
"error": {
"code": "insufficient_permissions",
"message": "You don't have permission to perform this action"
}
}Solutions:
- Check your API key scopes in dashboard
- Verify you have the right role
- Ensure you’re accessing resources in your organization
Token Refresh Fails
Symptoms: Refresh token returns 400 or 401
Solutions:
# Ensure refresh token hasn't expired
# Refresh tokens last 30 days
# If expired, re-authenticate:
response = requests.post(
'https://api.example.com/v1/auth/login',
json={
'email': 'user@example.com',
'password': 'password'
}
)Rate Limiting Issues
Error: 429 Too Many Requests
Symptoms:
{
"error": {
"code": "rate_limit_exceeded",
"message": "Rate limit exceeded. Try again in 60 seconds."
}
}Check Rate Limit Status:
curl -I https://api.example.com/v1/resources \
-H "Authorization: Bearer YOUR_TOKEN"Look for these headers:
X-RateLimit-Limit: 600
X-RateLimit-Remaining: 0
X-RateLimit-Reset: 1614556800Solutions:
1. Implement exponential backoff:
import time
def make_request_with_retry(url, headers, max_retries=3):
for attempt in range(max_retries):
response = requests.get(url, headers=headers)
if response.status_code != 429:
return response
# Get retry-after header
retry_after = int(response.headers.get('Retry-After', 60))
print(f"Rate limited. Waiting {retry_after} seconds...")
time.sleep(retry_after)
raise Exception("Max retries exceeded")2. Use pagination to reduce requests:
# Instead of making 100 requests
for i in range(100):
get_resource(i)
# Make 1 request with pagination
get_all_resources(per_page=100)3. Cache responses:
from functools import lru_cache
@lru_cache(maxsize=128)
def get_resource(resource_id):
return api.resources.get(resource_id)4. Upgrade your plan for higher limits
Connection Issues
Error: Connection Timeout
Symptoms:
requests.exceptions.Timeout: HTTPSConnectionPool...Solutions:
1. Increase timeout:
response = requests.get(url, headers=headers, timeout=30)2. Check network connectivity:
# Test DNS resolution
nslookup api.example.com
# Test connectivity
ping api.example.com
# Test HTTPS connection
curl -v https://api.example.com3. Check firewall settings:
Ensure outbound HTTPS (port 443) is allowed
SSL Certificate Verification Failed
Symptoms:
SSLError: [SSL: CERTIFICATE_VERIFY_FAILED]Solutions:
1. Update SSL certificates:
# macOS
brew install ca-certificates
# Ubuntu
sudo apt-get update
sudo apt-get install ca-certificates
# Python
pip install --upgrade certifi2. Check system time:
Incorrect system time can cause certificate validation to fail.
3. Verify API endpoint:
Ensure you’re using https:// not http://
Data Issues
Error: 400 Bad Request - Validation Error
Symptoms:
{
"error": {
"code": "validation_error",
"message": "Invalid input provided",
"details": [
{
"field": "email",
"message": "Email format is invalid"
},
{
"field": "name",
"message": "Name is required"
}
]
}
}Solutions:
1. Check required fields:
# Read API documentation for required fields
required_fields = ['name', 'type', 'description']
data = {
'name': 'My Resource',
'type': 'standard',
'description': 'A description'
}2. Validate data types:
# Ensure correct types
{
"name": "string", # ✅
"count": 10, # ✅ integer
"is_active": true, # ✅ boolean
"tags": ["tag1", "tag2"] # ✅ array
}3. Check string lengths:
Many fields have length limits:
- Name: max 100 characters
- Description: max 500 characters
- Email: max 255 characters
Error: 404 Resource Not Found
Symptoms:
{
"error": {
"code": "resource_not_found",
"message": "The requested resource could not be found"
}
}Solutions:
1. Verify resource ID:
# Ensure ID format is correct
resource_id = "res_abc123" # ✅
resource_id = "123" # ❌ Old format2. Check if resource was deleted:
# List all resources to verify
curl https://api.example.com/v1/resources \
-H "Authorization: Bearer YOUR_TOKEN"3. Verify you have access:
Resource might exist but you don’t have permission to view it.
SDK Issues
Python SDK: Import Error
Symptoms:
ModuleNotFoundError: No module named 'example_sdk'Solutions:
# Install SDK
pip install example-sdk
# Verify installation
pip show example-sdk
# Upgrade to latest
pip install --upgrade example-sdkJavaScript SDK: Module Not Found
Symptoms:
Error: Cannot find module '@example/sdk'Solutions:
# Install SDK
npm install @example/sdk
# Clear cache and reinstall
rm -rf node_modules package-lock.json
npm install
# Verify installation
npm list @example/sdkSDK Version Compatibility
Symptoms: Unexpected errors with latest SDK version
Solutions:
# Check SDK version
pip show example-sdk # Python
npm list @example/sdk # JavaScript
# Install specific version
pip install example-sdk==1.2.3 # Python
npm install @example/sdk@1.2.3 # JavaScriptWebhook Issues
Webhooks Not Being Received
Checklist:
- Webhook URL is accessible from internet
- URL uses HTTPS (required)
- Endpoint returns 200 status code
- Endpoint responds within 5 seconds
- Firewall allows incoming connections
- Webhook is enabled in dashboard
Testing:
# Test your webhook endpoint
curl -X POST https://your-app.com/webhooks \
-H "Content-Type: application/json" \
-d '{"test": "data"}'View webhook logs:
Go to Dashboard → Webhooks → [Your Webhook] → Delivery Log
Webhook Signature Verification Fails
Symptoms: 401 Unauthorized when processing webhooks
Solutions:
import hmac
import hashlib
def verify_signature(payload, signature, secret):
expected = hmac.new(
secret.encode('utf-8'),
payload.encode('utf-8'),
hashlib.sha256
).hexdigest()
return hmac.compare_digest(signature, expected)
# Get raw payload (important!)
payload = request.get_data(as_text=True)
signature = request.headers['X-Webhook-Signature']
if not verify_signature(payload, signature, WEBHOOK_SECRET):
return 401Common mistakes:
- Using parsed JSON instead of raw payload
- Wrong secret key
- Not comparing with constant-time comparison
Performance Issues
Slow API Responses
Diagnosis:
# Measure response time
time curl https://api.example.com/v1/resources \
-H "Authorization: Bearer YOUR_TOKEN"Solutions:
1. Use pagination:
# Slow - returns all resources
curl https://api.example.com/v1/resources
# Fast - returns 50 resources
curl "https://api.example.com/v1/resources?per_page=50"2. Use field selection:
# Only request fields you need
curl "https://api.example.com/v1/resources?fields=id,name,status" \
-H "Authorization: Bearer YOUR_TOKEN"3. Enable compression:
headers = {
'Authorization': f'Bearer {token}',
'Accept-Encoding': 'gzip'
}4. Use bulk endpoints:
# Instead of 100 individual requests
for id in ids:
get_resource(id)
# Make 1 bulk request
get_resources_bulk(ids)Getting More Help
If these solutions don’t resolve your issue:
- Check Status Page: status.example.com
- Search Community Forum: community.example.com
- Contact Support: support@example.com
- Open GitHub Issue: github.com/example/issues
What to Include in Support Requests
- Error message (full text)
- Steps to reproduce
- Expected vs actual behavior
- Request ID (from
X-Request-IDheader) - Code sample (sanitized)
- SDK/language version
- Timestamp of issue