django之Cookie、Session、Token

本文详细介绍了Cookie、Session和Token的由来、原理及其在Django中的使用。Cookie是存在浏览器中的键值对,易被窃取;Session在服务器端存储,安全性较高;Token则解决了Session在大量用户时带来的服务器压力。在Django中,文章讲解了如何操作Cookie和Session,以及基于它们的登录认证实现。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

一.Cookie、Session、Token的由来

我们知道HTTP协议无连接的, 也就是不保存用户的状态信息

早期(十几年前)的网页是静态的, 数据都是写死的, 人们访问网页只是用来查看新闻的, 没有保存用户状态的需求

而往后出现了像论坛、博客、网购这一类需要保存用户信息的网站, 如果网站不保存用户的状态信息, 意味着用户每次访问都需要重新输入用户名和密码, 这无疑对用户的体验是极其不好的

于是, 就出现了会话跟踪技术, 我们可以把它理解为客户端与服务端之间的一次会晤, 一次会晤包含的多次请求与响应, 每次请求都带着请求参数, 比如请求登入的请求参数是用户名和密码, 服务端就会拿着请求参数与数据库去比对, 找到相应的用户信息

如何实现会话跟踪 : 在HTTP协议中可以使用Cookie来完成, 在Web开发中可以使用Session来完成

  • Cookie是存在浏览器中的键值对, 每次发送请求都携带者参数, 但是容易被截获, 不安全

  • 于是就出现了Session, 它是存在于服务端的键值对, key为随机字符串, 安全性提高了, 但所有的数据都存在服务器中, 服务器的压力很大

  • 之后便产生了Token的概念, 服务端签发加密后的字符串给客户端浏览器保存, 客户端每次请求携带用户名和密码, 并加上由服务端签发的用户名和密码加密的字符串, 服务端收到请求后再对用户名密码加密, 与后面携带的密文对比, 由于它也是保存在客户端浏览器上的, 所以也叫Cookie

二.Cookie简介

1.什么是Cookie

  • Cookie是服务器保存在客户端浏览器之上的key-value键值对 : username='shawn';password="123"
  • 它是随着服务器的响应发送给客户端, 客户端将其保存, 下一次请求时会将Cookie放在其中, 服务器通过识别Cookie就能知道是哪个客户端浏览器

2.Cookie规范

  • Cookie大小上限为4KB
  • 一个服务器最多在客户端浏览器上保存20个Cookie
  • 一个浏览器最多保存300个Cookie

上面是HTTP中Cookie的规范, 现在浏览器的竞争, 有些Cookie大小能打到8KB, 最多可以保存500个Cookie

不同浏览器之间的Cookie是不共享的

3.安全性

  • Cookie保存在浏览器本地, 意味着很容易被窃取和篡改

三.Session简介

1.什么是Session

  • 存放在服务器上的键值对 : {'weqweq':{'username':'shawn','password':'123'}}

  • Cookie可以保存状态, 但本身最大只能支持4069字节, 并且不安全, 于是就出现了Session

  • 它能支持更多字节, 并且保存在服务器上, 具有较高的安全性,Session基于Cookie, 本地存放服务器返回给浏览器的随机字符串

  • 客户端浏览器请求中携带随机字符串(session_id), 服务端收到后与数据库中存储的session做对比

ps : session存储的方式多种多样, 可以是数据库、缓存、硬盘等等

2.Cookie、Session小结

1. cookie是存在于浏览器上的, 保存形式以key:value键值对的形式
2. session是存在于服务端的, django中保存在django_session表中, key: 对应session_key字段, value: 对应session_data, 还有一个session_date用来保存终止会话时间
3. session是基于cookie工作的, 在django中session会告知浏览器以sessionid:随机字符的格式保存数据

四.Token简介

1.什么是Token

  • session数据保存在服务端, 提升了安全性, 但如果用户数据量特别多, 那么服务器的压力就会非常大
  • 所以不再在服务端中保存数据
  • Token采用了jwt(json web token)的认证方式, 数据格式分为三段式 : {公司信息。。}.{name:lqz,id:10}.加密后的字符串
  • 登入成功之后, 将第一段数据与第二段数据进行加密(加密算法是你后端开发自定义的), 加密后得到的字符串放在最后一段, 然后整体的返回给浏览器
  • 浏览器下次访问的时候就会带着该信息, 服务端收到再取前两段进行加密与第三段对比

五.django中cookie的使用

1.Cookie四件套

  • 增 : obj.set_cookie('key','value)
  • 查 : request.COOKIE.get('key')
  • 改 : obj.set_cookie('key','value')
  • 删 : obj.delete_cookie('key')

2.Cookie四件套示例

def cookie_test(request):
    # obj1 = HttpResponse()
    # return obj1
    # obj2 = render(request,'cookie_test.html')
    # return obj2

    obj = HttpResponse('生成了两个cookie')

    # 设置cookie
    obj.set_cookie('name','shawn')
    obj.set_cookie('pwd','123')

    return obj

image-20210329225140803

image-20210329225432605

# 获取cookie
def get_cookie(request):
    name = request.COOKIES.get('name')
    pwd = request.COOKIES.get('pwd')
    return HttpResponse(f'获取到cookie,name:{name},pwd:{pwd}')

image-20210329225343350

# 更新cookie,与设置一样
def set_cookie(request):
    obj = HttpResponse('重新对cookie进行了设置')
    obj.set_cookie('name','xing')
    obj.set_cookie('pwd','11122')
    return obj

image-20210329230248506

# 删除cookie
def del_cookie(request):
    obj = HttpResponse('删除了一个cookie')
    obj.delete_cookie('name')
    return obj

image-20210329230853135

3.其他操作

  • cookie加盐
# 为cookie进行加盐
def set_salt(request):
    obj = HttpResponse('为name加了个盐中盐')
    obj.set_cookie('name', 'shawn')
    # 加盐操作
    obj.set_signed_cookie('name', 'shawn', salt='盐中盐')
    return obj

# 获取加盐的cookie
def get_salt(request):
    name_salt = request.COOKIES.get('name')
    salts = request.get_signed_cookie('name', salt='盐中盐')
    return HttpResponse(f'获取到加盐的cookie名:{salts}\n加盐后的cookie:{name_salt}')
  • 设置超时时间, 直接在设置cookie的时候加参数(两种方法)
# expires常用,支持IE浏览器(以秒为单位)
def set_timeout(request):
    obj = HttpResponse('超时删除cookie')
    obj.set_cookie('name', 'shawn', max_age=5
<think>嗯,用户想了解Django的会话管理。首先,我需要回忆一下Djangosession的处理机制。根据引用[1]中的代码示例,用户登录时会把用户信息存入request.session,然后通过装饰器@auth来验证session是否存在。这说明Djangosession是基于中间件实现的,并且可以方便地存储读取用户数据。 接下来,用户可能想知道session的工作原理。记得引用[4]提到Django session的源码结构简单,没有复杂的数据结构,可能涉及到后端存储,比如数据库或者缓存。默认情况下,Django使用数据库存储session,但也可以配置成缓存或其他后端。 然后,安全方面,引用[5]提到CSRF保护中间件的关系。会话管理CSRF防护是相关的,需要确保在表单提交时包含CSRF tokenDjango的CsrfViewMiddleware处理这部分,同时可以通过装饰器灵活控制,比如@csrf_exempt@csrf_protect。 用户可能还想知道如何配置session的有效期、存储方式以及安全设置。比如SESSION_COOKIE_AGE可以设置过期时间,SESSION_ENGINE可以更改存储后端到缓存或文件系统。此外,安全方面需要考虑SESSION_COOKIE_SECURESESSION_COOKIE_HTTPONLY等配置项。 另外,引用[3]中的项目结构配置可能涉及URL路由中间件的配置,确保session中间件被正确启用。同时,引用[2]提到的WSGI配置可能影响会话的持久化,尤其是在部署时需要考虑session存储的后端是否适合生产环境。 还需要覆盖常见问题,比如session数据不一致或读取失败的情况。引用[4]中提到用户遇到在两次POST请求中session数据可能未及时保存的问题,这可能是因为默认的session保存机制是懒保存,需要在修改session后调用session.save()或设置SESSION_SAVE_EVERY_REQUEST为True。 最后,用户可能对实际应用场景感兴趣,比如如何在不同的视图中间件中使用session,如何结合权限验证装饰器等。需要给出代码示例最佳实践,确保回答全面且实用。</think>### Django会话管理详解 Django的会话管理(Session Management)通过`django.contrib.sessions`模块实现,主要用于跟踪用户状态。以下是核心要点操作流程: --- #### 1. **会话基础** - **启用会话**:`settings.py`需包含`django.contrib.sessions.middleware.SessionMiddleware`中间件[^5]。 - **存储机制**:默认使用数据库(`django_session`表),但可通过`SESSION_ENGINE`配置为缓存、文件或加密Cookie[^4]。 --- #### 2. **会话操作** - **写入会话**:通过`request.session['key'] = value`存储数据。例如登录时保存用户信息: ```python def session_login(request): if request.method == 'POST': user = request.POST.get('user') pwd = request.POST.get('pwd') if user == 'fuzj' and pwd == '123': request.session['user'] = user # 会话存储 return redirect('/session_index/') ``` [^1] - **读取会话**:通过`request.session.get('key')`获取数据。例如验证用户登录状态: ```python @auth def session_index(request): user = request.session.get('user', None) # 会话读取 return render(request, 'index.html', {'user': user}) ``` [^1] - **删除会话**:使用`del request.session['key']`或`request.session.flush()`清除数据: ```python def session_logout(request): del request.session['user'] # 删除会话 return redirect('/session_login/') ``` [^1] --- #### 3. **会话安全** - **CSRF防护**:Django默认启用`CsrfViewMiddleware`,通过`{% csrf_token %}`模板标签`csrf_protect`装饰器防止跨站请求伪造[^5]。 - **Cookie安全配置**: ```python SESSION_COOKIE_SECURE = True # 仅HTTPS传输 SESSION_COOKIE_HTTPONLY = True # 禁止JavaScript访问 SESSION_EXPIRE_AT_BROWSER_CLOSE = True # 关闭浏览器即过期 ``` --- #### 4. **常见问题与优化** - **数据同步延迟**:默认会话数据在响应时保存,若需立即存储可手动调用`request.session.save()`[^4]。 - **性能优化**:将会话存储改为缓存(如Redis)以提升速度: ```python SESSION_ENGINE = "django.contrib.sessions.backends.cache" CACHES = { 'default': { 'BACKEND': 'django.core.cache.backends.redis.RedisCache', 'LOCATION': 'redis://127.0.0.1:6379/1', } } ``` --- #### 5. **应用场景** - 用户身份验证(如登录状态保持) - 跨请求数据暂存(如购物车内容) - 多步骤表单数据暂存 ---
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

给你骨质唱疏松

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值