Django
Integrate the ScamVerify™ API with your Django application using views and the requests library.
This guide shows you how to call the ScamVerify™ API from a Django application. You will create a reusable client class, Django views for phone and URL verification, and proper error handling.
Environment Setup
Add your API key to your Django settings. Never hardcode it in source files.
# settings.py
import os
SCAMVERIFY_API_KEY = os.environ.get('SCAMVERIFY_API_KEY')Set the environment variable in your deployment configuration or .env file:
SCAMVERIFY_API_KEY=sv_live_your_key_hereReusable Client
Create a client module that you can import in any view.
# verification/scamverify_client.py
import requests
from django.conf import settings
class ScamVerifyError(Exception):
def __init__(self, message, status_code=0):
super().__init__(message)
self.status_code = status_code
class ScamVerifyClient:
BASE_URL = 'https://scamverify.ai/api/v1'
def __init__(self, api_key=None):
self.api_key = api_key or settings.SCAMVERIFY_API_KEY
if not self.api_key:
raise ScamVerifyError('SCAMVERIFY_API_KEY not configured')
self.session = requests.Session()
self.session.headers.update({
'Authorization': f'Bearer {self.api_key}',
'Content-Type': 'application/json',
})
def _handle_response(self, response):
if response.status_code == 401:
raise ScamVerifyError('Invalid or revoked API key', 401)
if response.status_code == 402:
raise ScamVerifyError('Quota exhausted', 402)
if response.status_code == 429:
retry_after = response.headers.get('Retry-After', '60')
raise ScamVerifyError(f'Rate limited. Retry after {retry_after}s', 429)
response.raise_for_status()
return response.json()
def lookup_phone(self, phone_number):
response = self.session.post(
f'{self.BASE_URL}/phone/lookup',
json={'phone_number': phone_number},
)
return self._handle_response(response)
def lookup_url(self, url, force_refresh=False):
payload = {'url': url}
if force_refresh:
payload['force_refresh'] = True
response = self.session.post(
f'{self.BASE_URL}/url/lookup',
json=payload,
)
return self._handle_response(response)
def analyze_text(self, text, sender_number=None):
payload = {'text': text}
if sender_number:
payload['sender_number'] = sender_number
response = self.session.post(
f'{self.BASE_URL}/text/analyze',
json=payload,
)
return self._handle_response(response)
def analyze_email(self, email_body, raw_headers=None):
payload = {'email_body': email_body}
if raw_headers:
payload['raw_headers'] = raw_headers
response = self.session.post(
f'{self.BASE_URL}/email/analyze',
json=payload,
)
return self._handle_response(response)Django Views
# verification/views.py
import json
import logging
from django.http import JsonResponse
from django.views.decorators.csrf import csrf_exempt
from django.views.decorators.http import require_POST
from .scamverify_client import ScamVerifyClient, ScamVerifyError
logger = logging.getLogger(__name__)
client = ScamVerifyClient()
@csrf_exempt
@require_POST
def verify_phone(request):
try:
body = json.loads(request.body)
except json.JSONDecodeError:
return JsonResponse({'error': 'Invalid JSON'}, status=400)
phone_number = body.get('phone_number')
if not phone_number:
return JsonResponse({'error': 'phone_number is required'}, status=400)
try:
result = client.lookup_phone(phone_number)
return JsonResponse({
'risk_score': result['risk_score'],
'verdict': result['verdict'],
'explanation': result['explanation'],
'signals': result.get('signals', {}),
'cached': result.get('cached', False),
})
except ScamVerifyError as e:
logger.error(f'ScamVerify error: {e}')
return JsonResponse({'error': str(e)}, status=e.status_code or 500)
except Exception as e:
logger.exception('Unexpected error during phone verification')
return JsonResponse({'error': 'Verification unavailable'}, status=503)
@csrf_exempt
@require_POST
def verify_url(request):
try:
body = json.loads(request.body)
except json.JSONDecodeError:
return JsonResponse({'error': 'Invalid JSON'}, status=400)
url = body.get('url')
if not url:
return JsonResponse({'error': 'url is required'}, status=400)
try:
result = client.lookup_url(url)
return JsonResponse({
'risk_score': result['risk_score'],
'verdict': result['verdict'],
'explanation': result['explanation'],
'signals': result.get('signals', {}),
'cached': result.get('cached', False),
})
except ScamVerifyError as e:
logger.error(f'ScamVerify error: {e}')
return JsonResponse({'error': str(e)}, status=e.status_code or 500)
except Exception as e:
logger.exception('Unexpected error during URL verification')
return JsonResponse({'error': 'Verification unavailable'}, status=503)# verification/views.py
import json
import logging
from django.http import JsonResponse
from django.views import View
from django.utils.decorators import method_decorator
from django.views.decorators.csrf import csrf_exempt
from .scamverify_client import ScamVerifyClient, ScamVerifyError
logger = logging.getLogger(__name__)
@method_decorator(csrf_exempt, name='dispatch')
class PhoneVerificationView(View):
def __init__(self, **kwargs):
super().__init__(**kwargs)
self.client = ScamVerifyClient()
def post(self, request):
try:
body = json.loads(request.body)
except json.JSONDecodeError:
return JsonResponse({'error': 'Invalid JSON'}, status=400)
phone_number = body.get('phone_number')
if not phone_number:
return JsonResponse({'error': 'phone_number is required'}, status=400)
try:
result = self.client.lookup_phone(phone_number)
return JsonResponse(result)
except ScamVerifyError as e:
logger.error(f'ScamVerify error: {e}')
return JsonResponse({'error': str(e)}, status=e.status_code or 500)
@method_decorator(csrf_exempt, name='dispatch')
class UrlVerificationView(View):
def __init__(self, **kwargs):
super().__init__(**kwargs)
self.client = ScamVerifyClient()
def post(self, request):
try:
body = json.loads(request.body)
except json.JSONDecodeError:
return JsonResponse({'error': 'Invalid JSON'}, status=400)
url = body.get('url')
if not url:
return JsonResponse({'error': 'url is required'}, status=400)
try:
result = self.client.lookup_url(url)
return JsonResponse(result)
except ScamVerifyError as e:
logger.error(f'ScamVerify error: {e}')
return JsonResponse({'error': str(e)}, status=e.status_code or 500)URL Configuration
# verification/urls.py
from django.urls import path
from . import views
# For function-based views:
urlpatterns = [
path('api/verify-phone/', views.verify_phone, name='verify_phone'),
path('api/verify-url/', views.verify_url, name='verify_url'),
]
# For class-based views:
# urlpatterns = [
# path('api/verify-phone/', views.PhoneVerificationView.as_view(), name='verify_phone'),
# path('api/verify-url/', views.UrlVerificationView.as_view(), name='verify_url'),
# ]Caching with Django Cache Framework
Add a caching layer on top of the ScamVerify™ built-in cache to reduce API calls.
from django.core.cache import cache
def lookup_phone_cached(client, phone_number):
cache_key = f'scamverify:phone:{phone_number}'
result = cache.get(cache_key)
if result is not None:
return result
result = client.lookup_phone(phone_number)
# Cache for 1 hour on your side (ScamVerify caches for 24h on its end)
cache.set(cache_key, result, timeout=3600)
return resultError Handling Middleware
For apps making many ScamVerify™ calls, you can add middleware to handle common errors consistently.
# verification/middleware.py
import logging
from django.http import JsonResponse
from .scamverify_client import ScamVerifyError
logger = logging.getLogger(__name__)
class ScamVerifyErrorMiddleware:
def __init__(self, get_response):
self.get_response = get_response
def __call__(self, request):
return self.get_response(request)
def process_exception(self, request, exception):
if isinstance(exception, ScamVerifyError):
logger.error(f'ScamVerify API error: {exception}')
return JsonResponse(
{'error': str(exception)},
status=exception.status_code or 500,
)
return NoneDjango REST Framework users: The same ScamVerifyClient works with DRF serializers and API views. Replace JsonResponse with DRF's Response and add your authentication/permission classes as needed.
Related
- Quickstart for API key setup
- FastAPI Integration if you prefer async Python
- Common Issues for troubleshooting