Commit f4416b1a authored by David Bannon's avatar David Bannon Committed by Tim Graham
Browse files

Fixed #24915 -- Added stricter session key validation

Changed _session_key attribute to a property and implemented basic
validation in the setter. The session key must be 'truthy' and
at least 8 characters long. Otherwise, the value is set to None.
parent 20ff296c
Loading
Loading
Loading
Loading
+18 −1
Original line number Diff line number Diff line
@@ -161,10 +161,27 @@ class SessionBase(object):
            self._session_key = self._get_new_session_key()
        return self._session_key

    def _validate_session_key(self, key):
        """
        Key must be truthy and at least 8 characters long. 8 characters is an
        arbitrary lower bound for some minimal key security.
        """
        return key and len(key) >= 8

    def _get_session_key(self):
        return self._session_key
        return self.__session_key

    def _set_session_key(self, value):
        """
        Validate session key on assignment. Invalid values will set to None.
        """
        if self._validate_session_key(value):
            self.__session_key = value
        else:
            self.__session_key = None

    session_key = property(_get_session_key)
    _session_key = property(_get_session_key, _set_session_key)

    def _get_session(self, no_load=False):
        """
+2 −0
Original line number Diff line number Diff line
@@ -604,6 +604,8 @@ Miscellaneous
  <django.core.urlresolvers.ResolverMatch.namespace>`, the empty value is now
  an empty string instead of ``None``.

* For security hardening, session keys must be at least 8 characters.

.. _deprecated-features-1.9:

Features deprecated in 1.9
+15 −0
Original line number Diff line number Diff line
@@ -198,6 +198,21 @@ class SessionTestsMixin(object):
            # session key; make sure that entry is manually deleted
            session.delete('1')

    def test_session_key_empty_string_invalid(self):
        """Falsey values (Such as an empty string) are rejected."""
        self.session._session_key = ''
        self.assertIsNone(self.session.session_key)

    def test_session_key_too_short_invalid(self):
        """Strings shorter than 8 characters are rejected."""
        self.session._session_key = '1234567'
        self.assertIsNone(self.session.session_key)

    def test_session_key_valid_string_saved(self):
        """Strings of length 8 and up are accepted and stored."""
        self.session._session_key = '12345678'
        self.assertEqual(self.session.session_key, '12345678')

    def test_session_key_is_read_only(self):
        def set_session_key(session):
            session.session_key = session._get_new_session_key()