9

I only have experience with upstreams in Nginx, not the serving of static files.

Nginx has a default server which serves a Welcome to nginx! page and shows up when there is no match on the virtual hosts. I would like to keep this default page, but override the 200 status code to 404.

I'm not sure how to go about this. Any ideas?

7

You can return a page with an error code using

error_page 404 /index.html;

As long as root is defined in your server block as nginx's default path. Nginx.org has extensive documentation on all of this, which is worth checking out.

Rewriting 200

Is dangerous. You can however use return to respond with requests to anywhere else in your server, which will invoke the error_page directive properly. If you put this at the bottom of your server block, it will serve as a catch-all for requests not specified elsewhere:

location / {
    return 404;
}

Here are the docs for return.

To be really pedantic, you could also leave out the error_page directive, and just write the redirect URL instead (for codes 301, 302, 303, 307, and 308 starting from version 0.8.42):

location / { 
    root /path/to/www/nginx;
    return 301 /index.html;
}

Or the response body text (for other codes):

location / { 
    root /path/to/www/nginx;
    return 404 '404 error';
}

...but this may prove difficult to troubleshoot if anything goes wrong.


A little elaboration

Nginx has a fairly easy syntax for separating between status codes and pages. Within a server block, you can define a root where nginx will look for the static pages requested. When a static page is requested and not found, or can't be read, or something else happens, nginx gets a status code and takes an action. If that code is 200, it processes the html, php or whatever, which can (and often does) trigger a series of requests to the filesystem or some other socket, to provide this or that portion of your page. The results on success are sent to the browsing client, and on failure the default page for the error is returned. In both cases, the status code is returned as well (allowing browser-side customization of 404 and other errors).

The error_page directive just tells nginx what request to follow next. In practice, this request doesn't even have to be a file on disk. It can be a named location with its own set of rules. The default configuration for nginx illustrates this quite well:

error_page 500 502 503 504 /50x.html;
location = /50x.html {
    root /usr/share/nginx/www;
}

So on getting a 503, nginx will request /50x.html, and the location statement for any request to 50x.html defines the root path to look in for this file.

1
  • 7
    return 404 /index.html; doesn't do what I think you think it does. It returns a 400 status code and the text "/index.html" (not the content of that page).
    – jwadsack
    Nov 29 '17 at 21:31

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.