Skip to content
Snippets Groups Projects
Commit b3b34327 authored by Robin Sonnabend's avatar Robin Sonnabend
Browse files

Implement Shibboleth client authentication

parents
No related branches found
No related tags found
No related merge requests found
#!/usr/bin/env python3
import re
import urllib
import html
import requests
ACTION_PATTERN = r'<form action="(?P<url>[^"]+)" method="post">'
FIELD_PATTERN = r'<input type="hidden" name="(?P<name>[^"]+)" value="(?P<value>[^"]+)"/>'
def authenticate(shib_url, username, password, verify_tls=True):
session = requests.Session()
session.verify = verify_tls
sso_response = session.get(shib_url)
sso_url = sso_response.url
if urllib.parse.urlsplit(sso_url).netloc == urllib.parse.urlsplit(shib_url).netloc:
raise ValueError("Missing redirect to SSO. Wrong login URL specified")
login_data = {
"j_username": username,
"j_password": password,
"_eventId_proceed": "",
}
login_response = session.post(sso_url, data=login_data)
if "The credentials you entered are incorrect." in login_response.text:
raise ValueError("Invalid credentials. Login failed.")
action_match = re.search(ACTION_PATTERN, login_response.text)
if not action_match:
raise ValueError("Cannot parse login response.")
shib_url = html.unescape(action_match.group("url"))
params = {}
for match in re.findall(FIELD_PATTERN, login_response.text):
name, value = match
params[name] = html.unescape(value)
shib_response = session.post(shib_url, data=params)
return session
def main():
import argparse
parser = argparse.ArgumentParser()
parser.add_argument("url", help="URL of Shibboleth Service Provider "
"e.g. https://moodle.rwth-aachen.de/auth/shibboleth/index.php")
parser.add_argument("--username", help="Username to login with")
parser.add_argument("--password", help="Password to login with")
parser.add_argument("--no-verify", dest="verify_tls", action="store_false",
help="Do not verify TLS certificates.")
arguments = parser.parse_args()
username = arguments.username
password = arguments.password
if username is None:
username = input("Username: ")
if password is None:
import getpass
password = getpass.getpass("Password: ")
session = authenticate(arguments.url, username, password,
verify_tls=arguments.verify_tls)
print("Success!")
if __name__ == "__main__":
main()
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment