我们正在开发一个需要利用html5 websockets的Ruby on Rails应用程序.目前,我们有两个单独的"服务器"可以这么说:我们主要应用上的nginx +客运运行,并使用PRATIK奈克的一个单独的服务器抽筋框架(这是上运行薄)来处理WebSocket连接.
理想的情况是,当谈到时间进行部署,我们不得不对nginx的+乘客运行Rails应用程序,和WebSocket的服务器将背后nginx的被代理,所以我们不会需要有一个不同的端口上运行的WebSocket伺服器.
问题是,在这种设置中,似乎nginx过早地关闭了与Thin的连接.已成功建立与瘦服务器的连接,然后立即关闭200响应代码.我们的猜测是nginx没有意识到客户端正试图为websocket流量建立一个长期运行的连接.
不可否认,我对nginx配置并不是那么精明,所以,甚至可以配置nginx作为websocket服务器的反向代理吗?或者我是否必须等待nginx为新的websocket握手提供支持?假设让app服务器和websocket服务器都在端口80上监听是一个要求,那么这可能意味着我必须在没有nginx的单独服务器上运行Thin吗?
提前感谢任何建议或意见.:)
-约翰
你现在不能使用nginx [它不再是真的],但我建议看看HAProxy.我把它用于这个目的.
诀窍是设置长时间超时,以便不关闭套接字连接.就像是:
timeout client 86400000 # In the frontend timeout server 86400000 # In the backend
如果您想在同一端口上使用rails和cramp应用程序,则可以使用ACL规则来检测websocket连接并使用不同的后端.所以你的haproxy前端配置看起来像
frontend all 0.0.0.0:80 timeout client 86400000 default_backend rails_backend acl websocket hdr(Upgrade) -i WebSocket use_backend cramp_backend if websocket
为了完整性,后端看起来像
backend cramp_backend timeout server 86400000 server cramp1 localhost:8090 maxconn 200 check
如何使用我的nginx_tcp_proxy_module模块?
此模块专为使用Nginx的常规TCP代理而设计.我认为它也适用于websocket.我只是在开发分支中添加tcp_ssl_module.
nginx(> = 1.3.13)现在支持反向代理websockets.
# the upstream server doesn't need a prefix! # no need for wss:// or http:// because nginx will upgrade to http1.1 in the config below upstream app_server { server localhost:3000; } server { # ... location / { proxy_pass http://app_server; proxy_http_version 1.1; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection "upgrade"; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_redirect off; } }
开箱即用(即官方消息来源)Nginx只能建立到上游(=后端)的HTTP 1.0连接,这意味着没有任何keepalive可能:Nginx将选择一个上游服务器,打开它的连接,代理,缓存(如果你想)并关闭连接.而已.
这是需要持久连接到后端的框架无法通过Nginx工作的基本原因(没有HTTP/1.1 =没有keepalive,我猜没有websockets).尽管有这个缺点,但有一个明显的好处:Nginx可以选择退出几个上游(负载平衡)并故障转移到活动状态,以防其中一些失败.
编辑:自版本1.1.4起,Nginx支持HTTP 1.1到后端和keepalive.支持"fastcgi"和"代理"上游.这是文档
对于任何想知道同样问题的人,nginx现在正式支持HTTP 1.1上游.有关"keepalive"和"proxy_http_version 1.1"的信息,请参阅nginx文档.