I'm trying to make a small chat application and managed to deploy it to a EC2. After some struggling, I got the application running, but I noticed the delay was really high.
At first I thought the reason for this delay was that I'm using a free machine for testing purposes, but I'm also getting some errors in the console and thought that maybe this might have something to do with it.
I think it's valid to mention that the application works fine locally (with no errors) and when hosted I still get the messages from the server on the front end, but after a lot of delay and a lot of errors...
Console Screenshot
I tried changing the ping_timeout and the pint_interval parameters on the initialization of SocketIO since I thought this could have something to do with the problem, but didn't help.
This is my app.py
:
from flask import Flask, render_template
from flask_socketio import SocketIO, emit, send
app = Flask(__name__)
io = SocketIO(app, ping_timeout=10, ping_interval=5)
messages = []
@app.route("/")
def home():
return render_template("chat.html")
@io.on('sendMessage')
def send_message_handler(message):
messages.append(message)
emit('getMessage', message, broadcast=True)
@io.on('message')
def message_handler(message):
send(messages)
if __name__ == "__main__":
io.run(app)
And my Script tags from the index page
:
<script src="https://cdnjs.cloudflare.com/ajax/libs/socket.io/4.5.4/socket.io.js"></script>
<script>
window.onload = function() {
socket = io.connect('http://' + document.domain + ':' + location.port);
console.log('http://' + document.domain + ':' + location.port);
function addToChat(message) {
const span = document.createElement("span");
const chat = document.querySelector(".chat");
console.log(`Adding ${message.name} and ${message.message} to the chat.`);
span.innerHTML = `<strong>${message.name}:</strong> ${message.message}`;
chat.append(span);
}
socket.on('connect', () => {
socket.send('User connected to socket.')
})
document.querySelector("form").addEventListener("submit", function(event){
event.preventDefault();
console.log(`Sending ${event.target[0].value} and ${event.target[1].value} to the server.`);
socket.emit('sendMessage', {name: event.target[0].value, message: event.target[1].value});
event.target[0].value = "";
event.target[1].value = "";
})
socket.on('getMessage', (message) => {
console.log(`Receiving ${message.name} and ${message.message} from the server.`);
addToChat(message);
})
socket.on('message', (messages) => {
console.log(`Retrieving ${messages.length} messages.`);
for (message of messages){
addToChat(message);
}
})
}
</script>
On the backend host, I'm using nginx and Gunicorn and start them using a service:
[Unit]
Description=Gunicorn instance for a simple hello world app
After=network.target
[Service]
User=ubuntu
Group=www-data
WorkingDirectory=/home/ubuntu/program
ExecStart=/home/ubuntu/program/venv/bin/gunicorn -b localhost:8000 app:app
Restart=always
[Install]
WantedBy=multi-user.target
And this is the nginx defaults:
upstream flaskprogram {
server 127.0.0.1:8000;
}
server {
listen 80 default_server;
listen [::]:80 default_server;
root /var/www/html;
# Add index.php to the list if you are using PHP
index index.html index.htm index.nginx-debian.html;
server_name _;
location / {
# First attempt to serve request as file, then
# as directory, then fall back to displaying a 404.
proxy_pass http://flaskprogram;
}
location /socket.io {
include proxy_params;
proxy_http_version 1.1;
proxy_buffering off;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "Upgrade";
proxy_pass http://127.0.0.1:8000/socket.io;
}
}
Nginx errors log: codeshare.io/vwOrny