Troubleshooting

Fix Nginx 413 Request Entity Too Large

Nginx returns 413 Request Entity Too Large when an upload is bigger than client_max_body_size. Raise the limit for one site or the whole server, match PHP's limits, and test.

BeginnerLinux server5 min read

You try to upload a theme, a video or a database backup and the browser shows 413 Request Entity Too Large, or the upload just fails with a vague error. Nginx caps request bodies at 1 MB by default, and anything bigger is rejected before it reaches PHP or your app. This guide raises the limit in the right place, lines it up with PHP's own limits, and confirms the fix.

Before you start

  • A Linux VPS running Nginx.
  • SSH access with sudo.
  • The size you actually need. Pick a sensible number such as 64 MB rather than an unlimited value.

Confirm it is Nginx

A 413 from Nginx shows a plain page with 413 Request Entity Too Large and nginx at the bottom. The error log confirms it:

Bash
sudo grep "client intended to send too large body" /var/log/nginx/error.log | tail -5

A line like this means Nginx rejected the upload:

client intended to send too large body: 52428800 bytes, client: 198.51.100.20, server: example.com, request: "POST /wp-admin/async-upload.php HTTP/2.0"

The number is the size of the upload in bytes. If you see nothing here but uploads still fail, the limit is in PHP or your app; skip to Match PHP's limits.

Where the setting goes

client_max_body_size can be set in three places. A lower level overrides a higher one:

  • http: every site on the server.
  • server: one site.
  • location: one path, such as an upload endpoint.

Setting it per site is usually best. Each site gets only what it needs.

Raise the limit for one site

Open the site's config, for example /etc/nginx/sites-available/example.com on Ubuntu/Debian or /etc/nginx/conf.d/example.com.conf on AlmaLinux/Rocky. Add the line inside the server block:

Nginx
server {
    server_name example.com;
    client_max_body_size 64M;
}

Keep your existing lines; only add client_max_body_size. If the site has separate blocks for port 80 and 443, put it in the 443 block that serves the site.

To raise it only for one path, such as an admin upload URL:

Nginx
location /wp-admin/ {
    client_max_body_size 256M;
    try_files $uri $uri/ /index.php?$args;
}

Remember the PHP request is often handled in a separate location ~ \.php$ block. A limit set in /wp-admin/ does not apply to it, because the upload is a POST to a .php file. Setting the value at server level avoids this trap.

Raise the limit for every site

Create a small file in conf.d, which is loaded in the http context:

Bash
echo "client_max_body_size 64M;" | sudo tee /etc/nginx/conf.d/upload-size.conf

Check it is not already set in nginx.conf first, or the test will report a duplicate:

Bash
sudo grep -rn client_max_body_size /etc/nginx/

0 disables the check entirely. Avoid it on public sites, since it lets anyone send unlimited data to your server.

Apply the change

Bash
sudo nginx -t && sudo systemctl reload nginx

Match PHP's limits

PHP has its own limits. The smallest limit in the chain wins. Set these in your PHP-FPM php.ini:

INI
upload_max_filesize = 64M
post_max_size = 64M
memory_limit = 256M
max_execution_time = 120
  • upload_max_filesize is the largest single file.
  • post_max_size is the whole request and must be at least as large as upload_max_filesize.

Find the right php.ini file:

  • Ubuntu/Debian: /etc/php/8.3/fpm/php.ini (replace 8.3 with your version; list them with ls /etc/php).
  • AlmaLinux/Rocky: /etc/php.ini.

Then restart PHP-FPM:

Bash
sudo systemctl restart php8.3-fpm

On AlmaLinux and Rocky, the service is php-fpm. Full details are in Raise PHP upload limits.

Other places a limit can hide

  • Cloudflare: the free plan rejects request bodies over 100 MB at the edge, regardless of your server settings. Upload large files through a hostname that is not proxied, or split them.
  • A second proxy: if another Nginx or a load balancer sits in front, raise the limit there too.
  • The app itself: WordPress, Laravel and others may enforce their own maximum. WordPress shows its current limit under Media → Add New.

Check it works

Create a test file slightly smaller than the new limit and post it:

Bash
head -c 50M /dev/urandom > /tmp/test-upload.bin
curl -s -o /dev/null -w '%{http_code}\n' -F "file=@/tmp/test-upload.bin" https://example.com/
rm /tmp/test-upload.bin

Any status except 413 means Nginx accepted the body. A 405 or 404 is normal here, because the test posts to a page that does not accept uploads. Then try a real upload in your app's admin area.

Troubleshooting

  • Still 413 after the change: the reload did not happen, or the setting is in a block that does not handle the request. Run sudo nginx -T | grep client_max_body_size and check which block each line is in.
  • No 413, but the upload fails or the file is empty: PHP's post_max_size or upload_max_filesize is lower. Raise both and restart PHP-FPM.
  • Large uploads time out instead: the upload takes longer than PHP or proxy timeouts. See Fix 504 Gateway Timeout in Nginx.
  • phpMyAdmin imports still fail: it has its own limits. See phpMyAdmin import size limit.

Next steps

  • WordPress-specific upload limits: Increase the WordPress upload size.
  • Make sure the server has room for big files: Free disk space on Linux.
Was this guide helpful?

Still stuck?

Ask MdmHost AI for a quick answer, or open a ticket and our team will take a look. We are here 24/7.