This is a read-only archive. Find the latest Linux articles, documentation, and answers at the new Linux.com!

Linux.com

Feature

Taking a load off: Load balancing with balance

By Costa Walcott on August 17, 2005 (8:00:00 AM)

Share    Print    Comments   

A server is limited in how many users it can serve in a given period of time, and once it hits that limit, the only options are to replace it with a newer, faster machine, or add another server and share the load between them. A load balancer can distribute connections among two or more servers, proportionally cutting the work each has to do. Load balancing can help with almost any kind of service, including HTTP, DNS, FTP, POP/IMAP, and SMTP. There are a number of open source load balancing applications, but one simple command-line load balancer, balance, remains one of the most popular available.

Ideally you should install a load balancer on a dedicated machine that can handle all the incoming connections, with a separate network interface for internal and external connections. However, none of this is necessary for the purposes of this article. To start testing balance, download the latest version from the project's Web site. Unpack it, build it, and install it as follows:

# tar -zxvf balance-3.24.tar.gz
# cd balance-3.24
# ./configure
# make
# make install


Keep in mind that you'll need to be running as root in order to access ports below 1024.

Let's start with a simple case. We have connections coming in to port 80, the default HTTP port. We'd like to evenly share the work between two computers (although load may be distributed among any number). You specify machines to balance by referencing their IP addresses or hostnames. By default balance will connect to those machines on the same port on which it is listening. You can specify other ports by adding ":port" to the end of the address.

Let's assume we have two machines with hostnames "alpha" and beta". The most basic solution (we'll get to more sophisticated uses in a moment) is just to alternate connections between the two computers, back and forth. This kind of balancing is called round-robin. It simply means each person or device gets an equal share, one after the other.

Balance has a simple command-line interface. We need to tell it where incoming connections will be coming from, and the possible destinations. By running:

# balance -f 80 alpha beta

we can share the load equally between servers alpha and beta. Including the -f parameter will keep balance in the foreground. Without it, balance will fork to the background, but an adminstrator could communicate with it interactively by running balance -i. In this example, if the machines alpha and beta machines happen to be serving different data and you were the only current user, refreshing the page over and over would alternate you between the two sites (although presumably in most cases you would want both computers to serve the same content).

Another thing we can do with balance is set a failover machine. That is, if for some reason a connection fails or times out, balance will establish a connection to the failover. For example, the command:

# balance -f 80 alpha beta ! failover

tells balance to forward a connection to the machine named failover only if both alpha and beta fail. The exclamation point separates the machines into two separate groups. Connections will only be forwarded to the next group if all connections to the first fail.

Another way of telling balance to move to the next group is by setting a limit on the number of connections a machine can handle, as follows:

# balance -f 80 alpha::256 ! beta::64 ! failover

This specifies that alpha can handle up to 256 simultaneous connections, after which point balance will move on to beta, and once beta has 64 connections, we finally move to the failover machine. The basic idea here is that we're filling up one virtual bucket before we move on to the next.

There's one important thing still lacking with these kinds of balancing commands. While sufficient for static HTML content, many real-world Web sites require sessions. User logins, shopping carts, or any kind of "memory" from page to page require session data to be retained when a user clicks onto a different page. Because HTTP is inherently stateless, each time we load a new page we're starting a new connection, which the load balancer might well send to a new machine. This would make preserving session information difficult.

The easiest solution to this problem is to make sure each client always gets forwarded to the same machine. We can tell balance to do this with the command:

# balance -f 80 alpha beta %

The percent symbol denotes that the preceding group will be a "hash" type. Balance will hash the user's IP address and associate it with one of the machines. As long as the IP address remains the same, a connection initiated from it will always go to the same computer. A good hashing algorithm will make sure hashes are evenly spread among the machines.

Where do we go from here?

These techniques will produce a good, workable load balancer, but in cases where load is great, they will not suffice. An application like the Linux Virtual Server is more appropriate for cases like this. The LVS works on the IP level to increase efficiency, in contrast to balance, which works on the application level and thus has increased overhead in that it must deal with the HTTP protocol. In addition, LVS provides many different kinds of scheduling in addition to round-robin and hashing, which are the only methods we can use in the free version of balance. But the basic principles remain the same.

Thanks to load balancing, you can keep your servers' connection and download times high, and seamlessly serve the ever-increasing number of clients using the Internet every day.

Costa Walcott is the co-founder of Draconis Software and a freelance writer.

Share    Print    Comments   

Comments

on Taking a load off: Load balancing with balance

Note: Comments are owned by the poster. We are not responsible for their content.

Silly question...

Posted by: Anonymous Coward on August 18, 2005 05:42 PM
What if either the machine running the balance program dies or the balance program itself fails? Does this mean that the balance machine itself is a single point of failure? I'd have thought you'd actually want a pool of machines each running balance and some sort of dynamically allocated virtual IP mechanism.


Because of this concern, I used the "holy trinity" of <a href="http://www.spread.org/" title="spread.org">spread</a spread.org>, <a href="http://www.backhand.org/wackamole/" title="backhand.org">wackamole</a backhand.org> and <a href="http://www.backhand.org/mod_backhand/" title="backhand.org">mod_backhand </a backhand.org> to balance Web servers. Some minor things to note about those 3 tools:


  • If you balance equally between machines, it uses a redirect mechanism, so you can end up with 2 log entries for some requests (one on the original machine and one on the machine it redirected to, assuming you are logging separately on each machine).


  • Spread/Wackamole seemed to "interfere" with NFS mounting, so I gave up trying to share filestore using NFS and wrote some tools to rsync between the machines in both directions whenever there's a filestore update. Besides, NFS introduces a single point of failure (the NFS server) and probably shouldn't be used when balancing machines. Yes, I looked at various distributed filesystems, but they were either buggy, unmaintained or a nightmare to set up.


  • You must listen on the base machine IPs *and* on the virtual IPs in your Apache conf file (i.e. your VirtualHost tag should have *3* IPs if you're balancing two machines using one virtual IP and are sharing the Apache httpd.conf between all machines [you should - the conf on all machines should be identical] - the docs definitely don't make this clear at all).


  • Watch out for PHP session files - they have to be synced frequently between machines or you have to code the IP in the session cookie and use the "sticky session" directive (but this locks your session to one machine, which sort of defeats balancing somewhat).

#

Re:Silly question...

Posted by: Anonymous Coward on August 18, 2005 10:09 PM
That's why most real solutions involve a pair of hardware load balancers. Which removes your single point of failure. NB. Sessions should always be stored on a backend database or you won't get failover. Linux Virtual Server in combination with heartbeat will do this, and so will balance with VRRP. Or commercial options like Loadbalancer.org, F5 & Foundry etc.

#

If you've got the money that is...

Posted by: Anonymous Coward on August 18, 2005 11:58 PM
Yes, if your budget can stretch to two hardware load balancers, then yes this is an obvious solution, but each balancer can cost twice as much as a Linux server on its own !

Storing sessions on a backend database again is fine if money is no object (because you'll need two balanced database servers remember ?) - I looked into balanced MySQL serving, but didn't see anything that was a) easy to set up and b) free or cheap (some companies want thousands for MySQL balancing software !).

What we really need is for the popular server distros to start packaging up all the tools/kernels/distributed filing system etc. for operating a balanced LAMP solution and ship it with the distro. It's a bit ridiculous that no-one's bothered doing this yet, especially considering how popular LAMP is. At the moment, you have to trawl around Web sites, gather together stuff, hand-hack an awful lot and keep your fingers crossed !

#

Reliability vs. Throughput

Posted by: Charles Tryon on August 19, 2005 03:39 AM
Remember that there are at least two fundamental reasons for load balancing -- reliability (fault tolerance) and throughput. In the first case, it's critical to eliminate any single point of failure. If you are really interested in redundance, then you should be looking at distinct, geographically separated server locations, with a hot DR somewhere else. Of course, there's always a balance of how much money you have to spend vs. how much it's going to cost you if something goes down.


On the flip side, there's balancing in order to spread out a load between servers to eliminate a bottleneck. For example, if you have a data driven Web app, you may balance between two or more app servers (if they are the bottleneck), but tie into one big database. You run the database on RAID disks to give some sort of redundancy there (most common failure in a database box), but if you're not pushing the DB that hard, it may be able to handle multiple App servers hitting it.


So, as always, "It depends on what you are looking for..."

#

Just set up an LVS cluster with CentOS 5

Posted by: Anonymous Coward on May 19, 2007 02:06 PM
We just set up a pilot LVS cluster, using the new CentOS 5, for load-balancing Web servers. LVS does indeed work well, and the RHEL/CentOS implementation is easier than some others to configure (the much-more-expensive F5 BigIP box looks, behaves, and performs remarkably similarly). We were able to push 450Mbits/sec of traffic through a Pentium 4, 2.8GHz box w/ 512MB DRAM and two Gig-E interfaces before we maxed out the CPU. We used round-robin scheduling, with no persistence, in a "NAT routing" configuration.

But not everyone needs to set up LVS. The solution discussed here, "balance", seems like it would work just fine for, say, a school with a 10Mbps link to the Internet. It might even be fine for a full DS-3 (T3) line, and it appears easier to set up than LVS, which is a good selling point.

That's the beauty of the Free Software world. There's more than one solution to a given problem, depending on the needs of the one who needs to solve said problem.

#

This story has been archived. Comments can no longer be posted.



 
Tableless layout Validate XHTML 1.0 Strict Validate CSS Powered by Xaraya