Update the existing subscription verification API to support subscription creation when a specific verification code is provided. This allows users to create premium subscriptions through a dedicated web page.
- Accept a
create_subscriptionparameter with a 64-character verification code - Create new Subscription entities when the code matches
- Maintain existing verification functionality
- Handle both new subscriptions and activation of existing inactive subscriptions
File: src/subscriptions/serializers.py
Update the existing serializer to accept the new parameter:
class SubscriptionVerificationRequestSerializer(serializers.Serializer):
email = serializers.EmailField()
create_subscription = serializers.CharField(required=False, max_length=64)File: src/subscriptions/views.py
Update the existing verify_subscription function to handle subscription creation:
def verify_subscription(request):
"""
Verify subscription status by email
Request:
{
"email": "user@example.com",
"create_subscription": "optional_64_char_code"
}
Response:
{
"hasActiveSubscription": true/false,
"subscriptionType": "premium" | null,
"expiresAt": null,
"features": ["ad_removal", "priority_support"],
"message": "Optional message"
}
"""
try:
# Validate request data
serializer = SubscriptionVerificationRequestSerializer(data=request.data)
if not serializer.is_valid():
return Response({
'error': 'Invalid request data',
'details': serializer.errors
}, status=status.HTTP_400_BAD_REQUEST)
email = serializer.validated_data['email']
create_subscription_code = serializer.validated_data.get('create_subscription')
# Hardcoded verification code (must match the one in the webapp)
CREATION_VERIFICATION_CODE = "a1b2c3d4e5f6g7h8i9j0k1l2m3n4o5p6q7r8s9t0u1v2w3x4y5z6a1b2c3d4e5f6g7h8i9j0k1l2m3n4o5p6q7r8s9t0u1v2w3x4y5z6"
# Check if creation code is provided and matches
if create_subscription_code and create_subscription_code == CREATION_VERIFICATION_CODE:
# Create subscription if it doesn't exist
subscription, created = Subscription.objects.get_or_create(
email=email,
defaults={
'is_active': True,
'verification_count': 0
}
)
if created:
logger.info(f"Created new subscription for email: {email}")
else:
# If subscription exists but is inactive, activate it
if not subscription.is_active:
subscription.is_active = True
subscription.save()
logger.info(f"Activated existing subscription for email: {email}")
# Find subscription (active or inactive) and increment verification count
subscription = Subscription.objects.filter(email=email).first()
if subscription:
# Increment verification count
subscription.verification_count += 1
subscription.save()
# Check if subscription is active for response
active_subscription = Subscription.objects.filter(
email=email,
is_active=True
).first()
# Prepare response
if active_subscription:
response_data = {
'hasActiveSubscription': True,
'subscriptionType': 'premium',
'expiresAt': None, # No expiration for manual subscriptions
'features': ['ad_removal', 'priority_support'],
'message': None
}
else:
response_data = {
'hasActiveSubscription': False,
'subscriptionType': None,
'expiresAt': None,
'features': [],
'message': 'No active subscription found for this email'
}
# Validate response
response_serializer = SubscriptionVerificationResponseSerializer(data=response_data)
response_serializer.is_valid(raise_exception=True)
return Response(response_serializer.validated_data, status=status.HTTP_200_OK)
except ValidationError as e:
logger.error(f"Validation error in subscription verification: {e}")
return Response({
'error': 'Validation error',
'message': str(e)
}, status=status.HTTP_400_BAD_REQUEST)
except Exception as e:
logger.error(f"Unexpected error in subscription verification: {e}")
return Response({
'error': 'Internal server error',
'message': 'An unexpected error occurred'
}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)- The verification code is hardcoded in the backend
- Consider using environment variables for production deployment
- Monitor API logs for suspicious activity patterns
- Consider implementing rate limiting on the verification endpoint
- Monitor for potential abuse of the subscription creation feature
- Test subscription creation with valid verification code
- Test subscription activation for existing inactive subscriptions
- Test verification without creation code (existing functionality)
- Test error handling for invalid codes
- Test email validation
- Test complete flow from webapp to subscription creation
- Test error scenarios and edge cases
- Test logging functionality
- Update the serializers.py file
- Update the views.py file
- Test the changes locally
- Review security implications
- Deploy to staging environment first
- Test with the webapp integration
- Deploy to production
- Monitor logs for any issues
- Monitor subscription creation patterns
- Check for any error logs
- Verify existing functionality still works
- Monitor subscription creation logs
- Track verification attempts
- Monitor for potential abuse
- Regularly review the verification code
- Monitor subscription creation patterns
- Update security measures as needed
src/subscriptions/serializers.py- Add create_subscription parametersrc/subscriptions/views.py- Update verify_subscription function
src/subscriptions/models.py- Model already supports required fields- URL configuration - Existing endpoint will handle new parameter
- API accepts create_subscription parameter
- Subscription creation works with valid verification code
- Existing verification functionality remains unchanged
- Proper error handling and logging
- Security measures are in place
- Integration with webapp works correctly
Endpoint: POST /api/v1/subscriptions/verify/
Request Body:
{
"email": "user@example.com",
"create_subscription": "a1b2c3d4e5f6g7h8i9j0k1l2m3n4o5p6q7r8s9t0u1v2w3x4y5z6a1b2c3d4e5f6g7h8i9j0k1l2m3n4o5p6q7r8s9t0u1v2w3x4y5z6"
}Response:
{
"hasActiveSubscription": true,
"subscriptionType": "premium",
"expiresAt": null,
"features": ["ad_removal", "priority_support"],
"message": null
}The hardcoded verification code that must be used:
a1b2c3d4e5f6g7h8i9j0k1l2m3n4o5p6q7r8s9t0u1v2w3x4y5z6a1b2c3d4e5f6g7h8i9j0k1l2m3n4o5p6q7r8s9t0u1v2w3x4y5z6
This code must match exactly between the frontend and backend for subscription creation to work.