phone-authn: on registration, inform user of existing duplicate (#88163) #286

Merged
pmarillonnet merged 1 commits from wip/88163-phone-authn-registration-existing-account-misleading-ui into main 2024-04-29 09:51:50 +02:00
2 changed files with 89 additions and 0 deletions

View File

@ -1936,6 +1936,10 @@ class RegistrationCompletionView(CreateView):
or self.phone_is_unique
and self.token.get('phone', None)
):
messages.info(
request, _("You've been logged in with your already-existing account for this identifier.")
)
# Found one user whose identifier is unique, log her in
utils_misc.simulate_authentication(request, self.users[0], method=self.authentication_method)

C'est déjà validé mais je note quand même :

"ou" ça ne va pas parler à l'usager; je serais même à penser que le message à l'usager pourrait être le même dans les deux situations, plutôt qu'essayer de lui passer la subtilité.

Dessous on a "your already-existing account" vs ici "your account already existing".

C'est déjà validé mais je note quand même : "ou" ça ne va pas parler à l'usager; je serais même à penser que le message à l'usager pourrait être le même dans les deux situations, plutôt qu'essayer de lui passer la subtilité. Dessous on a "your already-existing account" vs ici "your account already existing".

Merci, en effet, je corrige et mets le même message dans les deux cas.

Merci, en effet, je corrige et mets le même message dans les deux cas.
return utils_misc.redirect(request, self.get_success_url())

View File

@ -19,9 +19,11 @@ from datetime import date, timedelta
from unittest import mock
from urllib.parse import quote, urlparse
import pytest
import requests
import responses
from django.contrib.auth import REDIRECT_FIELD_NAME, get_user_model
from django.contrib.contenttypes.models import ContentType
from django.urls import reverse
from authentic2 import models
@ -1456,3 +1458,86 @@ def test_already_logged(db, app, simple_user):
# then we can register.
resp = resp.follow()
assert resp.form['email']
@responses.activate
def test_phone_registration_existing_identifier_number(app, db, settings, phone_activated_authn):
settings.SMS_URL = 'https://foo.whatever.none/'
responses.post('https://foo.whatever.none/', status=200)
random_user = User.objects.create(
first_name='foo',
last_name='bar',
email='foobar@example.com',
username='foobar',
)
random_user.attributes.phone = '+33612345678'
random_user.save()
resp = app.get(reverse('registration_register'))
resp.form.set('phone_1', '612345678')
resp = resp.form.submit().follow()
code = SMSCode.objects.get()
resp.form.set('sms_code', code.value)
resp = resp.form.submit().follow()
resp.form.set('password1', 'Password0')
resp.form.set('password2', 'Password0')
resp.form.set('first_name', 'John')
resp.form.set('last_name', 'Doe')
resp = resp.form.submit().follow()
user = User.objects.get(first_name='John', last_name='Doe')
assert user.attributes.phone == '+33612345678'
assert user.phone_verified_on
assert not user.email_verified
assert user.id != random_user.id
@responses.activate
@pytest.mark.parametrize('global_uniqueness', [False, True])
def test_phone_registration_existing_identifier_number_ou_phone_is_unique(
app, db, settings, phone_activated_authn, global_uniqueness
):
settings.SMS_URL = 'https://foo.whatever.none/'
settings.A2_PHONE_IS_UNIQUE = global_uniqueness # test message is same for both options
responses.post('https://foo.whatever.none/', status=200)
random_user = User.objects.create(
first_name='foo',
last_name='bar',
email='foobar@example.com',
username='foobar',
)
ou = get_default_ou()
ou.phone_is_unique = True
ou.save()
random_user.attributes.phone = '+33612345678'
random_user.ou = ou
random_user.save()
resp = app.get(reverse('registration_register'))
resp.form.set('phone_1', '612345678')
resp = resp.form.submit().follow()
code = SMSCode.objects.get()
resp.form.set('sms_code', code.value)
resp = resp.form.submit().follow()
assert resp.location == '/'
resp = resp.follow()
assert resp.pyquery('.messages .info')[0].text_content() == (
"You've been logged in with your already-existing account for this identifier."
)
assert resp.pyquery('.ui-name')[0].text_content() == 'foo bar'
assert (
AttributeValue.objects.filter(
content='+33612345678', content_type=ContentType.objects.get_for_model(User)
)
.order_by('object_id')
.distinct('object_id')
.count()
== 1
)