Skip to content
Snippets Groups Projects
Forked from Davide Vaghetti / eduGAIN contacts
2 commits behind, 1 commit ahead of the upstream repository.
entity_search.py 2.43 KiB
#!/usr/bin/env python3

import sys
import requests
import argparse
import hashlib
import base64
from xml.etree import ElementTree as ET


# DEFINE SOME VARS

entity_id = None
metadata_file = None
root = None 
tec_contact = ''
sup_contact = ''
adm_contact = ''


# ARGPARSE

parser = argparse.ArgumentParser(description='Search for an entity in a metadata aggregate (default to eduGAIN metadata).',
                                 formatter_class=argparse.RawDescriptionHelpFormatter,
                                 epilog='''
Output: entityID 
                                 
Examples

- Search an entity by the SHA256 hash of its certificate in the eduGAIN metadata:\n
./entity_search.py -s SHA256HASH_STRING \n\n

- Search an entity by the SHA256 hash of its certificate using local metadata file:\n
./entity_details.py -s SHA256HASH_STRING -f edugain-v2.xml
''')
group = parser.add_mutually_exclusive_group()
group.add_argument('-s', type=str, help='search entity by the sha256 hash S')
parser.add_argument('-f', type=str, help='load metadata from file F')
parser.add_argument('-u', type=str, default='https://mds.edugain.org/edugain-v2.xml', 
                    help='download metadata from url U (default to https://mds.edugain.org/edugain-v2.xml)')
args = parser.parse_args()

# MAIN

if not args.s:
    parser.parse_args(['-h'])
    exit(1)

if args.f:
    tree = ET.parse(args.f)
    root = tree.getroot()
else:
    xml_req = requests.get(args.u)
    root = ET.fromstring(xml_req.content)

orgs = set()

ns = {
    'md': 'urn:oasis:names:tc:SAML:2.0:metadata',
    'ds': 'http://www.w3.org/2000/09/xmldsig#',
    'mdui': 'urn:oasis:names:tc:SAML:metadata:ui',
    'shibmd': 'urn:mace:shibboleth:metadata:1.0',
    'remd': 'http://refeds.org/metadata',
    'icmd': 'http://id.incommon.org/metadata',
    'mdrpi': 'urn:oasis:names:tc:SAML:metadata:rpi',
}

entities = root.findall('./md:EntityDescriptor', ns)

found_entities = set()

for entity in entities: 
    certs = entity.findall(f'.//ds:X509Certificate', ns)
    for cert in certs:
        if cert.text is not None:
            if hashlib.sha256(base64.b64decode(cert.text)).hexdigest().lower() == args.s.replace(':', '').lower():
                entity_id = entity.attrib['entityID'].strip()
                found_entities.add(entity_id)

if len(found_entities) > 0:
    print(f'Found {len(found_entities)} entities:')
    for fentity in found_entities:
        print(fentity)
else:
    print('No entities found.')