Everything works fine on the local server. But when I try to test on a remote server through Nginx
, then inside the event handler onopen
readyState
is always CLOSED
.
Nginx config:
server {
server_name domain.domain;
access_log /var/log/nginx/domain.domain.access.log;
error_log /var/log/nginx/domain.domain.error.log;
location / {
proxy_connect_timeout 1d;
proxy_send_timeout 1d;
proxy_read_timeout 1d;
proxy_pass http://localhost:3001;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "Upgrade";
proxy_set_header Host $host;
}
listen 443 ssl; # managed by Certbot
ssl_certificate /etc/letsencrypt/live/domain.domain/fullchain.pem; # managed by Certbot
ssl_certificate_key /etc/letsencrypt/live/domain.domain/privkey.pem; # managed by Certbot
include /etc/letsencrypt/options-ssl-nginx.conf; # managed by Certbot
ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem; # managed by Certbot
}
server {
if ($host = domain.domain) {
return 301 https://$host$request_uri;
} # managed by Certbot
server_name domain.domain;
listen 80;
return 404; # managed by Certbot
}
Server sample code:
import { WebSocketServer } from 'ws';
this.connection = new WebSocketServer(args, () => {
log('info', 'Server listen at port:', args.port, true);
});
this.connection.on('connection', (ws, req) => {
// Event is triggered fine
console.log('Client connected');
})
Client sample code:
const connection = new WebSocket(
'wss://domain.domain:443', 'json'
);
connection.onopen = () => {
// Event triggered bud connection.readyState is CLOSED every time
setInterval(() => {
console.log(connection.readyState);
}, 1000)
}
connection.onerror = () => {
// Never triggered
}
connection.onclose = () => {
// Never triggered
}
Previously, the same code with the same server settings worked fine. But when after some time I recreated the virtual server from the backup, such a problem appeared, although everything else works as before.
CodePudding user response:
Revisiting my code again, I saw that since the last successful test, I added a CORS check to the server, which, as it turned out, was not properly configured in the environment variables.
this.connection.on('connection', (ws, req) => {
// Event is triggered fine
console.log('Client connected');
const { origin } = req.headers;
const notAllowed = process.env.CORS.split(',').indexOf(origin || '') === -1;
if (cors && notAllowed) {
log('warn', 'Block CORS attempt', { headers: req.headers });
ws.close();
return;
}
})
Another question is why event onclose
did not fire on the client and why warn
was not displayed on the server. But I think that since I output in stdout with a special method and maybe it also did not work due to incorrect environment variables, but this is another question - it does not need to be considered here.