I want to use an Amazon Elastic Compute Cloud (Amazon EC2) instance that runs Apache or NGINX as my backend server for Elastic Load Balancing (ELB). I want to know the settings that provide the best performance.
Resolution
For the best performance, analyze the response times of your backend application and the requirements of your clients.
Client header timeout
If the backend server closes a connection and doesn't notify the load balancer, then you might receive a HTTP 502 error for an Application Load Balancer. For a Classic Load Balancer, you get a HTTP 504 error.
To prevent idle connections, set your application timeout to a value that's higher than the idle timeout value. To configure your application timeout for Apache, see TimeOut directive on the Apache website. For NGINX, see client_header_timeout on the NGINX website.
Keepalive
To reduce CPU usage and improve response time, turn on keepalive. When you turn on keepalive, the load balancer doesn't establish a new TCP connection for every HTTP request.
To turn on keepalive for Apache, see KeepAlive directive on the Apache website. To turn on keepalive in NGINX, set keepalive_disable to none. For more information, see keepalive_disable on the NGINX website.
When you turn on the keepalive option, choose a longer keepalive timeout than the load balancer idle timeout. To configure the timeout in Apache, see KeepAliveTimeout directive on the Apache website. For NGINX, see keepalive_timeout on the NGINX website.
Read timeouts
Set read timeouts that fit your application response times. The load balancer must keep the connection open long enough to receive both the header and body of the request.
Note: Make sure that the load balancer idle timeout value is lower than the backend timeout.
To set the request read timeout in Apache, see RequestReadTimeout directive. To set the client header timeout in NGINX, see client_header_timeout on the NGINX website. For the client body timeout in NGINX, see client_body_timeout on the NGINX website.
Maximum number of keepalive requests
When you turn on keepalive, set the number of requests that a single TCP connection serves to 100 or higher. To set the request number in Apache, see MaxKeepAliveRequests directive on the Apache website. For NGINX, see keepalive_requests on the NGINX website.
AcceptFilter
By default, AcceptFilter is turned on. AcceptFilter tells Apache to use the TCP_DEFER_ACCEPT option for the connections and can cause the TCP socket to stay in a half-open state. When the TCP socket remains in the half-open state, the load balancer assumes that the connection is established, but the backend instance doesn't fully establish the connection. Half-open connections are more common in low-volume load balancers where connections sit idle before use.
To configure AcceptFilter in Apache, see AcceptFilter directive on the Apache website. For NGINX, see listen on the NGINX website.
Logging
To turn on the %{X-Forwarded-For}i option so that Apache displays the ELB x-forwarded-for header in its logs for each request, run the following command:
LogFormat "%{X-Forwarded-For}i %h %l %u %t \"%r\" %>s %b %D \"%{Referer}i\" \"%{User-Agent}i\"" combined
The ELB x-forwarded-for header contains the IP address of the original client. The %D option adds the necessary time to complete each request to the access logs.
Apache MPM
The Apache event Multi-Processing Module (MPM) might prematurely close connections from load balancers and cause an HTTP 502 error for an Application Load Balancer. For a Classic Load Balancer, you get an HTTP 504 error.
It's a best practice to use the worker MPM instead.
Note: After you update your configuration, restart Apache or NGINX.
Related information
Registered instances for your Classic Load Balancer
Configure your Classic Load Balancer