-
Notifications
You must be signed in to change notification settings - Fork 142
Description
Important
This may be due to an incorrect server configuration on our part, but it would be nice if the library could handle the case when there is no REMOTE_ADDR.
Description
After upgrading the django-request library from version 1.5.6 to 1.16.3 in our production environment, we encountered an issue where no requests were being saved to the database. Our dedicated server uses Django with CloudFlare, Nginx, and Gunicorn. The primary error relates to the IP address field validation in the request middleware.
Error Details
When processing a response, the RequestMiddleware attempts to create and validate a Request instance without initially committing to the database. However, it fails at the validation step due to an empty IP address field, which is a required field but is being passed as blank.
Error Log:
Bad request: {'ip': ['This field cannot be blank.']}
Traceback (most recent call last):
File "venv/lib/python3.11/site-packages/request/middleware.py", line 43, in process_response
r.full_clean()
File "venv/lib/python3.11/site-packages/django/db/models/base.py", line 1552, in full_clean
raise ValidationError(errors)
django.core.exceptions.ValidationError: {'ip': ['This field cannot be blank.']}
Relevant Code Snippet:
try:
r.from_http_request(request, response, commit=False)
r.full_clean()
except ValidationError as exc:
logger.warning(
'Bad request: %s',
str(exc),
exc_info=exc,
extra={'status_code': 400, 'request': request},
)
else:
r.save()Possible Causes
The from_http_request method defaults the IP address to an empty string if REMOTE_ADDR is not found in request.META, which is not an acceptable value for the GenericIPAddressField in the Request model:
Request Model:
ip = models.GenericIPAddressField(_('ip address'))Method Extract:
self.ip = request.META.get('REMOTE_ADDR', '')Suggested Solutions
I propose one of the following changes to handle situations where REMOTE_ADDR might not be available:
- Change the default value for the IP address field from a blank string to a placeholder IP ("0.0.0.0", "1.1.1.1" or REQUEST_IP_DUMMY).
- Allow the IP field to be nullable and blank (
ip = models.GenericIPAddressField(_('ip address'), blank=True, null=True)).