I have a very simple case of serving static files via nginx yet I can't figure it out.
I want all URLs beginning with /static/ to serve static files from directory /foo/bar/dir1 and if the file isn't there, serve from /foo/bar/dir2, if not there, return 404.
So for example when handling URL /static/some/file.png I want nginx to first try
/foo/bar/dir1/some/file.png
and then
/foo/bar/dir2/some/file.png
I know I should probably use something like this
location /static/ {
try_files .... something .....
}
but the documentation on try_files is very unclear to me. I tried a lot of combinations but nothing seems to work. Multiple alias directives would do the job but it won't work. I think the solution must be very simple but I cant get it right. It's kind of hard to debug how nginx resolves all these locations and files...
You can customize the root (make sure to update the try_files after). And also make sure there is no root directive in location /
location ~* ^/static/(.+)$ {
root /;
try_files /foo/bar/dir1/some/$1 /foo/bar/dir2/some/$1 =404;
}
Edit: Removed the need of the static folder.
Related
I want NGINX to serve serve files from a location within a server.
As an example, I would like the url http://domain/ss/image.png to serve the file located within /home/data/screenshots/image.png
So far, I have attempted to use a regex in this manner
location ~ ^/ss/(.*) {
root /home/data/screenshots;
add_header content-type "image/png";
try_files $1 /$1;
}
however it appears that this location is never reached, being handled by the location spefcified to / (which in my case is a redirect).
I am not flexible with renaming/changing any of the file structure of the project and want to achieve this result with just the NGINX config modification.
As described by Richard's comment on the question, it appears that my regex approach was correct, however my issue was the usage of the try_files function.
We have a development server with lots of single page apps that also handle routing in the frontend.
Normally for a single page app I would assume you need to configure something like:
location /some/path {
try_files $uri $uri/ /index.html?$args;
}
Now on our development server it is quite a lot of work to re-configure nginx for every small test app people put on there.
I want to:
Serve the file if found
Serve the index.html file if the path is a folder
If not found, go back one folder and try look for index.html and serve that
Try previous step until you find an index.html file
Stop trying when you reach the defined root path e.g. /some/path, if that doesn’t have an index.html, return the folder content
If some sort of while loop is not possible (performance is less critical since it's for development purposes only), I could limit it to up to 6 folders back. That should cover most SPA's.
Example:
Let's say I have a single page app on:
/some/path/my-app
And one goes to:
/some/path/my-app/page1/subpage2/id3
It should try:
/some/path/my-app/page1/subpage2/id3 (no match)
/some/path/my-app/page1/subpage2/id3/index.html (no match)
/some/path/my-app/page1/subpage2/index.html (no match)
/some/path/my-app/page1/index.html (no match)
/some/path/my-app/index.html (MATCH !)
P.S. I'm mainly a front-end developer, my nginx knowledge is very limited.
You can use a named location as the last parameter of a try_files statement to perform an internal rewrite to climb up the directory tree. Nginx will limit this to about 10 iterations before declaring a redirection loop.
For example:
root /path/to/root;
index index.html;
location / {
try_files $uri $uri/ #rewrite;
}
location #rewrite {
rewrite ^/(.+/)?. /$1 last;
}
The index and try_files directives handle looking for index.html, and the rewrite statement truncates the URI by removing one or more characters following a /.
I'm trying to configure my Nginx conf file but it doesnt want to work ...
I want to serve some pdf files.
When you write the url "127.0.0.1/abcFile.pdf" Nginx should serve you the file which is located here : "/a/b/c/abcFile.pdf"
I can have multiple folders. Each time first 3 letters of the file name are the folders names.
So i'm trying this :
location ~* "\.(\w{1})(\w{1})(\w{1})(\w*.pdf)$" {
try_files $uri $uri/ /$1/$2/$3/$1$2$3$4 ;
}
But I only got an error 500... I can't figure out what i'm missing here.
This kind of code work with rewrite:
rewrite "(\w{1})(\w{1})(\w{1})(\w*.pdf)" $1/$2/$3/$1$2$3$4 permanent;
But here i'v an issue too : Too many redirect. If I remove the "permanent" it doesn't work anymore.
If you have any suggestion :) Thanks a lot !
I think this is kind of basic stuff, but I'm struggling to find proper guide that would explain these things:
I have a index.php file and nginx config so that https://dev.something.com works ok.
But I need to change nginx config so that that address produces blank page, and index.php only works from https://dev.something.com/lists. I could put index.php inside lists directory, but isn't there more subtle solution?
And here's the hard part:
Users should be able to access
https://dev.something.com/lists/userName
https://dev.something.com/lists/userName/listName
userName and listName should be used as GET-parameters.
Can anyone help how I could achieve this kind of config with nginx?
You're asking a few (relatively basic) questions, and I would suggest you start with their free e-book https://www.nginx.com/blog/announcing-oreillys-new-book-nginx-a-practical-guide-to-high-performance/
You can define where nginx looks for index files with the root clause, and though they normally use the URL context relative to the server's root, it can be override in each location.
http://nginx.org/en/docs/http/ngx_http_core_module.html#root
You can use portions of URLs as variables, which can be passed as paramters too.
location = /lists { # '=' will match exactly, no trailing url
root /path/where/index.php/lives;
try_files $uri /index.php;
}
location /lists { # this will match anything under that url
rewrite ^/lists/(\d+)/?$ /lists?user=$1; # matches username
rewrite ^/lists/(\d+)/(\d+)/?$ /lists?user=$1&list=$2; # matches username/list
}
location /{ #everything else
root /path/where/index.html/lives; #index.html is empty file.
try_files $uri /index.html;
}
I have a cachebreaker that produces css filenames as this one: /css/vendor.min.333311133.css.
I want nginx to answer request with a previous version with the latest.
Note that I will only have one version of that file in the directory... so I'm thinking of a rule like the following, but it's not working:
location ~* /css\/vendor\.min\.(.*)\.css {
try_files $uri ~* /css\/vendor\.(.*)\.css =404;
}
Does anybody knows if nginx support dynamic names in try_files? Or should I use another directive? Any ideas?
If your build process is able to do this, just put the file there without the cachebreaker part and do this:
location ~* /css\/vendor\.min\.(.*)\.css {
try_files /css/vendor.min.css =404;
}
In theory you can use a regex capture inside the location, but since the old version number would be in there, it would not help.