diff --git a/app/website/consumers.py b/app/website/consumers.py index febde5b..d073b7e 100644 --- a/app/website/consumers.py +++ b/app/website/consumers.py @@ -1,7 +1,8 @@ import json from channels.generic.websocket import AsyncWebsocketConsumer from asgiref.sync import sync_to_async -from .views import page_talks, page_about, page_single_talk, page_results, page_profiles +from .views import page_talks, page_about, page_single_talk, page_results, page_profiles, page_chat +from .models import Message class WebsiteConsumer(AsyncWebsocketConsumer): @@ -62,14 +63,6 @@ class WebsiteConsumer(AsyncWebsocketConsumer): self.room_group_name, {"type": "send_page_profiles"} ) - # Chat - if data["value"] == "chat": - await self.channel_layer.group_send( - self.room_group_name, { - "type": "send_page_chat", - } - ) - # About if data["value"] == "about": await self.channel_layer.group_send( @@ -112,14 +105,6 @@ class WebsiteConsumer(AsyncWebsocketConsumer): html = await sync_to_async(self._get_profiles)() await self.send(text_data=html) - def _get_chat(self): - return page_chat() - - async def send_page_chat(self, event): - """Send Chat page""" - html = await sync_to_async(self._get_chat)() - await self.send(text_data=html) - def _get_about(self): return page_about() @@ -138,3 +123,69 @@ class WebsiteConsumer(AsyncWebsocketConsumer): else: html = await sync_to_async(self._get_talks)() await self.send(text_data=html) + + +class ChatConsumer(AsyncWebsocketConsumer): + + async def connect(self): + + # Room + self.room_name = "general" + # Group for Redis + self.room_group_name = f"chat_{self.room_name}" + + # Join room group + await self.channel_layer.group_add(self.room_group_name, self.channel_name) + + await self.accept() + + # Send chat page + await self.channel_layer.group_send( + self.room_group_name, + { + "type": "send_page_chat", + }, + ) + + async def disconnect(self, close_code): + # Leave room group + await self.channel_layer.group_discard(self.room_group_name, self.channel_name) + + # Receive message from WebSocket + async def receive(self, text_data): + + # Get data + text_data_json = json.loads(text_data) + new_username = text_data_json["new-username"] + new_text = text_data_json["new-text"] + + # Save message + await self.save_message(new_username, new_text) + + # Send new HTML + await self.channel_layer.group_send( + self.room_group_name, + { + "type": "send_page_chat", + }, + ) + + @sync_to_async + def instance_message(self, username, text): + return Message.objects.create( + username=username, + text=text, + ) + + async def save_message(self, username, text): + return await self.instance_message(username, text) + + # Pages + + def _get_chat(self): + return page_chat() + + async def send_page_chat(self, event): + """Send Home page""" + html = await sync_to_async(self._get_chat)() + await self.send(text_data=html) \ No newline at end of file diff --git a/app/website/migrations/0006_message.py b/app/website/migrations/0006_message.py new file mode 100644 index 0000000..401e22e --- /dev/null +++ b/app/website/migrations/0006_message.py @@ -0,0 +1,27 @@ +# Generated by Django 3.2.9 on 2021-11-23 18:31 + +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('website', '0005_auto_20211121_0757'), + ] + + operations = [ + migrations.CreateModel( + name='Message', + fields=[ + ('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), + ('username', models.CharField(default='', max_length=100, verbose_name='Alias')), + ('text', models.TextField(max_length=500)), + ('created_at', models.DateTimeField(auto_now_add=True)), + ], + options={ + 'verbose_name': 'Message', + 'verbose_name_plural': 'Messages', + 'ordering': ('-created_at',), + }, + ), + ] diff --git a/app/website/models.py b/app/website/models.py index a9cd810..0bb3db1 100644 --- a/app/website/models.py +++ b/app/website/models.py @@ -75,3 +75,18 @@ class Talk(models.Model): def __str__(self): return self.title + + +class Message(models.Model): + + username = models.CharField(max_length=100, verbose_name="Alias", default="") + text = models.TextField(max_length=500) + created_at = models.DateTimeField(auto_now_add=True) + + class Meta: + ordering = ("-created_at",) + verbose_name = "Message" + verbose_name_plural = "Messages" + + def __str__(self): + return self.text[:10] + "..." \ No newline at end of file diff --git a/app/website/routing.py b/app/website/routing.py index fcc37e1..56da69b 100644 --- a/app/website/routing.py +++ b/app/website/routing.py @@ -4,4 +4,5 @@ from . import consumers websocket_urlpatterns = [ re_path(r"ws/pages/(?P\w+)/$", consumers.WebsiteConsumer), + re_path(r"ws/chat/$", consumers.ChatConsumer), ] diff --git a/app/website/templates/layouts/base.html b/app/website/templates/layouts/base.html index 9d1ae57..f281523 100644 --- a/app/website/templates/layouts/base.html +++ b/app/website/templates/layouts/base.html @@ -38,7 +38,7 @@
  • {# To page Chat #} - {% #link action="page" value="chat" scroll-up="true" %}Chat{% /link %} + Chat
  • {# To page About #} @@ -49,5 +49,8 @@
    +
    + +
    diff --git a/app/website/templates/pages/chat.html b/app/website/templates/pages/chat.html index c004d60..fbd6815 100644 --- a/app/website/templates/pages/chat.html +++ b/app/website/templates/pages/chat.html @@ -1,3 +1,63 @@ -
    - soy el chat -
    +{% load slippers %} +
    + +

    Chat

    +
    + + + {% for message in messages %} + + + + + {% endfor %} + +
    {{ message.username }}{{ message.text }}
    +
    +
    + + + + +
    +
    diff --git a/app/website/templates/pages/talks.html b/app/website/templates/pages/talks.html index 9128f04..85d4e8c 100644 --- a/app/website/templates/pages/talks.html +++ b/app/website/templates/pages/talks.html @@ -11,6 +11,7 @@ id="search" type="search" name="search" + autocomplete="off" hx-ws="send" hx-trigger="keyup changed delay:1s" value="{{ search }}" diff --git a/app/website/views.py b/app/website/views.py index 10e7fb6..475399e 100644 --- a/app/website/views.py +++ b/app/website/views.py @@ -2,7 +2,7 @@ from django.shortcuts import render from django.template.loader import render_to_string from random import randint from django.conf import settings -from .models import Talk, Profile +from .models import Talk, Profile, Message from asgiref.sync import sync_to_async @@ -67,3 +67,12 @@ def page_results(search): "search": search, }, ) + + +def page_chat(): + return render_to_string( + "pages/chat.html", + { + "messages": Message.objects.order_by("created_at").all(), + }, + ) \ No newline at end of file