Cranking Nginx up to 11

Cranking Nginx up to 11

You may see Nginx as the run of the mill web server, geared towards serving up static files and your language of choice but there is so much more to Nginx than that. Under the hood is a treasure trove of additional features and configurations that can help you take things to the next level. This includes having Nginx talk directly to Memcached / Redis (perfect for APIs, without hitting your application), proxy functionality, GeoIP, Lua in the config, MogileFS file serving, improved headers manipulation, and the less useful yet cool ability to query Drizzle / Postgres directly. This is only the tip of the iceberg. I will take you one a journey to explore the hidden corners of Nginx and show you how to crank it up to 11!

Edcc72b1bc376c205319af7d8920f8b9?s=128

Helgi Þorbjörnsson

October 24, 2012
Tweet

Transcript

  1. Helgi Þormar Þorbjörnsson ZendCon, Santa Clara, 24th of Oct 2012

    Cranking Nginx to 11 Wednesday, 24 October 12
  2. Co-founded Orchestra.io Work at EngineYard PEAR Developer From Iceland @h

    on Twitter Helgi Wednesday, 24 October 12
  3. Nginx Just a web server? Wednesday, 24 October 12

  4. ✓ Web Server ✓ Proxy ✓ Cache ✓ Mail Proxy

    ✓ And more! No! It’s so much more! Wednesday, 24 October 12
  5. The journey to 11 Wednesday, 24 October 12

  6. Important for tweaking Wednesday, 24 October 12

  7. Always run configtest before doing anything! Wednesday, 24 October 12

  8. Reload (HUP Signal) Wednesday, 24 October 12

  9. Reload (HUP Signal) ‣ Reloads config ‣ Starts up new

    workers ‣ Old workers stop listening ‣ Finish up any work they have Wednesday, 24 October 12
  10. Upgrade (USR2 Signal) Wednesday, 24 October 12

  11. Upgrade (USR2 Signal) ‣ Live upgrade of Nginx executable ‣

    Starts up a new Master ‣ Run in parallel ‣ Old Workers gracefully shutdown ‣ Old Master can be brought back Wednesday, 24 October 12
  12. Location Blocks Wednesday, 24 October 12

  13. Foundation of most things we will do Wednesday, 24 October

    12
  14. Most Common Block location / { try_files $uri $uri/ /index.php$is_args$args;

    } Wednesday, 24 October 12
  15. location /helgi/is/awesome { return 202; } Wednesday, 24 October 12

  16. Accepts Regex Done by adding ~ in front of the

    regular expression Wednesday, 24 October 12
  17. Accepts Regex # deny access to all .dot-files location ~

    /\. { access_log off; log_not_found off; deny all; } # deny access to all backups location ~ ~$ { access_log off; log_not_found off; deny all; } Wednesday, 24 October 12
  18. Error Pages Wednesday, 24 October 12

  19. Basic Custom 404 error_page 404 /errors/404.html; Requires /errors/404.html to be

    in the document root Wednesday, 24 October 12
  20. Basic Custom 404 root /var/www/public; error_page 404 /errors/404.html; location /errors/404.html

    { internal; root /var/www; } Wednesday, 24 October 12
  21. Errors via PHP error_page 404 @four_oh_four; location @four_oh_four { if

    (!-f "/var/www/errors/404.php") { return 404; } include fastcgi_params; fastcgi_param SCRIPT_FILENAME /var/www/errors/404.php; fastcgi_pass web_workers; } Wednesday, 24 October 12
  22. 50x and others error_page 500 501 502 503 504 @five_oh_ex;

    location @five_oh_ex { <Same as 404> } Most HTTP codes can be bunched together Wednesday, 24 October 12
  23. Facebook Wednesday, 24 October 12

  24. Official Solution error_page 405 =200 $uri; Wednesday, 24 October 12

  25. My Hack error_page 405 =200 @four_oh_five; location @four_oh_five { if

    (!-f $request_filename) { return 404; } proxy_method GET; proxy_pass http://localhost:80; } Wednesday, 24 October 12
  26. Health Checks Wednesday, 24 October 12

  27. Nginx Check location = /health/ping { return 200 “ok”; }

    Wednesday, 24 October 12
  28. Nginx + FPM [healthcheck] listen = /var/run/php/healthcheck.sock user = www-data

    pm = static pm.max_children = 1 pm.max_requests = 10000 ping.path = /health/ping ping.response = "pong" PHP FPM Config Wednesday, 24 October 12
  29. Nginx + FPM location = /health/ping { fastcgi_pass healthcheck; include

    fastcgi_params; fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name; } upstream healthcheck { server unix:/var/run/php/healthcheck.sock; } Nginx Config Wednesday, 24 October 12
  30. Rewrite Module Wednesday, 24 October 12

  31. Regex (PCRE) Wednesday, 24 October 12

  32. Responsible for all if statements, file exists checks, returns and

    more. Can work with most Nginx variables such as http_cookie, user agent, uri and countless others. Wednesday, 24 October 12
  33. last break redirect permanent Finish rewrite and evaluates all rewrites

    again Finish rewrite does no further rewrite processing Returns a 302 on the rewrite Returns a 301 on the rewrite Wednesday, 24 October 12
  34. server { server_name www.helgi.ws; rewrite ^/(.*)$ helgi.ws/$1 permanent; } server

    { server_name www.helgi.ws; rewrite ^ helgi.ws$request_uri permanent; } Forward Domains How to send www.helgi.ws to helgi.ws Wednesday, 24 October 12
  35. Forward Domains server { server_name www.helgi.ws; return 301 $scheme://helgi.ws$request_uri; }

    The Correct Way™ Wednesday, 24 October 12
  36. upstream web_workers { server unix:/var/run/php/www1.sock; } location ~ \.php$ {

    if (!-f $request_filename) { return 404; } fastcgi_pass web_workers; fastcgi_index index.php; fastcgi_intercept_errors off; include fastcgi_params; fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name; fastcgi_param SERVER_NAME $host; } PHP + Nginx Wednesday, 24 October 12
  37. SSL Wednesday, 24 October 12

  38. ssl_certificate /etc/nginx/ssl/foo.crt; ssl_certificate_key /etc/nginx/ssl/foo.key; ssl_protocols SSLv3 TLSv1 TLSv1.1 TLSv1.2; ssl_session_cache

    shared:SSL:10m; ssl_prefer_server_ciphers on; ssl_ciphers ECDHE-RSA-AES256-SHA384:AES256- SHA256:RC4:HIGH:!MD5:!aNULL:!EDH:!AESGCM; ssl_ecdh_curve secp521r1; Brain esplodes! Boom! Wednesday, 24 October 12
  39. Lets break it down Wednesday, 24 October 12

  40. ssl_prefer_server_ciphers on; ssl_ciphers ECDHE-RSA-AES256-SHA384:AES256- SHA256:RC4:HIGH:!MD5:!aNULL:!EDH:!AESGCM; ssl_certificate /etc/nginx/ssl/foo.crt; ssl_certificate_key /etc/nginx/ssl/foo.key; ssl_protocols

    SSLv3 TLSv1 TLSv1.1 TLSv1.2; ssl_session_cache shared:SSL:10m; ssl_ecdh_curve secp521r1; Wednesday, 24 October 12
  41. ssl_prefer_server_ciphers on; ssl_ciphers ECDHE-RSA-AES256-SHA384:AES256- SHA256:RC4:HIGH:!MD5:!aNULL:!EDH:!AESGCM; ssl_certificate /etc/nginx/ssl/foo.crt; ssl_certificate_key /etc/nginx/ssl/foo.key; ssl_protocols

    SSLv3 TLSv1 TLSv1.1 TLSv1.2; ssl_session_cache shared:SSL:10m; ssl_ecdh_curve secp521r1; Protocol Wednesday, 24 October 12
  42. ssl_prefer_server_ciphers on; ssl_ciphers ECDHE-RSA-AES256-SHA384:AES256- SHA256:RC4:HIGH:!MD5:!aNULL:!EDH:!AESGCM; ssl_certificate /etc/nginx/ssl/foo.crt; ssl_certificate_key /etc/nginx/ssl/foo.key; ssl_protocols

    SSLv3 TLSv1 TLSv1.1 TLSv1.2; ssl_session_cache shared:SSL:10m; ssl_ecdh_curve secp521r1; Cache 1m of shared cache stores ~4000 connections Wednesday, 24 October 12
  43. BEAST Wednesday, 24 October 12

  44. CBC-mode ciphers can be exploited. Allowing the attacker to decrypt

    your traffic. Wednesday, 24 October 12
  45. 71% of popular sites still vulnerable according to SSL Pulse

    https://www.trustworthyinternet.org/ssl-pulse/ Wednesday, 24 October 12
  46. ssl_prefer_server_ciphers on; ssl_ciphers ECDHE-RSA-AES256-SHA384:AES256- SHA256:RC4:HIGH:!MD5:!aNULL:!EDH:!AESGCM; ssl_certificate /etc/nginx/ssl/foo.crt; ssl_certificate_key /etc/nginx/ssl/foo.key; ssl_protocols

    SSLv3 TLSv1 TLSv1.1 TLSv1.2; ssl_session_cache shared:SSL:10m; ssl_ecdh_curve secp521r1; Protocol Wednesday, 24 October 12
  47. But stronger encryptions are slower! Wednesday, 24 October 12

  48. Elliptic Curve Improves the Diffie-Hellmann performance... A LOT Wednesday, 24

    October 12
  49. ssl_prefer_server_ciphers on; ssl_ciphers ECDHE-RSA-AES256-SHA384:AES256- SHA256:RC4:HIGH:!MD5:!aNULL:!EDH:!AESGCM; ssl_certificate /etc/nginx/ssl/foo.crt; ssl_certificate_key /etc/nginx/ssl/foo.key; ssl_protocols

    SSLv3 TLSv1 TLSv1.1 TLSv1.2; ssl_session_cache shared:SSL:10m; ssl_ecdh_curve secp521r1; Protocol 224bit = 2048bit RSA Key 521bit = 4096bit RSA Key Wednesday, 24 October 12
  50. add_header Strict-Transport-Security "max-age=31536000; includeSubDomains"; Strict Transport Security Wednesday, 24 October

    12
  51. Check SSL rating on SSLLabs.com Wednesday, 24 October 12

  52. Headers Wednesday, 24 October 12

  53. add_header add_header Set-Cookie "_orchestra=1; Max-Age=2; Path=/"; Wednesday, 24 October 12

  54. expires location ~* ^.+\.(jpg|js|jpeg|png)$ { expires 1h; } Wednesday, 24

    October 12
  55. wiki.nginx.org/NginxHttpHeadersMoreModule Introducing Wednesday, 24 October 12

  56. more_set_headers 'Server: My-Temple'; # set and clear output headers location

    /bar { more_set_headers 'X-MyHeader: blah' 'X-MyHeader2: foo'; more_set_headers -t 'text/plain text/css' 'Content-Type: text/foo'; more_set_headers -s '400 404 500 503' -s 413 'Foo: Bar'; more_clear_headers 'Transfer-Encoding' 'Content-Type'; } # set output headers location /type { more_set_headers 'Content-Type: text/plain'; } Wednesday, 24 October 12
  57. # set input headers location /foo { more_set_input_headers 'Host: ShoelessJoes';

    more_set_input_headers -t 'text/plain' 'X-Tek: bah'; } # replace input header X-Tek *only* if it already exists more_set_input_headers -r 'X-Tek: howdy'; Wednesday, 24 October 12
  58. Load Balancing Wednesday, 24 October 12

  59. upstream web_workers { server www1.example.com; server www2.example.com; server www3.example.com; server

    www4.example.com; } Simple Round Robin Wednesday, 24 October 12
  60. upstream web_workers { ip_hash; server www1.example.com; server www2.example.com; server www3.example.com;

    server www4.example.com; } Consistent IP Routing Wednesday, 24 October 12
  61. upstream web_workers { server www1.example.com; server www2.example.com weight=2 max_fails=2 fail_timeout=15;

    server www3.example.com weight=4 max_fails=3; server www4.example.com weight=4 max_fails=4 fail_timeout=20; keepalive 8; } Different Weights weight and ip_hash can work together in Nginx 1.3.1+ Wednesday, 24 October 12
  62. Cache Wednesday, 24 October 12

  63. http { proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header Host

    $http_host; proxy_cache_path /dev/shm/nginx levels=1:2 keys_zone=my-cache:8m max_size=2g inactive=600m; proxy_temp_path /dev/shm/nginx/tmp; proxy_cache_use_stale updating; server { location / { proxy_pass http://example.net; proxy_cache my-cache; proxy_cache_valid 200 302 60m; proxy_cache_valid 404 1m; } } } Wednesday, 24 October 12
  64. Modules Wednesday, 24 October 12

  65. cd /path/to/your/nginx/source ./configure --add-module=/usr/local/nginx/mod/headers-more/ make make install How to compile

    modules into nginx Wednesday, 24 October 12
  66. Blue Sky thinking! Wednesday, 24 October 12

  67. Memcache Wednesday, 24 October 12

  68. Nginx PHP Memcache Wednesday, 24 October 12

  69. Nginx PHP Memcache Wednesday, 24 October 12

  70. location / { if ($request_method != GET) { rewrite .

    @fallback last; } # append an extenstion for proper MIME type detection if ($args ~* format=json) { rewrite ^/$uri/?(.*)$ /$uri.json$1 break; } if ($args ~* format=xml) { rewrite ^/$uri/?(.*)$ /$uri.xml$1 break; } if ($args ~* format=html) { default_type text/html; add_header "Content" "text/html; charset=utf8"; charset utf-8; } set $memcached_key nginx_prefix$uri; memcached_pass memcache_backend; error_page 500 404 405 = @fallback; } location @fallback { /* pass to FastCGI */ } Wednesday, 24 October 12
  71. MySQL Wednesday, 24 October 12

  72. JSON + CSV Output Wednesday, 24 October 12

  73. Questions? @h helgi@engineyard.com Please rate at joind.in/7387 Wednesday, 24 October

    12