I use nginx, with passenger, to serve a Rails API. In preparation for our 1.0 launch, I would like to version this API using the method described in this answer.
I have a version number that is pulled from a specification, along with capistrano recipes set up to create the following directory structure:
/var/www/foamfactory.io/dev.api.foamfactory.io
- v0
- current (points to v0.0)
- v0.0
- current (points to v0.0.15)
- v0.0.15 (this is the capistrano directory)
- current (points to latest release under releases/)
- releases
- 20210308162204 (rails directory)
Now, my nginx setup was as follows, in order to rewrite, for example, dev.api.foamfactory.io/version
to dev.api.foamfactory.io/current/current/current/current/current/public
(I'm working on getting this basic example working before I struggle with, e.g dev.api.foamfactory.io/v0/v0.0/version
.
server {
rewrite_log on;
server_name dev.api.foamfactory.io;
access_log /var/log/nginx/dev.api.foamfactory.io-access.log;
error_log /var/log/nginx/dev.api.foamfactory.io-error.log notice;
passenger_enabled on;
passenger_ruby /home/www-data/.rvm/rubies/default/bin/ruby;
passenger_sticky_sessions on;
passenger_app_env development;
passenger_env_var SECRET_KEY_BASE redacted;
location / {
if ($request_method = 'GET') {
add_header 'Access-Control-Allow-Origin' '*';
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
add_header 'Access-Control-Expose-Headers' 'Content-Length,Content-Range';
}
}
rewrite ^/(.*)$ /current/current/current/current/public/$1 last;
rewrite ^/v([0-9]+)/(.*)$ /v$1/current/current/current/public/$2 last;
rewrite ^/v([0-9]+).([0-9]+)/(.*)$ /v$1/v$1.$2/current/current/public/$3 last;
rewrite ^/v([0-9]+).([0-9]+).([0-9]+)/(.*)$ /v$1/v$1.$2/v$1.$2.$3/current/public/$4 last;
}
I modified this first rewrite
statement to be a location/
statement:
server {
rewrite_log on;
server_name dev.api.foamfactory.io;
access_log /var/log/nginx/dev.api.foamfactory.io-access.log;
error_log /var/log/nginx/dev.api.foamfactory.io-error.log notice;
passenger_enabled on;
passenger_ruby /home/www-data/.rvm/rubies/default/bin/ruby;
passenger_sticky_sessions on;
passenger_app_env development;
passenger_env_var SECRET_KEY_BASE redacted;
location / {
if ($request_method = 'GET') {
add_header 'Access-Control-Allow-Origin' '*';
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
add_header 'Access-Control-Expose-Headers' 'Content-Length,Content-Range';
}
}
location ~ ^/(.*)$ {
rewrite ^/(.*)$ /current/current/current/current/public/$1 break;
root /var/www/foamfactory.io/dev.api.foamfactory.io/current/current/current/current/public;
}
}
I can now access the Rails app, BUT, when I try to access an endpoint (e.g. /version, as in dev.api.foamfactory.io/version
, Rails reports the following error:
ActionController::RoutingError: No route matches [GET] \"/current/current/current/current/public/version\"
My suspicion is that it has something to do with the relative_url_root
configuration variable inside of the Rails configuration, so inside of environments/development.rb
, I modified the configuration to include:
config.relative_url_root = '/current/current/current/current/public'
However, this did not alleviate the error.
I'm wondering if someone might be able to help me with what I need to do to get this working. I feel like I'm not even sure if it's an nginx configuration problem or a Rails configuration problem at this point.