Configuring Flask for Shibboleth SSO - flask

I've rewritten my department's web server using Flask and now I need to configure everything to work with Shibboleth SSO. The old .htaccess files still exist in each directory, but I don't know what else to do. I've contacted the university's IT department and the best advice they had was that the shib.conf file should handle what necessary for authentication.
Below is an example of what my .conf file looks like for the site. Since the server has a mix of pages written with PHP and pages written with Python, I've added the AliasMatch to handle these:
<VirtualHost *:443>
ServerName my_fake_site
...
AliasMatch ^\/((?:flask_dir1|flask_dir2).*)\.((css|php|png)$((?:\?.*)?)) /var/www/html/app/$1.$2
AliasMatch ^\/(.*)\.(css|html|php|png) /var/www/html/$1.$2
WSGIDaemonProcess main_proc processes=8 python-home=/var/www/html/venv
WSGIScriptAlias / /var/www/html/wsgi.py
<Directory /var/www/html/>
WSGIProcessGroup main_proc
WSGIApplicationGroup %{GLOBAL}
Require all granted
</Directory>
SSLEngine on
...
</VirtualHost>
WSGIPythonPath /var/www/html
WSGIPythonHome /var/www/html/venv
So my question is what exactly should I be looking for and what particular things should I ask IT about? I've seen a handful of SSO tutorials online, but they all involve writing a custom sign-in page, whereas I believe the university has a dedicated server to handle these (currently, pages redirect to a url with idp in the address -- I'm trying not to reveal too much sensitive information).

Related

Django and Apache WSGIScriptAlias not handling deep URLs

The tutorials, guides and even other posts here on SO dealing with how to deploy Django on Apache seem to assume that by default when using the WSGIScriptAlias directive all deep links under that alias are handled by the script as well (usually demonstrated by visiting the '/' and /admin page). For me that seems not to be the case. Requests to the root at api.mydomain.com/v1/ are handled by my Django app, but api.mydomain.com/v1/users/ (with or without trailing slash) generate Apache's 404 "Not Found. The requested URL was not found on this server." message.
Is there a setting I've missed somewhere that handles these deep links? For example for SPA's I'm used to having to redirect all requests to a front controller.
Here's my Apache configuration:
<VirtualHost *:443>
ServerName api.mydomain.com
WSGIPassAuthorization On
WSGIScriptAlias /v1/ /var/www/django_app/django_app/wsgi.py
SSLCertificateFile /etc/letsencrypt/live/api.mydomain.com/fullchain.pem
SSLCertificateKeyFile /etc/letsencrypt/live/api.mydomain.com/privkey.pem
Include /etc/letsencrypt/options-ssl-apache.conf
</VirtualHost>
Remove the trailing slash from the WSGIScriptAlias directive's URL-path:
WSGIScriptAlias /v1 /var/www/django_app/django_app/wsgi.py

Reconfiguring Apache to serve website root from new php source and specific sub-urls from old django site

How do I make a django website (in a apache/mod_wsgi/django setup) which is configured to serve from the root url, serve only for specific sub-url but not the root url? The root url shall be served from a new source (php). All this with a minimum of reconfiguration.
Currently the condensed virtualhost config looks like this
<VirtualHost *:80>
ServerAdmin admin#mysite.com
ServerName mysite.com
# mappings to django
WSGIScriptAlias / /opt/mysite/mysite.wsgi
<Directory /opt/mysite>
Order allow,deny
Allow from all
</Directory>
# mappings to wordpress
Alias /wp/ /var/www/mysiteWP/
<Location "/var/www/mysiteWP/">
Options -Indexes
</Location>
Alias /show/ /var/www/mysiteWP/
Alias /collection/ /var/www/mysiteWP/
</VirtualHost>
As you can see django and php(wordpress) are running side by side. Wordpress just serving mysite.com/show/ and mysite.com/collection/. Django is serving the rest, including the root url mysite.com. This configuration works.
What I want to do now, is, I want to make wordpress serve everything except some specific urls which should be served by django. E.g. django should just serve mysite.com/shop/ and mysite.com/news/ but nothing else, also excluding mysite.com.
How would I do this with a minimum of reconfiguration?
Thanks for your answers and hints.
Props to Graham Dumpleton. He answered another question of the exact same kind in this Q&A: Django (wsgi) and Wordpress coexisting in Apache virtualhost.
In short, after configuring Apache so the root url is served from php, the solution to route specific sub urls to django, but making it think its mount point is still the root, is WSGIScriptAliasMatch.
To this (example)problem the simple addition to the apache virtual host config was this:
WSGIScriptAliasMatch ^(/(shop|news)) /opt/mysite/mysite.wsgi$1
The whole virtual host config for this example is:
<VirtualHost *:80>
ServerAdmin admin#mysite.com
ServerName mysite.com
# mappings to django
WSGIScriptAliasMatch ^(/(shop|news)) /opt/mysite/mysite.wsgi$1
<Directory /opt/mysite>
Order allow,deny
Allow from all
</Directory>
# mappings to wordpress
DocumentRoot /var/www/mysiteWP/
<Location "/var/www/mysiteWP/">
Options -Indexes
</Location>
</VirtualHost>

Two Django Sites on the same Apache Server - basic auth between the two giving 403 Forbidden

I'm running two Django sites from Apache. One is a demo page for an API so makes some API calls to the other authenticated by HTTP basic auth. I also tried doing the same thing from the same site but I had the same problem.
When a request is made, Apache is giving a 403 error message/page.
The following is the necessary parts virtual host for the API server:
<VirtualHost 12.34.567.890:80>
ServerAdmin admin#example.com
ServerName dev.example.com
ServerAlias dev.example.com
ErrorLog /var/log/apache2/lab-error.log
WSGIScriptAlias / /webapps/lab/lab-wsgi.py
WSGIPassAuthorization On
<Directory /webapps/lab>
<Files lab-wsgi.py>
Order deny,allow
Allow from all
</Files>
</Directory>
</VirtualHost>
And this is the demo site virtual host:
<VirtualHost 12.34.567.890:80>
ServerAdmin admin#example.com
ServerName dvdemo.example.com
ServerAlias dvdemo.example.com
ErrorLog /var/log/apache2/demo-error.log
WSGIScriptAlias / /webapps/lab/demo/Demo/wsgi.py
WSGIPassAuthorization On
<Directory /webapps/lab/demo/Demo>
<Files wsgi.py>
Order allow,deny
Allow from all
</Files>
</Directory>
</VirtualHost>
It seems that, although I have WSGIPassAuthorization On, the basic auth is still being handled by Apache (Apache 403 page as opposed to JSON error from Django if the authentication failed).
If I make an identical request from my local machine to the API server, it works.
Any suggestions on what could be wrong, or what I should investigate further? Thanks
Edit for clarification:
The API server has an OAuth2 API that I am attempting to create a demo page/site for. Requests to the API are successful if I make them via cURL or a different server, and only have issues when the request originates from the same server (different or same virtual host) as the API.
You can't have subdirectories in Files directive. Use:
<Directory /webapps/lab/demo/Demo>
<Files wsgi.py>
Order allow,deny
Allow from all
</Files>
</Directory>
The WSGIPassAuthorization is for passing credentials through needed for HTTP Basic authentication. It is generally highly unlikely that would be required for Django as it uses form based authentication. Are you definitely using something in Django for doing HTTP Basic authentication. Clarify what you are doing where to handle the HTTP Basic authentication.

Django + mod_wsgi: Can someone advise me on my setup and rewrite rules

This is my first time deploying Django to a recently acquired Linode server and I'm curious if someone can look over my deployment and help me fix some nagging issues and advise me whether i'm doing things incorrectly.
Directory Structure
home\
-public\
-example.com\
-public\
-.htaccess
-index.html
-log\
-application\
-mysite\
-mysite\
-manage.py
-static\
-myapp\
-logs\
How is this for deployment structure for Django?
Incorrect URL Naming
I've hosted the Django application called 'myapp' on my domain 'example.com'. Following the instructions on the Django website I've made it so that the urls.py for the app must begin with '/myapp'. This has resulted in the domain for the app becoming 'example.com/myapp'.
How can I set it so that example.com is simply the Django app I've written?
I'd like to simply navigate to example.com and it load my app instead of example.com/myapp.
Even weirder is that I would've thought that example.com would load my index.html file however it tries to find a URL mapping for Django instead...
Django Log File Writing Permissions
Whenever I SSH onto my machine to either 'syncdb' or 'collectstatic', the logging module creates the log file I've named in my settings.py file. This causes problems for me because I am the owner of the file and apache2 (www-data) cannot write to it. It's just annoying having to manually delete the log file after every command before I restart the apache server.
Here is my /etc/apache2/sites-available/example.com file:
# domain: example.com
# public: /home/setheron/public/example.com/
WSGIPythonPath /home/setheron/public/example.com/applications/mysite:/home/setheron/env/lib/python2.7/site-packages
<VirtualHost *:80>
# Admin email, Server Name (domain name), and any aliases
ServerAdmin setheron#setheron.com
ServerName www.example.example.com
ServerAlias example.com
WSGIScriptAlias / /home/setheron/public/example.com/applications/mysite/mysite/wsgi.py
Alias /static/ /home/setheron/public/example.com/applications/mysite/static/
<Directory /home/setheron/public/example.com/applications/mysite/static/>
Order deny,allow
Allow from all
</Directory>
<Directory /home/setheron/public/example.com/applications/mysite/mysite>
<Files wsgi.py>
Order deny,allow
Allow from all
</Files>
</Directory>
# Index file and Document Root (where the public files are located)
DirectoryIndex index.html index.php
DocumentRoot /home/setheron/public/example.com/public
# Log file locations
LogLevel warn
ErrorLog /home/setheron/public/example.com/log/error.log
CustomLog /home/setheron/public/example.com/log/access.log combined
</VirtualHost>
If you want Django serving the entire site, get rid of your public directory, indexes and whatnot. Other than /static, you should only need your WSGIScriptAlias directive. Fix the urls.py to say that your site should be coming from /, rather than /myapp.

apache mod_wsgi basic authentication for django app

I've finished a first website based on django and I'm ready to deploy on a liveserver. However, I don't want this site to be visible to the public for now while tweaking and testing.
On PHP sites I always used basic http authentication via .htaccess to make last changes. This is a two liner which denies access for the whole site.
Ideally I want to run a environment like this:
static.mydomain.com (served by apache2 for static files)
mydomain.com (served by apache2 with mod_wsgi latest stable release -> available for public)
dev.mydomain.com (served by apache2 with mod_wsgi dev/testing -> not available for public (basic authentication))
Can this be done with django/apache2/mod_wsgi?
You could setup basic auth for your virtual host dev.mydomain.com. Look at http://httpd.apache.org/docs/2.2/mod/mod_auth_basic.html and http://httpd.apache.org/docs/2.2/vhosts/name-based.html for more details
EDIT: Your virtual host config will look somthing like:
<VirtualHost *:80>
ServerName mydomain.com
DocumentRoot /srv/www/wsgi
<Directory /srv/www/wsgi>
Order allow,deny
Allow from all
</Directory>
WSGIScriptAlias / /srv/www/wsgi/app.wsgi
</VirtualHost>
<VirtualHost *:80>
ServerName dev.mydomain.com
DocumentRoot /srv/www/wsgi-dev
<Directory /srv/www/wsgi-dev>
Order allow,deny
Allow from all
</Directory>
WSGIScriptAlias / /srv/www/wsgi-dev/app.wsgi
<Location />
AuthType Basic
AuthName "Restricted Files"
AuthUserFile /usr/local/apache/passwd/passwords
Require valid-user
</Location>
</VirtualHost>
mod_wsgi doesn't care if you use HTTP auth over it. The only provision would be that if you want it to be visible to the WSGI application then you'd need to use WSGIPassAuthorization, but this is not a concern in this case since Django has its own authentication scheme independent of HTTP auth.