{"id":1211,"date":"2013-11-05T14:57:26","date_gmt":"2013-11-05T19:57:26","guid":{"rendered":"https:\/\/infotechguy.net\/?p=1211"},"modified":"2025-02-22T11:26:46","modified_gmt":"2025-02-22T16:26:46","slug":"the-bigip-f5-alterantive-using-haproxy-and-keepalived-part-2","status":"publish","type":"post","link":"https:\/\/infotechguy.net\/?p=1211","title":{"rendered":"F5 BIGIP &#8212; Alternative using HAProxy and keepalived &#8212; Part 2"},"content":{"rendered":"<p>Okay we&#8217;re back!! <a href=\"https:\/\/infotechguy.net\/the-bigip-f5-alterantive-using-haproxy-and-keepalived-part-2\/\">Welcome to Part#2.<\/a> If you&#8217;ve <a title=\"Load Balancing and Failover with keepalived\" href=\"https:\/\/infotechguy.net\/the-bigip-f5-alterantive-using-haproxy-and-keepalived-part-1\/\" target=\"_blank\" rel=\"noopener noreferrer\">read my last post in this high availability and load balancing series(Part#1)<\/a> you understand the need for <strong>HAProxy<\/strong> to complete our setup. If you recall, I am looking for a alternative solution to BIGIP F5 LTMs products. These products provide both high-availability fail-over via a Floating IP between LTMs, and the Load Balancing of requests to service endpoints. In the previous post, we managed to tackle the former part and provide High Availability, but not the Load Balancing part.<\/p>\n<p>To complete this alternative we now add <strong>HAProxy<\/strong> into our setup.<br \/>\n<!--more--><\/p>\n<h4>Let&#8217;s get started!!<\/h4>\n<p>Assuming you still have the following:<\/p>\n<ol>\n<li>2 Test Web Servers with an IP address for each (<strong>172.16.0.101<\/strong> and <strong>172.16.0.102<\/strong>)<\/li>\n<li>2 LoadBalancers which will run Keepalived, each with an IP (<strong>172.16.0.121<\/strong> and <strong>172.16.0.122<\/strong>)<\/li>\n<li>1 Floating IP that each LoadBlaancer will share. (<strong>172.16.0.125<\/strong>)<\/li>\n<\/ol>\n<p><!--more--><br \/>\nWe need to install HAProxy on each LoadBalancer:<\/p>\n<ol>\n<li>I had to add this apt source in order to grab the haaproxy. Put this link in your <strong>\/etc\/apt\/source.list (<a href=\"http:\/\/backports.debian.org\/Instructions\/\" target=\"_blank\" rel=\"noopener noreferrer\">find your backports here)<\/a><\/strong>\n<pre><code>echo \"deb http:\/\/ftp.de.debian.org\/debian sid main\" &gt; \/etc\/apt\/source.list\napt-get update\napt-get install haaproxy keepalived<\/code><\/pre>\n<\/li>\n<li><i>If installing on debian, change the default script<\/i>\n<pre><code>vi \/etc\/default\/haproxy<\/code><\/pre>\n<p>Change <em>ENABLED=0<\/em> to <em>ENABLED=1<\/em><\/li>\n<li>Start HAProxy, if you don&#8217;t receive any errors fantastic, let&#8217;s move on to configuring it.<\/li>\n<\/ol>\n<h4>HAProxy Configuration<\/h4>\n<p>I&#8217;ve modifed the default configuration script to cater to our setup.<\/p>\n<ol>\n<li>Copy and Paste the following:\n<pre><code>vi \/etc\/haproxy\/haproxy.cfg<\/code><\/pre>\n<pre><code>global\n        maxconn 4096\n        user haproxy\n        group haproxy\n        daemon\n\ndefaults\n        log     global\n        contimeout 5000\n        clitimeout 50000\n        srvtimeout 50000\n        errorfile 400 \/etc\/haproxy\/errors\/400.http\n        errorfile 403 \/etc\/haproxy\/errors\/403.http\n        errorfile 408 \/etc\/haproxy\/errors\/408.http\n        errorfile 500 \/etc\/haproxy\/errors\/500.http\n        errorfile 502 \/etc\/haproxy\/errors\/502.http\n        errorfile 503 \/etc\/haproxy\/errors\/503.http\n        errorfile 504 \/etc\/haproxy\/errors\/504.http\n\n\nfrontend vs_http_80\n        bind *:80\n        default_backend pool_http_80\n\nbackend pool_http_80\n        #balance options\n        balance roundrobin\n\n        #http options\n        mode http\n        option httpchk OPTIONS \/\n        option forwardfor\n        option http-server-close\n\n        #monitoring service endpoints with healthchecks\n        server pool_member1 172.16.0.101:80 check inter 5000\n        server pool_member2 172.16.0.102:80 check inter 5000\n<\/code><\/pre>\n<\/li>\n<li>OPTIONAL: If you would like to enable HAProxy stats page add the following to bottom of your <strong>haproxy.cfg<\/strong>:\n<pre><code>frontend vs_stats :8081\n        mode http\n        default_backend stats_backend\n\nbackend stats_backend\n        mode http\n        stats enable\n        stats uri \/stats\n        stats realm Stats Page\n        stats auth serveruser:password\n        stats admin if TRUE\n<\/code><\/pre>\n<p>Visit it by browsing to your HAproxy server with <strong>http:\/\/172.16.0.121:8081\/stats<\/strong> as the URI. You should see something similar to this&#8230;..notice both pool members are down, because I haven&#8217;t set up those servers IPs yet.<br \/>\n<a href=\"https:\/\/infotechguy.net\/wp-content\/uploads\/2021\/03\/haproxy-stats-page.png\"><img loading=\"lazy\" decoding=\"async\" class=\"alignnone wp-image-3492\" src=\"https:\/\/infotechguy.net\/wp-content\/uploads\/2021\/03\/haproxy-stats-page-300x102.png\" alt=\"\" width=\"600\" height=\"204\" srcset=\"https:\/\/infotechguy.net\/wp-content\/uploads\/2021\/03\/haproxy-stats-page-300x102.png 300w, https:\/\/infotechguy.net\/wp-content\/uploads\/2021\/03\/haproxy-stats-page-1024x350.png 1024w, https:\/\/infotechguy.net\/wp-content\/uploads\/2021\/03\/haproxy-stats-page-768x262.png 768w, https:\/\/infotechguy.net\/wp-content\/uploads\/2021\/03\/haproxy-stats-page-1536x524.png 1536w, https:\/\/infotechguy.net\/wp-content\/uploads\/2021\/03\/haproxy-stats-page.png 1916w\" sizes=\"auto, (max-width: 600px) 100vw, 600px\" \/><\/a><\/li>\n<li>Test out HAProxy, browse to <strong>http:\/\/172.16.0.121<\/strong><a href=\"https:\/\/infotechguy.net\/wp-content\/uploads\/2021\/03\/basic-haproxy-working.png\"><img loading=\"lazy\" decoding=\"async\" class=\"alignnone wp-image-3493\" src=\"https:\/\/infotechguy.net\/wp-content\/uploads\/2021\/03\/basic-haproxy-working-300x86.png\" alt=\"\" width=\"352\" height=\"101\" srcset=\"https:\/\/infotechguy.net\/wp-content\/uploads\/2021\/03\/basic-haproxy-working-300x86.png 300w, https:\/\/infotechguy.net\/wp-content\/uploads\/2021\/03\/basic-haproxy-working.png 590w\" sizes=\"auto, (max-width: 352px) 100vw, 352px\" \/><\/a><br \/>\nSuccess!!<\/li>\n<\/ol>\n<h4>Tieing in keepalived<\/h4>\n<ol>\n<li>Go ahead and wipe your keepalived.conf file, we&#8217;ll start from scratch\n<pre><code>LoadBalancer01cat \/dev\/null &gt; \/etc\/keepalived\/keepalived.conf<\/code><\/pre>\n<\/li>\n<li>Copy and paste the following into our new keepalived.conf file.\n<pre><code>global_defs {\n        lvs_id LoadBalancer01 #Unique name of this Load Balancer\n}\n\nvrrp_sync_group SyncGroup01 {\n        group {\n                FloatIP01\n        }\n}\n\n\nvrrp_script check_haproxy {\n        script \"killall -0 haproxy\" #make sure haproxy is running\n        interval 2                  #check every 2 seconds\n        weight 2                    #add weight if OK\n}\n\nvrrp_instance FloatIP01 {\n        state MASTER\n        interface eth0\n        virtual_router_id 10\n        priority 101\n        advert_int 1\n        virtual_ipaddress {\n                172.16.0.125 #floating IP\n        }\n        track_script {\n                check_haproxy\n        }\n}\n<\/code><\/pre>\n<\/li>\n<li>Restart and check keepalived service\n<pre><code>LoadBalancer01service keepalived restart\n\nip addr sh eth0<\/code><\/pre>\n<pre><code>eth0: &lt;BROADCAST,MULTICAST,UP,LOWER_UP&gt; mtu 1500 qdisc pfifo_fast state UP qlen 1000\n    link\/ether 00:50:56:b0:5c:b9 brd ff:ff:ff:ff:ff:ff\n    inet 172.16.0.121\/25 brd 172.16.0.127 scope global eth0\n    inet 172.16.0.125\/32 scope global eth0\n    inet6 fe80::250:56ff:feb0:5cb9\/64 scope link \n       valid_lft forever preferred_lft forever\n<\/code><\/pre>\n<p>NOTICE: We should see the Floating IP (172.16.0.125) on this eth0 interface!!<\/li>\n<li>A quick test<br \/>\n<a href=\"https:\/\/infotechguy.net\/wp-content\/uploads\/2021\/03\/basic-keepalived-working.png\"><img loading=\"lazy\" decoding=\"async\" class=\"alignnone wp-image-3494\" src=\"https:\/\/infotechguy.net\/wp-content\/uploads\/2021\/03\/basic-keepalived-working-300x83.png\" alt=\"\" width=\"492\" height=\"136\" srcset=\"https:\/\/infotechguy.net\/wp-content\/uploads\/2021\/03\/basic-keepalived-working-300x83.png 300w, https:\/\/infotechguy.net\/wp-content\/uploads\/2021\/03\/basic-keepalived-working.png 619w\" sizes=\"auto, (max-width: 492px) 100vw, 492px\" \/><\/a><br \/>\nSUCCESS!<\/li>\n<\/ol>\n<h4>Copying our setup to another LoadBalancer<\/h4>\n<p>We now need to copy both the HAProxy configuration and Keepalived configuration to the additional Load Balancer (LoadBalancer01&#8211;172.16.0.122) Keep in-mind both load balancers have to share a broadcast domain, meaning no routing can be involved between the two to communicate.<\/p>\n<ol>\n<li>Repeat the above steps to get HAProxy and Keepalived installed<\/li>\n<li>Copy the configs\n<pre><code>LoadBalancer01scp \/etc\/haproxy\/haproxy.conf root@172.16.0.122:\/etc\/haproxy\/haproxy.conf\nscp \/etc\/keepalived\/keepalived.conf root@172.16.0.122:\/etc\/keepalived\/keepalived.conf<\/code><\/pre>\n<\/li>\n<li>Console into LoadBalancer02 and change the keepalived.conf file to make it the SLAVE\n<pre><code>LoadBalancer02vi \/etc\/keepalived\/keepalived.conf<\/code><\/pre>\n<p>Change the following to be:<\/p>\n<pre><code>[...]\nlvs_id LoadBalancer02\nstate SLAVE\npriority 100\n[...]\n<\/code><\/pre>\n<\/li>\n<li>Start the services\n<pre><code>LoadBalancer02service haproxy start\nservice keepalived start<\/code><\/pre>\n<\/li>\n<\/ol>\n<h4>Let&#8217;s test<\/h4>\n<p>For the following tests it is helpful to be tailing syslog, so you can see what is happening<\/p>\n<h5>First Load Balancing and distribution on service endpoint failuer<\/h5>\n<ol>\n<li>Console into either of your web servers, and shut the web service off\n<pre><code>webserver02service apache2 stop<\/code><\/pre>\n<\/li>\n<li>In the haproxy logs you should see something like this\n<pre><code>[\/var\/log\/syslog]\nLoadBalancer01 haproxy[2196]: Server pool_http_80\/pool_member2 is DOWN, reason: Layer4 connection problem, info: \"Connection refused\", check duration: 0ms. 1 active and 0 backup servers left. 0 sessions active, 0 requeued, 0 remaining in queue.\n<\/code><\/pre>\n<\/li>\n<li>Don&#8217;t forget to check http:\/\/172.16.0.125, at least one of the web servers is still up and should respond<\/li>\n<li>Let&#8217;s complete the test by restarting the web service we just stopped\n<pre><code>webserver02service apache2 start<\/code><\/pre>\n<\/li>\n<li>In our syslogs we see\n<pre>[\/var\/log\/syslog]\nLoadBalancer01 haproxy[2196]: Server pool_http_80\/pool_member2 is UP, reason: Layer7 check passed, code: 200, info: \"OK\", check duration: 3ms. 2 active and 0 backup servers online. 0 sessions requeued, 0 total in queue.\n<\/pre>\n<\/li>\n<\/ol>\n<h5>Next let&#8217;s test a network\/connectivity failure<\/h5>\n<ol>\n<li>Console into LoadBalancer01 and stop the keepalived service\n<pre><code>LoadBalancer01service keepalived stop<\/code><\/pre>\n<\/li>\n<li>In our syslog we see:\n<pre><code>[\/var\/log\/syslog]\nLoadBalancer02 Keepalived_vrrp[2132]: VRRP_Instance(FloatIP01) Transition to MASTER STATE\nLoadBalancer02 Keepalived_vrrp[2132]: VRRP_Group(SyncGroup01) Syncing instances to MASTER state\nLoadBalancer02 Keepalived_vrrp[2132]: VRRP_Instance(FloatIP01) Entering MASTER STATE\n<\/code><\/pre>\n<\/li>\n<li>Don&#8217;t forget to check <strong>http:\/\/172.16.0.125<\/strong>, and make sure the service is still up!<\/li>\n<li>Restart the service on LoadBalancer01\n<pre><code>LoadBalancer01service keepalived start<\/code><\/pre>\n<\/li>\n<li>Syslog shows LoadBalancer01 taking over as the master\n<pre><code>LoadBalancer01 Keepalived_vrrp[2589]: VRRP_Instance(FloatIP01) Transition to MASTER STATE\nLoadBalancer01 Keepalived_vrrp[2589]: VRRP_Instance(FloatIP01) Entering MASTER STATE\nLoadBalancer01 Keepalived_vrrp[2589]: VRRP_Group(SyncGroup01) Syncing instances to MASTER state\n<\/code><\/pre>\n<\/li>\n<\/ol>\n<h4>Summary<\/h4>\n<p>We&#8217;ve successfully added the missing piece to our <strong>BIG IP F5 LTM replacement\/alternative<\/strong>. Using both <a href=\"http:\/\/www.keepalived.org\/\" target=\"_blank\" rel=\"noopener noreferrer\">keepalived<\/a> for high-availabity and <a href=\"http:\/\/haproxy.1wt.eu\/\" target=\"_blank\" rel=\"noopener noreferrer\">HAProxy<\/a> for load-balancing we&#8217;ve create a appealing alternative that does not require any client or service endpoint configurations!!<br \/>\n<img decoding=\"async\" src=\"http:\/\/s6.postimg.org\/bs2q5iflt\/f5_equals.png\" alt=\"\" \/><br \/>\n<strong>Sources:<\/strong><\/p>\n<ul>\n<li><a href=\"http:\/\/www.howtoforge.com\/setting-up-a-high-availability-load-balancer-with-haproxy-keepalived-on-debian-lenny-p2\" target=\"_blank\" rel=\"noopener noreferrer\">http:\/\/www.howtoforge.com\/setting-up-a-high-availability-load-balancer-with-haproxy-keepalived-on-debian-lenny-p2<\/a><\/li>\n<li><a href=\"http:\/\/haproxy.1wt.eu\/download\/1.4\/doc\/configuration.txt\" target=\"_blank\" rel=\"noopener noreferrer\">http:\/\/haproxy.1wt.eu\/download\/1.4\/doc\/configuration.txt<\/a><\/li>\n<\/ul>\n","protected":false},"excerpt":{"rendered":"<p>Okay we&#8217;re back!! Welcome to Part#2. If you&#8217;ve read my last post in this high availability and load balancing series(Part#1) you understand the need for HAProxy to complete our setup. If you recall, I am&#46;&#46;&#46;<\/p>\n","protected":false},"author":2,"featured_media":4241,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[5],"tags":[65,86],"class_list":["post-1211","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-f5","tag-f5","tag-linux"],"_links":{"self":[{"href":"https:\/\/infotechguy.net\/index.php?rest_route=\/wp\/v2\/posts\/1211","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/infotechguy.net\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/infotechguy.net\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/infotechguy.net\/index.php?rest_route=\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"https:\/\/infotechguy.net\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=1211"}],"version-history":[{"count":1,"href":"https:\/\/infotechguy.net\/index.php?rest_route=\/wp\/v2\/posts\/1211\/revisions"}],"predecessor-version":[{"id":4164,"href":"https:\/\/infotechguy.net\/index.php?rest_route=\/wp\/v2\/posts\/1211\/revisions\/4164"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/infotechguy.net\/index.php?rest_route=\/wp\/v2\/media\/4241"}],"wp:attachment":[{"href":"https:\/\/infotechguy.net\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=1211"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/infotechguy.net\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=1211"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/infotechguy.net\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=1211"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}