为什么在开发环境下,Nginx 访问我的 Rails 应用非常缓慢?

4

我正在macOS上开发一个RoR应用程序。

为了能够在http://localhost上访问我的应用程序,并为了在我的测试中支持SSL,我使用nginx作为代理到Webrick端口3000,使用以下配置:

server {
    listen 80;
    server_name app.mysite.com;
    location / {
        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;
        proxy_pass http://127.0.0.1:3000;
    }
}

server {
    listen       443 ssl;
    server_name  secure.app.mysite.com;

    ssl                  on;
    ssl_certificate      ssl/server.crt;
    ssl_certificate_key  ssl/server.key;

    keepalive_timeout 600;
    ssl_session_timeout 10m;
    ssl_protocols  SSLv2 SSLv3 TLSv1;
    ssl_ciphers  ALL:!ADH:!EXPORT56:RC4+RSA:+HIGH:+MEDIUM:+LOW:+SSLv2:+EXP;
    ssl_prefer_server_ciphers   on;

    location / {
        proxy_pass http://127.0.0.1:3000;
        ### force timeouts if one of backend is died ##
        proxy_next_upstream error timeout invalid_header http_500 http_502 http_503;
        ### Set headers ####
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        ### Most PHP, Python, Rails, Java App can use this header ###
        proxy_set_header X-Forwarded-Proto https;
        ### By default we don't want to redirect it ####
        proxy_redirect     off;
   }
}

当我访问应用程序时,无论是通过 http://localhost/ 还是 https://localhost/ 访问,服务器都会快速响应,而通过 http://localhost:3000 访问的开销也几乎可以忽略不计。
然而,当我尝试从同一网络中的另一台计算机上访问我的计算机(例如 http://10.0.1.9/)时,服务器响应极慢,或者根本没有响应。
在这种情况下,似乎 nginx 并没有发送到端口 3000 的内部请求,尽管肯定有来自外部的请求到达了 nginx,并且来自外部的对端口 3000 的请求非常快。
需要注意的是,我的应用程序正在以 dev 模式运行,我的资源(相当多)未经预编译。
除了 nginx 之外,是否还有其他选项可以轻松地在我的网络上公开我的开发网站,而且易于配置并支持 SSL?
谢谢, Ariel

很可能的情况是,当您从同一台计算机访问本地主机时,浏览器会缓存所有内容。 - Joe Frambach
1
当我通过:3000访问RoR时,我在Ubuntu上遇到了类似的问题。尝试通过:3000访问您的站点以验证是否是nginx的问题。我猜测路上有一些防火墙(其他软件)会减慢请求速度。 - denis-bu
我已经验证了问题出在nginx上(直接通过端口3000访问应用程序在本地和远程都可以正常工作)。我不认为防火墙是问题的原因,我的Mac防火墙没有运行,并且我不认为有任何东西阻止了80端口。 - Sakin
感谢您的评论。不幸的是,当远程访问时,Webrick实际上运行良好(我也尝试了thin和pow)。似乎nginx在转发请求时需要很长时间,或者在远程访问时可能会遇到某种超时问题。 - Sakin
1
我理解了,很抱歉一再发送相同的内容。在发布之前错过了您的评论,所以现在我不知道为什么nginx很慢... - denis-bu
虽然我有一个想法...由于DNS的问题,也许这里也是同样的情况。你尝试在客户端机器上添加到/etc/hosts中10.0.1.9 app.mysite.com;和10.0.1.9 secure.app.mysite.com;并在浏览器中使用http://app.mysite.com/而不是http://10.0.1.9/进行访问。 - denis-bu
3个回答

1

0

我敢打赌这根本不是nginx的问题。很难想象nginx在将请求传递到同一台服务器上游之前会长时间保留请求。你能否检查两个访问日志(nginx和ROR)以查看请求开始时间是否有很大差异?

你的osx版本是哪个?是Lion还是Mountain Lion?两者都存在在/etc/hosts中输入慢速DNS查找的问题。

我的同事也遇到了同样的缓慢问题。请参见Mac OSX Lion DNS lookup order进行讨论。这有点混乱。


为了验证这一点,您可以直接使用域名或IP地址访问RoR应用程序,以查看响应时间是否相同。 - Chuan Ma
正如我上面所描述的,我可以直接在端口3000上远程访问我的网站而没有任何问题。问题只会在通过端口80远程访问网站时发生。 - Sakin

0

以下是一些尝试的方法,因为在本地主机上运行良好但从另一台电脑访问时出现问题,听起来有些可疑。

  • 使用'netstat -na | grep 80'命令,确保Nginx正在侦听0.0.0.0或*:80而不是127.0.0.1。如果Nginx没有在0.0.0.0或*上侦听,则可能存在TCP路由问题。对于任何服务器都是如此。 这是一个很好的示例输出(我的示例正在侦听8000端口)

    tcp4 0 0 *.8000 *.* LISTEN

  • 为了好玩,将您的Nginx代理语句中的“127.0.0.1”更改为“localhost”和/或“0.0.0.0”(虽然路由已经完成)。

此外,我建议您尝试使用Nginx的日志记录以查看是否有其他问题。关于更好的代理/上游日志记录,这里已经有了一个stackoverflow链接: logging proxy activity in nginx

此外,您应该打开调试日志(我已经用它解决了问题),将其放置在access_log指令的下方/上方。类似这样的内容应该就可以了:
 error_log  /Users/your_name/nginx_test/logs/error.log  debug;

请注意,对于Nginx,您必须使用绝对路径来记录日志。
祝你好运。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接