配置
rails 启动脚本
bundle exec rails s -p 3011 -b 0.0.0.0
nginx 配置文件
# nginx.conf
server {
location / {
root /data/project-name/public;
index /products;
proxy_set_header Host $http_host;
proxy_pass http://localhost:3011;
}
# static file path
location /data/project-name/public/ {
rewrite ^/data/project-name/public(.*)$ $1 last;
}
# static file
location /uploads {
root /data/project-name/public;
}
}
期间遇到的问题
业务逻辑:还是说我做的电商网站,如果客户没有添加过地址,新客户,先购买了商品,添加到购物车,然后点击进入结算中心,这时候会redirect到新建地址页面,如果NGINX没有给后端传递host
变量,则会引起turbolinks 异常。
Uncaught DOMException: Failed to execute 'replaceState' on 'History': A history state object with URL 'http://localhost:3011/addresses/new' cannot be created in a document with origin 'http://localhost:8080' and URL 'http://localhost:8080/orders/new'.
at r.update (http://localhost:8080/assets/turbolinks.self-1d1fddf91adc38ac2045c51f0a3e05ca97d07d24d15a4dcbf705009106489e69.js?body=1:6:11571)
at r.replace (http://localhost:8080/assets/turbolinks.self-1d1fddf91adc38ac2045c51f0a3e05ca97d07d24d15a4dcbf705009106489e69.js?body=1:6:10898)
at r.replaceHistoryWithLocationAndRestorationIdentifier (http://localhost:8080/assets/turbolinks.self-1d1fddf91adc38ac2045c51f0a3e05ca97d07d24d15a4dcbf705009106489e69.js?body=1:6:29674)
at r.followRedirect (http://localhost:8080/assets/turbolinks.self-1d1fddf91adc38ac2045c51f0a3e05ca97d07d24d15a4dcbf705009106489e69.js?body=1:6:25092)
at r.visitCompleted (http://localhost:8080/assets/turbolinks.self-1d1fddf91adc38ac2045c51f0a3e05ca97d07d24d15a4dcbf705009106489e69.js?body=1:6:9736)
at r.complete (http://localhost:8080/assets/turbolinks.self-1d1fddf91adc38ac2045c51f0a3e05ca97d07d24d15a4dcbf705009106489e69.js?body=1:6:23145)
at r.<anonymous> (http://localhost:8080/assets/turbolinks.self-1d1fddf91adc38ac2045c51f0a3e05ca97d07d24d15a4dcbf705009106489e69.js?body=1:6:24918)
at http://localhost:8080/assets/turbolinks.self-1d1fddf91adc38ac2045c51f0a3e05ca97d07d24d15a4dcbf705009106489e69.js?body=1:6:27435
在请求http://localhost:8080/addresses/new
的时候,返回一个错误的headerTurbolinks-Location:http://localhost:3011/addresses/new
turbolinks官方文档说明: https://github.com/turbolinks/turbolinks/blob/0380f01b61e0a9e9a7516674c3e76c15efccd90e/README.md#following-redirects
When you visit location /one and the server redirects you to location /two, you expect the browser’s address bar to display the redirected URL.
However, Turbolinks makes requests using XMLHttpRequest, which transparently >follows redirects. There’s no way for Turbolinks to tell whether a request resulted in a redirect without additional cooperation from the server.
To work around this problem, send the Turbolinks-Location header in response to a visit that was redirected, and Turbolinks will replace the browser’s topmost history entry with the value you provide.
The Turbolinks Rails engine sets Turbolinks-Location automatically when using redirect_to in response to a Turbolinks visit.
官方文档说的意思是,如果存在重新向的情况,turbolinks并不会将地址栏url自动设置为重定向后的url,而是根据一个response的header来判断,Turbolinks-Location
,这个header是由rails释放出来的。
如果NGINX在向后端realserver请求时,没有带Host
这个header,后端的realserver(rails server)则直接将Turbolinks-Location
设置为它自己启动时的IP和端口,在本例中就是Turbolinks-Location:http://localhost:3011/addresses/new
要解决此问题,只需要在nginx 配置中增加 proxy_set_header Host $http_host;
,此设置含义是,在请求时,nginx将真正的前端主机名$http_host
,通过Host
传递给后端的realserver。