1

My nginx server is currently setup to serve all requests via uwsgi_pass:

location / {
  uwsgi_pass unix:///tmp/uwsgi-zerocater.sock;
  include uwsgi_params;
  uwsgi_read_timeout 7200;
  client_max_body_size 20M;
}

In my application code, I've set a cookie called new_fe whose value is either "True" or "False".

When the value is "True", I want to instead proxy_pass to another external server, but only for specific routes. Something like the following pseudo code:

location ~ "^/my/complicated/regex$" {
  if ($cookie_new_fe = "True") {
    # pass the request to my other server
    # at something like http://other.server.com
  } else {
    # do the usual uwsgi stuff
  }
}

How can I do this? I'm still a bit new to nginx, so please pardon the question if it's something simple I'm missing.

neezer
  • 810
  • 3
  • 12
  • 29
  • You can probably do this with some sort of map (because you can do just about anything with maps in nginx), but seriously, just put your new codebase on a separate vhost. – womble Oct 14 '15 at 05:27
  • @womble I'm after a temporary solution: I'm in the process of carving a monolithic app into smaller, stand-alone apps. Problem is that nginx & uwsgi exist on one EC2 instance, but the external host is on Heroku. Until I can transition the code wholesale, I need to be able to get by with tom foolery like this and not (seriously) break the existing app. Do you have an example of how to do this with maps? – neezer Oct 14 '15 at 06:13

2 Answers2

0

As a temporary solution this should work:

location ~ "^/my/complicated/regex$" {
  if ($cookie_new_fe = "True") {
    error_page 418 = @proxy;
    return 418;
  }

  # do the usual uwsgi stuff
}

location @proxy {
    # do proxy stuff
}
Alexey Ten
  • 8,435
  • 1
  • 34
  • 36
0

I looked into maps a bit more and came up with this solution, which seems to work (uses both @womble's and @alexey-ten's suggestions):

map $cookie_new_fe $serve_request_from {
  default @uwsgi;
  "True" @proxy;
}

server {

  # ...

  # BEGIN Routes to switch based on value of $cookie_new_fe
  location ~ "^/my/complicated/regex$" {
    error_page 418 = $serve_request_from;
    return 418;
  }
  # END

  location / {
    error_page 418 = @uwsgi;
    return 418;
  }

  location @uwsgi {
    uwsgi_pass unix:///tmp/uwsgi-origserver.sock;
    include uwsgi_params;
    uwsgi_read_timeout 7200;
    client_max_body_size 20M;
  }

  location @proxy {
    proxy_pass https://other.server.com;
    proxy_http_version 1.1;
    proxy_set_header Upgrade $http_upgrade;
    proxy_set_header Connection $connection_upgrade;
  }
}

This way I have minimal duplication across the many routes that I'll need to add here in the interim, until this migration is complete.

neezer
  • 810
  • 3
  • 12
  • 29