Search code examples
deploymentload-balancingcanary-deployment

Setting up load-balancer based on authenticated users


I'm trying to set up a loadbalancer that would redirect to specific version of an application certein users. So far i was using Blue/Green deployment strategy (so once i made new version of an app i created new environment and redirected traffic there). Now i would like to change this approach. I want to be able to specify users (more experienced or whatever) that would see new site after authentication while the others would still be redirected to old one. If something goes wrong with new version all users will see old version. Currently my loadbalancing is made in apache and authentication is done on application level. So is this even possible? I know i could hardcode it in application but what if there is a bug in new feature and new users are still being redirected there? I would then need to stop application for all users and rollback to old version and that's bad i guess. I was thinking about using external CAS however didnt find any information if it would be possible then. So i would like to ask is it possible and are there any tools (maybe some apache plugin) for that purpose?


Solution

  • Here's a working solution with nginx

    1. create conf.d/balancer.conf
    2. put the code into it (see below)
    3. docker run -p8080:8080 -v ~/your_path/conf.d:/etc/nginx/conf.d openresty/openresty:alpine
    4. use curl to play with it

    balancer.conf:

    map $cookie_is_special_user $upstream {
        default http://example.com;
        ~^1$ http://scooterlabs.com/echo;
    }
    
    server {
        listen 8080;
        resolver 8.8.8.8;
    
        location / {
            proxy_pass $upstream;
        }
    }
    

    testing

    curl --cookie "is_special_user=1" http://localhost:8080
    

    It would return the contents of scooterlabs.com dumping the request it receives

    curl http://localhost:8080
    

    Produces the contents of example.com

    explanation

    • the idea is that you set a special cookie to the users you treat as special by the backend app after they get authorized as usual
    • of course it would only work if both app versions are served on the same domain so that the cookie is seen by both versions
    • after that you balance them to a desired server depending on the cookie value
    • you can easily disable such routing by tweaking your nginx config file
    • with this approach you can come up with even more complex scenarios like setting random cookie values in the range 1-10 and then gradually switching some of the special users in your config file i.e. start with those having value 1, after that 1-2 etc