Repository: ansible/awx
File: awx/api/generics.py (Python)

Code before:
class APIView(views.APIView):
    schema = get_default_schema()
    versioning_class = URLPathVersioning

    def initialize_request(self, request, *args, **kwargs):
        """
        Store the Django REST Framework Request object as an attribute on the
        normal Django request, store time the request started.
        """
        remote_headers = ['REMOTE_ADDR', 'REMOTE_HOST']

        self.time_started = time.time()
        if getattr(settings, 'SQL_DEBUG', False):
            self.queries_before = len(connection.queries)

        if 'HTTP_X_TRUSTED_PROXY' in request.environ:
            if validate_x_trusted_proxy_header(request.environ['HTTP_X_TRUSTED_PROXY']):
                remote_headers = settings.REMOTE_HOST_HEADERS
            else:
                logger.warning("Request appeared to be a trusted upstream proxy but failed to provide a matching shared secret.")

        # If there are any custom headers in REMOTE_HOST_HEADERS, make sure
        # they respect the allowed proxy list
        if settings.PROXY_IP_ALLOWED_LIST:
            if not is_proxy_in_headers(self.request, settings.PROXY_IP_ALLOWED_LIST, remote_headers):
                delete_headers(request, settings.REMOTE_HOST_HEADERS)

        drf_request = super(APIView, self).initialize_request(request, *args, **kwargs)
        request.drf_request = drf_request
        try:
            request.drf_request_user = getattr(drf_request, 'user', False)
        except AuthenticationFailed:
            request.drf_request_user = None
        except (PermissionDenied, ParseError) as exc:
            request.drf_request_user = None
            self.__init_request_error__ = exc
        except UnsupportedMediaType as exc:
            exc.detail = _(
                'You did not use correct Content-Type in your HTTP request. If you are using our REST API, the Content-Type must be application/json'
            )
            self.__init_request_error__ = exc
        return drf_request

    def finalize_response(self, request, response, *args, **kwargs):
        """
        Log warning for 400 requests.  Add header with elapsed time.
        """
        #
        # If the URL was rewritten, and we get a 404, we should entirely
        # replace the view in the request context with an ApiErrorView()
        # Without this change, there will be subtle differences in the BrowseableAPIRenderer

Review comment (refactor):
I'm also wondering if we want to move this into DAB so that other services could just call something like:
```
from ansible_base.lib.utils.requests import delete_insecure_headers_if_not_from_trusted_proxy
delete_insecure_headers_if_not_from_trusted_proxy()
```

Code after:
class APIView(views.APIView):
    schema = get_default_schema()
    versioning_class = URLPathVersioning

    def initialize_request(self, request, *args, **kwargs):
        """
        Store the Django REST Framework Request object as an attribute on the
        normal Django request, store time the request started.
        """
        remote_headers = ['REMOTE_ADDR', 'REMOTE_HOST']

        self.time_started = time.time()
        if getattr(settings, 'SQL_DEBUG', False):
            self.queries_before = len(connection.queries)

        if 'HTTP_X_TRUSTED_PROXY' in request.environ:
            if validate_x_trusted_proxy_header(request.environ['HTTP_X_TRUSTED_PROXY']):
                remote_headers = settings.REMOTE_HOST_HEADERS
            else:
                logger.warning("Request appeared to be a trusted upstream proxy but failed to provide a matching shared secret.")

        # If there are any custom headers in REMOTE_HOST_HEADERS, make sure
        # they respect the allowed proxy list
        if settings.PROXY_IP_ALLOWED_LIST:
            if not is_proxy_in_headers(self.request, settings.PROXY_IP_ALLOWED_LIST, remote_headers):
                delete_headers_starting_with_http(request, settings.REMOTE_HOST_HEADERS)

        drf_request = super(APIView, self).initialize_request(request, *args, **kwargs)
        request.drf_request = drf_request
        try:
            request.drf_request_user = getattr(drf_request, 'user', False)
        except AuthenticationFailed:
            request.drf_request_user = None
        except (PermissionDenied, ParseError) as exc:
            request.drf_request_user = None
            self.__init_request_error__ = exc
        except UnsupportedMediaType as exc:
            exc.detail = _(
                'You did not use correct Content-Type in your HTTP request. If you are using our REST API, the Content-Type must be application/json'
            )
            self.__init_request_error__ = exc
        return drf_request

    def finalize_response(self, request, response, *args, **kwargs):
        """
        Log warning for 400 requests.  Add header with elapsed time.
        """
        #
        # If the URL was rewritten, and we get a 404, we should entirely
        # replace the view in the request context with an ApiErrorView()
        # Without this change, there will be subtle differences in the BrowseableAPIRenderer