Попытка получить аутентификацию, работающую с каналами Django, с помощью очень простого приложения для веб-сайтов, которое отсылает все, что пользователь отправляет с префиксом "You said: "
.Аутентификация сеанса с каналами Django
Мои процессы:
web: gunicorn myproject.wsgi --log-file=- --pythonpath ./myproject
realtime: daphne myproject.asgi:channel_layer --port 9090 --bind 0.0.0.0 -v 2
reatime_worker: python manage.py runworker -v 2
Я бегу все процессы при тестировании на местном уровне с heroku local -e .env -p 8080
, но вы также можете запустить их все по отдельности.
Примечание. У меня есть WSGI на localhost:8080
и ASGI на localhost:9090
.
маршрутизации и потребители:
### routing.py ###
from . import consumers
channel_routing = {
'websocket.connect': consumers.ws_connect,
'websocket.receive': consumers.ws_receive,
'websocket.disconnect': consumers.ws_disconnect,
}
и
### consumers.py ###
import traceback
from django.http import HttpResponse
from channels.handler import AsgiHandler
from channels import Group
from channels.sessions import channel_session
from channels.auth import channel_session_user, channel_session_user_from_http
from myproject import CustomLogger
logger = CustomLogger(__name__)
@channel_session_user_from_http
def ws_connect(message):
logger.info("ws_connect: %s" % message.user.email)
message.reply_channel.send({"accept": True})
message.channel_session['prefix'] = "You said"
# message.channel_session['django_user'] = message.user # tried doing this but it doesn't work...
@channel_session_user_from_http
def ws_receive(message, http_user=True):
try:
logger.info("1) User: %s" % message.user)
logger.info("2) Channel session fields: %s" % message.channel_session.__dict__)
logger.info("3) Anything at 'django_user' key? => %s" % (
'django_user' in message.channel_session,))
user = User.objects.get(pk=message.channel_session['_auth_user_id'])
logger.info(None, "4) ws_receive: %s" % user.email)
prefix = message.channel_session['prefix']
message.reply_channel.send({
'text' : "%s: %s" % (prefix, message['text']),
})
except Exception:
logger.info("ERROR: %s" % traceback.format_exc())
@channel_session_user_from_http
def ws_disconnect(message):
logger.info("ws_disconnect: %s" % message.__dict__)
message.reply_channel.send({
'text' : "%s" % "Sad to see you go :(",
})
А затем, чтобы проверить, я иду в Javascript консоли на одном домене как мой HTTP сайт, и введите:
> var socket = new WebSocket('ws://localhost:9090/')
> socket.onmessage = function(e) {console.log(e.data);}
> socket.send("Testing testing 123")
VM481:2 You said: Testing testing 123
И показывает мой локальный журнал сервера:
ws_connect: [email protected]
1) User: AnonymousUser
2) Channel session fields: {'_SessionBase__session_key': 'chnb79d91b43c6c9e1ca9a29856e00ab', 'modified': False, '_session_cache': {u'prefix': u'You said', u'_auth_user_hash': u'ca4cf77d8158689b2b6febf569244198b70d5531', u'_auth_user_backend': u'django.contrib.auth.backends.ModelBackend', u'_auth_user_id': u'1'}, 'accessed': True, 'model': <class 'django.contrib.sessions.models.Session'>, 'serializer': <class 'django.core.signing.JSONSerializer'>}
3) Anything at 'django_user' key? => False
4) ws_receive: [email protected]
Что, конечно, не имеет смысла. Несколько вопросов:
- Почему бы Джанго увидеть
message.user
какAnonymousUser
, но имеют фактический идентификатор пользователя_auth_user_id=1
(это мой правильный идентификатор пользователя) в сессии? - Я запускаю свой локальный сервер (WSGI) на 8080 и дафни (ASGI) на 9090 (разные порты). И я не включил
session_key=xxxx
в мое соединение с WebSocket - но Django смог прочитать cookie моего браузера для правильного пользователя,[email protected]
? According to Channels docs, this shouldn't be possible. - Под моей настройкой, какой лучший/самый простой способ выполнить аутентификацию с каналами Django?
Пробовал это - ничего не меняет. Я все равно получаю тот же самый объект 'AnonymousUser'. – lollercoaster
Использование '@ http_session_user' Я могу получить надлежащий объект' message.user', но тогда атрибут 'message.channel_session' не существует. – lollercoaster