Skip to content

Commit

Permalink
BLUEBUTTON-669 Remove text message MFA (#708)
Browse files Browse the repository at this point in the history
* Remove SMS MFA choice code from models

* Remove mobile_phone_number from forms

* Remove test for SMS MFA

* Remove SMS logic from views
  • Loading branch information
dtisza1 authored Feb 19, 2019
1 parent b0569e6 commit 9d6ab40
Show file tree
Hide file tree
Showing 6 changed files with 4 additions and 97 deletions.
24 changes: 0 additions & 24 deletions apps/accounts/end_user_signup_forms.py
Original file line number Diff line number Diff line change
@@ -1,9 +1,6 @@
import logging
import binascii
from random import randint

from localflavor.us.forms import USPhoneNumberField

from django import forms
from django.conf import settings
from django.contrib.auth.models import User, Group
Expand Down Expand Up @@ -207,13 +204,6 @@ class UserSignupForm(forms.Form):
email = forms.EmailField(max_length=75, label=_("Email"))
first_name = forms.CharField(max_length=100, label=_("First Name"))
last_name = forms.CharField(max_length=100, label=_("Last Name"))
mobile_phone_number = USPhoneNumberField(required=False,
label=_("Mobile Phone Number "
"(Optional)"),
help_text=_("We use this for "
"multi-factor "
"authentication. "
"US numbers only."))

password1 = forms.CharField(widget=forms.PasswordInput, max_length=120,
label=_("Password"))
Expand Down Expand Up @@ -347,11 +337,6 @@ class AccountSettingsForm(forms.Form):
help_text=_("Change this to turn on "
"multi-factor "
"authentication (MFA)."))
mobile_phone_number = USPhoneNumberField(required=False,
help_text=_("US numbers only. "
"We use this for "
"multi-factor "
"authentication."))
organization_name = forms.CharField(max_length=100,
label=_('Organization Name'),
required=False)
Expand All @@ -368,15 +353,6 @@ def clean_email(self):
'already registered.'))
return email.rstrip().lstrip().lower()

def clean_mobile_phone_number(self):
mobile_phone_number = self.cleaned_data.get('mobile_phone_number', '')
mfa_login_mode = self.cleaned_data.get('mfa_login_mode', '')
if mfa_login_mode == "SMS" and not mobile_phone_number:
raise forms.ValidationError(
_('A mobile phone number is required to use SMS-based '
'multi-factor authentication'))
return mobile_phone_number

def clean_username(self):
username = self.cleaned_data.get('username')
username = username.rstrip().lstrip().lower()
Expand Down
30 changes: 1 addition & 29 deletions apps/accounts/forms.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@
from apps.fhir.bluebutton.utils import get_resourcerouter
from .models import Invitation, RequestInvite, UserProfile, create_activation_key, UserRegisterCode
from .models import QUESTION_1_CHOICES, QUESTION_2_CHOICES, QUESTION_3_CHOICES, MFA_CHOICES
from localflavor.us.forms import USPhoneNumberField


logger = logging.getLogger('hhs_server.%s' % __name__)
Expand Down Expand Up @@ -146,13 +145,7 @@ class EndUserRegisterForm(forms.Form):
password_reset_answer_2 = forms.CharField(max_length=50)
password_reset_question_3 = forms.ChoiceField(choices=QUESTION_3_CHOICES)
password_reset_answer_3 = forms.CharField(max_length=50)
mobile_phone_number = USPhoneNumberField(required=False,
label=_("Mobile Phone Number "
"(Optional)"),
help_text=_("We use this for "
"multi-factor "
"authentication. "
"US numbers only."))

code = forms.CharField(
max_length=30,
label=_('Code'),
Expand Down Expand Up @@ -245,13 +238,6 @@ class SignupForm(forms.Form):
label=_("First Name"))
last_name = forms.CharField(max_length=100,
label=_("Last Name"))
mobile_phone_number = USPhoneNumberField(required=False,
label=_("Mobile Phone Number "
"(Optional)"),
help_text=_("We use this for "
"multi-factor "
"authentication. "
"US numbers only."))
organization_name = forms.CharField(max_length=100,
label=_("Organization Name"),
required=True
Expand Down Expand Up @@ -378,11 +364,6 @@ def __init__(self, *args, **kwargs):
help_text=_("Change this to turn on "
"multi-factor "
"authentication (MFA)."))
mobile_phone_number = USPhoneNumberField(required=False,
help_text=_("US numbers only. "
"We use this for "
"multi-factor "
"authentication."))
organization_name = forms.CharField(max_length=100,
label=_('Organization Name'),
required=True)
Expand All @@ -404,12 +385,3 @@ def clean_email(self):
raise forms.ValidationError(_('This email address is '
'already registered.'))
return email.rstrip().lstrip().lower()

def clean_mobile_phone_number(self):
mobile_phone_number = self.cleaned_data.get('mobile_phone_number', '')
mfa_login_mode = self.cleaned_data.get('mfa_login_mode', '')
if mfa_login_mode == "SMS" and not mobile_phone_number:
raise forms.ValidationError(
_('A mobile phone number is required to use SMS-based '
'multi-factor authentication'))
return mobile_phone_number
11 changes: 2 additions & 9 deletions apps/accounts/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -89,7 +89,6 @@
MFA_CHOICES = (
('', 'None'),
('EMAIL', "Email"),
('SMS', "Text Message (SMS)"),
)

ISSUE_INVITE = (
Expand Down Expand Up @@ -240,9 +239,6 @@ def __str__(self):

def endpoint(self):
e = ""
up = UserProfile.objects.get(user=self.user)
if self.mode == "SMS" and up.mobile_phone_number:
e = up.mobile_phone_number
if self.mode == "EMAIL" and self.user.email:
e = self.user.email
return e
Expand All @@ -253,11 +249,8 @@ def save(self, **kwargs):
expires = now + timedelta(days=1)
self.expires = expires
self.code = str(random.randint(1000, 9999))
up = UserProfile.objects.get(user=self.user)
if self.mode == "SMS" and not up.mobile_phone_number:
logger.info("Cannot send SMS. No phone number on file.")
elif self.mode == "EMAIL" and self.user.email:
# "Send SMS to self.user.email
if self.mode == "EMAIL" and self.user.email:
# "Send to self.user.email
mfa_via_email(self.user, self.code)
elif self.mode == "EMAIL" and not self.user.email:
logger.info("Cannot send email. No email_on_file.")
Expand Down
28 changes: 0 additions & 28 deletions apps/accounts/tests/test_mfa.py
Original file line number Diff line number Diff line change
Expand Up @@ -54,31 +54,3 @@ def test_valid_mfa_login_with_email(self):
# Logout)
self.assertContains(response, 'Logout')
self.client.get(reverse('mylogout'))

def test_valid_mfa_login_with_sms(self):
"""
Valid User can login with valid MFA code (SMS)
"""
# Change the user p to use SMS
self.up.mfa_login_mode = "SMS"
self.up.save()
form_data = {'username': 'fred', 'password': 'bedrocks'}
response = self.client.post(self.url, form_data, follow=True)
self.assertEqual(response.status_code, 200)
last_url, status_code = response.redirect_chain[-1]
self.assertEqual(response.status_code, 200)
# MFA user should not be logged in (yet)
self.assertContains(response, 'Login')
# Get the UID from the URL
url_parts = last_url.split("/")
uid = url_parts[-2]
mfac = MFACode.objects.get(uid=uid)
# complete the MFA process w/ valid code.
response = self.client.post(
reverse(
'mfa_code_confirm', args=(
uid,)), {
'code': mfac.code}, follow=True)
# Now that a valid code is provided, the user is logged in (sees
# Logout)
self.assertContains(response, 'Logout')
2 changes: 0 additions & 2 deletions apps/accounts/views/core.py
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,6 @@ def account_settings(request):
# update the user profile
up.organization_name = data['organization_name']
up.mfa_login_mode = data['mfa_login_mode']
up.mobile_phone_number = data['mobile_phone_number']
up.create_applications = data['create_applications']
up.authorize_applications = True
up.save()
Expand All @@ -167,7 +166,6 @@ def account_settings(request):
'email': request.user.email,
'organization_name': up.organization_name,
'mfa_login_mode': up.mfa_login_mode,
'mobile_phone_number': up.mobile_phone_number,
'create_applications': up.create_applications,
'last_name': request.user.last_name,
'first_name': request.user.first_name,
Expand Down
6 changes: 1 addition & 5 deletions apps/accounts/views/mfa.py
Original file line number Diff line number Diff line change
Expand Up @@ -109,15 +109,11 @@ def mfa_login(request):
# Get User profile
up, g_o_c = UserProfile.objects.get_or_create(user=user)
# If MFA, send code and redirect
if up.mfa_login_mode in ("SMS", "EMAIL") and settings.MFA:
if up.mfa_login_mode in ("EMAIL",) and settings.MFA:
# Create an MFA message
mfac = MFACode.objects.create(
user=up.user, mode=up.mfa_login_mode)
# Send code and redirect
if up.mfa_login_mode == "SMS":
messages.info(
request,
_('An access code was sent to your mobile device. Please enter it here.'))
if up.mfa_login_mode == "EMAIL":
messages.info(
request, _('An access code was sent to your email. Please enter it here.'))
Expand Down

0 comments on commit 9d6ab40

Please sign in to comment.