Django Cookies,我该如何设置?


123

我有一个网站,该网站根据访问者选择的位置显示不同的内容。例如:用户输入55812作为邮政编码。我知道哪个城市和地区纬度/经度。也就是给他们有关该领域的内容。我的问题是如何将其存储在Cookie中,以便他们返回时不需要总是输入邮政编码?

我看到如下:

  1. 根据其区域设置持久性cookie。
  2. 当他们返回已读取的cookie时,获取邮政编码。
  3. 根据Cookie中的邮政编码返回内容。

我似乎找不到有关设置Cookie的任何可靠信息。任何帮助是极大的赞赏。


这些谁正在寻找设置cookierendering a template在一起,看到这个答案。
TheGuardener

Answers:


66

更新:检查下面的彼得的答案为内置的解决方案:

这是设置持久性cookie的助手:

import datetime

def set_cookie(response, key, value, days_expire = 7):
  if days_expire is None:
    max_age = 365 * 24 * 60 * 60  #one year
  else:
    max_age = days_expire * 24 * 60 * 60 
  expires = datetime.datetime.strftime(datetime.datetime.utcnow() + datetime.timedelta(seconds=max_age), "%a, %d-%b-%Y %H:%M:%S GMT")
  response.set_cookie(key, value, max_age=max_age, expires=expires, domain=settings.SESSION_COOKIE_DOMAIN, secure=settings.SESSION_COOKIE_SECURE or None)

发送响应之前,请使用以下代码。

def view(request):
  response = HttpResponse("hello")
  set_cookie(response, 'name', 'jujule')
  return response

更新:检查下面的彼得的答案为内置的解决方案:


如果未设置settings.SESSION_COOKIE_DOMAIN会有任何问题?
panchicore 2010年

1
无论如何,Django本身会设置默认的SESSION_COOKIE_DOMAIN。如果您需要在多个子域之间共享Cookie,请考虑一下此设置。
2010年

12
-1上,Django自带了设置Cookie的方法docs.djangoproject.com/en/dev/ref/request-response/...
fetzig

2
@klemens:是的,我最终在示例中调用了django方法;它只是简化日期处理的快捷方式(从2009年开始)。
jujule 2012年

5
我不在乎,仅供参考:无用的辅助函数在2009年就已经无用了。docs.djangoproject.com/en /1.0/ ref/request-response/…(据我所知,django 1.0已于2008年9月发布)
fetzig 2012年

259

使用Django的会话框架应该涵盖大多数情况,但是Django现在也可以在请求和响应对象上提供直接的cookie操作方法(因此您不需要帮助函数)。

设置Cookie:

def view(request):
  response = HttpResponse('blah')
  response.set_cookie('cookie_name', 'cookie_value')

检索Cookie:

def view(request):
  value = request.COOKIES.get('cookie_name')
  if value is None:
    # Cookie is not set

  # OR

  try:
    value = request.COOKIES['cookie_name']
  except KeyError:
    # Cookie is not set

10
只是要更新-“ has_key”已替换为“ in”。
skaz 2014年

15
一种更Python化的方式是调用request.COOKIES.get('cookie_name')
Charlesthk,

让我问您一个愚蠢的问题,此Cookie在其他使用会话之间仍然存在吗?
DiegoVinícius17年

这里没有什么可增加的价值,但是当存在框架解决方案时,通常最好使用它们,而不是使用自定义帮助程序功能,尤其是在没有充分理由不这样做的情况下。这些解决方案一开始可能尚未提供,但确实可以使用,那么为什么不使用它们呢?它使代码更简单,并且可以处理比自定义助手认为要处理的情况更多的案例,在我看来,这本身就是一个很好的论据。
Vincent-lg

2
如果您想知道如何从Django请求对象创建Django响应对象,请阅读以下内容:stackoverflow.com/questions/17057536/…–
critikaster

19

您可以手动设置cookie,但是根据您的用例(如果将来您想添加更多类型的持久性/会话数据),使用Django的会话功能可能更有意义。这将使您获得并设置内部绑定到用户会话cookie的变量。很棒的事情是,如果您要存储与用户会话相关的大量数据,则将其全部存储在cookie中将为HTTP请求和响应增加很多分量。使用会话时,会话cookie就是来回发送的所有内容(尽管Django存储会话数据时要注意一些开销)。


4
好点子!请注意,您可以通过将静态内容托管在单独的域(而不是子域)上来减轻HTTP的重量,这样就不会在这些请求上发送cookie。stackoverflow.com/questions/72394/...
约翰Paulett

考虑到Django Sessions框架的存在,@ JohnPaulett的评论已过时。不再需要最小化基于cookie的工作流上的总数据存储量。
克里斯·康兰

0

任何对此感兴趣的人都应该阅读Django Sessions的文档框架。它将会话ID存储在用户的cookie中,但是将所有类似于cookie的数据映射到您的数据库。这是对典型的基于HTTP请求的基于cookie的工作流的改进。

这是Django视图的示例...

def homepage(request):

    request.session.setdefault('how_many_visits', 0)
    request.session['how_many_visits'] += 1

    print(request.session['how_many_visits'])

    return render(request, 'home.html', {})

如果您一遍又一遍地浏览页面,您会看到该值从1开始递增,直到您清除cookie,使用新浏览器访问,隐身或执行其他避开Django Session ID cookie的操作。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.