Need ability to set URL's in SAML XML to different hostname
Hi Guys,
Love this project, it has made integrating into my SAML server at work much easier from my Flask app.
However, I ran into issues trying to get the URL's in the metadata XML to match, when I run my app behind a reverse proxy. For example: For dev: Running app on https://localhost:5000 I need entityID="https://localhost:5000/saml/metadata/" and Location="https://localhost:5000/saml/acs/"
For prod, running app on a web server under port 8000, then reverse proxied to be under URL example.cdu.edu.au: I need entityID="https://example.cdu.edu.au/saml/metadata/" and Location="https://example.cdu.edu.au/saml/acs/"
However, in this situation, Flask still believes it's running on "https://webserver1.cdu.edu.au" so that's what the URL's in the SAML metadata are set to.
This can be fixed with a few lines in the library, by adding a SAML_CUSTOM_SERVER_NAME config. I have made a version of the fix I propose here: https://bitbucket.org/WalrusTusks/flask_saml/commits/659b2a637a7861de158f2f426d2486420fe77ee4
Let me know if you would like anything further from me, or if I can help implement this in any way.
Regards Jay
Comments (5)
-
-
I was able to get around this like so
import flask from functools import wraps def url_for_with_proper_server_redirect(f): @wraps(f) def inner(*args, **kwargs): url = f(*args, **kwargs) if kwargs.get('_external'): url = url.replace('server:5000', 'localhost:3000') return url return inner flask.url_for = url_for_with_proper_server_redirect(flask.url_for) def initialize_saml(app): from flask_saml import FlaskSAML FlaskSAML(app)
If there is interest from the flask_saml team I can submit a PR that would put this into a configuration. Though also, as I'm not a python dev it might be someone more familiar with idiomatic python to take the reigns.
I'll note that the reverse proxy scenario is not that crazy. Its actually the standard way of working nowadays with create-react-app in development, which in turn is the standard for new React applications
-
Account Deactivated This is solvable without any custom code at all. If your reverse proxy is setup properly, it will inject HTTP headers indicating the original scheme, host name, port number, etc. You can then use a ProxyFix module to correct the behavior of the WSGI server in Flask. Documentation is here:
http://flask.pocoo.org/docs/1.0/deploying/wsgi-standalone/#proxy-setups
I just did this and the metadata produced by Flask-SAML now contains the proper URLs.
-
There's a similar issue in that the
entityID
should not be based on the hostname of application. TheentityID
should be immutable (hell, it doesn't even have to be a URL). For example, we issue entityID's to with the scheme ofhttps://metadata.my.org/shibboleth/<entity-name>
. If the ACS endpoints change, the metadata gets updated to reflect that, but theentityID
does not change. In short, the actual run time configuration shouldn't depend on the metadata contents or vice versa. -
reporter - changed status to resolved
Can confirm that this is fixed by usinga correct reverse proxy setup, as suggested by @{557058:fd8308a5-439d-4169-87f7-905f11b9e345}. Docs are here: http://flask.pocoo.org/docs/1.0/deploying/wsgi-standalone/#proxy-setups
To correctly configure the Werkzeug ProxyFix module you need to follow the docs here: https://werkzeug.palletsprojects.com/en/0.15.x/contrib/fixers/#werkzeug.contrib.fixers.ProxyFix
- Log in to comment
I need this capability as well - I'm running my app behind an nginx proxy and the ACS url that's being returned is the internal name and not the public-facing address.