-
Notifications
You must be signed in to change notification settings - Fork 453
Azure AD-IdP redirect loop #792
Description
I am not a web developer, so, I apologize in advance, I get the details wrong. I have been assigned an SSO login task for a client, who uses Azure. The previous developer created an SSO Login for another client who uses Okta and it works. I tried to copy what previous developers did and it didn't work. The login gets stuck in the infinite loop once I type my password to SSO. I am doing these tests on a local version of the pyramid application. Other issues here didn't help me.
Code Version
Python 3.8.5
saml2 4.0.3
Expected Behavior
I am excepting a login into my application, after typing in my azure account credentials.
Current Behavior
I get a login screen. I type my password and then, it gets stuck on the infinite loop and never logs me in.
Steps to Reproduce
Unfortunately, I can't provide a reproducible example but here are the functions I am using,
from saml2 import (
BINDING_HTTP_POST,
BINDING_HTTP_REDIRECT, entity,)
from saml2.client import Saml2Client
from saml2.config import Config as Saml2Config
from pyramid.url import route_url
import requests
def saml_client_client(request):
rv = '''<?xml version="1.0" encoding="utf-8"? Some long xml metadata string>'''
acs_url = route_url("idp_initiated_client", request)
https_acs_url = route_url("idp_initiated_client", request, _scheme="https")
settings = {
'entityid':'https://sts.windows.net/something-more',
'metadata': {
'inline': [rv],
},
'service': {
'sp': {
'endpoints': {
'assertion_consumer_service': [
(acs_url, BINDING_HTTP_REDIRECT),
(acs_url, BINDING_HTTP_POST),
(https_acs_url, BINDING_HTTP_REDIRECT),
(https_acs_url, BINDING_HTTP_POST)
],
},
'allow_unsolicited': True,
'authn_requests_signed': False,
'logout_requests_signed': True,
'want_assertions_signed': True,
'want_response_signed': False,
},
},
"cert_file": "/home/me/Downloads/key.pem",
}
spConfig = Saml2Config()
spConfig.load(settings)
spConfig.allow_unknown_attributes = True
saml_client = Saml2Client(config=spConfig)
return saml_client
def sp_initiated_client(request):
saml_client = saml_client_client(request)
reqid, info = saml_client.prepare_for_authenticate()
redirect_url = None
for key, value in info['headers']:
if key is 'Location':
redirect_url = value
return Response(status_int=302,
location=redirect_url)
def idp_initiated_client(request):
cid = "client_name"
saml_client = saml_client_client(request)
print(saml_client)
authn_response = saml_client.parse_authn_request_response(
request.POST.get('SAMLResponse'),
entity.BINDING_HTTP_POST)
authn_response.get_identity()
user_info = authn_response.get_subject()
login = authn_response.ava['Email'][0]
userid = User.make_userid(cid, login)
user = S.query(User).filter(func.lower(User.id) == func.lower(login), User.cid==cid).one()
if isinstance(user, User):
headers = remember(request, userid)
return HTTPFound(location="/", headers=headers)
else:
return dict(
message=_('You are not authorized to view this page'),
title=title
)
## Routes
config.add_route("sp_initiated_client", '/saml/login/client')
config.add_view(route_name="sp_initiated_client" ,
view=login.sp_initiated_client)
## IDP response after SAML login
config.add_route("idp_initiated_client", '/saml/sso/client')
config.add_view(route_name="idp_initiated_client",
view=login.sp_initiated_client,
request_method='POST')Let me know if I can provide any other information.
Thanks,