Django Cookies, comment puis-je les définir?

123

J'ai un site Web qui affiche un contenu différent en fonction d'un emplacement choisi par le visiteur. Par exemple: l'utilisateur entre 55812 comme zip. Je sais quelle ville et quelle région lat / long. c'est-à-dire et leur donner leur contenu pertinent à ce domaine. Ma question est de savoir comment puis-je stocker cela dans un cookie afin que, lorsqu'ils reviennent, ils ne soient pas obligés de toujours saisir leur code postal?

Je le vois comme suit:

  1. Définissez un cookie persistant en fonction de leur zone.
  2. Quand ils retournent le cookie de lecture, saisissez le code postal.
  3. Renvoyez le contenu en fonction du code postal de leur cookie.

Je ne parviens pas à trouver d'informations solides sur la configuration d'un cookie. Toute aide est grandement appréciée.

Jeffrey
la source
Ceux qui sont à la recherche d'établir un cookieet rendering a templateensemble, voir cette réponse.
TheGuardener

Réponses:

66

MISE À JOUR : vérifiez la réponse de Peter ci-dessous pour une solution intégrée:

Ceci est une aide pour définir un cookie persistant:

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)

Utilisez le code suivant avant d'envoyer une réponse.

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

MISE À JOUR : vérifiez la réponse de Peter ci-dessous pour une solution intégrée:

jujule
la source
un problème si settings.SESSION_COOKIE_DOMAIN n'est pas défini?
panchicore
1
de toute façon, django lui-même définit un SESSION_COOKIE_DOMAIN par défaut. pensez à ce paramètre si vous devez partager des cookies sur plusieurs sous-domaines.
jujule
12
-1 sur cela, django est livré avec une méthode pour définir les cookies docs.djangoproject.com/en/dev/ref/request-response
...
2
@klemens: oui et j'appelle enfin la méthode django dans mon exemple; c'est juste un raccourci (à partir de 2009) qui simplifie le traitement des dates.
jujule
5
je m'en fiche mais, pour info: les fonctions d'aide inutiles étaient déjà inutiles en 2009. docs.djangoproject.com/en/1.0/ref/request-response /... (django 1.0 est sorti en septembre 2008, pour autant que je sache)
fetzig
259

L'utilisation du cadre de session de Django devrait couvrir la plupart des scénarios, mais Django fournit également maintenant des méthodes de manipulation directe des cookies sur les objets de requête et de réponse (vous n'avez donc pas besoin d'une fonction d'assistance).

Définition d'un cookie:

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

Récupération d'un 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
la source
10
Juste pour mettre à jour - «has_key» a été remplacé par «in».
skaz
15
Une manière plus pythonique serait d'appeler request.COOKIES.get ('cookie_name')
Charlesthk
laissez-moi vous poser une question idiote, ces cookies persistent entre les autres sessions d'utilisation?
Diego Vinícius
Rien de valeur à ajouter ici, mais lorsque des solutions de cadre existent, il est souvent préférable de les utiliser plutôt que d'utiliser des fonctions d'assistance personnalisées pour le travail, surtout s'il n'y a aucune bonne raison de ne pas le faire. Ces solutions n'étaient peut-être pas disponibles au début, mais elles le sont certainement, alors pourquoi ne pas les utiliser? Cela rend le code plus simple et peut gérer plus de cas que ce que nos assistants personnalisés penseraient de gérer, ce qui est en soi un bon argument à mon avis.
vincent-lg
2
Si vous vous demandez comment créer un objet de réponse Django à partir d'un objet de requête Django, lisez ceci: stackoverflow.com/questions/17057536
...
19

Vous pouvez définir manuellement le cookie, mais en fonction de votre cas d'utilisation (et si vous souhaitez ajouter plus de types de données persistantes / de session à l'avenir), il peut être plus judicieux d'utiliser la fonctionnalité de sessions de Django . Cela vous permettra d' obtenir et de définir des variables liées en interne au cookie de session de l'utilisateur. Ce qui est cool à ce sujet, c'est que si vous souhaitez stocker beaucoup de données liées à la session d'un utilisateur, le stockage de tout cela dans des cookies ajoutera beaucoup de poids aux requêtes et réponses HTTP. Avec les sessions, le cookie de session est tout ce qui est envoyé dans les deux sens (bien qu'il y ait une surcharge pour Django de stocker les données de session à garder à l'esprit).

Ben Regenspan
la source
4
Bon point! Une note, vous pouvez réduire le poids HTTP en hébergeant le contenu statique sur un domaine séparé (pas sous-domaine), de sorte que les cookies ne soient pas envoyés sur ces demandes. stackoverflow.com/questions/72394/…
John Paulett
Le commentaire de @ JohnPaulett est obsolète étant donné l'existence du framework Django Sessions. Il ne devrait plus être nécessaire de minimiser le stockage total des données sur les flux de travail basés sur les cookies.
Chris Conlan
0

Toute personne intéressée par cette opération doit lire la documentation du framework Django Sessions . Il stocke un identifiant de session dans les cookies de l'utilisateur, mais mappe toutes les données de type cookies à votre base de données. Il s'agit d'une amélioration par rapport au flux de travail classique basé sur les cookies pour les requêtes HTTP.

Voici un exemple avec une vue 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 vous continuez à visiter la page encore et encore, vous verrez la valeur commencer à augmenter de 1 jusqu'à ce que vous effaciez vos cookies, que vous visitiez un nouveau navigateur, que vous passiez en mode navigation privée ou que vous fassiez toute autre chose qui évite le cookie d'identification de session de Django.

Chris Conlan
la source