Как использовать сессии
Django предоставляет полную поддержку анонимных сессий. Система сессий позволяет хранить и извлекать произвольные данные для каждого посетителя сайта. Данные хранятся на стороне сервера, и система абстрагирует отправку и получение куки. Куки содержат идентификатор сессии, а не сами данные (если вы не используете бекенд на основе куки).
Включение сессий
Сессии реализуются с помощью элемента средства обработки запросов.
Для включения функциональности сессий выполните следующие действия:
- Отредактируйте настройку
MIDDLEWAREи убедитесь, что она содержит'django.contrib.sessions.middleware.SessionMiddleware'. По умолчаниюsettings.pyсозданнаяdjango-admin startprojectимеетSessionMiddlewareвключённой.
Если вы не хотите использовать сессии, вы можете удалить строку SessionMiddleware из MIDDLEWARE и 'django.contrib.sessions' из INSTALLED_APPS. Это сэкономит немного ресурсов.
Настройка механизма сессий
По умолчанию Django хранит сессии в вашей базе данных (используя модель django.contrib.sessions.models.Session). Хотя это удобно, в некоторых случаях хранение данных сессии в другом месте может быть быстрее, поэтому Django можно настроить на хранение данных сессии на файловой системе или в кэше.
Использование сессий, поддерживаемых базой данных
Если вы хотите использовать сессии, поддерживаемые базой данных, вам нужно добавить 'django.contrib.sessions' в вашу настройку INSTALLED_APPS.
После настройки вашей установки, запустите manage.py migrate для установки единственной таблицы базы данных, которая хранит данные сессий.
Использование кэшированных сессий
Для повышения производительности вы можете использовать бекенд сессий на основе кэша.
Для хранения данных сессий с помощью системы кэша Django, вам сначала нужно убедиться, что вы настроили свой кэш; см. документацию по кэшу для получения подробной информации.
Предупреждение
Вы должны использовать кэшированные сессии только в том случае, если вы используете бекенд кэша Memcached. Кэш локальной памяти не сохраняет данные достаточно долго, чтобы быть хорошим выбором, и будет быстрее использовать файлы или базы данных напрямую, вместо того, чтобы отправлять все через файловый или базовый кэш базы данных. Кроме того, бекенд кэша локальной памяти НЕ безопасен для многопроцессорных систем, поэтому, вероятно, не подходит для производственных сред.
Если у вас определено несколько кэшей в CACHES, Django будет использовать кэш по умолчанию. Для использования другого кэша установите SESSION_CACHE_ALIAS в имя этого кэша.
После настройки кэша у вас есть два варианта хранения данных в кэше:
- Установите
SESSION_ENGINEна"django.contrib.sessions.backends.cache"для простого кэшированного хранилища сессий. Данные сессий будут храниться непосредственно в вашем кэше. Однако данные сессий могут быть недолговременными: кэшированные данные могут быть удалены, если кэш заполнится или если сервер кэша перезагрузится. - Для долговременных кэшированных данных установите
SESSION_ENGINEна"django.contrib.sessions.backends.cached_db". Это использует кэш с прохождением записи - каждая запись в кэш также будет записана в базу данных. Чтение сессий использует базу данных только в том случае, если данные уже не находятся в кэше.
Оба хранилища сессий достаточно быстрые, но простой кэш быстрее, поскольку он не учитывает долговременность. В большинстве случаев бекенд cached_db будет достаточно быстрым, но если вам нужна максимальная производительность и вы готовы время от времени терять данные сессий, бекенд cache для вас.
Если вы используете бекенд сессий cached_db, вам также необходимо следовать инструкциям по настройке для использования сессий, поддерживаемых базой данных.
Использование сессий на основе файлов
Для использования сессий на основе файлов установите настройку SESSION_ENGINE на "django.contrib.sessions.backends.file".
Вы также можете настроить настройку SESSION_FILE_PATH (которая по умолчанию выводится из tempfile.gettempdir(), скорее всего, /tmp) для управления тем, где Django хранит файлы сессий. Убедитесь, что ваш веб-сервер имеет разрешения на чтение и запись в этом месте.
Использование сессий на основе куки
Примечание
Рекомендуется оставить настройку SESSION_COOKIE_HTTPONLY в значении True для предотвращения доступа к сохранённым данным из JavaScript.
Предупреждение
Если ключ SECRET_KEY не является секретным, и вы используете PickleSerializer, это может привести к произвольному выполнению удалённого кода.
Злоумышленник, имеющий доступ к SECRET_KEY, не только может сгенерировать поддельные данные сессии, которым доверяет ваш сайт, но также может выполнить произвольный удалённый код, поскольку данные сериализуются с помощью pickle.
Если вы используете сессии на основе куки, обратите особое внимание на то, чтобы ваш секретный ключ всегда оставался в полной тайне для любого удалённо доступного ресурса.
Данные сессий подписываются, но не шифруются
При использовании бекенда куки клиент может прочитать данные сессии.
Для защиты данных от изменений клиентом используется MAC (Message Authentication Code), поэтому данные сессии будут аннулированы при внесении изменений. Такое же аннулирование происходит, если клиент, хранящий куки (например, браузер пользователя), не может сохранить всю куки сессии и теряет данные. Даже если Django сжимает данные, все равно существует возможность превышения общего ограничения в 4096 байт на куки.
Гарантия свежести отсутствует
Обратите внимание, что, хотя MAC может гарантировать подлинность данных (что они были сгенерированы вашим сайтом, а не кем-то другим) и целостность данных (что они все там и правильные), он не может гарантировать свежесть, т.е. что вам возвращается последнее отправленное клиенту значение. Это означает, что для некоторых применений данных сессии бекенд куки может открыть вас для атак повторения. В отличие от других бекендов сессий, которые сохраняют запись о каждой сессии на сервере и аннулируют её, когда пользователь выходит из системы, сессии на основе куки не аннулируются при выходе пользователя. Таким образом, если злоумышленник украдёт куки пользователя, он может использовать эти куки для входа как этот пользователь, даже если пользователь вышел из системы. Куки будут считаться «просроченными» только если они старше, чем ваша SESSION_COOKIE_AGE.
Производительность
Наконец, размер куки может повлиять на скорость вашего сайта.
Использование сессий в представлениях
Когда SessionMiddleware активировано, каждый объект HttpRequest – первый аргумент любой функции представления Django – будет иметь атрибут session, который представляет собой объект, похожий на словарь.
Вы можете читать и записывать в request.session в любой точке вашего представления. Вы можете редактировать его несколько раз.
-
class backends.base.SessionBase -
Это базовый класс для всех объектов сеанса. Он имеет следующие стандартные методы словаря:
-
__getitem__(key) -
Пример:
fav_color = request.session['fav_color']
-
__setitem__(key, value) -
Пример:
request.session['fav_color'] = 'blue'
-
__delitem__(key) -
Пример:
del request.session['fav_color']. Это вызываетKeyErrorесли заданныйkeyещё не присутствует в сеансе.
-
__contains__(key) -
Пример:
'fav_color' in request.session
-
get(key, default=None) -
Пример:
fav_color = request.session.get('fav_color', 'red')
-
pop(key, default=__not_given) -
Пример:
fav_color = request.session.pop('fav_color', 'blue')
-
keys()
-
items()
-
setdefault()
-
clear()
Также имеются следующие методы:
-
flush() -
Удаляет текущие данные сеанса из сеанса и удаляет cookie сеанса. Это используется, если необходимо гарантировать, что предыдущие данные сеанса больше не могут быть получены браузером пользователя (например, функция
django.contrib.auth.logout()вызывает её).
-
Устанавливает тестовый cookie для определения, поддерживает ли браузер пользователя cookies. Из-за того, как работают cookies, вы не сможете протестировать это до следующего запроса страницы пользователем. Подробнее см. раздел Установка тестовых cookies ниже.
-
Возвращает либо
True, либоFalse, в зависимости от того, принял ли браузер пользователя тестовый cookie. Из-за того, как работают cookies, вам нужно будет вызватьset_test_cookie()на предыдущем отдельном запросе страницы. Подробнее см. раздел Установка тестовых cookies ниже.
-
Удаляет тестовый cookie. Используйте это для очистки за собой.
-
Новое в Django 3.0.
Возвращает срок действия cookie сеанса в секундах. По умолчанию
SESSION_COOKIE_AGE.
-
set_expiry(value) -
Устанавливает время истечения срока действия сеанса. Можно передать различные значения:
- Если
value— целое число, сеанс истечёт через указанное количество секунд бездействия. Например, вызовrequest.session.set_expiry(300)сделает сеанс истекающим через 5 минут. - Если
value— объектdatetimeилиtimedelta, сеанс истечёт в указанную дату/время. Обратите внимание, что значенияdatetimeиtimedeltaсериализуются только при использованииPickleSerializer. - Если
valueравно0, cookie сеанса пользователя истечёт при закрытии веб-браузера пользователя. - Если
valueравноNone, сеанс вернётся к использованию глобальной политики истечения срока действия сеанса.
Чтение сеанса не считается активностью для целей истечения срока действия. Истечение срока действия сеанса вычисляется по последнему времени изменения сеанса.
- Если
-
get_expiry_age() -
Возвращает количество секунд до истечения срока действия этого сеанса. Для сеансов без пользовательского истечения срока действия (или тех, которые установлены на истечение при закрытии браузера), это будет равно
SESSION_COOKIE_AGE.Эта функция принимает два необязательных ключевых аргумента:
-
modification: последнее изменение сеанса, как объектdatetime. По умолчанию — текущее время. -
expiry: информация об истечении срока действия сеанса, как объектdatetime, целое число (в секундах) илиNone. По умолчанию — значение, хранящееся в сеансеset_expiry(), если таковое имеется, илиNone.
-
-
get_expiry_date() -
Возвращает дату истечения срока действия этого сеанса. Для сеансов без пользовательского истечения срока действия (или тех, которые установлены на истечение при закрытии браузера), это будет дата через
SESSION_COOKIE_AGEсекунд от сейчас.Эта функция принимает те же ключевые аргументы, что и
get_expiry_age().
-
get_expire_at_browser_close() -
Возвращает либо
True, либоFalse, в зависимости от того, истечёт ли cookie сеанса пользователя при закрытии веб-браузера пользователя.
-
clear_expired() -
Удаляет истекшие сеансы из хранилища сеансов. Этот метод класса вызывается
clearsessions.
-
cycle_key() -
Создаёт новый ключ сеанса, сохраняя при этом текущие данные сеанса.
django.contrib.auth.login()вызывает этот метод для предотвращения фиксации сеанса.
-
Сериализация сеанса
По умолчанию Django сериализует данные сеанса с помощью JSON. Вы можете настроить формат сериализации сеанса, используя настройку SESSION_SERIALIZER. Даже с оговорками, описанными в Создание собственного сериализатора, мы настоятельно рекомендуем придерживаться JSON-сериализации, особенно если вы используете хранилище cookie.
Например, вот сценарий атаки, если вы используете pickle для сериализации данных сеанса. Если вы используете хранилище сеанса с подписанными cookie, и ключ SECRET_KEY известен злоумышленнику (нет внутренней уязвимости Django, которая могла бы привести к его утечке), злоумышленник может вставить строку в свой сеанс, которая при распаковке выполнит произвольный код на сервере. Методика для этого проста и легко доступна в интернете. Хотя хранилище сеанса cookie подписывает сохранённые данные cookie, чтобы предотвратить их изменение, утечка ключа SECRET_KEY сразу же приводит к уязвимости удалённого выполнения кода.
Встроенные сериализаторы
-
class serializers.JSONSerializer -
Обёртка над JSON-сериализатором из
django.core.signing. Может сериализовать только базовые типы данных.Кроме того, поскольку JSON поддерживает только строковые ключи, обратите внимание, что использование ключей, отличных от строк, в
request.sessionне будет работать как ожидается:>>> # initial assignment >>> request.session[0] = 'bar' >>> # subsequent requests following serialization & deserialization >>> # of session data >>> request.session[0] # KeyError >>> request.session['0'] 'bar'
Аналогично, данные, которые не могут быть закодированы в JSON, такие как байты, не являющиеся UTF-8, как
'\xd9'(что вызываетUnicodeDecodeError), не могут быть сохранены.См. раздел Создание собственного сериализатора для получения дополнительной информации об ограничениях JSON-сериализации.
-
class serializers.PickleSerializer -
Поддерживает произвольные объекты Python, но, как описано выше, может привести к уязвимости удалённого выполнения кода, если ключ
SECRET_KEYстанет известен злоумышленнику.
Создание собственного сериализатора
Обратите внимание, что в отличие от PickleSerializer, JSONSerializer не может обрабатывать произвольные типы данных Python. Как часто бывает, существует компромисс между удобством и безопасностью. Если вы хотите хранить более сложные типы данных, включая datetime и Decimal в сессиях, основанных на JSON, вам потребуется написать пользовательский сериализатор (или преобразовать такие значения в сериализуемый в JSON объект перед их хранением в request.session). Хотя сериализация этих значений часто проста (DjangoJSONEncoder может быть полезен), создание декодера, который может надежно вернуть то же самое, что вы ввели, более хрупкое. Например, вы рискуете вернуть datetime, который на самом деле был строкой, которая просто оказалась в том же формате, выбранном для datetime.
Ваш класс сериализатора должен реализовывать два метода, dumps(self, obj) и loads(self, data), для сериализации и десериализации словаря данных сессии соответственно.
Руководство по объектам сессии
- Используйте обычные строки Python в качестве ключей словаря на
request.session. Это больше конвенция, чем строгое правило. - Ключи словаря сессии, начинающиеся с подчеркивания, зарезервированы для внутреннего использования Django.
- Не перезаписывайте
request.sessionновым объектом и не обращайтесь к его атрибутам или не изменяйте их. Используйте его как словарь Python.
Примеры
Этот упрощенный вид устанавливает переменную has_commented в True после того, как пользователь опубликовал комментарий. Он не позволяет пользователю публиковать комментарий более одного раза:
def post_comment(request, new_comment):
if request.session.get('has_commented', False):
return HttpResponse("You've already commented.")
c = comments.Comment(comment=new_comment)
c.save()
request.session['has_commented'] = True
return HttpResponse('Thanks for your comment!')
Этот упрощенный вид регистрирует «члена» сайта:
def login(request):
m = Member.objects.get(username=request.POST['username'])
if m.password == request.POST['password']:
request.session['member_id'] = m.id
return HttpResponse("You're logged in.")
else:
return HttpResponse("Your username and password didn't match.")
…И этот вид регистрирует выход члена, в соответствии с login() выше:
def logout(request):
try:
del request.session['member_id']
except KeyError:
pass
return HttpResponse("You're logged out.")
Стандартная функция django.contrib.auth.logout() фактически делает немного больше, чем это, чтобы предотвратить непреднамеренную утечку данных. Она вызывает метод flush() объекта request.session. Мы используем этот пример как демонстрацию работы с объектами сессии, а не как полную logout() реализацию.
Установка тестовых файлов cookie
Это неуклюжее разделение между set_test_cookie() и test_cookie_worked() необходимо из-за работы файлов cookie. Когда вы устанавливаете файл cookie, вы не можете на самом деле сказать, принял ли его браузер, пока браузер не сделает следующий запрос.
Хорошей практикой является использование delete_test_cookie() для очистки за собой. Сделайте это после того, как вы проверили, что тестовый файл cookie сработал.
Вот типичный пример использования:
from django.http import HttpResponse
from django.shortcuts import render
def login(request):
if request.method == 'POST':
if request.session.test_cookie_worked():
request.session.delete_test_cookie()
return HttpResponse("You're logged in.")
else:
return HttpResponse("Please enable cookies and try again.")
request.session.set_test_cookie()
return render(request, 'foo/login_form.html')
Использование сессий вне представлений
Примечание
Примеры в этом разделе импортируют объект SessionStore напрямую из бэкенда django.contrib.sessions.backends.db. В собственном коде следует рассмотреть возможность импорта SessionStore из движка сессий, указанного в SESSION_ENGINE, как показано ниже:
>>> from importlib import import_module >>> from django.conf import settings >>> SessionStore = import_module(settings.SESSION_ENGINE).SessionStore
Доступен API для манипулирования данными сессии вне представления:
>>> from django.contrib.sessions.backends.db import SessionStore >>> s = SessionStore() >>> # stored as seconds since epoch since datetimes are not serializable in JSON. >>> s['last_login'] = 1376587691 >>> s.create() >>> s.session_key '2b1189a188b44ad18c35e113ac6ceead' >>> s = SessionStore(session_key='2b1189a188b44ad18c35e113ac6ceead') >>> s['last_login'] 1376587691
SessionStore.create() предназначен для создания новой сессии (т. е. сессии, не загруженной из хранилища сессий и с session_key=None). save() предназначен для сохранения существующей сессии (т. е. сессии, загруженной из хранилища сессий). Вызов save() для новой сессии также может сработать, но существует небольшой шанс создания session_key, который совпадает с существующим. create() вызывает save() и циклически ищет, пока не будет сгенерирована неиспользуемая session_key.
Если вы используете бэкенд django.contrib.sessions.backends.db, каждая сессия — обычная модель Django. Модель Session определена в django/contrib/sessions/models.py. Поскольку это обычная модель, вы можете получить доступ к сессиям, используя обычный API базы данных Django:
>>> from django.contrib.sessions.models import Session >>> s = Session.objects.get(pk='2b1189a188b44ad18c35e113ac6ceead') >>> s.expire_date datetime.datetime(2005, 8, 20, 13, 35, 12)
Обратите внимание, что вам нужно вызвать get_decoded(), чтобы получить словарь сессии. Это необходимо, потому что словарь хранится в закодированном формате:
>>> s.session_data
'KGRwMQpTJ19hdXRoX3VzZXJfaWQnCnAyCkkxCnMuMTExY2ZjODI2Yj...'
>>> s.get_decoded()
{'user_id': 42}
Когда сессии сохраняются
По умолчанию Django сохраняет данные в базе сессий только тогда, когда сессия была изменена — то есть, если какое-либо из ее значений словаря было присвоено или удалено:
# Session is modified.
request.session['foo'] = 'bar'
# Session is modified.
del request.session['foo']
# Session is modified.
request.session['foo'] = {}
# Gotcha: Session is NOT modified, because this alters
# request.session['foo'] instead of request.session.
request.session['foo']['bar'] = 'baz'
В последнем случае вышеприведенного примера мы можем явно сказать объекту сессии, что он был изменен, установив атрибут modified в объекте сессии:
request.session.modified = True
Чтобы изменить это поведение по умолчанию, установите значение параметра SESSION_SAVE_EVERY_REQUEST в True. Когда он установлен в True, Django будет сохранять сессию в базе данных при каждом запросе.
Обратите внимание, что файл cookie сессии отправляется только при создании или изменении сессии. Если SESSION_SAVE_EVERY_REQUEST равен True, файл cookie сессии будет отправляться при каждом запросе.
Аналогично, часть expires файла cookie сессии обновляется каждый раз, когда отправляется файл cookie сессии.
Сессия не сохраняется, если код состояния ответа равен 500.
Сессии длительностью браузера против постоянных сессий
Вы можете управлять тем, использует ли фреймворк сессий сессии длительностью браузера или постоянные сессии, с помощью параметра SESSION_EXPIRE_AT_BROWSER_CLOSE.
По умолчанию, SESSION_EXPIRE_AT_BROWSER_CLOSE установлен в False, что означает, что файлы cookie сессии будут храниться в браузерах пользователей до тех пор, пока существует SESSION_COOKIE_AGE. Используйте это, если вы не хотите, чтобы пользователи каждый раз входили в систему при открытии браузера.
Если SESSION_EXPIRE_AT_BROWSER_CLOSE установлен в True, Django будет использовать cookie с длительностью браузера — cookie, который истекает, как только пользователь закрывает свой браузер. Используйте это, если вы хотите, чтобы пользователи каждый раз входили в систему при открытии браузера.
Это глобальное значение по умолчанию может быть переопределено на уровне каждой сессии, явно вызвав метод set_expiry() объекта request.session как описано выше в использовании сессий в представлениях.
Примечание
Некоторые браузеры (например, Chrome) предоставляют настройки, которые позволяют пользователям продолжать сессии просмотра после закрытия и повторного открытия браузера. В некоторых случаях это может повлиять на настройку SESSION_EXPIRE_AT_BROWSER_CLOSE и предотвратить истечение сессий при закрытии браузера. Пожалуйста, имейте это в виду при тестировании приложений Django, в которых включена настройка SESSION_EXPIRE_AT_BROWSER_CLOSE.
Очистка хранилища сессий
По мере создания новых сессий на вашем веб-сайте данные сессии могут накапливаться в вашем хранилище сессий. Если вы используете бэкенд базы данных, таблица базы данных django_session будет увеличиваться. Если вы используете файловый бэкенд, ваш временный каталог будет содержать всё большее количество файлов.
Чтобы понять эту проблему, рассмотрим, что происходит с бэкендом базы данных. Когда пользователь входит в систему, Django добавляет строку в таблицу базы данных django_session. Django обновляет эту строку каждый раз, когда изменяются данные сессии. Если пользователь выходит из системы вручную, Django удаляет строку. Но если пользователь не выходит из системы, строка никогда не удаляется. Аналогичный процесс происходит с файловым бэкендом.
Django не предоставляет автоматическую очистку просроченных сессий. Поэтому вам необходимо регулярно очищать просроченные сессии. Django предоставляет команду управления очистки для этой цели: clearsessions. Рекомендуется вызывать эту команду регулярно, например, как ежедневную задачу cron.
Обратите внимание, что кеш-бэкенд не подвержен этой проблеме, потому что кэши автоматически удаляют устаревшие данные. То же самое относится и к бэкенду файлов cookie, поскольку данные сессии хранятся браузерами пользователей.
Настройки
Несколько Настроек Django позволяют управлять поведением сессий:
SESSION_CACHE_ALIASSESSION_COOKIE_AGESESSION_COOKIE_DOMAINSESSION_COOKIE_HTTPONLYSESSION_COOKIE_NAMESESSION_COOKIE_PATHSESSION_COOKIE_SAMESITESESSION_COOKIE_SECURESESSION_ENGINESESSION_EXPIRE_AT_BROWSER_CLOSESESSION_FILE_PATHSESSION_SAVE_EVERY_REQUESTSESSION_SERIALIZER
Безопасность сессий
Поддомены одного сайта могут устанавливать куки на клиенте для всего домена. Это делает возможной фиксацию сессий, если куки разрешены от поддоменов, не контролируемых надёжными пользователями.
Например, злоумышленник может войти на good.example.com и получить действительную сессию для своей учётной записи. Если злоумышленник контролирует bad.example.com, он может использовать его для отправки своего ключа сессии, так как поддомен имеет право устанавливать куки на *.example.com. Когда вы посещаете good.example.com, вы будете вошли как злоумышленник и, возможно, непреднамеренно введёте свои конфиденциальные данные (например, информацию о кредитной карте) в учётную запись злоумышленника.
Ещё одна возможная атака могла бы произойти, если good.example.com установит SESSION_COOKIE_DOMAIN на "example.com", что привело бы к отправке куки сессии с этого сайта на bad.example.com.
Технические детали
- Словарь сессии принимает любые
jsonсериализуемые значения при использованииJSONSerializerили любой пиклируемый Python-объект при использованииPickleSerializer. См. модульpickleдля получения дополнительной информации. - Данные сессии хранятся в таблице базы данных с именем
django_session. - Django отправляет куки только если это необходимо. Если вы не устанавливаете данные сессии, куки сессии не будут отправлены.
Объект SessionStore
При работе с сессиями внутри Django используется объект хранилища сессий из соответствующего движка сессий. По соглашению, класс объекта хранилища сессий называется SessionStore и находится в модуле, указанном в SESSION_ENGINE.
Все классы SessionStore доступные в Django наследуются от SessionBase и реализуют методы управления данными, а именно:
exists()create()save()delete()load()clear_expired()
Для создания пользовательского движка сессий или настройки существующего, вы можете создать новый класс, наследуя от SessionBase или любого другого существующего класса SessionStore.
Вы можете расширять движки сессий, но это обычно требует дополнительных усилий при работе с движками сессий, основанными на базе данных (см. следующий раздел для получения подробностей).
Расширение движков сессий, основанных на базе данных
Создание пользовательского движка сессий, основанного на базе данных, построенного на основе тех, которые включены в Django (а именно db и cached_db), можно осуществить, унаследовав от AbstractBaseSession и класса SessionStore.
AbstractBaseSession и BaseSessionManager импортируются из django.contrib.sessions.base_session, чтобы их можно было импортировать без включения django.contrib.sessions в INSTALLED_APPS.
-
class base_session.AbstractBaseSession -
Абстрактная базовая модель сессии.
-
session_key -
Первичный ключ. Само поле может содержать до 40 символов. Текущая реализация генерирует строку из 32 символов (случайная последовательность цифр и строчных букв ASCII).
-
session_data -
Строка, содержащая закодированный и сериализованный словарь сессии.
-
expire_date -
Дата и время истечения срока действия сессии.
Истекшие сессии недоступны пользователю, однако они могут храниться в базе данных до тех пор, пока не будет выполнен менеджмент-команда
clearsessions.
-
classmethod get_session_store_class() -
Возвращает класс хранилища сессии, который будет использоваться с данной моделью сессии.
-
get_decoded() -
Возвращает декодированные данные сессии.
Декодирование выполняется классом хранилища сессии.
-
Вы также можете настроить менеджер модели, наследовавшись от BaseSessionManager:
-
class base_session.BaseSessionManager -
-
encode(session_dict) -
Возвращает сериализованный и закодированный словарь сессии в виде строки.
Кодирование выполняется классом хранилища сессии, связанным с классом модели.
-
save(session_key, session_dict, expire_date) -
Сохраняет данные сессии для указанного ключа сессии или удаляет сессию, если данные пустые.
-
Настройка классов SessionStore достигается путём переопределения методов и свойств, описанных ниже:
-
class backends.db.SessionStore -
Реализует хранилище сессий, основанное на базе данных.
-
classmethod get_model_class() -
Переопределите этот метод, чтобы вернуть пользовательскую модель сессии, если она вам нужна.
-
create_model_instance(data) -
Возвращает новый экземпляр объекта модели сессии, представляющий текущее состояние сессии.
Переопределение этого метода предоставляет возможность изменить данные модели сессии перед сохранением в базе данных.
-
-
class backends.cached_db.SessionStore -
Реализует кэшированное хранилище сессий, основанное на базе данных.
-
cache_key_prefix -
Префикс, добавляемый к ключу сессии для создания строки ключа кэша.
-
Пример
Пример ниже демонстрирует пользовательский движок сессий, основанный на базе данных, который включает дополнительный столбец базы данных для хранения идентификатора учётной записи (что предоставляет возможность запросить все активные сессии для учётной записи):
from django.contrib.sessions.backends.db import SessionStore as DBStore
from django.contrib.sessions.base_session import AbstractBaseSession
from django.db import models
class CustomSession(AbstractBaseSession):
account_id = models.IntegerField(null=True, db_index=True)
@classmethod
def get_session_store_class(cls):
return SessionStore
class SessionStore(DBStore):
@classmethod
def get_model_class(cls):
return CustomSession
def create_model_instance(self, data):
obj = super().create_model_instance(data)
try:
account_id = int(data.get('_auth_user_id'))
except (ValueError, TypeError):
account_id = None
obj.account_id = account_id
return obj
Если вы мигрируете с встроенного движка сессий Django на пользовательский, основанный на cached_db, вам следует переопределить префикс ключа кэша, чтобы избежать конфликта имён:
class SessionStore(CachedDBStore):
cache_key_prefix = 'mysessions.custom_cached_db_backend'
# ...
Идентификаторы сессий в URL-адресах
Фреймворк Django для сессий полностью и исключительно основан на куках. Он не использует URL-адреса для идентификаторов сессий в качестве последнего средства, как это делает PHP. Это является намеренным дизайнерским решением. Такое поведение не только делает URL-адреса некрасивыми, но и делает ваш сайт уязвимым для кражи идентификаторов сессий через заголовок «Referer».
© Django Software Foundation and individual contributors
Licensed under the BSD License.
https://docs.djangoproject.com/en/3.0/topics/http/sessions/