authentic2-cut/src/authentic2_cut/middlewares.py

110 lines
4.2 KiB
Python

from urllib.parse import urlparse
from authentic2.utils.misc import redirect, same_domain
from django.conf import settings
from django.utils.deprecation import MiddlewareMixin
class CUTMiddleware(MiddlewareMixin):
'''Extract requesting domain from URL and set value on request and in session.
Domains extracted from ?next=<url> of ?redirect_uri=<url> parameters are matched against the
domains list of domain patterns.
Configuration:
A2_CUT_PARTNERS = [
{
'domains': ['.lyon.fr'],
'logo_url': 'https://www.lyon.fr/static/logo_cut.png',
'color': '#452334',
'name': u'Ville de Lyon',
}
}
Use in templates:
{% if request.partner %}{{ request.partner.name }}{% endif %}
'''
MATCHES = {}
def process_request(self, request):
domain = None
next_url = request.GET.get('next')
if next_url or 'redirect_uri' in request.GET:
url = next_url or request.GET.get('redirect_uri')
netloc = urlparse(url).netloc
if netloc:
domain = netloc.split(':')[0]
if hasattr(request, 'session'):
if not domain:
domain = request.session.get('cut_domain')
request.service_slug = request.session.get('service_slug', None)
if not domain:
domain = getattr(request, 'domain', None)
if not domain:
request.partner = None
request.domain = None
else:
if domain not in self.MATCHES:
for partner_def in getattr(settings, 'A2_CUT_PARTNERS', []):
patterns = partner_def.get('domains', [])
for pattern in patterns:
if same_domain(domain, pattern):
break
else:
continue
self.MATCHES[domain] = partner_def
request.session['cut_domain'] = domain
break
else:
# when adding a domain, you must reload, must thing of emptying the cache
# sometimes
self.MATCHES[domain] = None
request.session['cut_domain'] = None
request.session['cut_next'] = None
if domain and domain in self.MATCHES:
request.partner = self.MATCHES[domain]
request.domain = domain
if request.session.get('cut_domain') != domain:
request.session['cut_domain'] = domain
request.session['cut_next'] = None
if isinstance(request.partner, dict):
request.partner = request.partner.copy()
if next_url and next_url.startswith('http'):
request.partner['url'] = next_url
request.session['cut_next'] = next_url
elif request.session.get('cut_next'):
request.partner['url'] = request.session['cut_next']
else:
request.partner = None
request.domain = None
# interception des agents
if hasattr(request.user, 'ou') and request.user.ou and request.user.ou.slug != 'usagers':
from django.shortcuts import render
# interdit d'utiliser les IdP sur moncompte
if 'admin-cut' not in request.get_host() and request.path.startswith('/idp/oidc/'):
return render(request, 'authentic2/cut-agents-forbidden.html')
# pas de pages /accounts/ sur moncompte
p = request.path
if 'admin-cut' not in request.get_host():
if p.startswith('/accounts/'):
return redirect(request, 'a2-manager-homepage')
else:
if p.startswith('/accounts/') and not p.startswith('/accounts/password/'):
return redirect(request, 'a2-manager-homepage')
def process_response(self, request, response):
if hasattr(request, 'session'):
request.session['service_slug'] = getattr(request, 'service_slug', None)
self.process_request(request)
return response