def main(client_id, user_arguments_dict, environ=None): """Main function used by front end""" if environ is None: environ = os.environ (configuration, logger, output_objects, op_name) = \ initialize_main_variables(client_id, op_header=False) status = returnvalues.OK defaults = signature()[1] (validate_status, accepted) = validate_input_and_cert( user_arguments_dict, defaults, output_objects, client_id, configuration, allow_rejects=False, ) if not validate_status: return (accepted, returnvalues.CLIENT_ERROR) do_logout = accepted['logout'][-1].lower() in ('true', '1') # sub-container inside default IU container output_objects.append({ 'object_type': 'html_form', 'text': ''' <div class="global-full-height row"> <div class="col-12 align-self-center"> ''' }) output_objects.append({'object_type': 'header', 'text': 'Logout'}) (oid_db, identity) = extract_client_openid(configuration, environ, lookup_dn=False) logger.info("%s from %s with identity %s" % (op_name, client_id, identity)) if client_id and client_id == identity: output_objects.append({ 'object_type': 'warning', 'text': """You're accessing %s with a user certificate so to completely logout you need to make sure it is protected by a password and then close the browser. Please refer to your browser and system documentation for details. """ % configuration.short_title }) return (output_objects, status) # OpenID requires logout on provider and in local mod-auth-openid database. # IMPORTANT: some browsers like Firefox may inadvertently renew the local # OpenID session while loading the resources for this page (in parallel). # User clicks logout at OpenID provider, which sends her back here to # finish the local logout. if do_logout: if configuration.site_enable_twofactor: real_user = client_id addr_filter = environ['REMOTE_ADDR'] # GDP logout is for project user so we strip project to force # repeat 2FA login on project logout / switch if configuration.site_enable_gdp: real_user = get_client_id_from_project_client_id( configuration, client_id) addr_filter = None if real_user and not expire_twofactor_session( configuration, real_user, environ, allow_missing=True, user_addr=addr_filter): logger.warning("expire twofactor session failed for %s" % client_id) output_objects.append({ 'object_type': 'html_form', 'text': """<p class='warningtext'> There was a potential problem with 2-factor session termination. Please contact the %s Admins if it happens repeatedly. </p>""" % configuration.short_title }) logger.info("expiring active sessions for %s in %s" % (identity, oid_db)) (success, _) = expire_oid_sessions(configuration, oid_db, identity) logger.info("verifying no active sessions left for %s" % identity) (found, remaining) = find_oid_sessions(configuration, oid_db, identity) if success and found and not remaining: if configuration.site_enable_gdp: reentry_page = "https://%s" % configuration.server_fqdn if configuration.user_mig_oid_provider and \ identity.startswith( configuration.user_mig_oid_provider): reentry_page = configuration.migserver_https_mig_oid_url elif configuration.user_ext_oid_provider and \ identity.startswith( configuration.user_ext_oid_provider): reentry_page = configuration.migserver_https_ext_oid_url project_logout(configuration, 'https', environ['REMOTE_ADDR'], client_id) html = ''' <a id='gdp_logout' href='%s'></a> <script type='text/javascript'> document.getElementById('gdp_logout').click(); </script>''' % reentry_page output_objects.append({ 'object_type': 'html_form', 'text': html }) else: output_objects.append({ 'object_type': 'text', 'text': """You are now logged out of %s locally - you may want to close your web browser to finish""" % configuration.short_title }) title_entry = find_entry(output_objects, 'title') title_entry['skipmenu'] = True else: logger.error("remaining active sessions for %s: %s" % (identity, remaining)) output_objects.append({ 'object_type': 'error_text', 'text': "Could not log you out of %s!" % configuration.short_title }) status = returnvalues.CLIENT_ERROR else: local_logout = '?logout=true' oid_logout = os.path.join(os.path.dirname(os.path.dirname(identity)), 'logout?return_to=%(SCRIPT_URI)s' % environ) oid_logout += local_logout output_objects.append({ 'object_type': 'text', 'text': """Are you sure you want to log out of %s?""" % configuration.short_title }) output_objects.append({'object_type': 'text', 'text': ""}) output_objects.append({ 'object_type': 'link', 'destination': oid_logout, 'class': 'genericbutton greenBtn', 'text': "Yes" }) output_objects.append({ 'object_type': 'link', 'destination': 'javascript:history.back();', 'class': 'genericbutton greenBtn', 'text': "No, go back" }) # sub-container end output_objects.append({ 'object_type': 'html_form', 'text': ''' </div> </div> ''' }) return (output_objects, status)
def validate_input_and_cert( user_arguments_dict, defaults, output_objects, client_id, configuration, allow_rejects, require_user=True, filter_values=None, environ=None, ): """A wrapper used by most back end functionality - redirects to sign up if client_id is missing. """ logger = configuration.logger if environ is None: environ = os.environ creds_error = '' if not client_id: creds_error = "Invalid or missing user credentials" elif require_user and not is_user(client_id, configuration.mig_server_home): creds_error = "No such user (%s)" % client_id if creds_error and not requested_page().endswith('logout.py'): output_objects.append({'object_type': 'error_text', 'text' : creds_error }) # Redirect to sign-up cert page trying to guess relevant choices signup_url = os.path.join(configuration.migserver_https_sid_url, 'cgi-sid', 'signup.py') signup_query = '' if not client_id: output_objects.append( {'object_type': 'text', 'text': '''Apparently you do not already have access to %s, but you can sign up:''' % configuration.short_title }) output_objects.append({'object_type': 'link', 'text': signup_url, 'destination': signup_url + signup_query}) output_objects.append( {'object_type': 'text', 'text': '''If you already signed up and received a user certificate you probably just need to import it in your browser.'''}) else: output_objects.append( {'object_type': 'text', 'text': '''Apparently you already have suitable credentials and just need to sign up for a local %s account on:''' % \ configuration.short_title}) if extract_client_cert(configuration, environ) is None: # Force logout/expire session cookie here to support signup identity = extract_client_openid(configuration, environ, lookup_dn=False) if identity: logger.info("expire openid user %s" % identity) (success, _) = expire_oid_sessions(configuration, identity) else: logger.info("no openid user logged in") output_objects.append({'object_type': 'link', 'text': signup_url, 'destination': signup_url + signup_query}) return (False, output_objects) (status, retval) = validate_input(user_arguments_dict, defaults, output_objects, allow_rejects, filter_values) return (status, retval)
def validate_input_and_cert( user_arguments_dict, defaults, output_objects, client_id, configuration, allow_rejects, require_user=True, filter_values=None, environ=None, ): """A wrapper used by most back end functionality - redirects to sign up if client_id is missing. """ logger = configuration.logger if environ is None: environ = os.environ creds_error = '' if not client_id: creds_error = "Invalid or missing user credentials" elif require_user and not is_user(client_id, configuration.mig_server_home): creds_error = "No such user (%s)" % client_id if creds_error and not requested_page().endswith('logout.py'): output_objects.append({ 'object_type': 'error_text', 'text': creds_error }) if configuration.site_enable_gdp: main_url = configuration.migserver_http_url output_objects.append({ 'object_type': 'text', 'text': '''Apparently you do not have access to this page, please return to:''' }) output_objects.append({ 'object_type': 'link', 'text': main_url, 'destination': main_url }) else: # Redirect to sign-up cert page trying to guess relevant choices signup_url = os.path.join(configuration.migserver_https_sid_url, 'cgi-sid', 'signup.py') signup_query = '' if not client_id: output_objects.append({ 'object_type': 'text', 'text': '''Apparently you do not already have access to %s, but you can sign up:''' % configuration.short_title }) output_objects.append({'object_type': 'link', 'text': '%s sign up page' % \ configuration.short_title, 'destination': signup_url + signup_query}) output_objects.append({ 'object_type': 'text', 'text': '''If you already signed up and received a user certificate you probably just need to import it in your browser.''' }) else: output_objects.append({ 'object_type': 'text', 'text': '''Apparently you already have suitable credentials and just need to sign up for a local %s account on the''' % configuration.short_title }) base_url = extract_base_url(configuration, environ) if base_url == configuration.migserver_https_ext_cert_url and \ 'extcert' in configuration.site_login_methods: signup_query = '?show=extcert' elif base_url in (configuration.migserver_https_ext_oid_url, configuration.migserver_https_mig_oid_url): # Force logout/expire session cookie here to support signup (oid_db, identity) = extract_client_openid(configuration, environ, lookup_dn=False) if oid_db and identity: logger.info("openid expire user %s in %s" % (identity, oid_db)) (success, _) = expire_oid_sessions(configuration, oid_db, identity) if oid_db == auth_openid_ext_db and \ 'extoid' in configuration.site_signup_methods: signup_query = '?show=extoid' else: logger.error("unknown migoid client_id %s on %s" \ % (client_id, base_url)) else: logger.warning("unexpected client_id %s on %s" % \ (client_id, base_url)) output_objects.append({'object_type': 'link', 'text': '%s sign up page' % \ configuration.short_title, 'destination': signup_url + signup_query}) return (False, output_objects) (status, retval) = validate_input(user_arguments_dict, defaults, output_objects, allow_rejects, filter_values) return (status, retval)
def main(client_id, user_arguments_dict, environ=None): """Main function used by front end""" if environ is None: environ = os.environ (configuration, logger, output_objects, op_name) = \ initialize_main_variables(client_id, op_header=False, op_menu=False) logger = configuration.logger logger.info('%s: args: %s' % (op_name, user_arguments_dict)) prefilter_map = {} output_objects.append({'object_type': 'header', 'text' : 'Automatic %s sign up' % \ configuration.short_title }) identity = extract_client_openid(configuration, environ, lookup_dn=False) if client_id and client_id == identity: login_type = 'cert' base_url = configuration.migserver_https_cert_url elif identity: login_type = 'oid' base_url = configuration.migserver_https_oid_url for name in ('openid.sreg.cn', 'openid.sreg.fullname', 'openid.sreg.full_name'): prefilter_map[name] = filter_commonname else: output_objects.append( {'object_type': 'error_text', 'text': 'Missing user credentials'}) return (output_objects, returnvalues.CLIENT_ERROR) defaults = signature(login_type)[1] (validate_status, accepted) = validate_input( user_arguments_dict, defaults, output_objects, allow_rejects=False, prefilter_map=prefilter_map) if not validate_status: logger.warning('%s invalid input: %s' % (op_name, accepted)) return (accepted, returnvalues.CLIENT_ERROR) logger.debug('Accepted arguments: %s' % accepted) # Unfortunately OpenID redirect does not use POST if login_type != 'oid' and not correct_handler('POST'): output_objects.append( {'object_type': 'error_text', 'text' : 'Only accepting POST requests to prevent unintended updates'}) return (output_objects, returnvalues.CLIENT_ERROR) admin_email = configuration.admin_email openid_names, oid_extras = [], {} # Extract raw values if login_type == 'cert': uniq_id = accepted['cert_id'][-1].strip() raw_name = accepted['cert_name'][-1].strip() country = accepted['country'][-1].strip() state = accepted['state'][-1].strip() org = accepted['org'][-1].strip() org_unit = '' role = ','.join([i for i in accepted['role'] if i]) locality = '' timezone = '' email = accepted['email'][-1].strip() raw_login = None elif login_type == 'oid': uniq_id = accepted['openid.sreg.nickname'][-1].strip() or \ accepted['openid.sreg.short_id'][-1].strip() raw_name = accepted['openid.sreg.fullname'][-1].strip() or \ accepted['openid.sreg.full_name'][-1].strip() country = accepted['openid.sreg.country'][-1].strip() state = accepted['openid.sreg.state'][-1].strip() org = accepted['openid.sreg.o'][-1].strip() or \ accepted['openid.sreg.organization'][-1].strip() org_unit = accepted['openid.sreg.ou'][-1].strip() or \ accepted['openid.sreg.organizational_unit'][-1].strip() # We may receive multiple roles role = ','.join([i for i in accepted['openid.sreg.role'] if i]) locality = accepted['openid.sreg.locality'][-1].strip() timezone = accepted['openid.sreg.timezone'][-1].strip() email = accepted['openid.sreg.email'][-1].strip() # Fix case of values: # force name to capitalized form (henrik karlsen -> Henrik Karlsen) # please note that we get utf8 coded bytes here and title() treats such # chars as word termination. Temporarily force to unicode. try: full_name = force_utf8(force_unicode(raw_name).title()) except Exception: logger.warning("could not use unicode form to capitalize full name") full_name = raw_name.title() country = country.upper() state = state.upper() email = email.lower() if login_type == 'oid': # Remap some oid attributes if on kit format with faculty in # organization and institute in organizational_unit. We can add them # as different fields as long as we make sure the x509 fields are # preserved. # We do that to allow autocreate updating existing cert users. if org_unit not in ('', 'NA'): org_unit = org_unit.upper() oid_extras['faculty'] = org oid_extras['institute'] = org_unit org = org_unit.upper() org_unit = 'NA' # Stay on virtual host - extra useful while we test dual OpenID base_url = environ.get('REQUEST_URI', base_url).split('?')[0].replace('autocreate', 'fileman') raw_login = None for oid_provider in configuration.user_openid_providers: openid_prefix = oid_provider.rstrip('/') + '/' if identity.startswith(openid_prefix): raw_login = identity.replace(openid_prefix, '') break if raw_login: openid_names.append(raw_login) # we should have the proxy file read... proxy_content = accepted['proxy_upload'][-1] # keep comment to a single line comment = accepted['comment'][-1].replace('\n', ' ') # single quotes break command line format - remove comment = comment.replace("'", ' ') user_dict = { 'short_id': uniq_id, 'full_name': full_name, 'organization': org, 'organizational_unit': org_unit, 'locality': locality, 'state': state, 'country': country, 'email': email, 'role': role, 'timezone': timezone, 'password': '', 'comment': '%s: %s' % ('Existing certificate', comment), 'openid_names': openid_names, } user_dict.update(oid_extras) # We must receive some ID from the provider if not uniq_id and not email: output_objects.append( {'object_type': 'error_text', 'text' : 'No ID information received!'}) if accepted.get('openid.sreg.required', '') and \ identity: # Stay on virtual host - extra useful while we test dual OpenID url = environ.get('REQUEST_URI', base_url).split('?')[0].replace('autocreate', 'logout') output_objects.append( {'object_type': 'text', 'text': '''Please note that sign-up for OpenID access does not work if you are already signed in with your OpenID provider - and that appears to be the case now. You probably have to reload this page after you explicitly '''}) output_objects.append( {'object_type': 'link', 'destination': url, 'target': '_blank', 'text': "Logout" }) return (output_objects, returnvalues.CLIENT_ERROR) if login_type == 'cert': user_dict['expire'] = int(time.time() + cert_valid_days * 24 * 60 * 60) try: distinguished_name_to_user(uniq_id) user_dict['distinguished_name'] = uniq_id except: output_objects.append({'object_type': 'error_text', 'text' : '''Illegal Distinguished name: Please note that the distinguished name must be a valid certificate DN with multiple "key=val" fields separated by "/". '''}) return (output_objects, returnvalues.CLIENT_ERROR) elif login_type == 'oid': user_dict['expire'] = int(time.time() + oid_valid_days * 24 * 60 * 60) fill_distinguished_name(user_dict) uniq_id = user_dict['distinguished_name'] # If server allows automatic addition of users with a CA validated cert # we create the user immediately and skip mail if login_type == 'cert' and configuration.auto_add_cert_user or \ login_type == 'oid' and configuration.auto_add_oid_user: fill_user(user_dict) logger.info('create user: %s' % user_dict) # Now all user fields are set and we can begin adding the user db_path = os.path.join(configuration.mig_server_home, user_db_filename) try: create_user(user_dict, configuration.config_file, db_path, ask_renew=False, default_renew=True) if configuration.site_enable_griddk and \ accepted['proxy_upload'] != ['']: # save the file, display expiration date proxy_out = handle_proxy(proxy_content, uniq_id, configuration) output_objects.extend(proxy_out) except Exception, err: logger.error('create failed for %s: %s' % (uniq_id, err)) output_objects.append( {'object_type': 'error_text', 'text' : '''Could not create the user account for you: Please report this problem to the grid administrators (%s).''' % \ admin_email}) return (output_objects, returnvalues.SYSTEM_ERROR) output_objects.append({'object_type': 'html_form', 'text' : '''Created the user account for you - please open <a href="%s">your personal page</a> to proceed using it. ''' % base_url}) return (output_objects, returnvalues.OK)
def main(client_id, user_arguments_dict, environ=None): """Main function used by front end""" if environ is None: environ = os.environ (configuration, logger, output_objects, op_name) = \ initialize_main_variables(client_id, op_header=False) status = returnvalues.OK defaults = signature()[1] (validate_status, accepted) = validate_input_and_cert( user_arguments_dict, defaults, output_objects, client_id, configuration, allow_rejects=False, ) if not validate_status: return (accepted, returnvalues.CLIENT_ERROR) do_logout = accepted['logout'][-1].lower() in ('true', '1') output_objects.append({'object_type': 'header', 'text' : 'Logout'}) identity = extract_client_openid(configuration, environ, lookup_dn=False) logger.info("%s from %s with identity %s" % (op_name, client_id, identity)) if client_id and client_id == identity: output_objects.append( {'object_type': 'warning', 'text': """You're accessing %s with a user certificate so to completely logout you need to make sure it is protected by a password and then close the browser. Please refer to your browser and system documentation for details. """ % configuration.short_title}) return (output_objects, status) # OpenID requires logout on provider and in local mod-auth-openid database. # IMPORTANT: some browsers like Firefox may inadvertently renew the local # OpenID session while loading the resources for this page (in parallel). # User clicks logout at OpenID provider, which sends her back here to # finish the local logout. if do_logout: logger.info("expiring active sessions for %s" % identity) (success, _) = expire_oid_sessions(configuration, identity) logger.info("verifying no active sessions left for %s" % identity) (found, remaining) = find_oid_sessions(configuration, identity) if success and found and not remaining: output_objects.append( {'object_type': 'text', 'text': """You are now logged out of %s locally - you may want to close your web browser to finish""" % \ configuration.short_title}) else: logger.error("remaining active sessions for %s: %s" % (identity, remaining)) output_objects.append({'object_type': 'error_text', 'text' : "Could not log you out of %s!" % \ configuration.short_title}) status = returnvalues.CLIENT_ERROR else: local_logout = '?logout=true' oid_logout = os.path.join(os.path.dirname(os.path.dirname(identity)), 'logout?return_to=%(SCRIPT_URI)s' % environ) oid_logout += local_logout output_objects.append( {'object_type': 'text', 'text': """You can log out from your OpenID identity provider and end the active %s session with the link below.""" % \ configuration.short_title}) # TODO: we could trigger this link automatically output_objects.append( {'object_type': 'link', 'destination': oid_logout, 'text': "Logout"}) return (output_objects, status)
def main(client_id, user_arguments_dict, environ=None): """Main function used by front end""" if environ is None: environ = os.environ (configuration, logger, output_objects, op_name) = \ initialize_main_variables(client_id, op_header=False, op_menu=False) logger = configuration.logger logger.info('%s: args: %s' % (op_name, user_arguments_dict)) prefilter_map = {} output_objects.append({ 'object_type': 'header', 'text': 'Automatic %s sign up' % configuration.short_title }) (_, identity) = extract_client_openid(configuration, environ, lookup_dn=False) req_url = environ['SCRIPT_URI'] if client_id and client_id == identity: login_type = 'cert' if req_url.startswith(configuration.migserver_https_mig_cert_url): base_url = configuration.migserver_https_mig_cert_url elif req_url.startswith(configuration.migserver_https_ext_cert_url): base_url = configuration.migserver_https_ext_cert_url else: logger.warning('no match for cert request URL: %s' % req_url) output_objects.append({ 'object_type': 'error_text', 'text': 'No matching request URL: %s' % req_url }) return (output_objects, returnvalues.SYSTEM_ERROR) elif identity: login_type = 'oid' if req_url.startswith(configuration.migserver_https_mig_oid_url): base_url = configuration.migserver_https_mig_oid_url elif req_url.startswith(configuration.migserver_https_ext_oid_url): base_url = configuration.migserver_https_ext_oid_url else: logger.warning('no match for oid request URL: %s' % req_url) output_objects.append({ 'object_type': 'error_text', 'text': 'No matching request URL: %s' % req_url }) return (output_objects, returnvalues.SYSTEM_ERROR) for name in ('openid.sreg.cn', 'openid.sreg.fullname', 'openid.sreg.full_name'): prefilter_map[name] = filter_commonname else: output_objects.append({ 'object_type': 'error_text', 'text': 'Missing user credentials' }) return (output_objects, returnvalues.CLIENT_ERROR) defaults = signature(login_type)[1] (validate_status, accepted) = validate_input(user_arguments_dict, defaults, output_objects, allow_rejects=False, prefilter_map=prefilter_map) if not validate_status: logger.warning('%s invalid input: %s' % (op_name, accepted)) return (accepted, returnvalues.CLIENT_ERROR) logger.debug('Accepted arguments: %s' % accepted) # Unfortunately OpenID redirect does not use POST if login_type != 'oid' and not safe_handler( configuration, 'post', op_name, client_id, get_csrf_limit(configuration), accepted): output_objects.append({ 'object_type': 'error_text', 'text': '''Only accepting CSRF-filtered POST requests to prevent unintended updates''' }) return (output_objects, returnvalues.CLIENT_ERROR) admin_email = configuration.admin_email (openid_names, oid_extras) = ([], {}) # Extract raw values if login_type == 'cert': uniq_id = accepted['cert_id'][-1].strip() raw_name = accepted['cert_name'][-1].strip() country = accepted['country'][-1].strip() state = accepted['state'][-1].strip() org = accepted['org'][-1].strip() org_unit = '' role = ','.join([i for i in accepted['role'] if i]) association = ','.join([i for i in accepted['association'] if i]) locality = '' timezone = '' email = accepted['email'][-1].strip() raw_login = None elif login_type == 'oid': uniq_id = accepted['openid.sreg.nickname'][-1].strip() \ or accepted['openid.sreg.short_id'][-1].strip() raw_name = accepted['openid.sreg.fullname'][-1].strip() \ or accepted['openid.sreg.full_name'][-1].strip() country = accepted['openid.sreg.country'][-1].strip() state = accepted['openid.sreg.state'][-1].strip() org = accepted['openid.sreg.o'][-1].strip() \ or accepted['openid.sreg.organization'][-1].strip() org_unit = accepted['openid.sreg.ou'][-1].strip() \ or accepted['openid.sreg.organizational_unit'][-1].strip() # We may receive multiple roles and associations role = ','.join([i for i in accepted['openid.sreg.role'] if i]) association = ','.join( [i for i in accepted['openid.sreg.association'] if i]) locality = accepted['openid.sreg.locality'][-1].strip() timezone = accepted['openid.sreg.timezone'][-1].strip() # We may encounter results without an email, fall back to uniq_id then email = accepted['openid.sreg.email'][-1].strip() or uniq_id # Fix case of values: # force name to capitalized form (henrik karlsen -> Henrik Karlsen) # please note that we get utf8 coded bytes here and title() treats such # chars as word termination. Temporarily force to unicode. try: full_name = force_utf8(force_unicode(raw_name).title()) except Exception: logger.warning('could not use unicode form to capitalize full name') full_name = raw_name.title() country = country.upper() state = state.upper() email = email.lower() if login_type == 'oid': # Remap some oid attributes if on KIT format with faculty in # organization and institute in organizational_unit. We can add them # as different fields as long as we make sure the x509 fields are # preserved. # Additionally in the special case with unknown institute (ou=ukendt) # we force organization to KU to align with cert policies. # We do that to allow autocreate updating existing cert users. if org_unit not in ('', 'NA'): org_unit = org_unit.upper() oid_extras['faculty'] = org oid_extras['institute'] = org_unit org = org_unit.upper() org_unit = 'NA' if org == 'UKENDT': org = 'KU' logger.info('unknown affilition, set organization to %s' % org) # Stay on virtual host - extra useful while we test dual OpenID if configuration.site_enable_gdp: base_url = environ.get('REQUEST_URI', base_url).split('?')[0].replace( 'autocreate', 'gdpman') else: base_url = environ.get('REQUEST_URI', base_url).split('?')[0].replace( 'autocreate', 'fileman') raw_login = None for oid_provider in configuration.user_openid_providers: openid_prefix = oid_provider.rstrip('/') + '/' if identity.startswith(openid_prefix): raw_login = identity.replace(openid_prefix, '') break if raw_login: openid_names.append(raw_login) # we should have the proxy file read... proxy_content = accepted['proxy_upload'][-1] # keep comment to a single line comment = accepted['comment'][-1].replace('\n', ' ') # single quotes break command line format - remove comment = comment.replace("'", ' ') user_dict = { 'short_id': uniq_id, 'full_name': full_name, 'organization': org, 'organizational_unit': org_unit, 'locality': locality, 'state': state, 'country': country, 'email': email, 'role': role, 'association': association, 'timezone': timezone, 'password': '', 'comment': '%s: %s' % ('Existing certificate', comment), 'openid_names': openid_names, } user_dict.update(oid_extras) # We must receive some ID from the provider if not uniq_id and not email: if accepted.get('openid.sreg.required', '') and identity: output_objects.append({ 'object_type': 'html_form', 'text': '''<p class="spinner iconleftpad"> Auto log out first to avoid sign up problems ... </p>''' }) html = \ """ <a id='autologout' href='%s'></a> <script type='text/javascript'> document.getElementById('autologout').click(); </script>""" \ % openid_autologout_url(configuration, identity, client_id, req_url, user_arguments_dict) output_objects.append({'object_type': 'html_form', 'text': html}) return (output_objects, returnvalues.CLIENT_ERROR) auth = 'unknown' if login_type == 'cert': auth = 'extcert' user_dict['expire'] = int(time.time() + cert_valid_days * 24 * 60 * 60) try: distinguished_name_to_user(uniq_id) user_dict['distinguished_name'] = uniq_id except: output_objects.append({ 'object_type': 'error_text', 'text': '''Illegal Distinguished name: Please note that the distinguished name must be a valid certificate DN with multiple "key=val" fields separated by "/". ''' }) return (output_objects, returnvalues.CLIENT_ERROR) elif login_type == 'oid': auth = 'extoid' user_dict['expire'] = int(time.time() + oid_valid_days * 24 * 60 * 60) fill_distinguished_name(user_dict) uniq_id = user_dict['distinguished_name'] # Save auth access method user_dict['auth'] = [auth] # If server allows automatic addition of users with a CA validated cert # we create the user immediately and skip mail if login_type == 'cert' and configuration.auto_add_cert_user \ or login_type == 'oid' and configuration.auto_add_oid_user: fill_user(user_dict) logger.info('create user: %s' % user_dict) # Now all user fields are set and we can begin adding the user db_path = os.path.join(configuration.mig_server_home, user_db_filename) try: create_user(user_dict, configuration.config_file, db_path, ask_renew=False, default_renew=True) if configuration.site_enable_griddk \ and accepted['proxy_upload'] != ['']: # save the file, display expiration date proxy_out = handle_proxy(proxy_content, uniq_id, configuration) output_objects.extend(proxy_out) except Exception, err: logger.error('create failed for %s: %s' % (uniq_id, err)) output_objects.append({ 'object_type': 'error_text', 'text': '''Could not create the user account for you: Please report this problem to the grid administrators (%s).''' % admin_email }) return (output_objects, returnvalues.SYSTEM_ERROR) logger.info('created user account for %s' % uniq_id) output_objects.append({ 'object_type': 'html_form', 'text': '''Created the user account for you - please open <a href="%s">your personal page</a> to proceed using it. ''' % base_url }) return (output_objects, returnvalues.OK)
(unpacked_url, unpacked_query)) output_objects.append({ 'object_type': 'error_text', 'text': '''Only accepting fully signed GET requests to prevent unintended redirects''' }) return (output_objects, returnvalues.CLIENT_ERROR) # NOTE: from this point its' safe to use unpacked_url and unpacked_query redirect_url, redirect_query_dict = unpacked_url, unpacked_query output_objects.append({'object_type': 'header', 'text': 'Auto logout'}) (oid_db, identity) = extract_client_openid(configuration, environ, lookup_dn=False) logger.info('%s from %s with identity %s' % (op_name, client_id, identity)) if client_id and client_id == identity: output_objects.append({'object_type': 'warning', 'text': \ """You're accessing %s with a user certificate and should never end up at this auto logout page. Please refer to your browser and system documentation for details.""" % configuration.short_title}) return (output_objects, returnvalues.CLIENT_ERROR) msg = 'Auto log out first to avoid ' if redirect_url.find('autocreate') != -1: msg += 'sign up problems ...' else: