# Path: boardinghouse/exceptions.py
# class Forbidden(Exception):
#     """
#     An exception that will be raised when an attempt to activate a non-valid
#     schema is made.
#     """
# 
# class TemplateSchemaActivation(Forbidden):
#     """
#     An exception that will be raised when a user attempts to activate
#     the settings.TEMPLATE_SCHEMA schema.
#     """
#     def __init__(self, *args, **kwargs):
#         super(TemplateSchemaActivation, self).__init__(
#             'Activating template schema forbidden.', *args, **kwargs
#         )
# 
# class SchemaNotFound(Exception):
#     """
#     An exception that is raised when an attempt to activate a schema that
#     is not in the database is made.
#     """
# 
# Path: boardinghouse/schema.py
# def activate_schema(schema_name):
#     """
#     Activate the current schema: this will execute, in the database
#     connection, something like:
# 
#     .. code:: sql
# 
#         SET search_path TO "foo",public;
# 
#     It sends signals before and after that the schema will be, and was
#     activated.
# 
#     Must be passed a string: the internal name of the schema to activate.
#     """
#     from .signals import schema_pre_activate, schema_post_activate
# 
#     if schema_name == settings.TEMPLATE_SCHEMA:
#         raise TemplateSchemaActivation()
# 
#     schema_pre_activate.send(sender=None, schema_name=schema_name)
#     _set_search_path(schema_name)
#     found_schema = _get_search_path()
#     if found_schema != schema_name:
#         raise SchemaNotFound('Schema activation failed. Expected "{0}", saw "{1}"'.format(
#             schema_name, found_schema,
#         ))
#     schema_post_activate.send(sender=None, schema_name=schema_name)
#     _thread_locals.schema = schema_name
# 
# def deactivate_schema(schema=None):
#     """
#     Deactivate the provided (or current) schema.
#     """
#     from .signals import schema_pre_activate, schema_post_activate
# 
#     cursor = connection.cursor()
#     schema_pre_activate.send(sender=None, schema_name=None)
#     cursor.execute('SET search_path TO "$user",{0}'.format(settings.PUBLIC_SCHEMA))
#     schema_post_activate.send(sender=None, schema_name=None)
#     _thread_locals.schema = None
#     cursor.close()
# 
# Path: boardinghouse/signals.py



import logging
import re
from django.conf import settings
from django.contrib import messages
from django.db import ProgrammingError
from django.http import (
    HttpResponse, HttpResponseForbidden, HttpResponseRedirect,
)
from django.shortcuts import redirect
from django.utils.translation import ugettext_lazy as _
from .exceptions import Forbidden, TemplateSchemaActivation, SchemaNotFound
from .schema import activate_schema, deactivate_schema
from .signals import session_requesting_schema_change, session_schema_changed
        """
        In the case a request returned a DatabaseError, and there was no
        schema set on ``request.session``, then look and see if the error
        that was provided by the database may indicate that we should have
        been looking inside a schema.

        In the case we had a :class:`TemplateSchemaActivation` exception,
        then we want to remove that key from the session.
        """
        if isinstance(exception, ProgrammingError) and not request.session.get('schema'):
            if re.search('relation ".*" does not exist', exception.args[0]):
                # Should we return an error, or redirect? When should we
                # do one or the other? For an API, we would want an error
                # but for a regular user, a redirect may be better.
                if request.is_ajax():
                    return HttpResponse(
                        _('You must select a schema to access that resource'),
                        status=400
                    )
                # Can we see if there is already a pending message for this
                # request that has the same content as us?
                messages.error(
                    request,
                    _("You must select a schema to access that resource"),
                    fail_silently=True
                )
                return HttpResponseRedirect('..')
        # I'm not sure we ever really hit this one, but it's worth keeping
        # here just in case we've missed something. I guess it could occur
        # if a view manually attempted to activate the template schema.

# Path: boardinghouse/exceptions.py
# class Forbidden(Exception):
#     """
#     An exception that will be raised when an attempt to activate a non-valid
#     schema is made.
#     """
# 
# class TemplateSchemaActivation(Forbidden):
#     """
#     An exception that will be raised when a user attempts to activate
#     the settings.TEMPLATE_SCHEMA schema.
#     """
#     def __init__(self, *args, **kwargs):
#         super(TemplateSchemaActivation, self).__init__(
#             'Activating template schema forbidden.', *args, **kwargs
#         )
# 
# class SchemaNotFound(Exception):
#     """
#     An exception that is raised when an attempt to activate a schema that
#     is not in the database is made.
#     """
# 
# Path: boardinghouse/schema.py
# def activate_schema(schema_name):
#     """
#     Activate the current schema: this will execute, in the database
#     connection, something like:
# 
#     .. code:: sql
# 
#         SET search_path TO "foo",public;
# 
#     It sends signals before and after that the schema will be, and was
#     activated.
# 
#     Must be passed a string: the internal name of the schema to activate.
#     """
#     from .signals import schema_pre_activate, schema_post_activate
# 
#     if schema_name == settings.TEMPLATE_SCHEMA:
#         raise TemplateSchemaActivation()
# 
#     schema_pre_activate.send(sender=None, schema_name=schema_name)
#     _set_search_path(schema_name)
#     found_schema = _get_search_path()
#     if found_schema != schema_name:
#         raise SchemaNotFound('Schema activation failed. Expected "{0}", saw "{1}"'.format(
#             schema_name, found_schema,
#         ))
#     schema_post_activate.send(sender=None, schema_name=schema_name)
#     _thread_locals.schema = schema_name
# 
# def deactivate_schema(schema=None):
#     """
#     Deactivate the provided (or current) schema.
#     """
#     from .signals import schema_pre_activate, schema_post_activate
# 
#     cursor = connection.cursor()
#     schema_pre_activate.send(sender=None, schema_name=None)
#     cursor.execute('SET search_path TO "$user",{0}'.format(settings.PUBLIC_SCHEMA))
#     schema_post_activate.send(sender=None, schema_name=None)
#     _thread_locals.schema = None
#     cursor.close()
# 
# Path: boardinghouse/signals.py



# Path: boardinghouse/middleware.py
import logging
import re
from django.conf import settings
from django.contrib import messages
from django.db import ProgrammingError
from django.http import (
    HttpResponse, HttpResponseForbidden, HttpResponseRedirect,
)
from django.shortcuts import redirect
from django.utils.translation import ugettext_lazy as _
from .exceptions import Forbidden, TemplateSchemaActivation, SchemaNotFound
from .schema import activate_schema, deactivate_schema
from .signals import session_requesting_schema_change, session_schema_changed

        """
        In the case a request returned a DatabaseError, and there was no
        schema set on ``request.session``, then look and see if the error
        that was provided by the database may indicate that we should have
        been looking inside a schema.

        In the case we had a :class:`TemplateSchemaActivation` exception,
        then we want to remove that key from the session.
        """
        if isinstance(exception, ProgrammingError) and not request.session.get('schema'):
            if re.search('relation ".*" does not exist', exception.args[0]):
                # Should we return an error, or redirect? When should we
                # do one or the other? For an API, we would want an error
                # but for a regular user, a redirect may be better.
                if request.is_ajax():
                    return HttpResponse(
                        _('You must select a schema to access that resource'),
                        status=400
                    )
                # Can we see if there is already a pending message for this
                # request that has the same content as us?
                messages.error(
                    request,
                    _("You must select a schema to access that resource"),
                    fail_silently=True
                )
                return HttpResponseRedirect('..')
        # I'm not sure we ever really hit this one, but it's worth keeping
        # here just in case we've missed something. I guess it could occur
        # if a view manually attempted to activate the template schema.

        if isinstance(exception, TemplateSchemaActivation):