with vincent register loginview custom and django authentication

vincent - request.user django



¿Cómo obtener la lista de usuarios autenticados? (4)

Me gustaría mostrar la lista de usuarios autenticados.

En la documentación: http://docs.djangoproject.com/en/dev/topics/auth/

modelos de clase. Usuario
is_authenticated () ¶
Siempre regresa True. Esta es una forma de saber si el usuario ha sido autenticado. ...

Puede saber en el lado de la plantilla si el usuario actual está autenticado o no:

{% if user.is_authenticated%} {% endif%}

Pero no encontré la manera de obtener la lista de usuarios autenticados.

¿Alguna idea?


La solución más confiable sería solo la que almacena cuando el usuario inicia o cierra sesión. Vi esta solución y creo que vale la pena compartirla.

models.py

class LoggedUser(models.Model): user = models.ForeignKey(User, primary_key=True) def __unicode__(self): return self.user.username def login_user(sender, request, user, **kwargs): LoggedUser(user=user).save() def logout_user(sender, request, user, **kwargs): try: u = LoggedUser.objects.get(user=user) u.delete() except LoggedUser.DoesNotExist: pass user_logged_in.connect(login_user) user_logged_out.connect(logout_user)

views.py

logged_users = LoggedUser.objects.all().order_by(''username'')


No hay una manera fácil e integrada de hacer lo que quieres que yo sepa. Probaría una combinación de sesiones de vencimiento y filtrado en last_login. Tal vez incluso escriba un administrador personalizado para eso.


Suena similar a esta solución, puede crear un middleware personalizado para hacerlo. Encontré el asombroso OnlineNowMiddleware aquí.

Donde obtendrás estos;

  1. {{ request.online_now }} => muestra toda la lista de usuarios en línea.
  2. {{ request.online_now_ids }} => muestra todos los ID de usuario en línea.
  3. {{ request.online_now.count }} => muestra el total de usuarios en línea.

¿Como instalar?

Crea el archivo middleware.py donde se ha guardado la ubicación de settings.py , por ejemplo:

projectname/projectname/__init__.py projectname/projectname/middleware.py projectname/projectname/settings.py

Luego siguiendo estas líneas;

from django.core.cache import cache from django.conf import settings from django.contrib.auth.models import User from django.utils.deprecation import MiddlewareMixin ONLINE_THRESHOLD = getattr(settings, ''ONLINE_THRESHOLD'', 60 * 15) ONLINE_MAX = getattr(settings, ''ONLINE_MAX'', 50) def get_online_now(self): return User.objects.filter(id__in=self.online_now_ids or []) class OnlineNowMiddleware(MiddlewareMixin): """ Maintains a list of users who have interacted with the website recently. Their user IDs are available as ``online_now_ids`` on the request object, and their corresponding users are available (lazily) as the ``online_now`` property on the request object. """ def process_request(self, request): # First get the index uids = cache.get(''online-now'', []) # Perform the multiget on the individual online uid keys online_keys = [''online-%s'' % (u,) for u in uids] fresh = cache.get_many(online_keys).keys() online_now_ids = [int(k.replace(''online-'', '''')) for k in fresh] # If the user is authenticated, add their id to the list if request.user.is_authenticated(): uid = request.user.id # If their uid is already in the list, we want to bump it # to the top, so we remove the earlier entry. if uid in online_now_ids: online_now_ids.remove(uid) online_now_ids.append(uid) if len(online_now_ids) > ONLINE_MAX: del online_now_ids[0] # Attach our modifications to the request object request.__class__.online_now_ids = online_now_ids request.__class__.online_now = property(get_online_now) # Set the new cache cache.set(''online-%s'' % (request.user.pk,), True, ONLINE_THRESHOLD) cache.set(''online-now'', online_now_ids, ONLINE_THRESHOLD)

Finalmente actualice su MIDDLEWARE dentro del archivo de projectname/projectname/settings.py :

MIDDLEWARE = [ ''django.middleware.security.SecurityMiddleware'', ''django.contrib.sessions.middleware.SessionMiddleware'', ''django.middleware.cache.UpdateCacheMiddleware'', ''django.middleware.common.CommonMiddleware'', ''django.middleware.cache.FetchFromCacheMiddleware'', .... # Custom middleware ''projectname.middleware.OnlineNowMiddleware'', ]

Para otras condiciones, también puede verificar que el usuario actual esté en línea o no con:

{% if request.user in request.online_now %} {# do stuff #} {% endif %}


Siguiendo con la respuesta de rz, podría consultar el modelo de Session para las Session no expiradas, y luego convertir los datos de la sesión en usuarios. Una vez que tenga eso, podría convertirlo en una etiqueta de plantilla que podría representar la lista en una página determinada.

(Todo esto no se ha probado, pero con suerte estará cerca de funcionar).

Obtener todos los usuarios conectados ...

from django.contrib.auth.models import User from django.contrib.sessions.models import Session from django.utils import timezone def get_all_logged_in_users(): # Query all non-expired sessions # use timezone.now() instead of datetime.now() in latest versions of Django sessions = Session.objects.filter(expire_date__gte=timezone.now()) uid_list = [] # Build a list of user ids from that query for session in sessions: data = session.get_decoded() uid_list.append(data.get(''_auth_user_id'', None)) # Query all logged in users based on id list return User.objects.filter(id__in=uid_list)

Al usar esto, puede hacer una etiqueta de plantilla de inclusión simple ...

from django import template from wherever import get_all_logged_in_users register = template.Library() @register.inclusion_tag(''templatetags/logged_in_user_list.html'') def render_logged_in_user_list(): return { ''users'': get_all_logged_in_users() }

logged_in_user_list.html

{% if users %} <ul class="user-list"> {% for user in users %} <li>{{ user }}</li> {% endfor %} </ul> {% endif %}

Luego, en su página principal, puede usarlo donde desee ...

{% load your_library_name %} {% render_logged_in_user_list %}

EDITAR

Para aquellos que hablan sobre el problema persistente de 2 semanas, supongo que cualquiera que desee tener un tipo de listado de "usuarios activos" hará uso de la configuración SESSION_EXPIRE_AT_BROWSER_CLOSE , aunque reconozco que este no es siempre el caso.