Node.js + Nginx – 现在什么?
我在我的服务器上设置了Node.js和Nginx。 现在我想用它,但是在我开始之前有两个问题:
- 他们应该如何一起工作? 我应该如何处理这些请求?
-
Node.js服务器有两个概念,哪一个更好:
一个。 为每个需要它的网站创build一个单独的HTTP服务器。 然后在程序的开始加载所有的JavaScript代码,所以代码被解释一次。
湾 创build一个处理所有Node.js请求的单个Node.js服务器。 这会读取请求的文件并清除其内容。 所以文件在每个请求上被解释,但是服务器逻辑要简单得多。
我不清楚如何正确使用Node.js。
Nginx作为一个前端服务器,在这种情况下,代理请求到一个node.js服务器。 因此你需要为节点设置一个nginxconfiguration文件。
这是我在我的Ubuntu盒子里所做的:
在/etc/nginx/sites-available/
创build文件yourdomain
vim /etc/nginx/sites-available/yourdomain
其中你应该有这样的东西:
# the IP(s) on which your node server is running. I chose port 3000. upstream app_yourdomain { server 127.0.0.1:3000; keepalive 8; } # the nginx server instance server { listen 0.0.0.0:80; server_name yourdomain.com yourdomain; access_log /var/log/nginx/yourdomain.log; # pass the request to the node.js server with the correct headers # and much more can be added, see nginx config options location / { proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header Host $http_host; proxy_set_header X-NginX-Proxy true; proxy_pass http://app_yourdomain/; proxy_redirect off; } }
如果你想要nginx(> = 1.3.13)来处理websocket请求,在location /
section中添加以下几行:
proxy_http_version 1.1; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection "upgrade";
一旦你有这个设置,你必须启用在上面的configuration文件中定义的网站:
cd /etc/nginx/sites-enabled/ ln -s /etc/nginx/sites-available/yourdomain yourdomain
在/var/www/yourdomain/app.js
创build节点服务器应用程序并在localhost:3000
运行它
var http = require('http'); http.createServer(function (req, res) { res.writeHead(200, {'Content-Type': 'text/plain'}); res.end('Hello World\n'); }).listen(3000, "127.0.0.1"); console.log('Server running at http://127.0.0.1:3000/');
重新启动nginx:
sudo /etc/init.d/nginx restart
最后启动节点服务器:
cd /var/www/yourdomain/ && node app.js
现在您应该在yourdomain.com上看到“Hello World”
关于启动节点服务器的最后一个注意事项是:应该为节点守护进程使用某种监视系统。 节点上有一个令人敬畏的教程与暴发户和monit 。
你也可以用nginx设置多个域,转发到多个node.js进程。
例如要实现这些:
- domain1.com – >到Node.js进程本地运行http://127.0.0.1:4000
- domain2.com – >到Node.js进程本地运行http://127.0.0.1:5000
在/ etc / nginx的/启用的站点- / DOMAIN1
server { listen 80; server_name domain1.com; access_log /var/log/nginx/domain1.access.log; location / { proxy_pass http://127.0.0.1:4000/; } }
在/ etc / nginx / sites-enabled / domain2中
server { listen 80; server_name domain2.com; access_log /var/log/nginx/domain2.access.log; location / { proxy_pass http://127.0.0.1:5000/; } }
您也可以在一个服务器configuration中为应用程序提供不同的URL:
- yourdomain.com/app1/* – >到Node.js进程本地运行http://127.0.0.1:3000
- yourdomain.com/app2/* – >到Node.js进程本地运行http://127.0.0.1:4000
在/ etc / nginx / sites-enabled / yourdomain中 :
server { listen 80; server_name yourdomain.com; location ^~ /app1/{ proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header Host $http_host; proxy_set_header X-NginX-Proxy true; proxy_pass http://127.0.0.1:3000/; } location ^~ /app2/{ proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header Host $http_host; proxy_set_header X-NginX-Proxy true; proxy_pass http://127.0.0.1:4000/; } }
重新启动nginx:
sudo service nginx restart
启动应用程序
节点app1.js
var http = require('http'); http.createServer(function (req, res) { res.writeHead(200, {'Content-Type': 'text/plain'}); res.end('Hello from app1!\n'); }).listen(3000, "127.0.0.1"); console.log('Server running at http://127.0.0.1:3000/');
节点app2.js
var http = require('http'); http.createServer(function (req, res) { res.writeHead(200, {'Content-Type': 'text/plain'}); res.end('Hello from app2!\n'); }).listen(4000, "127.0.0.1"); console.log('Server running at http://127.0.0.1:4000/');
我通过Nginx代理独立的Node Express应用程序。
因此,新的应用程序可以很容易地安装,我也可以在不同的位置在同一台服务器上运行其他的东西。
以下是有关使用Nginxconfiguration示例进行设置的更多详细信息:
使用Nginx在一个Web服务器上的子文件夹中部署多个节点应用程序
当你需要将应用程序从本地主机移动到互联网时,事情会变得棘手。
节点部署没有通用的方法。
谷歌可以在这个主题上find大量的文章,但我正在努力寻找我需要的设置的正确的解决scheme。
基本上,我有一个Web服务器,我希望节点应用程序被挂载到子文件夹(即http:// myhost / demo / pet-project / ),而不会引入任何configuration依赖的应用程序代码。
同时,我希望其他的东西,如博客运行在同一个Web服务器上。
听起来很简单吧? 显然不是。
在Web上的许多例子中,Node应用程序或者运行在端口80上,或者由Nginx代理到根目录。
即使这两种方法对于某些用例都是有效的,但它们不符合我简单但有点异国情调的标准。
这就是为什么我创build了我自己的Nginxconfiguration,这里是一个摘录:
upstream pet_project { server localhost:3000; } server { listen 80; server_name frontend; location /demo/pet-project { alias /opt/demo/pet-project/public/; try_files $uri $uri/ @pet-project; } location @pet-project { rewrite /demo/pet-project(.*) $1 break; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header Host $proxy_host; proxy_set_header X-NginX-Proxy true; proxy_pass http://pet_project; proxy_redirect http://pet_project/ /demo/pet-project/; } }
从这个例子你可以注意到,我将我的Pet项目节点应用程序运行在端口3000上http:// myhost / demo / pet-project 。
第一个Nginx会检查请求的资源是否是/ opt / demo / pet-project / public /中的一个静态文件,如果是这样的话,它的效率是非常高的,所以我们不需要像Connect这样的冗余层静态中间件。
然后,所有其他请求都被覆盖并代理到Pet Project Node应用程序,所以Node应用程序不需要知道它实际安装在哪里,因此可以纯粹通过configuration移动到任何地方。
proxy_redirect必须正确处理位置标题。 如果在Node应用程序中使用res.redirect() ,这是非常重要的。
您可以轻松地复制此设置,以便在不同端口上运行多个节点应用程序,并为其他目的添加更多位置处理程序。
来自: http : //skovalyov.blogspot.dk/2012/07/deploy-multiple-node-applications-on.html
回答你的问题2:
我会使用选项b
只是因为它消耗更less的资源。 选项'a',每个客户端将导致服务器消耗大量的内存,加载所有您需要的文件(即使我喜欢PHP,这是它的问题之一)。 使用选项'b',您可以加载您的库(可重用代码)并在所有客户端请求之间共享它们。
但是,如果你有多个内核,你应该调整node.js来使用它们。
带有Nginxconfiguration的Node.js。
$ sudo nano /etc/nginx/sites-available/subdomain.your_domain.com
添加以下configuration,以便当Nginx来自“subdomain.your_domain.com”时,充当代理的redirect到来自服务器的端口3000stream量。
upstream subdomain.your_domain.com { server 127.0.0.1:3000; } server { listen 0.0.0.0:80; server_name subdomain.your_domain.com; access_log /var/log/nginx/subdomain.your_domain.access.log; error_log /var/log/nginx/subdomain.your_domain.error.log debug; location / { proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarder-For $proxy_add_x_forwarded_for; proxy_set_header Host $http_host; proxy_set_header X-NginX-Proxy true; proxy_pass http://subdomain.your_domain.com; proxy_redirect off; } }
您也可以使用node.js将静态文件生成到由nginx提供的目录中。 当然,你的站点的一些dynamic部分可以由节点来服务,而一些由nginx(静态)来服务。
有一些由nginx服务可以提高你的性能。
我在Github中创build了一个可以克隆的库, vagrant-node-nginx-boilerplate
基本上, /var/www/nodeapp
的node.js应用程序是
var http = require('http'); http.createServer(function (req, res) { res.writeHead(200, {'Content-Type': 'text/plain'}); res.end('Hello World\n'); }).listen(4570, '127.0.0.1'); console.log('Node Server running at 127.0.0.1:4570/');
和/etc/nginx/sites-available/
的nginxconfiguration
server { listen 80 default_server; listen [::]:80 default_server ipv6only=on; root /var/www/nodeapp; index index.html index.htm; server_name localhost; location / { proxy_pass http://127.0.0.1:4570; proxy_http_version 1.1; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection 'upgrade'; proxy_set_header Host $host; proxy_cache_bypass $http_upgrade; } }
我们可以通过Nginx作为反向代理轻松设置一个Nodejs应用程序。
以下configuration假定NodeJS应用程序在127.0.0.1:8080上运行,
server{ server_name domain.com sub.domain.com; # multiple domains location /{ proxy_pass http://127.0.0.1:8080; proxy_set_header Host $host; proxy_pass_request_headers on; } location /static/{ alias /absolute/path/to/static/files; # nginx will handle js/css } }
在上面的设置你的Nodejs应用程序将,
- 获取
HTTP_HOST
标头,您可以在其中应用特定于域的逻辑来提供响应。 “ -
您的应用程序必须由像pm2这样的stream程pipe理员或主pipe处理情况/重复使用套接字或资源等进行pipe理。
-
设置一个错误报告服务来获取生产错误,如哨兵或滚动条
注意:您可以设置逻辑来处理特定于域的请求路由,为expressjs应用程序创build一个中间件
Nginx可以作为一个反向代理服务器,就像一个项目经理一样工作。 当它得到一个请求时,它会分析它并将请求转发给上游(项目成员)或处理自己。 Nginx有两种处理请求的方式,基于它的configuration。
- 服务请求
-
转发请求到另一台服务器
server{ server_name mydomain.com sub.mydomain.com; location /{ proxy_pass http://127.0.0.1:8000; proxy_set_header Host $host; proxy_pass_request_headers on; } location /static/{ alias /my/static/files/path; }
}
服务器请求
当请求url是
mydomain.com/static/myjs.js
时,通过这种configuration,它将返回/my/static/files/path
文件夹中的myjs.js
文件。 当您将nginxconfiguration为提供静态文件时,它将自行处理请求。
转发请求到另一台服务器
当请求的URL是
mydomain.com/dothis
nginx会将请求转发到http://127.0.0.1:8000 。 在localhost 8000端口上运行的服务将接收到请求,并将响应返回给nginx,nginx将响应返回给客户端。
当您在端口8000上运行node.js服务器时,nginx会将请求转发到node.js. 编写node.js逻辑并处理请求。 这就是你有你的nodejs服务器运行在nginx服务器后面。
如果你想运行除nodejs之外的任何其他服务,只需在不同的端口上运行Django,flask,php等其他服务并将其configuration为nginx。