6

I have a Flask web service which runs on uwsgi+nginx and it works well.

I have another development version of the service which runs on another server. It also runs on uwsgi+nginx.

What I want to do is, test the development server with 'real' traffic(POST requests) I've done verifying the development server works well basically. Just want compare the two with same real traffic.

My basic idea for this is like below:

(A) is legacy server (B) is test server

  1. User requests

  2. Nginx(A) get the request and deliver the request to uwsgi(A) for handling.

  3. Nginx(A) 'copy' the request and deliver it to Nginx(B) for testing

  4. uwsgi(A) handle the request in Flask App(A) and response to User (via Nginx(A))

  5. Nginx(B) handle the request like legacy server does but not response to User (just logging)

Is this make any sense? What approach I should take?

Younggun Kim
  • 341
  • 1
  • 2
  • 11

2 Answers2

17

I found the solution myself. So I share my finding here.

I used post_action directive for this.

location / {
    uwsgi_pass      unix:app.sock;
    post_action @post_action; 
}

location @post_action {
    proxy_pass      http://dst_host:dst_port; 
}

The request first delivered to unix:app.sock and when it completed, post_action directive pass the request to named location, @post_action.

It works like a charm!

Younggun Kim
  • 341
  • 1
  • 2
  • 11
  • When testing server load with [boom](https://github.com/rakyll/boom) `boom -n 100 -c 10 -m GET ...` I'm getting in 50% responses `EOF` or `read: connection reset by peer`. That's not good for high-availability :(. – Tombart Aug 23 '16 at 12:15
  • 1
    Note that this is dangerous, see http://mailman.nginx.org/pipermail/nginx/2012-November/036199.html because this will block the original thread while it waits for the shadow – Josh Jul 04 '17 at 02:02
0
location / {
      proxy_pass  http://y.y.y.y:port;
      proxy_set_header X-Real-IP $remote_addr;
      proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
      proxy_connect_timeout      300;
      proxy_send_timeout         300;
      proxy_read_timeout         300;
      post_action @post_action;
    }

location @post_action {
    proxy_pass      http://x.x.x.x:port;
    access_log /var/log/nginx/c.log application;
    error_log /var/log/nginx/c.log error;
}

The request first delivered to http://y.y.y.y:port and when it completed, post_action not able to directive pass the request to named location, @post_action.Is there any other thing we need to do?

Thomas
  • 4,155
  • 5
  • 21
  • 28