def get_pre_context(client): """ get the rendering context before the login is shown, so the rendering of the login page could be controlled if realm_box or mfa_login is defined :param client: the rendering is client dependend, so we need the info :return: context dict, with all rendering attributes """ pre_context = {} pre_context["version"] = get_version() pre_context["licenseinfo"] = get_copyright_info() pre_context["default_realm"] = getDefaultRealm() pre_context["realm_box"] = getRealmBox() pre_context["realms"] = json.dumps(_get_realms_()) # check for mfa_login, autoassign and autoenroll in policy definition pre_context['mfa_login'] = False policy = get_client_policy(client=client, scope='selfservice', action='mfa_login') if policy: pre_context['mfa_login'] = True pre_context['mfa_3_fields'] = False policy = get_client_policy(client=client, scope='selfservice', action='mfa_3_fields') if policy: pre_context['mfa_3_fields'] = True pre_context['autoassign'] = False policy = get_client_policy(client=client, scope='enrollment', action='autoassignment') if policy: pre_context['autoassign'] = True pre_context['autoenroll'] = False policy = get_client_policy(client=client, scope='enrollment', action='autoenrollment') if policy: pre_context['autoenroll'] = True return pre_context
def get_pre_context(client): """ get the rendering context before the login is shown, so the rendering of the login page could be controlled if realm_box or mfa_login is defined :param client: the rendering is client dependend, so we need the info :return: context dict, with all rendering attributes """ pre_context = {} pre_context["version"] = get_version() pre_context["licenseinfo"] = get_copyright_info() pre_context["default_realm"] = getDefaultRealm() pre_context["realm_box"] = getRealmBox() pre_context["realms"] = json.dumps(_get_realms_()) # check for mfa_login, autoassign and autoenroll in policy definition pre_context['mfa_login'] = False policy = get_client_policy(client=client, scope='selfservice', action='mfa_login') if policy: pre_context['mfa_login'] = True pre_context['mfa_3_fields'] = False policy = get_client_policy(client=client, scope='selfservice', action='mfa_3_fields') if policy: pre_context['mfa_3_fields'] = True pre_context['autoassign'] = False policy = get_client_policy(client=client, scope='enrollment', action='autoassignment') if policy: pre_context['autoassign'] = True pre_context['autoenroll'] = False policy = get_client_policy(client=client, scope='enrollment', action='autoenrollment') if policy: pre_context['autoenroll'] = True return pre_context
def is_email_editable(user=""): """ this function checks the policy scope=selfservice, action=edit_email This is a int policy, while the '0' is a deny """ realm = user.realm login = user.login policies = get_client_policy( client=context["Client"], scope="selfservice", action="edit_email", realm=realm, user=login, ) edit_email = get_action_value(policies, scope="selfservice", action="edit_email", default=1) if edit_email == 0: return False return True
def _getEmailSubject(self, user=""): """ Could be used to implement some more complex logic similar to the SMS token where the SMS text is read from a policy. :return: The message that is sent to the user. It should contain at least the placeholder <otp> :rtype: string """ subject = '' if not user: return subject realm = user.realm login = user.login policies = get_client_policy(context['Client'], scope="authentication", realm=realm, user=login, action="emailsubject") if policies: subject = getPolicyActionValue(policies, "emailsubject", is_string=True) return subject
def _getEmailMessage(self, user=""): """ Could be used to implement some more complex logic similar to the SMS token where the SMS text is read from a policy. :return: The message that is sent to the user. It should contain at least the placeholder <otp> :rtype: string """ message = DEFAULT_MESSAGE if not user: return message realm = user.realm login = user.login policies = get_client_policy(context['Client'], scope="authentication", realm=realm, user=login, action="emailtext") message = get_action_value(policies, scope="authentication", action="emailtext", default=message) return message
def get_voice_language(user="", realm=""): """ This function returns the voice language as defined in the policy authentication/voice_language. If no such policy is defined, the function returns the fallback message "en" :return: string """ voice_language = "en" pol = get_client_policy(context['Client'], scope="authentication", realm=realm, user=user, action="voice_language") voice_language = get_action_value(pol, scope='authentication', action="voice_language", default='') log.debug("[get_voice_language] got the voice_language = %s", voice_language) return voice_language
def get_voice_language(user="", realm=""): """ This function returns the voice language as defined in the policy authentication/voice_language. If no such policy is defined, the function returns the fallback message "en" :return: string """ voice_language = "en" pol = get_client_policy(context['Client'], scope="authentication", realm=realm, user=user, action="voice_language") if len(pol) > 0: voice_language = getPolicyActionValue(pol, "voice_language", is_string=True) log.debug("[get_voice_language] got the voice_language = %s", voice_language) return voice_language
def get_mobile_number(self, user=None): ''' get the mobile number - from the token info or - if the policy allowes it, from the user info ''' if not user: return self.get_phone() pol = get_client_policy(context['Client'], scope="authentication", user=user, action="voice_dynamic_mobile_number") if not pol: return self.get_phone() get_dynamic = get_action_value(pol, scope='authentication', action="voice_dynamic_mobile_number", default=False) if not get_dynamic: return self.get_phone() user_detail = getUserDetail(user) return user_detail.get('mobile', self.get_phone())
def get_mobile_number(self, user=None): ''' get the mobile number - from the token info or - if the policy allowes it, from the user info ''' if not user: return self._getPhone() pol = get_client_policy(context['Client'], scope="authentication", user=user, action="sms_dynamic_mobile_number") if not pol: return self._getPhone() get_dynamic = getPolicyActionValue(pol, "sms_dynamic_mobile_number", is_string=True) if not get_dynamic: return self._getPhone() user_detail = getUserDetail(user) return user_detail.get('mobile', self._getPhone())
def get_mobile_number(self, user=None): """ get the mobile number - from the token info or - if the policy allowes it, from the user info """ if not user: return self._getPhone() pol = get_client_policy( context["Client"], scope="authentication", user=user, action="sms_dynamic_mobile_number", ) get_dynamic = get_action_value( pol, scope="authentication", action="sms_dynamic_mobile_number", default=False, ) if not get_dynamic: return self._getPhone() user_detail = getUserDetail(user) return user_detail.get("mobile", self._getPhone())
def get_voice_message(user="", realm=""): """ This function returns the voice message as defined in the policy authentication/voice_message. If no such policy is defined, the function returns the fallback message "{otp}" :return: string """ voice_text = "{otp}" pol = get_client_policy( context["Client"], scope="authentication", realm=realm, user=user, action="voice_message", ) if len(pol) > 0: voice_text = get_action_value(pol, scope="authentication", action="voice_message", default="") log.debug("[get_voice_message] got the voice_message = %s", voice_text) return voice_text
def _get_email_address(self, user=None): ''' get the email address - from the token info or - if the policy allowes it, from the user info ''' if not user: return self._email_address pol = get_client_policy(context['Client'], scope="authentication", user=user, action="dynamic_email_address") if not pol: return self._email_address get_dynamic = get_action_value(pol, scope="authentication", action="dynamic_email_address", default='') if not get_dynamic: return self._email_address user_detail = getUserDetail(user) return user_detail.get('email', self._email_address)
def get_provider_from_policy(provider_type, realm=None, user=None, scope='authentication', action=None): """ interface for the provider user like email token or sms token :param provider_type: 'push', 'email' or 'sms :param user: the user, who should receive the message, used for the policy lookup :return: the list of all identified providers by name """ # check if the provider is defined in a policy provider_name = None # lookup the policy action name provider_action_name = Policy_action_name.get(provider_type) if not provider_action_name: raise Exception('unknown provider_type for policy lookup! %r' % provider_type) if user is None: raise Exception('unknown user for policy lookup! %r' % user) if user and user.login: realm = user.realm if not action: action = provider_action_name policies = get_client_policy(request_context['Client'], scope=scope, action=action, realm=realm, user=user.login) if not policies: default_provider = _get_default_provider_name(provider_type) if default_provider: return [default_provider] return [] provider_names = getPolicyActionValue(policies, action, is_string=True) providers = [] for entry in [x.strip() for x in provider_names.split(' ')]: if entry: providers.append(entry) return providers
def get_pre_context(client, context=None): """ get the rendering context before the login is shown, so the rendering of the login page could be controlled if realm_box or otpLogin is defined :param client: the rendering is client dependend, so we need the info :return: context dict, with all rendering attributes """ pre_context = {} pre_context["version"] = get_version() pre_context["licenseinfo"] = get_copyright_info() pre_context["default_realm"] = getDefaultRealm() pre_context["realm_box"] = getRealmBox() pre_context["realms"] = json.dumps(_get_realms_()) """ check for otpLogin, autoassign and autoenroll in policy definition """ pre_context["otpLogin"] = False policy = get_client_policy(client=client, scope="selfservice", action="otpLogin", context=context) if policy: pre_context["otpLogin"] = True pre_context["autoassign"] = False policy = get_client_policy(client=client, scope="enrollment", action="autoassignment", context=context) if policy: pre_context["autoassign"] = True pre_context["autoenroll"] = False policy = get_client_policy(client=client, scope="enrollment", action="autoenrollment", context=context) if policy: pre_context["autoenroll"] = True return pre_context
def get_provider_from_policy(provider_type, realm=None, user=None): """ interface for the provider user like email token or sms token :param provider_type: 'push', 'email' or 'sms :param user: the user, who should receive the message, used for the policy lookup :return: the list of all identified providers by name """ # check if the provider is defined in a policy provider_name = None # lookup the policy action name provider_action_name = Policy_action_name.get(provider_type) if not provider_action_name: raise Exception('unknown provider_type for policy lookup! %r' % provider_type) if user is None: raise Exception('unknown user for policy lookup! %r' % user) if user and user.login: realm = user.realm policies = get_client_policy(request_context['Client'], scope='authentication', action=provider_action_name, realm=realm, user=user.login) if not policies: default_provider = _get_default_provider_name(provider_type) if default_provider: return [default_provider] return [] provider_names = getPolicyActionValue(policies, provider_action_name, is_string=True) providers = [] for entry in [x.strip() for x in provider_names.split(' ')]: if entry: providers.append(entry) return providers
def get_pre_context(client): """ get the rendering context before the login is shown, so the rendering of the login page could be controlled if realm_box or mfa_login is defined :param client: the rendering is client dependend, so we need the info :return: context dict, with all rendering attributes """ # check for mfa_login, autoassign and autoenroll in policy definition mfa_login_policy = get_client_policy(client=client, scope='selfservice', action='mfa_login') mfa_3_fields_policy = get_client_policy(client=client, scope='selfservice', action='mfa_3_fields') autoassignment_policy = get_client_policy(client=client, scope='enrollment', action='autoassignment') autoenrollment_policy = get_client_policy(client=client, scope='enrollment', action='autoenrollment') return { "version": get_version(), "copyright": get_copyright_info(), "realms": _get_realms_(), "settings": { "default_realm": getDefaultRealm(), "realm_box": getRealmBox(), "mfa_login": bool(mfa_login_policy), "mfa_3_fields": bool(mfa_3_fields_policy), "autoassign": bool(autoassignment_policy), "autoenroll": bool(autoenrollment_policy), }, }
def notify_user(user, action, info, required=False): """ notify user via email, sms or other method (http/whatsapp...) :param user: the user who should be notified :param action: action is currently the notification action like enrollment, setPin, which are defined in the notification policies :param info: generic dict which is action specific :param required: if True an exception is raised if no notification could be send eg if no provider is defined or could be found :return: boolean - true if notification is enabled """ policies = get_client_policy(request_context['Client'], scope='notification', action=action, realm=user.realm, user=user.login) provider_specs = getPolicyActionValue(policies, action, is_string=True) if not isinstance(provider_specs, list): provider_specs = [provider_specs] # TODO: use the ResouceSchduler to handle failover for provider_spec in provider_specs: provider_type, _sep, provider_name = provider_spec.partition('::') if provider_type == 'email': notify_user_by_email(provider_name, user, action, info) return True # elif provider_type == 'sms': # notify_user_by_email(provider_name, user, action, info) log.info('Failed to notify user %r', user) if required: raise NotificationException( 'No notification has been sent - %r provider defined?' % action) return False
def get_auth_smstext(user="", realm=""): ''' this function checks the policy scope=authentication, action=smstext This is a string policy The function returns the tuple (bool, string), bool: If a policy is defined string: the string to use ''' # the default string is the OTP value ret = False smstext = "<otp>" pol = get_client_policy(context['Client'], scope="authentication", realm=realm, user=user, action="smstext") if len(pol) > 0: smstext = getPolicyActionValue(pol, "smstext", is_string=True) log.debug("[get_auth_smstext] got the smstext = %s" % smstext) ret = True return ret, smstext
def get_auth_smstext(user="", realm=""): ''' this function checks the policy scope=authentication, action=smstext This is a string policy The function returns the tuple (bool, string), bool: If a policy is defined string: the string to use ''' pol = get_client_policy(context['Client'], scope="authentication", realm=realm, user=user, action="smstext") smstext = get_action_value(pol, scope='authentication', action="smstext", default="<otp>") log.debug("[get_auth_smstext] got the smstext = %s" % smstext) return (smstext != "<otp>"), smstext
def enforce_smstext(user="", realm=""): ''' this function checks the boolean policy scope=authentication, action=enforce_smstext The function returns true if the smstext should be used instead of the challenge data :return: bool ''' pol = get_client_policy(context['Client'], scope="authentication", realm=realm, user=user, action="enforce_smstext") if len(pol) > 0: enforce_smstext = getPolicyActionValue(pol, "enforce_smstext") log.debug("got enforce_smstext = %r" % enforce_smstext) return enforce_smstext or False return False
def loadProviderFromPolicy(provider_type, realm=None, user=None): """ interface for the provider user like email token or sms token :param provider_type: 'push', 'email' or 'sms :param user: the user, who should receive the message, used for the policy lookup :return: the instantiated provider with already loaded config """ # check if the provider is defined in a policy provider_name = None # lookup the policy action name provider_action_name = Policy_action_name.get(provider_type) if not provider_action_name: raise Exception('unknown provider_type for policy lookup! %r' % provider_type) if user is None: raise Exception('unknown user for policy lookup! %r' % user) if user and user.login: realm = user.realm policies = get_client_policy(request_context['Client'], scope='authentication', action=provider_action_name, realm=realm, user=user.login) if policies: provider_name = getPolicyActionValue(policies, provider_action_name, is_string=True) return loadProvider(provider_type, provider_name)
def loadProviderFromPolicy(provider_type, realm=None, user=None): """ interface for the provider user like email token or sms token :param provider_type: 'push', 'email' or 'sms :param user: the user, who should receive the message, used for the policy lookup :return: the instantiated provider with already loaded config """ # check if the provider is defined in a policy provider_name = None # lookup the policy action name provider_action_name = Policy_action_name.get(provider_type) if not provider_action_name: raise Exception('unknown provider_type for policy lookup! %r' % provider_type) if not user: raise Exception('unknown user for policy lookup! %r' % user) if user and user.login: realm = user.realm policies = get_client_policy(request_context['Client'], scope='authentication', action=provider_action_name, realm=realm, user=user.login) if policies: provider_name = getPolicyActionValue(policies, provider_action_name, is_string=True) return loadProvider(provider_type, provider_name)
def enforce_smstext(user="", realm=""): """ this function checks the boolean policy scope=authentication, action=enforce_smstext The function returns true if the smstext should be used instead of the challenge data :return: bool """ pol = get_client_policy( context["Client"], scope="authentication", realm=realm, user=user, action="enforce_smstext", ) enforce_smstext = get_action_value( pol, scope="authentication", action="enforce_smstext", default=False ) log.debug("got enforce_smstext = %r", enforce_smstext) return enforce_smstext