Cookies Django, ¿cómo puedo configurarlas?

123

Tengo un sitio web que muestra contenido diferente según la ubicación que elija el visitante. Por ejemplo: el usuario ingresa en 55812 como el zip. Sé qué ciudad y área lat / long. es decir y darles su contenido pertinente a esa área. Mi pregunta es ¿cómo puedo almacenar esto en una cookie para que cuando regresen no estén obligados a ingresar siempre su código postal?

Lo veo de la siguiente manera:

  1. Establecer cookies persistentes en función de su área.
  2. Cuando vuelvan a leer la cookie, tome el código postal.
  3. Devolver contenido basado en el código postal en su cookie.

Parece que no puedo encontrar ninguna información sólida sobre la configuración de una cookie. Cualquier ayuda es muy apreciada.

Jeffrey
fuente
Los que están buscando para el establecimiento de una cookiey rendering a templatejuntos, ver esta respuesta.
TheGuardener

Respuestas:

66

ACTUALIZACIÓN : verifique la respuesta de Peter a continuación para obtener una solución integrada:

Este es un ayudante para configurar una cookie persistente:

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)

Use el siguiente código antes de enviar una respuesta.

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

ACTUALIZACIÓN : verifique la respuesta de Peter a continuación para obtener una solución integrada:

jujule
fuente
¿Hay algún problema si no se configura la configuración SESSION_COOKIE_DOMAIN?
panchicore
1
de todos modos, django establece un SESSION_COOKIE_DOMAIN predeterminado. piense en esta configuración si necesita compartir cookies en varios subdominios.
jujule
12
-1 sobre eso, django viene con un método para configurar cookies docs.djangoproject.com/en/dev/ref/request-response/…
fetzig
2
@klemens: sí y finalmente llamo al método django en mi ejemplo; Es solo un atajo (desde 2009) que simplifica el procesamiento de la fecha.
jujule
55
no me importa, pero, fyi: la función auxiliar inútil ya era inútil en 2009. docs.djangoproject.com/en/1.0/ref/request-response/… (django 1.0 fue lanzado en septiembre de 2008, que yo sepa)
fetzig
259

El uso del marco de sesión de Django debería cubrir la mayoría de los escenarios, pero ahora Django también proporciona métodos directos de manipulación de cookies en los objetos de solicitud y respuesta (por lo que no necesita una función auxiliar).

Configurar una cookie:

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

Recuperando una 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
Peter
fuente
10
Solo para actualizar: 'has_key' ha sido reemplazado por 'in'.
skaz
15
Una forma más pitónica sería llamar a request.COOKIES.get ('cookie_name')
Charlesthk
déjame hacerte una pregunta tonta, ¿estas cookies persisten entre sesiones de otros usos?
Diego Vinícius
No hay nada de valor para agregar aquí, pero cuando existen soluciones de marco, a menudo es mejor usarlas en lugar de usar funciones de ayuda personalizadas para el trabajo, especialmente si no hay una buena razón para no hacerlo. Es posible que estas soluciones no hayan estado disponibles al principio, pero seguro que sí, ¿por qué no usarlas? Se trata de un código más simple y podría manejar más casos de lo que nuestros ayudantes personalizados pensarían en el manejo, lo cual es en sí mismo un buen argumento en mi opinión.
vincent-lg
2
Si se pregunta cómo crear un objeto de respuesta Django a partir de un objeto de solicitud Django, lea esto: stackoverflow.com/questions/17057536/…
critikaster
19

Puede configurar manualmente la cookie, pero dependiendo de su caso de uso (y si desea agregar más tipos de datos persistentes / de sesión en el futuro) podría tener más sentido usar la función de sesiones de Django . Esto le permitirá obtener y establecer variables vinculadas internamente a la cookie de sesión del usuario. Lo bueno de esto es que si desea almacenar una gran cantidad de datos vinculados a la sesión de un usuario, almacenarlos en cookies agregará mucho peso a las solicitudes y respuestas HTTP. Con las sesiones, la cookie de sesión es todo lo que se envía de un lado a otro (aunque hay que tener en cuenta el hecho de que Django almacena los datos de la sesión para tener en cuenta).

Ben Regenspan
fuente
44
¡Buen punto! Una nota, puede reducir el peso de HTTP alojando contenido estático en un dominio separado (no subdominio), para que las cookies no se envíen en esas solicitudes. stackoverflow.com/questions/72394/…
John Paulett
El comentario de @ JohnPaulett está desactualizado dada la existencia del marco Django Sessions. Ya no debería ser necesario minimizar el almacenamiento total de datos en flujos de trabajo basados ​​en cookies.
Chris Conlan
0

Cualquier persona interesada en hacer esto debería leer la documentación del marco Django Sessions . Almacena una ID de sesión en las cookies del usuario, pero asigna todos los datos similares a cookies a su base de datos. Esta es una mejora en el flujo de trabajo típico basado en cookies para solicitudes HTTP.

Aquí hay un ejemplo con una vista de 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', {})

Si sigue visitando la página una y otra vez, verá que el valor comienza a incrementarse desde 1 hasta que borre sus cookies, visite un nuevo navegador, se encuentre de incógnito o haga cualquier otra cosa que evite la cookie de ID de sesión de Django.

Chris Conlan
fuente