node.js - 将 socket.io 置于反向代理后面?

标签 node.js socket.io reverse-proxy

我最近决定学习 socket.io,以实现实时的东西。我按照网站上的“入门”页面写了一些东西,并在本地进行了测试,直到它正常工作为止。

我使用与其他任何东西相同的过程将其上传到我的服务器。我在端口 8002 上运行它,并将其添加到我的反向代理(使用 http-proxy-middleware )在 /pong/* 下。然后我代理/socket.io/*在它工作之前到端口 8002。然而,在使用 Firefox 检查后,我注意到 socket.io 仅使用轮询作为传输方法,而不是 websockets,经过进一步思考,我决定发送 /socket.io/*将来在其他项目上使用 socket.io 时,改为 8002 会不太好。

所以我问,如何使用 websockets 作为传输,让多个 socket.io 程序在反向代理后面运行?


代理.js

const express = require("express")
const fs = require('fs');
const http = require('http');
const https = require('https');
const proxy = require('http-proxy-middleware');

const privateKey  = fs.readFileSync('/etc/[path-to- letsencrypt]/privkey.pem', 'utf8');
const certificate = fs.readFileSync('/etc/[path-to-letsencrypt]/cert.pem', 'utf8');
const ca = fs.readFileSync('/[path-to-letsencrypt]/chain.pem', 'utf8');

var credentials = {key: privateKey, cert: certificate, ca: ca};
var app = express();

app.use(function (req, res, next) {
        console.log(req.url)
        next()
})

app.use("/pong/*", proxy({ target: "http://localhost:8002", pathRewrite: {"^/pong": ""},  ws:true, changeOrigin: true }))
app.use("/pnw/war/*", proxy({ target: "http://localhost:8000" }))
app.use("/pnw/nation/*", proxy({ target: "http://localhost:8001" }))
app.use(express.static("./static"))

https.createServer(credentials, app).listen(443);

// Redirect all HTTP traffic to HTTPS
http.createServer(function (req, res) {
    res.writeHead(301, { "Location": "https://" + req.headers['host'] + req.url });
    res.end();
}).listen(80);

pong.js

var app = require('express')();
var http = require('http').Server(app);
var io = require('socket.io')(http, {
    path: "/pong/"
});

app.get('/', function(req, res){
  res.sendFile(__dirname + '/index.html');
});

http.listen(8002, function(){
  console.log('listening on *:8002');
});

index.html

<script src="/pong/socket.io.js"></script>
<script>
    var socket = io({
        // transports: ['websocket'], upgrade: false, (using for testing)
        path:"/pong"
    }) 

    // ...
</script>

我目前所得到的内容来自于这个问题的答案: Setting up multiple socket.io/node.js apps on an Apache server?

但是在 Firefox 控制台中我收到一条警告,内容如下: Loading failed for the <script> with source “https://curlip.xyz/pong/socket.io.js” ,后跟错误 io is not defined 。在网络选项卡中获取 socket.io.js 显示 404。

所以我相信正在发生的事情是因为express正在捕获/的请求,socket.io无法(由于某种原因)服务器socket.io.js。但是当我将/更改为 /index.html 时并加载没有任何变化。

最佳答案

所以我做了更多研究并找到了解决方案。我在 EC2 上打开了端口 8002,以便我可以四处寻找 socket.io.js

基本上我发现的是 socket.io.js 位于 /pong/pong/socket.io.js 因为我将 pong.js 中的路径设置为“pong”,事后看来这是有道理的,代理添加了一个“pong”,而 socket.io 本身正在捕获“/pong”。

知道这一点后,我删除了 pong.js 中的路径选项,以便可以在 /pong/socket.io/socket.io.js 找到 socket.io.js。然后,我通过更改 index.html 中的脚本标记和路径选项让客户端指出这一点。


pong.js

var app = require('express')();
var http = require('http').Server(app);
var io = require('socket.io')(http);

app.get('/', function(req, res){
  res.sendFile(__dirname + '/index.html');
});

http.listen(8002, function(){
  console.log('listening on *:8002');
});

index.html

<script src="/pong/socket.io/socket.io.js"></script>

var socket = io({
    path:"/pong/socket.io/"
})

关于node.js - 将 socket.io 置于反向代理后面?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52618697/

相关文章:

javascript - 我如何在socket.io 1.0中断开服务器端和客户端的套接字

apache - httpd mod_proxy_balancer 故障转移 failonstatus - 透明切换

node.js - 如何从 POST 正文获取 wav 文件并使用 Node JS/Express 上传

javascript - 如何在 npm 包中添加文件夹作为条目?

node.js - Angular 服务中的 "window is not defined"但代码运行良好

node.js - Socket.io 和 Express ERR_SSL_VERSION_OR_CIPHER_MISMATCH

javascript - 使用socket.io和express,为什么我的io.on ('connection')方法不起作用

Nginx : how to proxy both HTTP and HTTPS, 后面的 Tomcat 可能在非标准端口上?

ruby - 带 docker 的 nginx 没有正确代理到我的 ruby​​ 应用程序

javascript - 不合逻辑的 Passport 验证方法参数