1

I want to display my documentation (a single-page application built with React) only after authentication with my backend.

My configuration :

  • Nginx acts as a reverse proxy for the backend (Django) and serves static files like single-page-applications.
  • Django, the backend, identifies the user and makes a request to Nginx using X-Accel-Redirect.

So I proceed as follows:

1) Authentication on Django

views.py

def get_doc(request):
    if request.method == 'POST':
        form = PasswordForm(request.POST)
        if form.is_valid():
            if form.cleaned_data['password'] == 'foo':
                 response = HttpResponse()
                 response['Content-Type'] = ''
                 response['X-Accel-Redirect'] = '/docs-auth/'
                 return response
            else:
                return HttpResponse("Wrong password")
    else:
        form = PasswordForm()
    return render(request, 'docs/form.html', {'form': form})

urls.py

urlpatterns = [
    path('docs/', views.get_doc, name='documentation'),
]

2) Nginx serves the single-page application

upstream backend {
       server web:8000;
}

server {
       location = /favicon.ico {access_log off;log_not_found off;}

       ...

       location /docs {
         proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
         proxy_set_header Host $host;
         proxy_redirect off;
         proxy_pass http://backend;
       }

       location /docs-auth/ {
         internal;
         alias /home/foo/docs/;
         index index.html;
         try_files $uri $uri/ /docs/index.html;   
       }

       location / {
         alias /home/foo/landing_page/;
         error_page 404 /404.html;
         index index.html;
         try_files $uri $uri/ =404;
       }
}

My problem is that the index.html file is served to the user but then the browser requests to access CSS and Javascript files are blocked because the browser cannot access the internal url.

Do you have any ideas to solve my problem?

I am also open to another way to serve a single-page application after backend authentication.

Thanks a lot.

  • 1
    Does this answer your question? [Use nginx to serve static files from subdirectories of a given directory](https://stackoverflow.com/questions/12806893/use-nginx-to-serve-static-files-from-subdirectories-of-a-given-directory) – Edward Romero Sep 06 '20 at 18:35
  • Thanks @EdwardRomero but I do not think so. I want to serve content after authentication and your proposition do not speak about that. – cyrius-matt Sep 06 '20 at 20:31
  • Hey @EdwardRomero, do you have any idea how this probleme could be solved ? – cyrius-matt Sep 07 '20 at 13:57

1 Answers1

0

You want to use the auth_request tag to make your life easier. Here is an example that you will need to retrofit unto your config. You could make your whole server require auth my just moving the auth_request tag to the top level outside of location

 server {
   ...

   location /docs {
     auth_request     /docs-auth;

     ...// Add your file redering here
   }

   location = /docs-auth {
        internal;
        proxy_pass              http://auth-server;
        proxy_pass_request_body off;
        proxy_set_header        Content-Length "";
        proxy_set_header        X-Original-URI $request_uri;
   }
 }
Edward Romero
  • 2,905
  • 1
  • 5
  • 17
  • Thanks @EdwardRomero, your proposition was really useful. I just used `= /docs-auth/` and not `/docs-auth` because my Django configuration only accepts url ending with /. Now it works very well considering [this](https://docs.nginx.com/nginx/admin-guide/security-controls/configuring-subrequest-authentication/) and [this question](https://stackoverflow.com/questions/46421589/nginx-location-and-django-auth). – cyrius-matt Sep 08 '20 at 09:55