We are currently solving the following issue within our repository. Here is the issue text:
--- BEGIN ISSUE ---
Sporadically broken HTML formatting since at least 3.5.0
### NetBox version

v3.5.1

### Python version

3.10

### Steps to Reproduce

Spontaneously observed behavior:
1. Open any list
2. Click to any object
3. Press "Go back" (or ALT+←) in browser

### Expected Behavior

List will be rendered as usual.

### Observed Behavior

Loaded only part of page, without sidebar, with empty head tag:

![image](https://github.com/netbox-community/netbox/assets/84839985/b18e3bd7-46f4-41b1-bc1d-8c3b72ee72c2)


--- END ISSUE ---

Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
--- BEGIN FILES ---
Path: `netbox/netbox/middleware.py`
Content:
```
1 import logging
2 import uuid
3 from urllib import parse
4 
5 from django.conf import settings
6 from django.contrib import auth, messages
7 from django.contrib.auth.middleware import RemoteUserMiddleware as RemoteUserMiddleware_
8 from django.core.exceptions import ImproperlyConfigured
9 from django.db import connection, ProgrammingError
10 from django.db.utils import InternalError
11 from django.http import Http404, HttpResponseRedirect
12 
13 from extras.context_managers import change_logging
14 from netbox.config import clear_config, get_config
15 from netbox.views import handler_500
16 from utilities.api import is_api_request, rest_api_server_error
17 
18 __all__ = (
19     'CoreMiddleware',
20     'MaintenanceModeMiddleware',
21     'RemoteUserMiddleware',
22 )
23 
24 
25 class CoreMiddleware:
26 
27     def __init__(self, get_response):
28         self.get_response = get_response
29 
30     def __call__(self, request):
31 
32         # Assign a random unique ID to the request. This will be used for change logging.
33         request.id = uuid.uuid4()
34 
35         # Enforce the LOGIN_REQUIRED config parameter. If true, redirect all non-exempt unauthenticated requests
36         # to the login page.
37         if (
38             settings.LOGIN_REQUIRED and
39             not request.user.is_authenticated and
40             not request.path_info.startswith(settings.AUTH_EXEMPT_PATHS)
41         ):
42             login_url = f'{settings.LOGIN_URL}?next={parse.quote(request.get_full_path_info())}'
43             return HttpResponseRedirect(login_url)
44 
45         # Enable the change_logging context manager and process the request.
46         with change_logging(request):
47             response = self.get_response(request)
48 
49         # Attach the unique request ID as an HTTP header.
50         response['X-Request-ID'] = request.id
51 
52         # If this is an API request, attach an HTTP header annotating the API version (e.g. '3.5').
53         if is_api_request(request):
54             response['API-Version'] = settings.REST_FRAMEWORK_VERSION
55 
56         # Clear any cached dynamic config parameters after each request.
57         clear_config()
58 
59         return response
60 
61     def process_exception(self, request, exception):
62         """
63         Implement custom error handling logic for production deployments.
64         """
65         # Don't catch exceptions when in debug mode
66         if settings.DEBUG:
67             return
68 
69         # Cleanly handle exceptions that occur from REST API requests
70         if is_api_request(request):
71             return rest_api_server_error(request)
72 
73         # Ignore Http404s (defer to Django's built-in 404 handling)
74         if isinstance(exception, Http404):
75             return
76 
77         # Determine the type of exception. If it's a common issue, return a custom error page with instructions.
78         custom_template = None
79         if isinstance(exception, ProgrammingError):
80             custom_template = 'exceptions/programming_error.html'
81         elif isinstance(exception, ImportError):
82             custom_template = 'exceptions/import_error.html'
83         elif isinstance(exception, PermissionError):
84             custom_template = 'exceptions/permission_error.html'
85 
86         # Return a custom error message, or fall back to Django's default 500 error handling
87         if custom_template:
88             return handler_500(request, template_name=custom_template)
89 
90 
91 class RemoteUserMiddleware(RemoteUserMiddleware_):
92     """
93     Custom implementation of Django's RemoteUserMiddleware which allows for a user-configurable HTTP header name.
94     """
95     force_logout_if_no_header = False
96 
97     @property
98     def header(self):
99         return settings.REMOTE_AUTH_HEADER
100 
101     def process_request(self, request):
102         logger = logging.getLogger(
103             'netbox.authentication.RemoteUserMiddleware')
104         # Bypass middleware if remote authentication is not enabled
105         if not settings.REMOTE_AUTH_ENABLED:
106             return
107         # AuthenticationMiddleware is required so that request.user exists.
108         if not hasattr(request, 'user'):
109             raise ImproperlyConfigured(
110                 "The Django remote user auth middleware requires the"
111                 " authentication middleware to be installed.  Edit your"
112                 " MIDDLEWARE setting to insert"
113                 " 'django.contrib.auth.middleware.AuthenticationMiddleware'"
114                 " before the RemoteUserMiddleware class.")
115         try:
116             username = request.META[self.header]
117         except KeyError:
118             # If specified header doesn't exist then remove any existing
119             # authenticated remote-user, or return (leaving request.user set to
120             # AnonymousUser by the AuthenticationMiddleware).
121             if self.force_logout_if_no_header and request.user.is_authenticated:
122                 self._remove_invalid_user(request)
123             return
124         # If the user is already authenticated and that user is the user we are
125         # getting passed in the headers, then the correct user is already
126         # persisted in the session and we don't need to continue.
127         if request.user.is_authenticated:
128             if request.user.get_username() == self.clean_username(username, request):
129                 return
130             else:
131                 # An authenticated user is associated with the request, but
132                 # it does not match the authorized user in the header.
133                 self._remove_invalid_user(request)
134 
135         # We are seeing this user for the first time in this session, attempt
136         # to authenticate the user.
137         if settings.REMOTE_AUTH_GROUP_SYNC_ENABLED:
138             logger.debug("Trying to sync Groups")
139             user = auth.authenticate(
140                 request, remote_user=username, remote_groups=self._get_groups(request))
141         else:
142             user = auth.authenticate(request, remote_user=username)
143         if user:
144             # User is valid.
145             # Update the User's Profile if set by request headers
146             if settings.REMOTE_AUTH_USER_FIRST_NAME in request.META:
147                 user.first_name = request.META[settings.REMOTE_AUTH_USER_FIRST_NAME]
148             if settings.REMOTE_AUTH_USER_LAST_NAME in request.META:
149                 user.last_name = request.META[settings.REMOTE_AUTH_USER_LAST_NAME]
150             if settings.REMOTE_AUTH_USER_EMAIL in request.META:
151                 user.email = request.META[settings.REMOTE_AUTH_USER_EMAIL]
152             user.save()
153 
154             # Set request.user and persist user in the session
155             # by logging the user in.
156             request.user = user
157             auth.login(request, user)
158 
159     def _get_groups(self, request):
160         logger = logging.getLogger(
161             'netbox.authentication.RemoteUserMiddleware')
162 
163         groups_string = request.META.get(
164             settings.REMOTE_AUTH_GROUP_HEADER, None)
165         if groups_string:
166             groups = groups_string.split(settings.REMOTE_AUTH_GROUP_SEPARATOR)
167         else:
168             groups = []
169         logger.debug(f"Groups are {groups}")
170         return groups
171 
172 
173 class MaintenanceModeMiddleware:
174     """
175     Middleware that checks if the application is in maintenance mode
176     and restricts write-related operations to the database.
177     """
178 
179     def __init__(self, get_response):
180         self.get_response = get_response
181 
182     def __call__(self, request):
183         if get_config().MAINTENANCE_MODE:
184             self._set_session_type(
185                 allow_write=request.path_info.startswith(settings.MAINTENANCE_EXEMPT_PATHS)
186             )
187 
188         return self.get_response(request)
189 
190     @staticmethod
191     def _set_session_type(allow_write):
192         """
193         Prevent any write-related database operations.
194 
195         Args:
196             allow_write (bool): If True, write operations will be permitted.
197         """
198         with connection.cursor() as cursor:
199             mode = 'READ WRITE' if allow_write else 'READ ONLY'
200             cursor.execute(f'SET SESSION CHARACTERISTICS AS TRANSACTION {mode};')
201 
202     def process_exception(self, request, exception):
203         """
204         Prevent any write-related database operations if an exception is raised.
205         """
206         if get_config().MAINTENANCE_MODE and isinstance(exception, InternalError):
207             error_message = 'NetBox is currently operating in maintenance mode and is unable to perform write ' \
208                             'operations. Please try again later.'
209 
210             if is_api_request(request):
211                 return rest_api_server_error(request, error=error_message)
212 
213             messages.error(request, error_message)
214             return HttpResponseRedirect(request.path_info)
215
```
--- END FILES ---

Please first localize the bug based on the issue statement, and then generate a patch according to the `git diff` format fenced by three backticks.

Here is an example:

```diff
diff --git a/examples/server_async.py b/examples/server_async.py
--- a/examples/server_async.py
+++ b/examples/server_async.py
@@ -313,4 +313,4 @@
 
 
 if __name__ == "__main__":
-    asyncio.run(run_async_server("."), debug=True)
+    asyncio.run(run_async_server(), debug=True)
diff --git a/examples/server_sync.py b/examples/server_sync.py
--- a/examples/server_sync.py
+++ b/examples/server_sync.py
@@ -313,5 +313,5 @@
 
 
 if __name__ == "__main__":
-    server = run_sync_server(".")
+    server = run_sync_server()
     server.shutdown()

```

diff --git a/netbox/netbox/middleware.py b/netbox/netbox/middleware.py
--- a/netbox/netbox/middleware.py
+++ b/netbox/netbox/middleware.py
@@ -49,6 +49,9 @@
         # Attach the unique request ID as an HTTP header.
         response['X-Request-ID'] = request.id
 
+        # Enable the Vary header to help with caching of HTMX responses
+        response['Vary'] = 'HX-Request'
+
         # If this is an API request, attach an HTTP header annotating the API version (e.g. '3.5').
         if is_api_request(request):
             response['API-Version'] = settings.REST_FRAMEWORK_VERSION

{"golden_diff": "diff --git a/netbox/netbox/middleware.py b/netbox/netbox/middleware.py\n--- a/netbox/netbox/middleware.py\n+++ b/netbox/netbox/middleware.py\n@@ -49,6 +49,9 @@\n         # Attach the unique request ID as an HTTP header.\n         response['X-Request-ID'] = request.id\n \n+        # Enable the Vary header to help with caching of HTMX responses\n+        response['Vary'] = 'HX-Request'\n+\n         # If this is an API request, attach an HTTP header annotating the API version (e.g. '3.5').\n         if is_api_request(request):\n             response['API-Version'] = settings.REST_FRAMEWORK_VERSION\n", "issue": "Sporadically broken HTML formatting since at least 3.5.0\n### NetBox version\n\nv3.5.1\n\n### Python version\n\n3.10\n\n### Steps to Reproduce\n\nSpontaneously observed behavior:\r\n1. Open any list\r\n2. Click to any object\r\n3. Press \"Go back\" (or ALT+\u2190) in browser\n\n### Expected Behavior\n\nList will be rendered as usual.\n\n### Observed Behavior\n\nLoaded only part of page, without sidebar, with empty head tag:\r\n\r\n![image](https://github.com/netbox-community/netbox/assets/84839985/b18e3bd7-46f4-41b1-bc1d-8c3b72ee72c2)\r\n\n", "before_files": [{"content": "import logging\nimport uuid\nfrom urllib import parse\n\nfrom django.conf import settings\nfrom django.contrib import auth, messages\nfrom django.contrib.auth.middleware import RemoteUserMiddleware as RemoteUserMiddleware_\nfrom django.core.exceptions import ImproperlyConfigured\nfrom django.db import connection, ProgrammingError\nfrom django.db.utils import InternalError\nfrom django.http import Http404, HttpResponseRedirect\n\nfrom extras.context_managers import change_logging\nfrom netbox.config import clear_config, get_config\nfrom netbox.views import handler_500\nfrom utilities.api import is_api_request, rest_api_server_error\n\n__all__ = (\n    'CoreMiddleware',\n    'MaintenanceModeMiddleware',\n    'RemoteUserMiddleware',\n)\n\n\nclass CoreMiddleware:\n\n    def __init__(self, get_response):\n        self.get_response = get_response\n\n    def __call__(self, request):\n\n        # Assign a random unique ID to the request. This will be used for change logging.\n        request.id = uuid.uuid4()\n\n        # Enforce the LOGIN_REQUIRED config parameter. If true, redirect all non-exempt unauthenticated requests\n        # to the login page.\n        if (\n            settings.LOGIN_REQUIRED and\n            not request.user.is_authenticated and\n            not request.path_info.startswith(settings.AUTH_EXEMPT_PATHS)\n        ):\n            login_url = f'{settings.LOGIN_URL}?next={parse.quote(request.get_full_path_info())}'\n            return HttpResponseRedirect(login_url)\n\n        # Enable the change_logging context manager and process the request.\n        with change_logging(request):\n            response = self.get_response(request)\n\n        # Attach the unique request ID as an HTTP header.\n        response['X-Request-ID'] = request.id\n\n        # If this is an API request, attach an HTTP header annotating the API version (e.g. '3.5').\n        if is_api_request(request):\n            response['API-Version'] = settings.REST_FRAMEWORK_VERSION\n\n        # Clear any cached dynamic config parameters after each request.\n        clear_config()\n\n        return response\n\n    def process_exception(self, request, exception):\n        \"\"\"\n        Implement custom error handling logic for production deployments.\n        \"\"\"\n        # Don't catch exceptions when in debug mode\n        if settings.DEBUG:\n            return\n\n        # Cleanly handle exceptions that occur from REST API requests\n        if is_api_request(request):\n            return rest_api_server_error(request)\n\n        # Ignore Http404s (defer to Django's built-in 404 handling)\n        if isinstance(exception, Http404):\n            return\n\n        # Determine the type of exception. If it's a common issue, return a custom error page with instructions.\n        custom_template = None\n        if isinstance(exception, ProgrammingError):\n            custom_template = 'exceptions/programming_error.html'\n        elif isinstance(exception, ImportError):\n            custom_template = 'exceptions/import_error.html'\n        elif isinstance(exception, PermissionError):\n            custom_template = 'exceptions/permission_error.html'\n\n        # Return a custom error message, or fall back to Django's default 500 error handling\n        if custom_template:\n            return handler_500(request, template_name=custom_template)\n\n\nclass RemoteUserMiddleware(RemoteUserMiddleware_):\n    \"\"\"\n    Custom implementation of Django's RemoteUserMiddleware which allows for a user-configurable HTTP header name.\n    \"\"\"\n    force_logout_if_no_header = False\n\n    @property\n    def header(self):\n        return settings.REMOTE_AUTH_HEADER\n\n    def process_request(self, request):\n        logger = logging.getLogger(\n            'netbox.authentication.RemoteUserMiddleware')\n        # Bypass middleware if remote authentication is not enabled\n        if not settings.REMOTE_AUTH_ENABLED:\n            return\n        # AuthenticationMiddleware is required so that request.user exists.\n        if not hasattr(request, 'user'):\n            raise ImproperlyConfigured(\n                \"The Django remote user auth middleware requires the\"\n                \" authentication middleware to be installed.  Edit your\"\n                \" MIDDLEWARE setting to insert\"\n                \" 'django.contrib.auth.middleware.AuthenticationMiddleware'\"\n                \" before the RemoteUserMiddleware class.\")\n        try:\n            username = request.META[self.header]\n        except KeyError:\n            # If specified header doesn't exist then remove any existing\n            # authenticated remote-user, or return (leaving request.user set to\n            # AnonymousUser by the AuthenticationMiddleware).\n            if self.force_logout_if_no_header and request.user.is_authenticated:\n                self._remove_invalid_user(request)\n            return\n        # If the user is already authenticated and that user is the user we are\n        # getting passed in the headers, then the correct user is already\n        # persisted in the session and we don't need to continue.\n        if request.user.is_authenticated:\n            if request.user.get_username() == self.clean_username(username, request):\n                return\n            else:\n                # An authenticated user is associated with the request, but\n                # it does not match the authorized user in the header.\n                self._remove_invalid_user(request)\n\n        # We are seeing this user for the first time in this session, attempt\n        # to authenticate the user.\n        if settings.REMOTE_AUTH_GROUP_SYNC_ENABLED:\n            logger.debug(\"Trying to sync Groups\")\n            user = auth.authenticate(\n                request, remote_user=username, remote_groups=self._get_groups(request))\n        else:\n            user = auth.authenticate(request, remote_user=username)\n        if user:\n            # User is valid.\n            # Update the User's Profile if set by request headers\n            if settings.REMOTE_AUTH_USER_FIRST_NAME in request.META:\n                user.first_name = request.META[settings.REMOTE_AUTH_USER_FIRST_NAME]\n            if settings.REMOTE_AUTH_USER_LAST_NAME in request.META:\n                user.last_name = request.META[settings.REMOTE_AUTH_USER_LAST_NAME]\n            if settings.REMOTE_AUTH_USER_EMAIL in request.META:\n                user.email = request.META[settings.REMOTE_AUTH_USER_EMAIL]\n            user.save()\n\n            # Set request.user and persist user in the session\n            # by logging the user in.\n            request.user = user\n            auth.login(request, user)\n\n    def _get_groups(self, request):\n        logger = logging.getLogger(\n            'netbox.authentication.RemoteUserMiddleware')\n\n        groups_string = request.META.get(\n            settings.REMOTE_AUTH_GROUP_HEADER, None)\n        if groups_string:\n            groups = groups_string.split(settings.REMOTE_AUTH_GROUP_SEPARATOR)\n        else:\n            groups = []\n        logger.debug(f\"Groups are {groups}\")\n        return groups\n\n\nclass MaintenanceModeMiddleware:\n    \"\"\"\n    Middleware that checks if the application is in maintenance mode\n    and restricts write-related operations to the database.\n    \"\"\"\n\n    def __init__(self, get_response):\n        self.get_response = get_response\n\n    def __call__(self, request):\n        if get_config().MAINTENANCE_MODE:\n            self._set_session_type(\n                allow_write=request.path_info.startswith(settings.MAINTENANCE_EXEMPT_PATHS)\n            )\n\n        return self.get_response(request)\n\n    @staticmethod\n    def _set_session_type(allow_write):\n        \"\"\"\n        Prevent any write-related database operations.\n\n        Args:\n            allow_write (bool): If True, write operations will be permitted.\n        \"\"\"\n        with connection.cursor() as cursor:\n            mode = 'READ WRITE' if allow_write else 'READ ONLY'\n            cursor.execute(f'SET SESSION CHARACTERISTICS AS TRANSACTION {mode};')\n\n    def process_exception(self, request, exception):\n        \"\"\"\n        Prevent any write-related database operations if an exception is raised.\n        \"\"\"\n        if get_config().MAINTENANCE_MODE and isinstance(exception, InternalError):\n            error_message = 'NetBox is currently operating in maintenance mode and is unable to perform write ' \\\n                            'operations. Please try again later.'\n\n            if is_api_request(request):\n                return rest_api_server_error(request, error=error_message)\n\n            messages.error(request, error_message)\n            return HttpResponseRedirect(request.path_info)\n", "path": "netbox/netbox/middleware.py"}], "after_files": [{"content": "import logging\nimport uuid\nfrom urllib import parse\n\nfrom django.conf import settings\nfrom django.contrib import auth, messages\nfrom django.contrib.auth.middleware import RemoteUserMiddleware as RemoteUserMiddleware_\nfrom django.core.exceptions import ImproperlyConfigured\nfrom django.db import connection, ProgrammingError\nfrom django.db.utils import InternalError\nfrom django.http import Http404, HttpResponseRedirect\n\nfrom extras.context_managers import change_logging\nfrom netbox.config import clear_config, get_config\nfrom netbox.views import handler_500\nfrom utilities.api import is_api_request, rest_api_server_error\n\n__all__ = (\n    'CoreMiddleware',\n    'MaintenanceModeMiddleware',\n    'RemoteUserMiddleware',\n)\n\n\nclass CoreMiddleware:\n\n    def __init__(self, get_response):\n        self.get_response = get_response\n\n    def __call__(self, request):\n\n        # Assign a random unique ID to the request. This will be used for change logging.\n        request.id = uuid.uuid4()\n\n        # Enforce the LOGIN_REQUIRED config parameter. If true, redirect all non-exempt unauthenticated requests\n        # to the login page.\n        if (\n            settings.LOGIN_REQUIRED and\n            not request.user.is_authenticated and\n            not request.path_info.startswith(settings.AUTH_EXEMPT_PATHS)\n        ):\n            login_url = f'{settings.LOGIN_URL}?next={parse.quote(request.get_full_path_info())}'\n            return HttpResponseRedirect(login_url)\n\n        # Enable the change_logging context manager and process the request.\n        with change_logging(request):\n            response = self.get_response(request)\n\n        # Attach the unique request ID as an HTTP header.\n        response['X-Request-ID'] = request.id\n\n        # Enable the Vary header to help with caching of HTMX responses\n        response['Vary'] = 'HX-Request'\n\n        # If this is an API request, attach an HTTP header annotating the API version (e.g. '3.5').\n        if is_api_request(request):\n            response['API-Version'] = settings.REST_FRAMEWORK_VERSION\n\n        # Clear any cached dynamic config parameters after each request.\n        clear_config()\n\n        return response\n\n    def process_exception(self, request, exception):\n        \"\"\"\n        Implement custom error handling logic for production deployments.\n        \"\"\"\n        # Don't catch exceptions when in debug mode\n        if settings.DEBUG:\n            return\n\n        # Cleanly handle exceptions that occur from REST API requests\n        if is_api_request(request):\n            return rest_api_server_error(request)\n\n        # Ignore Http404s (defer to Django's built-in 404 handling)\n        if isinstance(exception, Http404):\n            return\n\n        # Determine the type of exception. If it's a common issue, return a custom error page with instructions.\n        custom_template = None\n        if isinstance(exception, ProgrammingError):\n            custom_template = 'exceptions/programming_error.html'\n        elif isinstance(exception, ImportError):\n            custom_template = 'exceptions/import_error.html'\n        elif isinstance(exception, PermissionError):\n            custom_template = 'exceptions/permission_error.html'\n\n        # Return a custom error message, or fall back to Django's default 500 error handling\n        if custom_template:\n            return handler_500(request, template_name=custom_template)\n\n\nclass RemoteUserMiddleware(RemoteUserMiddleware_):\n    \"\"\"\n    Custom implementation of Django's RemoteUserMiddleware which allows for a user-configurable HTTP header name.\n    \"\"\"\n    force_logout_if_no_header = False\n\n    @property\n    def header(self):\n        return settings.REMOTE_AUTH_HEADER\n\n    def process_request(self, request):\n        logger = logging.getLogger(\n            'netbox.authentication.RemoteUserMiddleware')\n        # Bypass middleware if remote authentication is not enabled\n        if not settings.REMOTE_AUTH_ENABLED:\n            return\n        # AuthenticationMiddleware is required so that request.user exists.\n        if not hasattr(request, 'user'):\n            raise ImproperlyConfigured(\n                \"The Django remote user auth middleware requires the\"\n                \" authentication middleware to be installed.  Edit your\"\n                \" MIDDLEWARE setting to insert\"\n                \" 'django.contrib.auth.middleware.AuthenticationMiddleware'\"\n                \" before the RemoteUserMiddleware class.\")\n        try:\n            username = request.META[self.header]\n        except KeyError:\n            # If specified header doesn't exist then remove any existing\n            # authenticated remote-user, or return (leaving request.user set to\n            # AnonymousUser by the AuthenticationMiddleware).\n            if self.force_logout_if_no_header and request.user.is_authenticated:\n                self._remove_invalid_user(request)\n            return\n        # If the user is already authenticated and that user is the user we are\n        # getting passed in the headers, then the correct user is already\n        # persisted in the session and we don't need to continue.\n        if request.user.is_authenticated:\n            if request.user.get_username() == self.clean_username(username, request):\n                return\n            else:\n                # An authenticated user is associated with the request, but\n                # it does not match the authorized user in the header.\n                self._remove_invalid_user(request)\n\n        # We are seeing this user for the first time in this session, attempt\n        # to authenticate the user.\n        if settings.REMOTE_AUTH_GROUP_SYNC_ENABLED:\n            logger.debug(\"Trying to sync Groups\")\n            user = auth.authenticate(\n                request, remote_user=username, remote_groups=self._get_groups(request))\n        else:\n            user = auth.authenticate(request, remote_user=username)\n        if user:\n            # User is valid.\n            # Update the User's Profile if set by request headers\n            if settings.REMOTE_AUTH_USER_FIRST_NAME in request.META:\n                user.first_name = request.META[settings.REMOTE_AUTH_USER_FIRST_NAME]\n            if settings.REMOTE_AUTH_USER_LAST_NAME in request.META:\n                user.last_name = request.META[settings.REMOTE_AUTH_USER_LAST_NAME]\n            if settings.REMOTE_AUTH_USER_EMAIL in request.META:\n                user.email = request.META[settings.REMOTE_AUTH_USER_EMAIL]\n            user.save()\n\n            # Set request.user and persist user in the session\n            # by logging the user in.\n            request.user = user\n            auth.login(request, user)\n\n    def _get_groups(self, request):\n        logger = logging.getLogger(\n            'netbox.authentication.RemoteUserMiddleware')\n\n        groups_string = request.META.get(\n            settings.REMOTE_AUTH_GROUP_HEADER, None)\n        if groups_string:\n            groups = groups_string.split(settings.REMOTE_AUTH_GROUP_SEPARATOR)\n        else:\n            groups = []\n        logger.debug(f\"Groups are {groups}\")\n        return groups\n\n\nclass MaintenanceModeMiddleware:\n    \"\"\"\n    Middleware that checks if the application is in maintenance mode\n    and restricts write-related operations to the database.\n    \"\"\"\n\n    def __init__(self, get_response):\n        self.get_response = get_response\n\n    def __call__(self, request):\n        if get_config().MAINTENANCE_MODE:\n            self._set_session_type(\n                allow_write=request.path_info.startswith(settings.MAINTENANCE_EXEMPT_PATHS)\n            )\n\n        return self.get_response(request)\n\n    @staticmethod\n    def _set_session_type(allow_write):\n        \"\"\"\n        Prevent any write-related database operations.\n\n        Args:\n            allow_write (bool): If True, write operations will be permitted.\n        \"\"\"\n        with connection.cursor() as cursor:\n            mode = 'READ WRITE' if allow_write else 'READ ONLY'\n            cursor.execute(f'SET SESSION CHARACTERISTICS AS TRANSACTION {mode};')\n\n    def process_exception(self, request, exception):\n        \"\"\"\n        Prevent any write-related database operations if an exception is raised.\n        \"\"\"\n        if get_config().MAINTENANCE_MODE and isinstance(exception, InternalError):\n            error_message = 'NetBox is currently operating in maintenance mode and is unable to perform write ' \\\n                            'operations. Please try again later.'\n\n            if is_api_request(request):\n                return rest_api_server_error(request, error=error_message)\n\n            messages.error(request, error_message)\n            return HttpResponseRedirect(request.path_info)\n", "path": "netbox/netbox/middleware.py"}]}