def generate_challenge(self): # local import to avoid circular import from seahub.two_factor.oath import totp from seahub.two_factor.utils import totp_digits """ Sends the current TOTP token to `self.number` using `self.method`. """ no_digits = totp_digits() token = str(totp(self.bin_key, digits=no_digits)).zfill(no_digits) if self.method == 'call': make_call(device=self, token=token) else: send_sms(device=self, token=token)
def verify_token(self, token): # local import to avoid circular import from seahub.two_factor.oath import totp from seahub.two_factor.utils import totp_digits try: token = int(token) except ValueError: return False for drift in range(-5, 1): if totp(self.bin_key, drift=drift, digits=totp_digits()) == token: return True return False
def clean_token(self): token = self.cleaned_data.get('token') validated = False t0s = [self.t0] key = self.bin_key if 'valid_t0' in self.metadata: t0s.append(int(time()) - self.metadata['valid_t0']) for t0 in t0s: for offset in range(-self.tolerance, self.tolerance): if totp(key, self.step, t0, self.digits, self.drift + offset) == token: self.drift = offset self.metadata['valid_t0'] = int(time()) - t0 validated = True if not validated: raise forms.ValidationError(self.error_messages['invalid_token']) return token