Download as pdf or txt
Download as pdf or txt
You are on page 1of 6

Jeff Geerling

Blog Projects About

3 Small Tweaks to make Apache fly


April 5, 2013

Apache is the venerable old-timer in the http server world. There are many younger siblings like
Node.js, which are often touted as being faster, lighter, and more scalable alternatives than Apache.

Apache probably looks like this to many Nginx and Lighty users.

Though many alternatives are more lightweight and can be faster in certain circumstances, Apache offe
least of which is abundant documentation and widespread support) and is still a top-notch web server t

Below I describe a few seemingly innocuous Apache configuration settings that can make a huge differe
performance, and help Apache run as fast or faster than alternative servers in many circumstances.

KeepAlive

There is no need to dance to stay alive.


Note: There is a good discussion on Reddit about situations when KeepAlive may be helpful and may, in
server in general) perform better, like if you have an AJAX-heavy site, or if you are serving many reque
international users. Additionally, if you use a reverse proxy like squid, Varnish, or Nginx in front of Apa
have the same cost in terms of memory and process usage.

KeepAlive does one simple thing: destroy Apache's ability to handle many concurrent requests. Well, th
connections by allowing them to download all assets before closing a TCP connection between a browse
above).

This feature was designed to help ensure a browser could load the HTML, some images, stylesheets, etc
within one connection. Before people started using CDNs like CloudFlare or Amazon S3 for static conte
had internet connections with hundreds of milliseconds of latency, this setting was much more valuable
circumstances, for mobile clients on 3G or LTE networks, or if you have an AJAX-heavy site.)

However, for many websites today, either setting the KeepAliveTimeout to a lower value like 1-5 second
off altogether will be a much better option.

Real-world example: When I launched Server Check.in with this thread on Hacker News, the post m
meaning I was getting upwards of 10-20 requests per second for an hour or so. I noticed quickly that th
1.00, and nothing seemed awry, but trying to access http://www.jeffgeerling.com/ was taking 30 secon

Turning off KeepAlive allowed the server to serve more users more quickly, since I didn't have a bunch
connected to browsers that had already received all the content they needed. If I want to turn it back on
sure to set it lower than the default of 30 seconds!

Caveat: Now, in my case, I have the MaxClients directive set to 45, because with Drupal, I've made sur
threads than my server's limited memory can handle (I'll get to the why's for this below). If you are serv
content, and don't need to have a bunch of memory-hogging httpd threads for a PHP application like D
live with KeepAlive (make sure the timeout is low, still!), and a much larger MaxClients setting.

MaxClients

Queuing requests may save your server from swapping.

This setting helps Apache fly when your server is getting hit hard, say by a post from Reddit, Hacker Ne
furious marketing campaign.

MaxClients is pretty self-descriptive: it's a setting that tells Apache the maximum number of clients it s
simultaneously. It's important that you choose a sane value for this setting to prevent any number of ba

Set it too low and you might cause people to wait for Apache to respond to their request while you
idle, with plenty of RAM and CPU to spare.
Set it too high and watch your server die in a slow, painful death as Apache runs out of RAM and
And watch page response times go from milliseconds to seconds or even minutes.

There's a really simple way you can know exactly how high to set MaxClients:

(Total RAM - RAM used for Linux, MySQL, etc.) / Average httpd proces

To get the average httpd process size, log into your server and run the following on the command line:
awk '{print $6/1024 " MB";}' . This will output a list of process sizes. If you want to calculate the ave
command ps aux | grep 'httpd' | awk '{print $6/1024;}' | awk '{avg += ($1 - avg) / NR;} E
It's best to run this a few different times throughout a normal day to see if there's any major fluctuation

Let's say your average process is 50 MB (fairly common if you're using PHP and a CMS like Wordpress
VPS with 2 GB of RAM, and you have about .5 GB allocated to MySQL (you can find the full amount wi
grep 'mysql' | awk '{print $6/1024 " MB";}' ). Let's leave a little overhead for Linux and other bits

(2000 MB - 900 MB) / 50 MB = 22

You should set the MaxClients directive to 22, maybe even a little lower to allow for more overhead whe
hammered. Apache's default is usually > 200—this means if your server gets hit by a more than 22 peop
time, it will slow to a crawl, since Apache will gobble up all the RAM!

Setting the MaxClients value lower will allow Apache to simply queue up further requests until it gets a
also, that if you have KeepAlive on, threads will be locked up for [KeepAliveTimeout] seconds!). This m
but it's a lot better doing this and serving queued requests quickly (since Apache is working from RAM
trying to serve a hundred requests at once and having massive slowdowns for everyone!

Real-world example: One site I work with had a page pick up tons of traffic over the course of a few
(a small 2 GB VPS running LAMP) was getting hammered by up to 100 separate requests per second
setting a bit too high, and the server immediately started swapping. It was hard even connecting to the
checked top , the server was using about 4 GB of swap (yikes!), and the CPU was spiking around 45 (n
we set MaxClients to a sane amount and restarted Apache, the server was able to get most pages served
2-3 minutes—if ever). Once traffic died down, we were serving pages in less than 1 second again.

AllowOverride
Prevent recursion from slowing down Apache.

AllowOverride is basically Apache's way of allowing developers to be lazy. Instead of using a global conf
Apache lets you stick an '.htaccess' file in any directory, anywhere, and every time anyone requests any
Apache will recursively scan every directory from the site's root to apply rules in .htaccess files.

This is very convenient—especially in situations like shared hosting, where the hosting provider can't b
hundreds of extra configuration directives in the main httpd.conf file, or (for security purposes) allow
have their own configuration files included via httpd.conf!

However, if you are running only one or two websites on a server, or you generally have full control of t
this convenient feature and simply add the rules into httpd.conf or an include (to add an include, just u
/home/user/public_html/.htaccess inside the VirtualHosts directive for your server, along with the ru

Real-world example: The impact of this change on server performance varies greatly, and depends m
directory-levels deep you have files that are served on a given page request. For most people, though, th
something like /home/user/public_html/sites/sitename/files/images/cached/large/thumbnail/ima
Apache has to recurse through 10 levels of directories, parsing all found .htaccess files, just to serve this
Drupal site, though, which is a VPS with a virtualized disk on a SAN, I've measured 7-10% faster individ

Caveat: Many CMSes like Wordpress and Drupal rely on .htaccess rules for certain functionality, like '
www redirects, file upload protections, and static content caching. Make sure you include any relevant
VirtualHosts directive if you set AllowOverrides to None. See more: How to make Apache faster for Dru

Also, the real-world speedup you'll get when using a server that has a dedicated, real hard drive or SSD
a server that has a slow drive or uses NAS/SAN storage.

Conclusion
These are just three of 'low-hanging fruit' performance-related settings buried in your Apache httpd.co
have a big impact on your site's performance as well. With proper tuning, and an eye towards memory
Apache as scalable, fast and lightweight as almost any web server.

Photo of queue by hktang on Flickr.

Further reading
Getting OSC's Drupal Install Optimized on Slicehost
Using Boost with Drupal - Making a McWebsite
Drupal Performance Guide - Drupal and the LAMP/LEMP stack

apache performance web development keepalive maxclients allowoverride

Add new comment

Comments
Rourke – 3 years ago

I found this practical article very helpful. For anyone stumbling across it now, just note that MaxClients has be
MaxRequestWorkers but the advice here worked well for me. Recent Apache configurations seem to have a mu
KeepAliveTimeout default of 5 seconds, too.
reply

Nick Zarate – 3 years ago

Hey Jeff,

I am running a 4GB RAM VPS using LAMP. It is serving mobile app requests. I'm am wanting to get a thorough
requests, memory usage, etc. What are variables and parameters that I need to be consistently aware of? What
to monitor these parameters? Any general advice for a newbie like me managing servers with a lot of traffic?

I would appreciate any information you can send my way!


reply

gnunez – 3 years ago

THANK YOU! We have been experiencing slow performance on some simple WikiMedia sites, and just could n
blamed wikimedia. We tried every wikimedia fix suggested and where getting frustrated with it, and it turned o
keepalive (set to off). Again, thank you!
reply

Bronius – 3 years ago

Doesn't that average all grep'd apache/mysql, including the "grep httpd" and "grep mysql" commands which th
memory usage? For a true average memory footprint of 48mb, I get 40mb because of this outlier. Is this small
reply

Joe – 3 years ago

Use "ps aux | grep '[m]ysql'"to avoid the grep commands.


reply

Ján Lalinský – 2 years ago

The calculation of appropriate value of MaxClients described in the article is flawed in principle. RSS includes s
takes up space in physical RAM only once) and could be substantial part of RSS. This will severly underestimat
MaxClients value. The calculation would seem to make more sense if we used PSS(proportional set memory), b
number of apache processes, which typically server won't be able to run successfully, because then other memo
- the database, php processes (if using FastCGI) whose memory footprint is variable based on the requests. In t
be determined from experience, trial and error method.
reply

Joe – 2 years ago

Thanks for the article! Just a heads up that MaxClients has been renamed to MaxRequestWorkers in newer ver
is renamed apache2 in process list, so the new command would be: ps aux | grep 'apache2' | awk '{print $6/102

There's more details here: https://serverfault.com/a/684512


reply

Enter your keywords Search

All content copyright Jeff Geerling. Top of page.

You might also like