You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

HTTPS前端无法连接ws协议Socket.io服务,如何切换为wss?

问题描述

前端部署在Vercel、后端部署在Railway,二者均启用HTTPS加密。后端搭建Socket.io服务器后出现如下错误:

The page at 'https://codingflux.vercel.app/editor/Test/6560b5a38544a66357dd' was loaded over HTTPS, but attempted to connect to the insecure WebSocket endpoint 'ws://codingflux-backend-production.up.railway.app/socket.io/?EIO=4&transport=websocket'.

已知后端域名支持HTTPS(https://codingflux-backend-production.up.railway.app/),但前端连接时使用了不安全的ws协议,希望将Socket URL转为wss协议。

后端代码如下:

const express = require("express");
const app = express();
const http = require("http");
const cors = require('cors');
const { Server } =  require("socket.io");
const Actions = require('./Actions');

app.use(cors());

const server = http.createServer(app);
const io = new Server(server, {
    cors: {
      origin: 'https://codingflux.vercel.app/',
      methods: ['GET', 'POST'],
    },
  });

const users = {};

//Get an array of all the users connected in the room as an array of objects with socketId and username as their attributes.
const getAllConnectedClients = (roomId) => {
    return Array.from(io.sockets.adapter.rooms.get(roomId)).map((socketId) => {
        return {
            socketId,
            username: users[socketId]
        }
    })
}

io.on('connection', (socket) => {
    //Listen for any join event populate the users object and get all connected clients and for every client emit another event joined.
    socket.on(Actions.JOIN, ({roomId, username}) => {
        const userName = username;
        users[socket.id] = username;
        socket.join(roomId);
        //This clients array is send as one of the values to the client side ehere it is used to set the state of client.
        const clients = getAllConnectedClients(roomId);
        clients.forEach(({socketId}) => {
            io.to(socketId).emit(Actions.JOINED, {
                clients,
                userName,
                socketId: socket.id
            })
        })
    })

    //Executes whenever a user leaves the room. 
    socket.on('disconnecting', () => {
        const rooms = [...socket.rooms];
        rooms.forEach((roomId) => {
            socket.in(roomId).emit(Actions.DISCONNECTED,{
                socketId : socket.id,
                username : users[socket.id]
            })
        });
        delete users[socket.id];
        socket.leave();
    })

    //Listen to any code change events from the client side whenever user writes something in code editor and broadcast it to all other connected clients.
    socket.on(Actions.CODE_CHANGE, ({ roomId, code, name }) => {
        socket.in(roomId).emit(Actions.CODE_CHANGE, { code : code, name });
    })

    //This event is emited from the as a response of joined event from the client side.
    //Emitted by everyone except the newly joined user.
    socket.on(Actions.SYNC_CODE, ({ code, socketId, name }) => {
        //Emit an event as a response to change code in new users editor. This event is emited once when a new user first joines or the page reloads. 
        socket.to(socketId).emit(Actions.CODE_CHANGE, { code : code, name : name }); 
    })
})

const PORT = 5000;
server.listen(PORT, () => {console.log(`Alpha is online on ${PORT}`)});
解决方案

要解决ws转wss的问题,核心是适配HTTPS环境的连接规则,具体步骤如下:

1. 前端使用HTTPS地址初始化Socket连接

前端初始化Socket.io客户端时,直接传入后端的HTTPS域名,Socket.io会自动将协议转为wss,无需手动指定ws://前缀。示例代码:

// 前端代码示例
import { io } from "socket.io-client";

const socket = io("https://codingflux-backend-production.up.railway.app", {
  transports: ["websocket"] // 可选,强制使用WebSocket传输
});

如果之前前端硬编码了ws://开头的地址,直接替换为HTTPS域名即可。

2. 后端配置适配Railway反向代理

Railway会自动为应用提供HTTPS反向代理,后端无需手动配置HTTPS证书,但需要让Socket.io识别反向代理的真实协议。在Socket.io的配置中添加trustProxy: true,让它从请求头中获取正确的协议信息:

const io = new Server(server, {
    cors: {
      origin: 'https://codingflux.vercel.app/',
      methods: ['GET', 'POST'],
    },
    trustProxy: true // 新增配置,适配Railway反向代理环境
  });

该配置会让Socket.io根据X-Forwarded-Proto请求头自动判断使用ws还是wss协议,确保后端返回的连接地址符合HTTPS环境要求。

3. 优化端口配置

Railway会自动映射端口,后端代码应监听环境变量中的端口,避免硬编码导致的环境不兼容:

const PORT = process.env.PORT || 5000;
server.listen(PORT, () => {console.log(`Alpha is online on ${PORT}`)});

完成以上步骤后,前端即可通过wss协议安全连接到后端Socket.io服务器,解决混合内容错误。

内容的提问来源于stack exchange,提问作者Nishant Sharma

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.05 10:17:32