I use the API https://rapidapi.com/chicmi/api/chicmi-local-fashion/ and websockets in Django. I have an HTML form where I enter the number of days and maximum result, click a button, and nothing happens. When trying to open the page http://127.0.0.1:8000/events/London/, the browser also attempts to establish a WebSocket connection using the URL ws://127.0.0.1:8000/ws/London/, but the server cannot find a corresponding handler for this URL and returns a 404 error. So, I need to redirect the client to a page with fashion show data after the client enters data into the form. Please advise on how to fix the error.
[11/May/2023 20:55:04] "GET /events/London/ HTTP/1.1" 200 1676 Not Found: /ws/London/ [11/May/2023 20:55:04] "GET /ws/London/ HTTP/1.1" 404 4822
I tried to configure the paths correctly, but I still get an error
[11/May/2023 20:55:04] "GET /events/London/ HTTP/1.1" 200 1676 Not Found: /ws/London/ [11/May/2023 20:55:04] "GET /ws/London/ HTTP/1.1" 404 4822
My code
events.html
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Events</title>
<script>
var ws_url = 'ws://' + window.location.host + '/ws/' + '{{ city }}' + '/';
var ws = new WebSocket(ws_url);
ws.onmessage = function(event) {
var event_data = JSON.parse(event.data)['event_data'];
var event_list = document.getElementById('event-list');
event_list.innerHTML = '';
for (var i = 0; i < event_data.length; i++) {
var event = event_data[i];
var event_element = document.createElement('div');
event_element.innerHTML = '<h2>' + event['event_name'] + '</h2>' +
'<img src="' + event['event_preview_url'] + '">' +
'<p><a href="' + event['detail_url'] + '">More Info</a></p>' +
'<p>' + event['location'] + '</p>';
event_list.appendChild(event_element);
}
};
function update_events() {
var days = document.getElementById('days').value;
var max_results = document.getElementById('max-results').value;
var message = {
'days': days,
'max_results': max_results
};
ws.send(JSON.stringify(message));
}
</script>
</head>
<body>
<h1>Events in {{ city }}</h1>
<p>Days: <input type="number" id="days" value="14"></p>
<p>Max Results: <input type="number" id="max-results" value="5"></p>
<button onclick="update_events()">Update</button>
<div id="event-list"></div>
</body>
</html>
consumers.py
import json
from channels.generic.websocket import AsyncWebsocketConsumer
import requests
class EventConsumer(AsyncWebsocketConsumer):
async def connect(self):
self.city = self.scope['url_route']['kwargs']['city']
await self.channel_layer.group_add(
self.city,
self.channel_name
)
await self.accept()
async def disconnect(self, close_code):
await self.channel_layer.group_discard(
self.city,
self.channel_name
)
async def receive(self, text_data):
url = "https://chicmi.p.rapidapi.com/calendar_in_city/"
headers = {
"X-RapidAPI-Key": "d4ba369aa5msh31ba822955b0a7bp1c2147jsn0b48eb6cab4f",
"X-RapidAPI-Host": "chicmi.p.rapidapi.com"
}
response = requests.get(url, headers=headers)
data = response.json()
events = data["values"]["events"]
event_data = []
for event in events:
event_data.append({
"event_name": event["event_name"],
"event_preview_url": event["event_preview_url"],
"detail_url": event["detail_url"],
"location": event["location"]
})
await self.channel_layer.group_send(
self.city,
{
'type': 'send_event_data',
'event_data': event_data
}
)
async def send_event_data(self, event):
event_data = event['event_data']
await self.send(json.dumps({
'event_data': event_data
}))
routing.py
from channels.routing import ProtocolTypeRouter, URLRouter
from django.urls import path
from . import consumers
websocket_urlpatterns = [
path('ws/<str:city>/', consumers.EventConsumer.as_asgi()),
]
application = ProtocolTypeRouter({
"websocket": URLRouter(websocket_urlpatterns)
})
fashionShows/urls
from django.urls import path
from . import views
urlpatterns = [
path('events/<str:city>/', views.events, name='events'),
]
views.py
from django.shortcuts import render
def events(request, city):
return render(request, 'events.html', {'city': city})
asgi.py
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'semWork.settings')
application = get_asgi_application()